我了解到Java有instanceof运营商.你能详细说明它的使用地点和优势吗?
具有一系列"instanceof"操作被认为是"代码味道".标准答案是"使用多态".在这种情况下我该怎么做?
基类有许多子类; 没有一个在我的控制之下.类似的情况是Java类Integer,Double,BigDecimal等.
if (obj instanceof Integer) {NumberStuff.handle((Integer)obj);}
else if (obj instanceof BigDecimal) {BigDecimalStuff.handle((BigDecimal)obj);}
else if (obj instanceof Double) {DoubleStuff.handle((Double)obj);}
Run Code Online (Sandbox Code Playgroud)
我确实可以控制NumberStuff等等.
我不想在几行代码中使用多行代码.(有时我将一个HashMap映射到一个IntegerStuff的实例,将BigDecimal.class映射到一个BigDecimalStuff的实例等等.但是今天我想要一些更简单的东西.)
我想要像这样简单的东西:
public static handle(Integer num) { ... }
public static handle(BigDecimal num) { ... }
Run Code Online (Sandbox Code Playgroud)
但是Java不会那样工作.
我想在格式化时使用静态方法.我正在格式化的东西是复合的,其中Thing1可以包含一个数组Thing2s和Thing2可以包含一个Thing1s数组.当我实现这样的格式化程序时,我遇到了问题:
class Thing1Formatter {
private static Thing2Formatter thing2Formatter = new Thing2Formatter();
public format(Thing thing) {
thing2Formatter.format(thing.innerThing2);
}
}
class Thing2Formatter {
private static Thing1Formatter thing1Formatter = new Thing1Formatter();
public format(Thing2 thing) {
thing1Formatter.format(thing.innerThing1);
}
}
Run Code Online (Sandbox Code Playgroud)
是的,我知道HashMap和更多代码也可以修复它.但相比之下,"instanceof"似乎更具可读性和可维护性.有什么简单但不臭吗?
注释已添加5/10/2010:
事实证明,将来可能会添加新的子类,而我现有的代码必须优雅地处理它们.在这种情况下,类上的HashMap不起作用,因为找不到类.一系列if语句,从最具体的开始到以最一般的结尾,可能是最好的:
if (obj instanceof SubClass1) …Run Code Online (Sandbox Code Playgroud) java reflection polymorphism instanceof chain-of-responsibility
我对访客模式及其用途感到困惑.我似乎无法想象使用这种模式或其目的的好处.如果有人可以用例子解释,如果可能的话会很好.
我正在尝试实现我的第一个工厂设计模式,我不确定在将工厂制造的对象添加到列表时如何避免使用instanceof.这就是我想要做的:
for (ABluePrint bp : bluePrints) {
AVehicle v = AVehicleFactory.buildVehicle(bp);
allVehicles.add(v);
// Can I accomplish this without using 'instanceof'?
if (v instanceof ACar) {
cars.add((ACar) v);
} else if (v instanceof ABoat) {
boats.add((ABoat) v);
} else if (v instanceof APlane) {
planes.add((APlane) v);
}
}
Run Code Online (Sandbox Code Playgroud)
从我在SO上看到的,使用'instanceof'是代码气味.有没有更好的方法来检查工厂创建的车辆类型而不使用'instanceof'?
我欢迎任何关于我的实施的反馈/建议,因为我不确定我是否正确地采用了这种方式.
完整示例如下:
import java.util.ArrayList;
class VehicleManager {
public static void main(String[] args) {
ArrayList<ABluePrint> bluePrints = new ArrayList<ABluePrint>();
ArrayList<AVehicle> allVehicles = new ArrayList<AVehicle>();
ArrayList<ACar> cars = new ArrayList<ACar>();
ArrayList<ABoat> boats = new …Run Code Online (Sandbox Code Playgroud) 我有以下课程.
public class B
{
public A a;
public B()
{
a= new A();
System.out.println("Creating B");
}
}
Run Code Online (Sandbox Code Playgroud)
和
public class A
{
public B b;
public A()
{
b = new B();
System.out.println("Creating A");
}
public static void main(String[] args)
{
A a = new A();
}
}
Run Code Online (Sandbox Code Playgroud)
可以清楚地看到,类之间存在循环依赖关系.如果我试着跑A级,我最终会得到一个StackOverflowError.
如果创建了依赖关系图,其中节点是类,则可以轻松识别此依赖关系(至少对于具有少量节点的图).那为什么JVM不能识别这个,至少在运行时?StackOverflowErrorJVM可以在开始执行之前至少发出警告,而不是抛出.
[更新]某些语言不能具有循环依赖关系,因为这样就不会构建源代码.例如,请参阅此问题和接受的答案.如果循环依赖是C#的设计气味那么为什么它不适用于Java呢?只是因为Java可以(编译循环依赖的代码)?
[update2]最近发现了jCarder.根据该网站,它通过动态检测Java字节代码并在对象图中查找周期来发现潜在的死锁.任何人都可以解释该工具如何找到周期?