方法声明中的泛型
Generic within method declaration
假设我有一个名为 class 的抽象,它具有这个抽象方法
removeItem(GeneralItem item, String reason);
但是在子class中我有
removeItem(SpecificItemThatExtendsGeneralItem item, String reason){ //code }
如何使第二个 removeItem 算作第一个的实现?例如
removeItem(<? extends GeneralItem> item, String reason);
子类不能更改它们在方法中接受的类型。但是你绝对可以检查类型是否是你期望的:
removeItem(GeneralItem item, String reason)
{
if (!(item instanceof SpecificItemThatExtendsGeneralItem))
throw InvalidArgumentException("Only SpecificItemThatExtendsGeneralItem accepted");
}
然而,这在编译时不会被检查,只是因为当有人调用
abstractClassInstance.removeItem(OtherSpecificItemThatExtendsGeneralItem)
编译器无法知道这应该会失败,它不知道 abstractClassInstance
实际上是哪个实现。
这不可能。
方法:
removeItem(SpecificItemThatExtendsGeneralItem item, String reason){ //code }
并未涵盖调用您希望它覆盖的方法的所有有效方式。因此,拥有一个(仅)实现此方法的 class 不履行父 class.
的合同
如果能改baseclass,就可以泛化第一个参数:
class BaseClass<T extends GeneralItem> {
void removeItem(T item, String reason) {
}
}
class SubClass extends BaseClass<SpecificItemThatExtendsGeneralItem> {
@Override
void removeItem(SpecificItemThatExtendsGeneralItem item, String reason) {
}
}
具有签名的方法...
removeItem(SpecificItemThatExtendsGeneralItem item, String reason)
...不实施...
removeItem(GeneralItem item, String reason)
...因为后者可以接受任何GeneralItem
,包括那些不是SpecificItemThatExtendsGeneralItem
.
但是,如果您可以更改摘要 class,那么您就可以实现:
abstract class MyAbstractClass <T extends GeneralItem> {
abstract public void removeItem(T item, String reason);
}
class MySubclass extends MyAbstractClass<SpecificItemThatExtendsGeneralItem> {
@Override
public void removeItem(SpecificItemThatExtendsGeneralItem item,
String reason) {
// ...
}
}
但是,在那种情况下,请注意类型 MySubclass
仍然与 MyAbstractClass<GeneralItem>
:
不兼容
MyAbstractClass<GeneralItem> = new MySubclass(); // ERROR
尽管它与 MyAbstractClass<?>
和 MyAbstractClass<SpecificItemThatExtendsGeneralItem>
兼容:
MyAbstractClass<?> c = new MySubclass(); // ok
MyAbstractClass<SpecificItemThatExtendsGeneralItem> = new MySubclass(); // ok
假设我有一个名为 class 的抽象,它具有这个抽象方法
removeItem(GeneralItem item, String reason);
但是在子class中我有
removeItem(SpecificItemThatExtendsGeneralItem item, String reason){ //code }
如何使第二个 removeItem 算作第一个的实现?例如
removeItem(<? extends GeneralItem> item, String reason);
子类不能更改它们在方法中接受的类型。但是你绝对可以检查类型是否是你期望的:
removeItem(GeneralItem item, String reason)
{
if (!(item instanceof SpecificItemThatExtendsGeneralItem))
throw InvalidArgumentException("Only SpecificItemThatExtendsGeneralItem accepted");
}
然而,这在编译时不会被检查,只是因为当有人调用
abstractClassInstance.removeItem(OtherSpecificItemThatExtendsGeneralItem)
编译器无法知道这应该会失败,它不知道 abstractClassInstance
实际上是哪个实现。
这不可能。
方法:
removeItem(SpecificItemThatExtendsGeneralItem item, String reason){ //code }
并未涵盖调用您希望它覆盖的方法的所有有效方式。因此,拥有一个(仅)实现此方法的 class 不履行父 class.
的合同如果能改baseclass,就可以泛化第一个参数:
class BaseClass<T extends GeneralItem> {
void removeItem(T item, String reason) {
}
}
class SubClass extends BaseClass<SpecificItemThatExtendsGeneralItem> {
@Override
void removeItem(SpecificItemThatExtendsGeneralItem item, String reason) {
}
}
具有签名的方法...
removeItem(SpecificItemThatExtendsGeneralItem item, String reason)
...不实施...
removeItem(GeneralItem item, String reason)
...因为后者可以接受任何GeneralItem
,包括那些不是SpecificItemThatExtendsGeneralItem
.
但是,如果您可以更改摘要 class,那么您就可以实现:
abstract class MyAbstractClass <T extends GeneralItem> {
abstract public void removeItem(T item, String reason);
}
class MySubclass extends MyAbstractClass<SpecificItemThatExtendsGeneralItem> {
@Override
public void removeItem(SpecificItemThatExtendsGeneralItem item,
String reason) {
// ...
}
}
但是,在那种情况下,请注意类型 MySubclass
仍然与 MyAbstractClass<GeneralItem>
:
MyAbstractClass<GeneralItem> = new MySubclass(); // ERROR
尽管它与 MyAbstractClass<?>
和 MyAbstractClass<SpecificItemThatExtendsGeneralItem>
兼容:
MyAbstractClass<?> c = new MySubclass(); // ok
MyAbstractClass<SpecificItemThatExtendsGeneralItem> = new MySubclass(); // ok