从泛型列表进行Java动态向下转换
如何在没有instanceof语句的情况下动态向下转换对象? 我读了Bruce Eckel在Java中的思想,还有使用类,还有这样一个主题,但我没有被接触 对我的英语很抱歉从泛型列表进行Java动态向下转换,java,generics,rtti,instanceof,downcast,Java,Generics,Rtti,Instanceof,Downcast,如何在没有instanceof语句的情况下动态向下转换对象? 我读了Bruce Eckel在Java中的思想,还有使用类,还有这样一个主题,但我没有被接触 对我的英语很抱歉 public class GenericTest { static private interface Base { } static private class A implements Base { } static private class B implements
public class GenericTest {
static private interface Base {
}
static private class A implements Base {
}
static private class B implements Base {
}
static private class C extends B {
}
private List<Class<? extends Base>> types;
private List<Base> objects;
public GenericTest() {
types = new ArrayList<Class<? extends Base>>();
types.add(A.class);
types.add(B.class);
types.add(C.class);
objects = new ArrayList<Base>(Arrays.asList(new A(), new B(), new C()));
for (Base base : objects) {
if (base instanceof A)
test((A) base);
else if (base instanceof C)
test((C) base);
else if (base instanceof B)
test((B) base);
for (Class<? extends Base> c : types)
if (base.getClass().equals(c))
test(c.cast(base));
}
}
private void test(A a) {
System.out.println("A");
}
private void test(B b) {
System.out.println("B");
}
private void test(C c) {
System.out.println("C");
}
private void test(Base base) {
System.out.println("Base");
}
public static void main(String[] args) {
new GenericTest();
}
}
公共类泛型测试{
静态专用接口库{
}
静态私有类A实现了基类{
}
静态私有类B实现了基类{
}
静态私有类C扩展了B{
}
private List有时,使用instanceof
表明您的设计存在缺陷,可能违反了面向对象编程的一些基本原则
在您的情况下,根据您的最终目标,我可以监督两个解决方案。第一个解决方案是将test()
的特定行为封装在类A
、B
和C
中。可以通过声明方法test()来完成
在接口Base
中,使其成为抽象类并在子类中实现
static private abstract class Base {
public void test() {
System.out.println("Base");
}
}
static private class A extends Base {
private void test() {
System.out.println("A");
}
}
static private class B implements Base {
private void test() {
System.out.println("B");
}
}
static private class C extends B {
private void test() {
System.out.println("C");
}
}
请注意,层次级别大于3的类不是一个好的做法。继承是两个对象之间可以达到的最高耦合度。这就是为什么我们倾向于这样做
如@SLaks所述,改进设计的第二种方法是使用访问者模式。有关此模式的更多信息,请参阅。关于此主题的推荐阅读内容是和。有时,使用instanceof
表明您的设计存在缺陷,可能违反了面向对象编程的一些基本原则
在您的情况下,根据您的最终目标,我可以监督两个解决方案。第一个解决方案是将test()
的特定行为封装在类A
、B
和C
中。可以通过声明方法test()来完成
在接口Base
中,使其成为抽象类并在子类中实现
static private abstract class Base {
public void test() {
System.out.println("Base");
}
}
static private class A extends Base {
private void test() {
System.out.println("A");
}
}
static private class B implements Base {
private void test() {
System.out.println("B");
}
}
static private class C extends B {
private void test() {
System.out.println("C");
}
}
请注意,层次级别大于3的类不是一个好的做法。继承是两个对象之间可以达到的最高耦合度。这就是为什么我们倾向于这样做
第二种改进设计的方法是,正如@SLaks所提到的,使用访问者模式。可以找到关于此模式的更多信息。关于此主题的推荐阅读内容是和。不清楚您想要做什么,但下面是如何在不使用强制转换和instanceof
的情况下实现相同的结果
将test
方法放在界面Base
上:
static private interface Base {
public void test();
}
然后实施它:
static private class A implements Base {
public void test() {
System.out.println("A");
}
同样地,对于B
和C
。
那么您的循环应该如下所示:
for (Base base : objects) {
base.test();
}
如果base
是A
的实例,这将导致调用A::test
,B::test
如果base
是B
的实例,等等。(该方法根据引用对象的运行时类型选择)
将test
方法放在界面Base
上:
static private interface Base {
public void test();
}
然后实施它:
static private class A implements Base {
public void test() {
System.out.println("A");
}
同样地,对于B
和C
。
那么您的循环应该如下所示:
for (Base base : objects) {
base.test();
}
如果base
是A
的实例,这将导致调用A::test
,B::test
如果base
是B
的实例,等等。(该方法根据引用对象的运行时类型选择)考虑使用访问者模式。更详细地描述你真正想要达到的目标。在大多数情况下,使用<代码> >至少是可疑的。发布的回答是否回答了你的问题?考虑使用访问者模式。更详细地描述你真正想要达到的目标。使用<代码>实例< <代码>至少是DuiBio。大多数情况下都是我们。贴出的回答回答了你的问题吗?我只是想把实现与类分开。现在,我正在阅读头先设计模式。头先设计模式是一个很好的起点。祝你好运。我只是想把实现与类分开。现在,我正在阅读头先设计模式。头先设计模式erns是一个很好的起点。祝你好运。