目录

从零开始学习JAVA-泛型

[从零开始学习JAVA ] 泛型

前言:

本文将详细介绍之前我们在JAVA 中一直在讲的 ,各位感兴趣的同学可以点击进来观看。

泛型:

泛型是一种编程概念,它允许在定义类、接口或方法时使用类型参数,这样可以在使用时指定实际的类型。通过使用泛型,可以创建可重用、类型安全的代码,同时提高代码的灵活性和可读性。 泛型的主要目的是在编译时提供类型检查,以确保类型的一致性和安全性。它允许在不同的场景中使用相同的代码,而无需为每种类型都编写单独的实现。泛型代码在运行时会被擦除为非泛型形式,这种机制称为类型擦除。 在Java中,泛型使用尖括号(<>)来指定类型参数。例如,可以定义一个泛型类List,其中E是类型参数,表示列表中的元素类型。使用List创建一个字符串类型的列表,使用List创建一个整数类型的列表,它们都是相同的泛型类的实例,但元素类型不同。 泛型还可以用于方法和接口的定义。在方法中使用泛型参数可以使方法适用于不同类型的数据,而无需为每种数据类型编写不同的方法。接口中的泛型参数可以在实现接口时指定具体的类型。 泛型的优点: 1 类型安全:编译器可以在编译时检查类型错误,避免运行时类型转换异常。 2 代码重用:可以编写通用的代码,适用于不同类型的数据。 3 可读性和可维护性:泛型代码更易于理解和维护,因为类型信息可以在定义时指定。 其实泛型的出现,统一了集合中存储的元素,如果不使用泛型,当我们往集合中添加元素的时候,可以添加各种元素:数字,字符串等等,但是泛型规范了字符串中存储的类型。 使用泛型时的注意事项: 1.泛型不能写基本数据类型。(下面有解释) 2.指定泛型的基本类型之后,传递数据的时候,可以传入该类类型或者其子类类型 2.如果不写泛型,类型默认是object类(其实写了最后也是object类,下文有解释) 不使用泛型向集合中输入数据: import java.util.ArrayList; import java.util.Iterator; public class test { public static void main(String[] args) { ArrayList list=new ArrayList(); list.add(123); list.add(“abc”); list.add(1.2); //遍历集合中的每一个元素 Iterator it = list.iterator(); while(it.hasNext()) { Object element = it.next(); System.out.println(element); } } } 运行结果:https://i-blog.csdnimg.cn/direct/5ddbf084d70a4c1e8a215052313505c3.png 在不使用泛型的情况下,所有的数据都是Object类型的,此时可以向集合中添任意类型的数据,但是缺点就是我们无法调用这个类型的特有行为,如果要强制调用就要使用类型转换,而类型转化有可能会带来意想不到的错误。 利用泛型向集合中输入数据: import java.util.ArrayList; import java.util.Iterator; public class test { public static void main(String[] args) { ArrayList list=new ArrayList<>(); list.add(113); list.add(125); list.add(133); //遍历集合中的每一个元素 Iterator it = list.iterator(); while(it.hasNext()) { int em=it.next(); System.out.println(em); } } } 运行结果:https://i-blog.csdnimg.cn/direct/61a929af12b34e58a7b304eca7b4532a.png 我们可以看到在使用了泛型之后,我们的输入元素就只能是指定类型,而且也不用object类型接收next的返回值,直接使用int类型的就可以了,这意味着我们可以直接调用这个类型的方法。

额外拓展:

但其实JAVA中的泛型是伪泛型 。 Java泛型在编译时提供类型检查的功能,但在运行时会进行类型擦除,即泛型的类型信息被擦除为原始类型(raw type)。 在Java中,泛型是在编译时执行类型检查的机制,通过使用泛型,可以在定义类、接口和方法时使用类型参数,并在使用时指定具体的类型。这样可以提高代码的类型安全性,并减少在运行时可能出现的类型错误。 然而,在Java中的泛型机制实际上是通过类型擦除来实现的。在编译时,编译器会对泛型类型进行检查,确保类型的一致性。但在生成的字节码中,泛型的类型信息会被擦除掉,所有的泛型类型都被替换为其原始类型。

由于类型擦除的存在,导致了一些限制和特殊情况: 1 无法使用基本类型作为类型参数,只能使用其对应的包装类 。例如,不能使用基本类型int,而需要使用Integer。 2 无法在运行时获取泛型的实际类型参数。例如,无法使用instanceof操作符或通过反射来确定泛型类型的实际参数化类型。 3 在集合中无法存储具体的泛型类型,只能存储其原始类型。例如,无法创建一个ArrayList,只能创建ArrayList。 基本类型对应的包装类https://i-blog.csdnimg.cn/direct/9549efc7768a4ae1bc6de77c6eee7f27.png 这种泛型类型擦除的机制被称为"伪泛型",因为在运行时无法获得泛型的类型信息。尽管如此,Java的泛型机制仍然提供了编译时的类型检查,减少了类型错误的发生,并提高了代码的可读性和可维护性。 总而言之,“Java中的泛型是伪泛型"意味着Java的泛型在编译时提供类型检查,但在运行时类型信息被擦除,只剩下原始类型。尽管存在一些限制和特殊情况,泛型仍然是一种有用的编程机制。 其实这些话概括起来就是:泛型虽然在向数组中输入数据的时候,规定了数据的类型,但是这些数据在转向字节码的时候,数据类型都会被抹去,还是变为object类型。我们把这种模式就叫做伪泛型。