Java 泛型的介绍和使用

什么是泛型?

1.数据类型变得广泛,或者是数据类型变量化,这就是泛型.(广泛的类型).

2.有一个变量是用来存放一个数据类型,这就叫做泛型.

比如泛型T存放的是一个int 就表示为:T=int

当然T也可以是其他的数据类型,就取决我们给它数据类型.

3.泛型允许程序员在强类型程序设计语言中编写代码时使用一些以后才指定的类型,在实例化时作为参数指明这些类型。

泛型的作用

1.对集合的数据类型进行约束.

如下程序


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {

//        定义集合
        ArrayList<Person> people = new ArrayList<>();

//        添加数据
        people.add(new Person("Doch",23));

//        试图添加一个不是人的数据类型.
        people.add(new Cat("stanc",22));
        

    }
}

class Person{
    private  String name;
    private  int age;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }
    @Override
    public String toString() {
        return this.name+"\t"+this.age;
    }

}

class Cat{
    private String name;
    private  int age;

    public Cat(String name, int age) {
        this.name = name;
        this.age = age;
    }

    @Override
    public String toString() {
        return this.name+"\t"+this.age;
    }
}

运行出错

这样就成功的限制了数据类型.

改进后


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {

//        定义集合
        ArrayList<Person> people = new ArrayList<>();

//        添加数据
        people.add(new Person("Doch",23));

//        遍历arraylist,限制了数据类型后,可以直接定义Person类型来遍历数据了.
        for(Person p :people)
        {
            System.out.println(p);
        }

    }
}

class Person{
    private  String name;
    private  int age;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }
    @Override
    public String toString() {
        return this.name+"\t"+this.age;
    }

}

class Cat{
    private String name;
    private  int age;

    public Cat(String name, int age) {
        this.name = name;
        this.age = age;
    }

    @Override
    public String toString() {
        return this.name+"\t"+this.age;
    }
}

2.提高集合的效率.

当我们指定了集合的数据类型,在使用集合的时候就不会出现了Object类型的转换.因为数据类型已经指定了.

就比如在遍历的时候.

//没有泛型

//在输出的时候会隐藏式将Object数据类型转换成Person然后再输出。
        for(Object p :people)
        {
            System.out.println(p);
        }

有泛型

//        遍历arraylist,限制了数据类型后,可以直接定义Person类型来遍历数据了.
//        因此在遍历输出的时候就直接输出了,没必要进行数据转换。
        for(Person p :people)
        {
            System.out.println(p);
        }

例子


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {
//      定义集合
        HashSet<Student> students = new HashSet<>();
        HashMap<String, Student> studentHashMap = new HashMap<String, Student>();
//      插入集合
        students.add(new Student("chanbing",23));
        students.add(new Student("chuchu",12));
//      遍历集合
        for(Student st : students)
        {
            System.out.println(st);
        }
//      插入集合
        studentHashMap.put("first",new Student("cela",11));
        studentHashMap.put("second",new Student("dita",23));
//遍历集合
        Collection collection=studentHashMap.values();

        for (Object student: collection)
        {
            System.out.println(student);
        }

    }
}

class Student{
    private String name;
    private int age;

    public Student(String name, int age) {
        this.name = name;
        this.age = age;
    }

    @Override
    public String toString() {
        return "Student{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
}

例子


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {

        ArrayList<Employee> employees = new ArrayList<>();

        MyDate myDate = new MyDate(1,1,2022);
        MyDate myDate1 = new MyDate(4,9,2023);
        MyDate myDate2 = new MyDate(11,25,2032);


        Employee employee = new Employee("Chandu",2344,myDate);
        Employee employee1 = new Employee("Jack",2334,myDate1);
        Employee employee2 = new Employee("Dister",4444,myDate2);

        employees.add(employee);
        employees.add(employee1);
        employees.add(employee2);

        employees.sort(new Comparator<Employee>() {
            @Override
            public int compare(Employee employee, Employee t1) {
                return (int)(employee.getSalary()-t1.getSalary()) ;
            }
        });



        for (Employee emp : employees)
        {
            System.out.println(emp);
        }
    }
}

class MyDate{
    private int month;
    private  int day;
    private  int year;

    public MyDate(int month ,int day,int year)
    {
        this.month=month;
        this.day=day;
        this.year=year;
    }
    public void setMonth(int month) {
        this.month = month;
    }

    public void setDay(int day) {
        this.day = day;
    }

    public void setYear(int year) {
        this.year = year;
    }

    public int getMonth() {
        return month;
    }

    public int getDay() {
        return day;
    }

    public int getYear() {
        return year;
    }

    @Override
    public String toString() {
        return "MyDate{" +
                "month=" + month +
                ", day=" + day +
                ", year=" + year +
                '}';
    }
}
class Employee{
    private String name;
    private double salary;
    private MyDate birthday;

    public Employee(String name, double salary, MyDate birthday) {
        this.name = name;
        this.salary = salary;
        this.birthday = birthday;
    }

    public String getName() {
        return name;
    }

    public double getSalary() {
        return salary;
    }

    public MyDate getBirthday() {
        return birthday;
    }

    public void setName(String name) {
        this.name = name;
    }

    public void setSalary(double salary) {
        this.salary = salary;
    }

    public void setBirthday(MyDate birthday) {
        this.birthday = birthday;
    }

    @Override
    public String toString() {
        return this.name+"\t"+this.salary+"\t"+this.birthday;
    }
}

泛型编程(自定义泛型)

定义语法:

class Classname<Typename1,Typename2...> {

        Typename attributes;

        Constructor...

        Methods...

}

接口

interface Interfacename<Typename1,Typename2...> {

        Typename attributes;

        Constructor...

        Methods...

}

实例化语法

Classname<Type...> className = new Classname<Type...>(arguments)

Classname<> className = new Classname<>(arguments)

接口

Interfacename<Type...> interfaceName = new Interfacename<Type...>(arguments)

Interfacename<> interfaceName = new Interfacename<>(arguments)

如下例子:


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {

//       设置数据类型为string
        Customize<String> goodName = new Customize<>("good name");
//        输出
        System.out.println(goodName);
//        输出给定数据类型
        goodName.showType();
    }
}
//定义如下自定义数据类型的类《T》
class Customize<T> {
    //    name是一个不确定数据类型
    T name;
    //构造器
    public Customize(T name) {
        this.name = name;
    }
    //tostring
    @Override
    public String toString() {
        return "Customize{" +
                "name=" + name +
                '}';
    }
    public  void showType()
    {
        System.out.println(this.name.getClass());
    }
}

例子


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {

//    不指定数据的类型,让运行时自动推导,但是这样效率不高。
        Customize<Object> objectCustomize = new Customize<>(1234);
//      输出。
        System.out.println(objectCustomize);
//        输出给定数据类型
        objectCustomize.showTyep();
    }
}
//定义如下自定义数据类型的类《T》
class Customize<T> {
//    name是一个不确定数据类型
    T name;
//构造器
    public Customize(T name) {
        this.name = name;
    }
//tostring
    @Override
    public String toString() {
        return "Customize{" +
                "name=" + name +
                '}';
    }

//    展示数据类型。
    public void showTyep()
    {
        System.out.println(this.name.getClass());
    }

}

使用泛型的注意事项

1.指定数据的类型必须是引用类型,比如如下的这就错了。


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {
//    设置int类型
        Customize<int> customize = new Customize<int>();

    }
}
class Customize<T>{
    T attribute;

    public Customize(T attribute) {
        this.attribute = attribute;
    }
}

改正后


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {
//    现在设置成了 Integer 数据类型.
        Customize<Integer> customize = new Customize<Integer>(232);

    }
}
class Customize<T>{
    T attribute;

    public Customize(T attribute) {
        this.attribute = attribute;
    }
}

2.如果指定了数据类型,也可以传入其子类型。


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {
//        正确,传入的是A()
        Customize<A> aCustomize = new Customize<A>(new A());
//        正确,传入的是A()的子类
        Customize<A> aCustomize1 = new Customize<A>(new B());

//        输出运行是类型
        aCustomize.showType();
        aCustomize1.showType();

    }
}
class Customize<T>{
    T attribute;

    public Customize(T attribute) {
        this.attribute = attribute;
    }

    public void showType()
    {
        System.out.println(attribute.getClass());
    }
}

class A {

}

class B extends A{

}

3.如果没有指定数据类型,默认的就是Object数据类型.


import java.lang.reflect.Array;
import java.security.cert.CollectionCertStoreParameters;
import java.util.*;

public class Main {
    public static void main(String[] args) {

        Customize aCustomize = new Customize();

//        等价于
        Customize<Object> objectCustomize = new Customize<>();
        

    }
}
class Customize<T>{
    T attribute;

    public Customize(){};

    public Customize(T attribute) {
        this.attribute = attribute;
    }

    public void showType()
    {
        System.out.println(attribute.getClass());
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值