泛型的边界

1.简述

CharSequence是String的父类,但List<CharSequence>不是List<String> 的父类。同样的,Class<CharSequence>也不是Class<String>的父类。
为了反映泛型类所持有元素的继承关系,可以用到泛型的边界。
void fun(){
		List<String> list=new ArrayList<>();
		//下行会报错.CharSequence是String的父类但List<CharSequence>不是List<String> 的父类。
		//List<CharSequence> list1=list;
		//下行报错
		//List<? super CharSequence> list2=list;
		//下行不报错
		List<? extends CharSequence> list3=list;
	}
<? entends A>,可以get,可以调用A类的方法。
<? super A>,可以set。

因为擦除移除了类型信息,所以能用无界泛型参数 (即?)调用的方法只是那些可以用Object调用的方法。

泛型中的extends

它将泛型参数限制为某个类型子集,那么就可以调用该类族的一些方法。

泛型参数表中的extends

//: generics/BasicBounds.java
//泛型参数列表的extends
interface HasColor { java.awt.Color getColor(); }

class Colored
   
   
    
     {
  T item;
  Colored(T item) { this.item = item; }
  T getItem() { return item; }
  // The bound allows you to call a method:
  java.awt.Color color() { return item.getColor(); }
}

class Dimension { public int x, y, z; }

// This won't work -- class must be first, then interfaces:
// class ColoredDimension
    
    
     
      {
	
// Multiple bounds:
class ColoredDimension
     
     
      
       {
  T item;
  ColoredDimension(T item) { this.item = item; }
  T getItem() { return item; }
  java.awt.Color color() { return item.getColor(); }
  int getX() { return item.x; }
  int getY() { return item.y; }
  int getZ() { return item.z; }
}

interface Weight { int weight(); }	

// As with inheritance, you can have only one
// concrete class but multiple interfaces:
class Solid
      
      
       
        {
  T item;
  Solid(T item) { this.item = item; }
  T getItem() { return item; }
  java.awt.Color color() { return item.getColor(); }
  int getX() { return item.x; }
  int getY() { return item.y; }
  int getZ() { return item.z; }
  int weight() { return item.weight(); }
}

class Bounded
extends Dimension implements HasColor, Weight {
  public java.awt.Color getColor() { return null; }
  public int weight() { return 0; }
}	

public class BasicBounds {
  public static void main(String[] args) {
    Solid
       
       
         solid = new Solid 
        
          (new Bounded()); solid.color(); solid.getY(); solid.weight(); } } ///:~ 
         
       
      
      
     
     
    
    
   
   

泛型类的extends

//: generics/InheritBounds.java
//泛型类的extends
interface HasColor { java.awt.Color getColor(); }
interface Weight { int weight(); }	
class Dimension { public int x, y, z; }
class Bounded
extends Dimension implements HasColor, Weight {
  public java.awt.Color getColor() { return null; }
  public int weight() { return 0; }
}	

class HoldItem
   
   
    
     {
  T item;
  HoldItem(T item) { this.item = item; }
  T getItem() { return item; }
}

class Colored2
    
    
     
      extends HoldItem
     
     
      
       {
  Colored2(T item) { super(item); }
  java.awt.Color color() { return item.getColor(); }
}

class ColoredDimension2
      
      
       
       
extends Colored2
       
       
         { ColoredDimension2(T item) { super(item); } int getX() { return item.x; } int getY() { return item.y; } int getZ() { return item.z; } } class Solid2 
        
          extends ColoredDimension2 
         
           { Solid2(T item) { super(item); } int weight() { return item.weight(); } } public class InheritBounds { public static void main(String[] args) { Solid2 
          
            solid2 = new Solid2 
           
             (new Bounded()); solid2.color(); solid2.getY(); solid2.weight(); } } ///:~ 
            
           
          
         
       
      
      
     
     
    
    
   
   
把第32行做些改变,会有如下报错:


泛型参数中的问号

//: generics/Holder.java
//Fruit是Apple的基类,但Holder
  
  
   
   不是Holder
   
   
    
    的基类,所以不能向上转型
//Holder
    
    
     
     可以向上转型为Holder<? extends Fruit>,此时set()方法不能用,只能用get()
class Fruit{}
class Apple extends Fruit{};
class Orange extends Fruit{};
class Jonathan extends Apple{};
public class Holder
     
     
      
       {
  private T value;
  public Holder() {}
  public Holder(T val) { value = val; }
  public void set(T val) { value = val; }
  public T get() { return value; }
  public boolean equals(Object obj) {
    return value.equals(obj);
  }	
  public static void main(String[] args) {
   fun1();
   System.out.println("******************************");
   fun2();
  }
  /**
   * ? extends Fruit 表示fruit持有的是Fruit及其子类。
   * Fruit的子类有很多,所以fruit.set(X),无论X是什么都不能编译通过。
   * 但Fruit的子类一定拥有Fruit类的方法,所以成员函数可以调用。
   */
  static void fun1(){
	  Holder
      
      
        Apple = new Holder 
       
         (new Apple()); Apple d = Apple.get(); Apple.set(d); // Holder 
        
          Fruit = Apple; // Cannot upcast Holder 
          fruit = Apple; // OK Fruit p = fruit.get(); d = (Apple)fruit.get(); // Returns 'Object' try { Orange c = (Orange)fruit.get(); // No warning } catch(Exception e) { System.out.println(e); } // fruit.set(new Apple()); // Cannot call set() // fruit.set(new Fruit()); // Cannot call set() System.out.println(fruit.equals(d)); // OK } /** * 
          表示fruit持有的是Apple及其父类。 * 所以fruit.set(X),无论X只要是Apple及其子类就可以编译通过。因为 父类 x=new 子类()是可以的。 * 但Apple类的成员方法不能再调用了。因为父类不知道子类的方法。 */ static void fun2(){ Holder 
         
           Apple = new Holder 
          
            (new Apple()); Apple d = Apple.get(); Apple.set(d); // Holder 
           
             Fruit = Apple; // Cannot upcast Holder 
             fruit = Apple; // OK Fruit p = (Fruit) fruit.get(); d = (Apple)fruit.get(); // Returns 'Object' try { Orange c = (Orange)fruit.get(); // No warning } catch(Exception e) { System.out.println(e); } fruit.set(new Apple()); // ok fruit.set(new Jonathan()); // ok //fruit.set(new Fruit()); // Cannot call set() System.out.println(fruit.equals(d)); // OK } } /* Output: (Sample) java.lang.ClassCastException: Apple cannot be cast to Orange true ****************************** java.lang.ClassCastException: Apple cannot be cast to Orange false */ 
            
           
          
         
        
      
     
     
    
    
   
   
  
  

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值