详谈 java泛型(参数化类型)

您所在的位置:网站首页 接口参数的类型有哪些 详谈 java泛型(参数化类型)

详谈 java泛型(参数化类型)

2024-07-05 07:22| 来源: 网络整理| 查看: 265

泛型 一、泛型概念1、什么是泛型?2、作用3、优点 二、泛型分类 :泛型类、泛型接口、泛型方法1、泛型类2、泛型方法3、泛型接口 三、泛型的通配符

一、泛型概念 1、什么是泛型?

泛型,即“参数化类型”。我们最熟悉的就是定义方法时有形参,然后调用此方法时传递实参。

本质:其本质是参数化类型,也就是说所操作的数据类型被指定为一个参数(type parameter)这种参数类型可以用在类、接口和方法的创建中,分别称为泛型类、泛型接口、泛型方法。 在这里插入图片描述

ArrayList objectName =new ArrayList(); 

E: 泛型数据类型,用于设置 objectName 的数据类型,只能为引用数据类型。

2、作用

第一是泛化。可以用T代表任意类型Java语言中引入泛型是一个较大的功能增强不仅语言、类型系统和编译器有了较大的变化,以支持泛型,而且类库也进行了大翻修,所以许多重要的类,比如集合框架,都已经成为泛型化的了,这带来了很多好处。

第二是类型安全。泛型的一个主要目标就是提高Java程序的类型安全,使用泛型可以使编译器知道变量的类型限制,进而可以在更高程度上验证类型假设。如果不用泛型,则必须使用强制类型转换,而强制类型转换不安全,在运行期可能发生ClassCast Exception异常,如果使用泛型,则会在编译期就能发现该错误。

第三是消除强制类型转换。泛型可以消除源代码中的许多强制类型转换,这样可以使代码更加可读,并减少出错的机会。

第四是向后兼容。支持泛型的Java编译器(例如JDK1.5中的Javac)可以用来编译经过泛型扩充的Java程序(Generics Java程序),但是现有的没有使用泛型扩充的Java程序仍然可以用这些编译器来编译。

3、优点

1、类型安全 2、消除强制类型转换 3、更高的运行效率 4、潜在的性能收益

二、泛型分类 :泛型类、泛型接口、泛型方法

首先我们得先了解泛型字母的含义

字母意义E-Element在集合中使用,因为集合中存放的是元素T-TypeJava类K - Key键v - Value值N- Number数值类型

首先我们来看看使用泛型跟不使用泛型的区别:

不使用泛型:

import java.util.ArrayList; import java.util.Iterator; /** * @Description: $泛型 * @Author: dyq * @Date: $ */ public class GenericDemo { public static void main(String[] args) { show01(); } /*创建集合对象,不使用泛型 好处: 集合不使用泛型,默认的类型就是object类型,可以存储任意类型的数据 弊端: 不安全,会引发异常 * */ private static void show01() { ArrayList l = new ArrayList(); l.add("hi"); l.add(1122); l.add(10f); l.add('男'); //用迭代器遍历集合 Iterator it = l.iterator(); while (it.hasNext()){ /* Object next = it.next(); //输出无异常,以为ArrayList默认的类型就是object类型 System.out.println(next);*/ String str = (String) it.next(); //输出异常 ,数组中不单单只有String类型,转型报错 System.out.println(str); } } }

运行输出报错: 在这里插入图片描述 使用泛型 当规定泛型的类型时,输入非规定类型数据会直接报错。 在这里插入图片描述

import java.util.ArrayList; import java.util.Iterator; /** * @Description: $泛型 * @Author: dyq * @Date: $ */ public class GenericDemo { public static void main(String[] args) { show01(); } /*创建集合对象,使用泛型 好处: 1 .避免了类型转换的麻烦,存储的是什么类型,取出的就是什么类型 2.把运行期异常(代码运行之后会批出的异常),提升到了编译期 弊端: 泛型是什么类型,只能存储什么类型的数据 */ private static void show01() { ArrayList l = new ArrayList(); l.add("小马"); l.add("小明"); l.add("小华"); l.add("小红"); //用迭代器遍历集合 Iterator it = l.iterator(); while (it.hasNext()){ String str = (String) it.next(); System.out.println(str); } } }

输出结果:

小马 小明 小华 小红 1、泛型类

定义格式:

修饰符 class类名{}

看一个指定泛型为String 的

public class GenericClass { private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } public static void main(String[] args) { GenericClass gc =new GenericClass(); gc.setName("我只能是字符串"); String name = gc.getName(); System.out.println(name); } }

输出 在这里插入图片描述 当我们使用不使用指定类型时

/** * @Description: $定义一个含有泛型的类, 模拟Arraylist集合 * 泛型是一个未知的数据类型,当我们不确定什么什么数据类型的时候,可以使用泛型 * 泛型可以接牧任意的数据类型,可以使用Integer , String, student.. . * 创建对象的时候确定泛型的数据类型 * @Author: dyq * @Date: $ */ public class GenericClass { private E name; public E getName() { return name; } public void setName(E name) { this.name = name; } public static void main(String[] args) { //不写泛型默认为Object GenericClass gc =new GenericClass(); gc.setName("我是Object"); Object name = gc.getName(); System.out.println(name); //可以通过创建对象时确定数据类型 //泛型使用Integer类型 GenericClass Igc = new GenericClass(); Igc.setName(1); Integer i = Igc.getName(); System.out.println("我是Interger类型:"+i); //泛型使用String类型 GenericClass sgc = new GenericClass(); sgc.setName("花花"); String s = sgc.getName(); System.out.println("我是String类型:"+s); } }

结果:

我是Object 我是Interger类型:1 我是String类型:花花 2、泛型方法

定义含有泛型的方法:泛型定义在方法的修饰符和返回值类型之间格式:

语法:

修饰符返回值类型方法名(参数列表(使用泛型)){ 方法体; }

代码示例:

/** * @Description: 泛型方法$ 含有泛型的方法,在调用方法的时候确定泛型的数据类型, * 传递什么类型的参数,泛型是什么类型 * @Author: dyq * @Date: $2021年2月5日 */ public class GenericMethod { //定义一个含有泛型的方法 public void method01(M m){ System.out.println(m); } //定义一个含有泛型的静态方法 public static void method02(S s){ System.out.println(s); } //测试含有泛型的主方法 public static void main(String[] args) { GenericMethod m = new GenericMethod(); m.method01(10); m.method01("你好"); m.method01('男'); m.method01(19); System.out.println("==============="); m.method02("我是方法02"); m.method02("ok!"); m.method02(1); m.method02('女'); } }

结果:

10 你好 男 19 =============== 我是方法02 ok! 1 女 3、泛型接口

定义格式∶

修饰符interface接口名{ }

代码演示: 新建一个接口

/** * @Description: 泛型接口$ * @Author: dyq * @Date: 2021年2月5日$ */ public interface GenericInterface { public abstract void add(E e); public abstract E getE(); }

有两种实现方法先创建一个GenericInterfaceImpl01类

/** * @Description: $含有泛型的接口,第一种方式:定义接口的实现,实现接口,指定接口的泛型 * @Author: dyq * @Date: $ */ public class GenericInterfaceImpl01 implements GenericInterface{ @Override public void add(String s) { System.out.println(s); } @Override public String getE() { return null; } }

再创建一个GenericInterfaceImpl02实现类

/** * @Description: $含有泛型的接口第二种使用方式:接口使用什么泛型, * 实现类就使用什么泛型,类跟着接口走就相当于定义了一个含有泛型的类, * 创建对象的时候确定泛型的类型 * @Author: dyq * @Date: $ * public interface List{ * boolean add(E e); * E get(int index); * } * public class ArrayList impLements List{ * } */ public class GenericInterfaceImpl02 implements GenericInterface { @Override public void add(I i) { System.out.println(i); } @Override public I getE() { return null; } }

最后新建一个测试类

/** * @Description: $测试含有泛型的接口 * @Author: dyq * @Date: $ */ public class GenericInterfaceTest { public static void main(String[] args) { //创建GenericInterfaceImpl GenericInterfaceImpl01 gil =new GenericInterfaceImpl01(); gil.add("哈哈哈~"); //创建GenericInterfaceImpl01 定义输出的数据类型 GenericInterfaceImpl02 gil2 = new GenericInterfaceImpl02(); gil2.add(10); GenericInterfaceImpl02 gil3 = new GenericInterfaceImpl02(); gil3.add(8.88); } }

结果:

哈哈哈~ 10 8.88 三、泛型的通配符

当使用泛型类或者接口时,传递的数据中,泛型类型不确定,可以通过通配符< ?>表示。但是一旦使用泛型的通配符后,只能使用Object类中的共性方法,集合中元素自身方法无法使用。

1、通配符基本使用

泛型的通配符:不知道使用什么类型来接收的时候,此时可以使用?,?表示未知通配符。此时只能接受数据,不能往该集合中存储数据。 代码示例:

import java.util.ArrayList; import java.util.Iterator; /** * @Description: $类型通配符一般是使用?代替具体的类型参数 * @Author: dyq * @Date: $ */ public class GenericTest { public static void main(String[] args) { ArrayList list = new ArrayList(); list.add(1); list.add(2); ArrayList list1 = new ArrayList(); list1.add("a"); list1.add("b"); printArray(list); printArray(list1); } /*定义一个方法,能遍历所有类型的ArrayList集合 * 这时候我们知道ArrList集合使用说明数据,可以泛型的通配符?来接收数据类型*/ public static void printArray(ArrayList list){ //使用迭代器遍历集合 Iterator it =list.iterator(); while (it.hasNext()){ //it.next()方法。取出的元素是object,可以接收任意的数据类型 Object o = it.next(); System.out.println(o); } } }

结果:

1 2 a b

2、类型通配符上限通过形如List来定义,如此定义就是通配符泛型值接受Number及其下层子类类型。 3、类型通配符下限通过形如 List



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3