我有一个关于泛型的问题。假设我有3个类“Foo”、“Bar”(它是“Foo”的子类)、一个类“Factory”和一个接口“TestInterface”。我想编写一个泛型方法,只允许“直接”实现该接口的对象,而不是其子类。这对我来说相当困难,因为Java8似乎比Java7“更聪明”。以下是示例:
好的,以下是我的课程。现在在
显然,现在这样做是不会编译的:
尽管通用参数为T且T应实现具有自己类的接口(抱歉,不知道该如何表达,希望您能理解),编译器仍然接受"Bar"作为参数。因此,编译器必须表现得像“好的,Bar不适合,但是也许一个超类会适合”。然后它“看到”它可以与超类“Foo”一起使用。然后Bar将被视为Foo,因为每个Bar都是某种Foo或类似于这样的东西??至少我是这么想的。
嗯,如果我尝试使用Java7编译该行,它会失败。因此,似乎Java8对类型擦除更加智能?!
在Java8中是否有任何方法不允许子类,以便不会编译此内容?
希望你能理解我的问题,我很少用英语写作。
问候。
public interface TestInterface<T extends TestInterface<T>> {
}
public class Foo implements TestInterface<Foo>{
}
public class Bar extends Foo {
}
public class Factory {
public static <T extends TestInterface<T>> T doSth(T arg) {
return arg;
}
}
好的,以下是我的课程。现在在
doSth(T arg)
方法中,我希望允许Foo对象,在这种情况下,因为它是唯一“直接”实现该接口的类。显然,现在这样做是不会编译的:
Bar b = Factory.doSth(new Bar());
因为 Bar 没有实现 TestInterface<Bar>
接口。
我的问题是,这行代码编译时没有任何问题:
Foo f = Factory.doSth(new Bar());
尽管通用参数为T且T应实现具有自己类的接口(抱歉,不知道该如何表达,希望您能理解),编译器仍然接受"Bar"作为参数。因此,编译器必须表现得像“好的,Bar不适合,但是也许一个超类会适合”。然后它“看到”它可以与超类“Foo”一起使用。然后Bar将被视为Foo,因为每个Bar都是某种Foo或类似于这样的东西??至少我是这么想的。
嗯,如果我尝试使用Java7编译该行,它会失败。因此,似乎Java8对类型擦除更加智能?!
在Java8中是否有任何方法不允许子类,以便不会编译此内容?
Foo f = Factory.doSth(new Bar());
希望你能理解我的问题,我很少用英语写作。
问候。
Foo f = Factory.doSth(new Bar());
无法编译,那么 Bar 就不能实现 TestInterface<Foo>,也就是说它不能扩展 Foo。 - user253751Bar
是Foo
的子类,那么Bar
的实例也是Foo
的实例,并且在需要接受Foo
的时候也必须接受Bar
。为什么您不希望在此处接受Bar
? - rgettmanFoo f = Factory.<Foo>doSth(new Bar());
应该可以正常工作。 - user253751