Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/379.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java类型擦除:为什么赢了';是否编译以下代码段?_Java_Oop_Generics_Compiler Errors - Fatal编程技术网

Java类型擦除:为什么赢了';是否编译以下代码段?

Java类型擦除:为什么赢了';是否编译以下代码段?,java,oop,generics,compiler-errors,Java,Oop,Generics,Compiler Errors,我目前正在为我的JavaSE11开发者证书做准备,我似乎无法理解类型擦除的概念。我有以下课程: public class BaseClass { public List<? extends CharSequence> transform(Set<? extends CharSequence> set) { return null; } } public class SubClass extends BaseClass { @Ov

我目前正在为我的JavaSE11开发者证书做准备,我似乎无法理解类型擦除的概念。我有以下课程:

public class BaseClass {
    public List<? extends CharSequence> transform(Set<? extends CharSequence> set) {
        return null;
    }
}

public class SubClass extends BaseClass {

    @Override
    public List<String> transform(Set<String> set) {
        return null;
    }
}
公共类基类{

public List如果您的代码已编译,那么您可以将
子类
的实例向上转换为
基类
,然后将
字符串
以外的其他类型的
字符序列
传递给
转换
方法

这显示了它将如何破坏类型安全:

class NotString implements CharSequence {
    public char charAt(int index) {
        return 'A';
    }

    public int length() {
        return 1;
    }

    public CharSequence subSequence(int start, int end) {
        return this;
    }

    public String toString() {
        return "A";
    }
}

BaseClass base = new SubClass();

// Oops, passing Set<NotString> to transform(Set<String> set).
base.transform(Set.of(new NotString()));
类NotString实现CharSequence{
公共字符(整型索引){
返回“A”;
}
公共整数长度(){
返回1;
}
公共字符序列子序列(int开始,int结束){
归还这个;
}
公共字符串toString(){
返回“A”;
}
}
BaseClass base=新的子类();
//Oops,将Set传递给transform(Set)。
base.transform(Set.of(new NotString());

类型擦除确保泛型类型在运行时不存在,但在编译时存在

其结果如下:

public List<? extends CharSequence> transform(Set set) {
    return null;
}

public List<String> transform(Set set) {
    return null;
}
  • 这些方法在运行时是等效的

  • 它们在编译时是不同的,编译器会检测到这种差异

由于泛型的目的是导致编译器错误(或未检查的警告),而不是获得您很可能不想要的行为,因此它只会给您提供信息性错误:


名称冲突:convarant.car.SubClass中的transform(java.util.Set)和transform(java.util.Set我相信是方法参数导致了错误。当你创建一个子类时,你的方法可以在返回的内容上更加具体(在你的例子中,
String
比你的
更具体)


public list感谢您提供的示例。这就更清楚了为什么不允许这样做。因此,基本上,这种协调对于返回类型是允许的,但是对于方法参数是不允许的?@joostdr_uuu正确。重写方法与它重写的方法具有相同的名称、参数数量和类型以及返回类型。重写方法满足以下条件:hod还可以返回重写方法返回的类型的子类型。此子类型称为协变返回类型。因此,在这种情况下,在类型擦除之后,两个方法看起来相同,但是,两个方法不会相互重写。
List<? extends CharSequence> out = baseClass.transform(
    Collections.singleton(new StringBuilder().append("Hi")));