Java对泛型的支持(一):基本语法

Java在J2SE 5.0后开始增加了泛型(Generics)功能,并且许多API都根据这个新的功能被重新改写了,例如List、Map、Set等与数据结构相关的类。如果我们不想使用泛型功能,也可以用J2SE 1.4或以前的版本的语法来使用这些类,但编译的时候就会出现一些警告。如果对泛型了解不足,那么就会完全不知编译器所云。因此,了解或学会使用泛型是十分必要的。

 

1、在没有泛型之前

先来看2个类:

IntegetTest : 

class IntegerTest{
    private Integer integer;
    
    public void setObj(Integer integer){
        this.integer = integer;
    }
 
    public Integer getObj(){
        return integer;
    }
}

 BooleanTest :

class BooleanTest{
private Boolean bool; public void setObj(Boolean bool){ this.bool = bool; } public Boolean getObj(){ return bool; } }

 通过观察我们发现,这两个类除了Boolean和Integer这两个关键字不同外,其它的代码都相同。如此相似的类如果我们必须要写两份代码就难免有些冗杂。我们都知道,Object类是所有类的父类,因此用Object类来实现泛型或许是个不错的解决方案。如:

class ObjectTest{
    private Object obj;
    
    public void setObj(Object obj){
        this.obj = obj;
    }
    
    public Object getObj(){
        return obj;
    }
}

 于是我们在使用ObjectTest这个类时就需要编写如下代码:

ObjectTest obj = new ObjectTest();
obj.setObj(new Integer(100)); //传递一个Integer对象的引用
//由于getObj()方法返回的是一个Object类型对象的引用,因此需要强制转换为Integer
Integer I = (Integer)obj.getObj();

 可以看出,如果要使用getObj()方法得到我们想要的对象,那么就必须 进行一次强制类型转换才能满足我们的需求。但问题就出在这里。很多时候,我们往往会忘记进行强制转换,这时候编译器就会报错

 

 

因此这就需要开发人员在写代码的时候要额外注意。在没有泛型之前,所有存入List, Map, Set窗口中的实例都会失去其类型信息,当我们要取出数据进行使用时,就必须再手动强制转换回它们原来的类型。

如果我们忘记了它们是什么类型的对象,那就费时了。。慢慢拉上去翻前面的代码吧。。。

 

2、定义泛型类

为了解决传统的泛型设计用Object定义类所带来的种种问题(如类型丢失、程序员忘记了转换类型、必须将其转换为原来的类型才能调用相应的方法),Java在J2SE 5.0之后提出了针对泛型设计的解决方案。

如:下面的代码用泛型类取代了Object :

// 在类名后面,使用<T>来声明一个类型持有者(Holder)
public class Demo<T>
{
    private T obj;
    
    public void setObj(T obj)
    {
        this.obj = obj;
    }
    public T getObj()
    {
        return obj;
    }
}

 使用泛型定义类时,可以用<T>来声明一个类型持有者(Holder)。然后就可以用 T 这个名称作为类型来声明成员、参数或返回值类型。在声明对象时,用尖括号一并指定泛型类类型持有者T的真正类型。如:

Demo<Integer> obj = new Demo<Integer>();

 这样,在调用getObj()方法时,返回的就会是一个我们在尖括号内所指定的Integet对象,而不是Object了,因此也就不必再进行类型转换了:

obj.setObj(new Integer(100));
Integer I = obj.getObj(); //无需强制转换

 如果我们使用泛型类声明对象的时候没有为它指定类型,那么 编译器默认会使用Object类型。这样的话我们就得又要像之前那样进行类型转换了。 

 

3、几个泛型的小例子

我们可以在定义泛型类时,同时声明多个类型持有者,如:

//声明了两个Holder
class Test<T1,T2> {
    private T1 obj1;
    private T2 obj2;
    
    public Test(T1 obj1,T2 obj2){
        this.obj1 = obj1;
        this.obj2 = obj2;
    }
}

 也可以声明数组,如:

class TestArray<T>{
    // 声明T类型的数组
    private T[] objs;
    
    public TestArray(T[] objs)
    {
        this.objs = objs;
    }
}

 但要注意的是,不允许使用泛型来建立数组的实例,如下面的操作是错误的:

class TestArray<T>{
    // 声明T类型的数组
    private T[] objs = new T[10]; //Error
    
    public TestArray(T[] objs){
        this.objs = objs;
    }
}

 

posted @ 2022-01-21 11:37  IT6889  阅读(78)  评论(0编辑  收藏  举报