我确定这是一个非常愚蠢的问题,但是我仍然想知道,是否可以动态地强制转换全局变量cause
,换句话说,无需使用instanceof
运算符?
这个问题的原因是,我觉得instanceof
运算符在这里没有做任何大的事情,它只是静态地投射cause
,但是无论哪种情况,它都在创建new IOException(cause)
因为cause
的类型为Object
,所以我必须将其类型强制转换为String
或Throwable
。
private Object cause; // global variable
//...
if (failed)
throw cause instanceof String ? new IOException((String) cause) : new IOException((Throwable) cause);
下面是实际的代码片段,其中两个被覆盖的方法将被异步调用。
public class Command implements ResponseListener {
private Object cause;
// ...
@Override
public void messageReceived(String message, String status) {
// ...
if (!status.equals(MyConstants.COMPLD_MSG)) {
this.cause = status + " received for " + command.split(":")[0] + message;
this.failed = true;
}
doNotify();
}
@Override
public void exceptionCaught(Throwable cause) {
this.cause = cause;
this.failed = true;
doNotify();
}
public void waitForResponse(int cmdTimeout) throws IOException, InterruptedException {
// ...
if (failed)
throw cause instanceof String ? new IOException((String) cause) : new IOException((Throwable) cause);
}
}
最佳答案
为什么不总是将Throwable作为您的原因变量? Throwable似乎比String更适合表示失败。另外,它避免了您使用“丑陋的”运算符instanceof。
public class Command implements ResponseListener {
private Throwable cause;
// ...
@Override
public void messageReceived(String message, String status) {
// ...
if (!status.equals(MyConstants.COMPLD_MSG)) {
this.cause = new Throwable(status + " received for " + command.split(":")[0] + message);
this.failed = true;
}
doNotify();
}
@Override
public void exceptionCaught(Throwable cause) {
this.cause = cause;
this.failed = true;
doNotify();
}
public void waitForResponse(int cmdTimeout) throws IOException, InterruptedException {
// ...
if (failed)
throw new IOException(cause);
}
}
在讨论之后更新:
public class Command implements ResponseListener {
private String cause;
// ...
@Override
public void messageReceived(String message, String status) {
// ...
if (!status.equals(MyConstants.COMPLD_MSG)) {
this.cause = status + " received for " + command.split(":")[0] + message;
this.failed = true;
}
doNotify();
}
@Override
public void exceptionCaught(Throwable cause) {
if(cause.getMessage().isEmpty()) {
this.cause = cause.toString();
}
else {
this.cause = cause.getMessage();
}
this.failed = true;
doNotify();
}
public void waitForResponse(int cmdTimeout) throws IOException, InterruptedException {
// ...
if (failed)
throw new IOException(cause);
}
}