为什么我不能添加到列表&lt ;?扩展String>在Java中? [英] Why can't I add to a List<? extends String> in Java?

查看:93
本文介绍了为什么我不能添加到列表&lt ;?扩展String>在Java中?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在下面的代码段中,将"Hulooo"添加到列表中会生成编译器错误,因为String不会扩展String. 但是,对字符串的ArrayList进行类型转换是可行的.但是类型转换对象的ArrayList不起作用.

In the snippet below, adding "Hulooo" to the list generates a compiler error since String doesnt extend String. However, typecasting an ArrayList of strings works. But typecasting an ArrayList of objects doesn't work.

有人可以解释为什么会这样吗? 什么适用于String(在这种情况下)而不适用于Object?

Can someone explain why this is happening? What applies to String(in this context) that doesn't apply to Object?

public static void takeList(List<? extends String> list)
{
    list.add("Hulloo");//ERROR
    list=new ArrayList<String>();
    list=new ArrayList<Object>();//ERROR
}

推荐答案

问号?是所谓的通配符. List<? extends String>表示:任何类型List<T>,其中TStringString的子类型. String是最终类,因此没有String的子类型,但是编译器没有考虑这一点.因此,编译器假定该列表可能是String的某些子类型的列表,并且不可能在该列表中添加String.

The question mark ? is a so-called wild-card operator. List<? extends String> means: any type List<T> where T is String or a sub-type of String. String is a final class, and thus there are no sub-types of String, but the compiler does not look at this. And thus, the compiler assumes that the list could be a list of some sub-type of String, and it would not be possible to add Strings to such a list.

让我们用一个非最终类A模拟您的示例,该类具有一个子类B:

Let's simulate your example with a non-final class, A, which has a sub-class, B:

class A { 
    // empty
}

class B extends A {
    void f();
}

现在考虑等效于您的方法:

And now consider the equivalent to your method:

public static void takeList(List<? extends A> list) {
    list.add(new A());
}

由于以下原因,它将无法编译.假设您按以下方式调用此方法:

This will not compile, for the following reason. Suppose you call this method as follows:

List<B> myList = new ArrayList<>();   // line 1
takeList(myList);                     // line 2
B element = myList.get(0);            // line 3
B.f();                                // line 4

由于BA的子类,因此第2行中的函数调用是合法的.但是方法takeListA添加到列表中,而不是B.然后B的列表包含一个不是B的元素,并且第3行和第4行出现故障.

Since B is a sub-class of A the function call in line 2 is legal. But the method takeList adds an A to the list which is not a B. An then the list of Bs contains an element which is not a B, and line 3 and 4 break down.

这里有类型系统来防止键入错误,因此,在一种情况下,您可以将错误类型的对象添加到列表中,类型系统必须禁止它.

The type system is there to prevent typing errors, so if there is one scenario where you could add an object of the wrong type to a list, the type system must forbid it.

这篇关于为什么我不能添加到列表&lt ;?扩展String&gt;在Java中?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆