关于泛型的一些问题
2017-01-14 13:32
197 查看
一、泛型在任何运行时需要知道确切类型信息的操作都将无法工作
二、泛型类型参数在声明什么类型就必须实例化什么类型,类型继承和多态不能用于泛型类型参数。
三、List<? extends T> 这里的T可以是任何类或者接口,?可以是T代表的这个类本身或子类;List<? super T>这里?可以是T代表的这个类本身或它的父类;
四、泛型对象的泛型参数类型在声明的时候确定
Holder<?> unbounded = new Holder<Long>();
这里unbounded的泛型类型参数是未知的;因为进行了泛型转型 擦除掉了。
五、泛型类对象做参数,使用方法的时候,传递的对象的泛型参数必须一致
这句没出错,说明参数可以为参数类型不确定的泛型。
六、 静态方法中不能使用类的泛型。
七、要用到泛型的方法必须在方法声明的时候声明为泛型方法。
格式为:
八、泛型通配符
泛型通配符的主要作用是为了在方法调用时,泛型参数使用通配符就可以让该参数类型不受限制。
1.使用类型 通配符:?,比如:List<?> ,Map<?,?>
List<?>是List<String>、List<Object>等各种泛型List的父类。
2. 读取List<?>的对象list中的元素时,永远是安全的,因为不管list的真实类型是什么,它包含的都是Object。
3. 写入list中的元素时,不行。因为我们不知道c的元素类型,我们不能向其中添加对象。唯一的例外是null,它是所有类型的成员。
• 将任意元素加入到其中不是类型安全的:
• Collection<?> c = new ArrayList<String>();
• c.add(new Object()); // 编译时错误
• 因为我们不知道c 的元素类型,我们不能向其中添加对象
。
• add方法有类型参数E作为集合的元素类型。我们传给add的任何参数都必须是一个未知类型的子类。因为我们不知道那是什么类型,所以我们无法传任何东西进去。
• 唯一的例外的是null ,它是所有类型的成员。
• 另一方面,我们可以调用get() 方法并使用其返回值。返回值是一个未知的类型,但是我们知道,它总是一个Object
public static void main(String[] args) {
List<?> list = null;
list = new ArrayList<String>();
list = new ArrayList<Double>();
//list.add(3);
list.add(null);
List<String> l1 = new ArrayList<String>();
List<Integer> l2 = new ArrayList<Integer>();
l1.add(“ 六星教育");
l2.add(15);
read(l1);
read(l2); }
static void read(List<?> list){
for(Object o : list){
System.out.println(o);
} }• <?>
• 允许所有泛型的引用调用
• 举例:
• <? extends Number> ( 无穷小 , Number]
• 只允许泛型为Number及Number子类的引用调用
• <? super Number> [Number , 无穷大)
• 只允许泛型为Number及Number父类的引用调用
• <? extends Comparable>
• 只允许泛型为实现Comparable接口的实现类的引用调用
public static void printCollection3(Collection<?
extends Person> coll){
//Iterator只能用Iterator<?>或Iterator<? extends
Person>.why?
Iterator<?> iterator = coll.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
} }
public static void printCollection4(Collection<? super
Person> coll){
Iterator<?> iterator = coll.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
} }
package generics; //: generics/Erased.java // {CompileTimeError} (Won't compile) public class Erased<T> { private final int SIZE = 100; public static void f(Object arg) { if(arg instanceof T) {} // Error T var = new T(); // Error T[] array = new T[SIZE]; // Error T[] array = (T)new Object[SIZE]; // Unchecked warning } } ///:~
二、泛型类型参数在声明什么类型就必须实例化什么类型,类型继承和多态不能用于泛型类型参数。
class Fruit {} class Apple extends Fruit {} class Orange extends Fruit {} public class NonCovariantGenerics { // Compile Error: incompatible types: List<Fruit> flist = new ArrayList<Apple>(); } ///:~在实例化一个List的时候 指定一个泛型类型,如果这个类型是Fruit,那么就代表后面所有继承Fruit的子类都可以添加到当前的集合中;但是在赋值的时候却是使用的 Apple,那么这个ArrayList 中的泛型定义就是 Apple类型,也就意味着后面对 这个 ArrayList 进行Add等操作都必须是Apple类型或者是Apple的子类;也就和前面的Fruit以及Fruit的子类自相矛盾了;所以不允许这样进行擦除。
三、List<? extends T> 这里的T可以是任何类或者接口,?可以是T代表的这个类本身或子类;List<? super T>这里?可以是T代表的这个类本身或它的父类;
四、泛型对象的泛型参数类型在声明的时候确定
Holder<?> unbounded = new Holder<Long>();
这里unbounded的泛型类型参数是未知的;因为进行了泛型转型 擦除掉了。
五、泛型类对象做参数,使用方法的时候,传递的对象的泛型参数必须一致
package generics; public class Wildcards { static <T> T wildSubtype(Holder<? extends T> holder, T arg) { T t = holder.get(); return t; } static <T> void wildSupertype(Holder<? super T> holder, T arg) { holder.set(arg); Object obj = holder.get(); } public static void main(String[] args) { Holder<Long> qualified = new Holder<Long>(); Holder<?> unbounded = new Holder<Long>(); Holder<? extends Long> bounded = new Holder<Long>(); Long lng = 1L; Long r10 = wildSubtype(qualified, lng); // OK, but can only return Object: Object r11 = wildSubtype(unbounded, lng);//Error Long r12 = wildSubtype(bounded, lng); wildSupertype(qualified, lng); wildSupertype(unbounded, lng); // Error: // wildSupertype(Holder<? super T>,T) cannot be // applied to (Holder<capture of ?>,Long) wildSupertype(bounded, lng); // Error: // wildSupertype(Holder<? super T>,T) cannot be // applied to (Holder<capture of ? extends Long>,Long) } } ///:~
Object r11 = wildSubtype(unbounded, lng);//Error
wildSupertype(unbounded, lng); // Error:
wildSupertype(bounded, lng); // Error:这三句话都是因为参数的泛型参数类型不对出错。
Long r12 = wildSubtype(bounded, lng);
这句没出错,说明参数可以为参数类型不确定的泛型。
六、 静态方法中不能使用类的泛型。
七、要用到泛型的方法必须在方法声明的时候声明为泛型方法。
格式为:
public static <T> void fromArrayToCollection(T[] a, Collection<T> c){//方法实现}//其中T不能是类的泛型
八、泛型通配符
泛型通配符的主要作用是为了在方法调用时,泛型参数使用通配符就可以让该参数类型不受限制。
1.使用类型 通配符:?,比如:List<?> ,Map<?,?>
List<?>是List<String>、List<Object>等各种泛型List的父类。
2. 读取List<?>的对象list中的元素时,永远是安全的,因为不管list的真实类型是什么,它包含的都是Object。
3. 写入list中的元素时,不行。因为我们不知道c的元素类型,我们不能向其中添加对象。唯一的例外是null,它是所有类型的成员。
• 将任意元素加入到其中不是类型安全的:
• Collection<?> c = new ArrayList<String>();
• c.add(new Object()); // 编译时错误
• 因为我们不知道c 的元素类型,我们不能向其中添加对象
。
• add方法有类型参数E作为集合的元素类型。我们传给add的任何参数都必须是一个未知类型的子类。因为我们不知道那是什么类型,所以我们无法传任何东西进去。
• 唯一的例外的是null ,它是所有类型的成员。
• 另一方面,我们可以调用get() 方法并使用其返回值。返回值是一个未知的类型,但是我们知道,它总是一个Object
public static void main(String[] args) {
List<?> list = null;
list = new ArrayList<String>();
list = new ArrayList<Double>();
//list.add(3);
list.add(null);
List<String> l1 = new ArrayList<String>();
List<Integer> l2 = new ArrayList<Integer>();
l1.add(“ 六星教育");
l2.add(15);
read(l1);
read(l2); }
static void read(List<?> list){
for(Object o : list){
System.out.println(o);
} }• <?>
• 允许所有泛型的引用调用
• 举例:
• <? extends Number> ( 无穷小 , Number]
• 只允许泛型为Number及Number子类的引用调用
• <? super Number> [Number , 无穷大)
• 只允许泛型为Number及Number父类的引用调用
• <? extends Comparable>
• 只允许泛型为实现Comparable接口的实现类的引用调用
public static void printCollection3(Collection<?
extends Person> coll){
//Iterator只能用Iterator<?>或Iterator<? extends
Person>.why?
Iterator<?> iterator = coll.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
} }
public static void printCollection4(Collection<? super
Person> coll){
Iterator<?> iterator = coll.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
} }
相关文章推荐
- 关于Java泛型的一些问题
- SOS!!!关于游戏汉化项目中遇到一些不能解决的问题。。。。。
- 关于软件地域化(Localization)中的一些问题(zz)
- javascript里面的确一些关于Width,Height,Top,Left的问题
- 关于Myeclipse的一些问题
- 关于ASPNET在IIS一些问题的经验总结
- 关于共享软件的一些问题-转贴
- [导入]关于ASPNET在IIS一些问题的经验总结
- 网友与我关于一些GUI编程问题的对话实录
- 关于网线的一些问题
- 关于ASP.NET在IIS一些问题的经验总结
- 关于char数组和字符串的一些问题
- 关于ASPNET在IIS一些问题的经验总结
- 关于ASP.NET在IIS一些问题的经验总结(zz)
- 关于ASPNET在IIS一些问题的经验总结
- 关于Tapestry的一些问题
- 一些关于中文乱码问题的一些解决方案和经验
- 关于ASP.NET在IIS一些问题的经验总结
- 关于session的一些问题
- 【转贴】关于ASPNET在IIS一些问题的经验总结