Skip to content

Commit 5c5afae

Browse files
authored
Update 08_Restrictions_on_Wildcards.md
1 parent 95281ed commit 5c5afae

File tree

1 file changed

+26
-26
lines changed

1 file changed

+26
-26
lines changed

ch02/08_Restrictions_on_Wildcards.md

+26-26
Original file line numberDiff line numberDiff line change
@@ -7,31 +7,31 @@
77

88
**实例创建**在类实例创建表达式中,如果类型是参数化类型,则没有任何类型参数可能是通配符。 例如,以下是非法的:
99

10-
```java
11-
List<?> list = new ArrayList<?>(); // 编译报错
12-
Map<String, ? extends Number> map = new HashMap<String, ? extends Number>(); // 编译报错
13-
```
10+
```java
11+
List<?> list = new ArrayList<?>(); // 编译报错
12+
Map<String, ? extends Number> map = new HashMap<String, ? extends Number>(); // 编译报错
13+
```
1414

1515
这通常不困难。 获取和放置告诉我们,如果一个结构体包含通配符,那么我们只应该从中得到值(如果它是一个扩展通配符)或者只将值放入它中(如果它是一个超级
1616
通配符)。 为了使结构有用,我们必须同时做到这两点。 因此,我们通常以精确的类型创建结构,即使我们使用通配符类型将值放入或从结构中获取值,如下例所示:
1717

1818
```java
19-
List<Number> nums = new ArrayList<Number>();
20-
List<? super Number> sink = nums;
21-
List<? extends Number> source = nums;
22-
for (int i=0; i<10; i++) sink.add(i);
23-
double sum=0; for (Number num : source) sum+=num.doubleValue();
19+
List<Number> nums = new ArrayList<Number>();
20+
List<? super Number> sink = nums;
21+
List<? extends Number> source = nums;
22+
for (int i=0; i<10; i++) sink.add(i);
23+
double sum=0; for (Number num : source) sum+=num.doubleValue();
2424
```
2525

2626
这里通配符出现在第二行和第三行,但不在创建列表的第一行。
2727

2828
禁止包含通配符的实例创建中只有顶级参数。 允许嵌套通配符。 因此,以下是合法的:
2929

3030
```java
31-
List<List<?>> lists = new ArrayList<List<?>>();
32-
lists.add(Arrays.asList(1,2,3));
33-
lists.add(Arrays.asList("four","five"));
34-
assert lists.toString().equals("[[1, 2, 3], [four, five]]");
31+
List<List<?>> lists = new ArrayList<List<?>>();
32+
lists.add(Arrays.asList(1,2,3));
33+
lists.add(Arrays.asList("four","five"));
34+
assert lists.toString().equals("[[1, 2, 3], [four, five]]");
3535
```
3636
3737
即使列表的列表是以通配符类型创建的,其中的每个单独列表都有一个特定的类型:第一个列表是整数列表,第二个列表是字符串列表。 通配符类型禁止我们将内部列表
@@ -41,9 +41,9 @@
4141
陈述:
4242

4343
```java
44-
List<?> list = new ArrayList<Object>(); // ok
45-
List<?> list = new List<Object>() // 编译报错
46-
List<?> list = new ArrayList<?>() // 编译报错
44+
List<?> list = new ArrayList<Object>(); // ok
45+
List<?> list = new List<Object>() // 编译报错
46+
List<?> list = new ArrayList<?>() // 编译报错
4747
```
4848

4949
第一个是合法的; 第二个是非法的,因为实例创建表达式需要一个类,而不是一个接口; 第三个是非法的,因为实例创建表达式需要普通类型而不是通配符。
@@ -54,28 +54,28 @@
5454
**泛型方法调用**如果泛型方法调用包含显式类型参数,那么这些类型参数不能是通配符。 例如,假设我们有以下通用方法:
5555

5656
```java
57-
class Lists {
58-
public static <T> List<T> factory() { return new ArrayList<T>(); }
59-
}
57+
class Lists {
58+
public static <T> List<T> factory() { return new ArrayList<T>(); }
59+
}
6060
```
6161

6262
您可以选择推断的类型参数,也可以传递一个明确的类型参数。 以下两项都是合法的:
6363

6464
```java
65-
List<?> list = Lists.factory();
66-
List<?> list = Lists.<Object>factory();
65+
List<?> list = Lists.factory();
66+
List<?> list = Lists.<Object>factory();
6767
```
6868

6969
如果传递一个显式的类型参数,它不能是通配符:
7070

7171
```java
72-
List<?> list = Lists.<?>factory(); // 编译报错
72+
List<?> list = Lists.<?>factory(); // 编译报错
7373
```
7474

7575
和以前一样,可以使用嵌套通配符:
7676

7777
```java
78-
List<List<?>> = Lists.<List<?>>factory(); // ok
78+
List<List<?>> = Lists.<List<?>>factory(); // ok
7979
```
8080
8181
这种限制的动机与之前的相似。 再次,目前还不清楚是否有必要,但这不太可能成为问题。
@@ -84,19 +84,19 @@
8484
型参数,则这些类型不能是通配符。例如,这个声明是非法的:
8585

8686
```java
87-
class AnyList extends ArrayList<?> {...} // 编译报错
87+
class AnyList extends ArrayList<?> {...} // 编译报错
8888
```
8989

9090
这也是:
9191

9292
```java
93-
class AnotherList implements List<?> {...} // 编译报错
93+
class AnotherList implements List<?> {...} // 编译报错
9494
```
9595

9696
但是,像以前一样,嵌套通配符是允许的:
9797

9898
```java
99-
class NestedList extends ArrayList<List<?>> {...} // ok
99+
class NestedList extends ArrayList<List<?>> {...} // ok
100100
```
101101

102102
这种限制的动机与前两种类似。 与以前一样,目前还不清楚是否有必要,但不太可能成为问题。

0 commit comments

Comments
 (0)