当前位置: 首页 > news >正文

数据结构之初识泛型

目录:

一.什么是泛型
二.引出泛型
三.泛型语法及,泛型类的使用和裸类型(Raw Type)  的了解
.
   四.泛型的编译:
   五.泛型的上界
   六.泛型方法

注意:在看泛型之前可以,回顾一下,包装类,包装类就是服务泛型的 :初识JAVA中的包装类,时间复杂度及空间复杂度-CSDN博客

一.什么是泛型:  

1.一般的类和方法只能使用具体的类型: 要么是基本类型,要么是自定义的类。如果要编写可以应用于多种类型的代码,这种刻板的限制对代码的束缚就会很大。

2.泛型是在JDK1.5引入的新的语法,通俗讲,泛型:就是适用于许多类型。从代码上讲,就是对类型实现了参数化。

二.引出泛型:

1.实现一个类,类中包含一个数组成员,使得数组中可以存放任何类型的数据,也可以根据成员方法返回数组中某个下标的值?看下面代码:问题是:1.如果数据太多,每次返回,向下转型太麻烦
2.元素放置也很混乱
class My_array {public Object[] array = new Object[10];public Object getArray(int pos) {return array[pos];}public void setArray(int pos, Object val) {this.array[pos] = val;}
}public class Test {public static void main0(String[] args) {My_array my_array = new My_array();//放置元素太乱,my_array.setArray(0, "haha");my_array.setArray(1, 2);//如果数据太多,每次返回,向下转型太麻烦String str = (String) my_array.getArray(0);}
}
3. 所以,泛型的主要目的: 就是指定当前的容器,要持有什么类型的对象 让编译
器去做检查 此时,就需要把类型,作为参数传递。需要什么类型,就传入什么类型

这个时候如果我们使用泛型,就可以解决这两个缺陷。泛型对数据结构学习也很重要

 

三.泛型语法及,泛型类的使用和裸类型(Raw Type) 的了解

1.语法 :下面给出一些泛型类的语法:

class 泛型类名称<类型形参列表> {
// 这里可以使用类型参数
}
class ClassName<T1, T2, ..., Tn> {
}class 泛型类名称<类型形参列表> extends 继承类/* 这里可以使用类型参数 */ {
// 这里可以使用类型参数
}
class ClassName<T1, T2, ..., Tn> extends ParentClass<T1> {
// 可以只使用部分类型参数
}

2.泛型类的使用:引出泛型在缺陷的,代码进行改写:

  
public static void main(String[] args) {//指定你要的类型My_array<Integer/*只能写类类型*/> my_array = new My_array</*Integer*/>();//        my_array.setArray(0, "haha");//自动类型检查my_array.setArray(0, 2);Integer a =  my_array.getArray(0);//自动类型转换System.out.println(a);/*** 想给数组放你想要的类型*/My_array<String> my_array1 = new My_array<>();my_array1.setArray(0, "haha");String str = my_a rray1.getArray(0);System.out.println(str);}}/*** 用泛型*///这个E相当于占位符
class My_array<E> {public Object[] array = new Object[10];public E getArray(int pos) {return (E) array[pos];}public void setArray(int pos, E val) {this.array[pos] = val;}
}

 注意:类名后的 <T> 代表占位符,表示当前类是一个泛型类,泛型只能接受类,所有的基本数据类型必须使用包装类! 

规范:类型形参一般使用一个大写字母表示,常用的名称有:
E 表示 Element
K 表示 Key
V 表示 Value
N 表示 Number
T 表示 Type
S, U, V 等等 - 第二、第三、第四个类型
3.裸类型(Raw Type) 的了解:用上面的例子里的,主方法说明:
注意:我们不要自己去使用裸类型,裸类型是为了兼容老版本的 API 保留的机制
总结:
1. 泛型是将数据类型参数化,进行传递
2. 使用 <T> 表示当前类是一个泛型类。
3. 泛型目前为止的优点:数据类型参数化,编译时自动进行类型检查和转换
   四.泛型的编译:
1. 擦除机制: 在Java虚拟机运行时,是不允许泛型 ,存在的,所以 在编译成字节码文件过程 会将所有的<E>替换为Object这种机制,我们称为:擦除机制。(可以到out目录,通过反汇编来查看) (命令:javap)
例子:下面这个代码中的,set方法的参数被擦除,为Object类:
class My_array<E> {public Object[] array = new Object[10];public E getArray(int pos) {return (E) array[pos];}public void setArray(int pos, E val) {this.array[pos] = val;}
}

   五.泛型的上界:

1.语法:这里用到extends关键字

class 泛型类名称<类型形参 extends 类型边界> {
...
}

2.来个例子:这里E继承了,Comparable接口,下面就可以使用,compareTo方法来,比较,

如果不规定这个边界那么通过擦除机制,就不能直接比较。规定了边界,就有了方法来比较

class Alg<E extends Comparable<E>> {public E Find_Max(E[] array) {E max = array[0];for (int i = 0; i < array.length; i++) {if (max.compareTo(array[i]) < 0) {max = array[i];}}return max;}
}public class Test {public static void main1(String[] args) {Integer[] array = new Integer[]{1,2,3,4,5,6};Alg<Integer> alg = new Alg<>();int ret = alg.Find_Max(array);//自动类型转换System.out.println(ret);}
}

这里还有一点值得注意:这里E继承了,Comparable接口,后没有重写,compareTo方法,因为你传的泛型参数(Integer)已经实现了Comparable接口,可以直接使用。

   六.泛型方法:

 1.  定义语法:方法限定符 <类型形参列表> 返回值类型 方法名称(形参列表) { ... }


class Alg2 {public<E extends Comparable<E>>  E Find_Max(E[] array) {E max = array[0];for (int i = 0; i < array.length; i++) {if (max.compareTo(array[i]) < 0) {max = array[i];}}return max;}
}public static void main2(String[] args) {Alg2 alg2 = new Alg2();Integer[] array = new Integer[]{1,2,3,4,5,6};int ret = alg2./*<Integer>*/Find_Max(array);System.out.println(ret);}

2.静态泛型方法:可以不用每次,实例化对象去调用方法,因为静态行为,不依赖对象,可以直接用类名调用

代码如下:


class Alg3 {public static  <E extends Comparable<E>>  E Find_Max(E[] array) {E max = array[0];for (int i = 0; i < array.length; i++) {if (max.compareTo(array[i]) < 0) {max = array[i];}}return max;}
}/*** 泛型静态方法2:加static* 静态行为,不依赖对象,可以直接用类名调用(不用每次,new对象)*/public static void main(String[] args) {Integer[] array = new Integer[]{1,2,3,4,5,6};int ret = Alg3./*<Integer>*/Find_Max(array);System.out.println(ret);}
}

相关文章:

  • idea有这个类却报红,无法用快捷键找到
  • k8s+RabbitMQ单机部署
  • 面试题——Spring
  • 我的创作纪念日 CF1620D Exact Change 题解
  • Python - 处理电子书的库
  • 【代码随想录训练营】【Day 49+】【动态规划-8】| Leetcode 121, 122, 123
  • C#使用OpenXml读取Word、PPT、Excel文档内容
  • linux pip 离线安装
  • 2024-6-10-zero shot,few shot以及无监督学习之间的关系是什么
  • NettyのBufferChannelSelector用法
  • 2024年春季学期《算法分析与设计》练习13
  • opencv中的图像操作
  • 端口占用多:UE4/UE5像素流送云推流时如何优化端口使用?
  • mac无法读取windows分区怎么办 苹果硬盘怎么读取
  • Android SDK版本号与API Level 的对应关系
  • IE9 : DOM Exception: INVALID_CHARACTER_ERR (5)
  • ES6简单总结(搭配简单的讲解和小案例)
  • HTTP请求重发
  • Java 9 被无情抛弃,Java 8 直接升级到 Java 10!!
  • JSONP原理
  • Less 日常用法
  • mysql_config not found
  • PHP的类修饰符与访问修饰符
  • spring + angular 实现导出excel
  • 基于OpenResty的Lua Web框架lor0.0.2预览版发布
  • 开源中国专访:Chameleon原理首发,其它跨多端统一框架都是假的?
  • 实习面试笔记
  • 小程序开发中的那些坑
  • 源码安装memcached和php memcache扩展
  • CMake 入门1/5:基于阿里云 ECS搭建体验环境
  • 完善智慧办公建设,小熊U租获京东数千万元A+轮融资 ...
  • ​LeetCode解法汇总2182. 构造限制重复的字符串
  • ​Spring Boot 分片上传文件
  • !!Dom4j 学习笔记
  • # .NET Framework中使用命名管道进行进程间通信
  • #define
  • #pragma once
  • (13):Silverlight 2 数据与通信之WebRequest
  • (26)4.7 字符函数和字符串函数
  • (vue)el-cascader级联选择器按勾选的顺序传值,摆脱层级约束
  • (阿里云万网)-域名注册购买实名流程
  • (附源码)springboot太原学院贫困生申请管理系统 毕业设计 101517
  • (附源码)计算机毕业设计SSM保险客户管理系统
  • (官网安装) 基于CentOS 7安装MangoDB和MangoDB Shell
  • (每日持续更新)信息系统项目管理(第四版)(高级项目管理)考试重点整理第3章 信息系统治理(一)
  • (转)Mysql的优化设置
  • ..thread“main“ com.fasterxml.jackson.databind.JsonMappingException: Jackson version is too old 2.3.1
  • .NET 4 并行(多核)“.NET研究”编程系列之二 从Task开始
  • .net oracle 连接超时_Mysql连接数据库异常汇总【必收藏】
  • .Net多线程总结
  • .Net语言中的StringBuilder:入门到精通
  • .Net转前端开发-启航篇,如何定制博客园主题
  • .py文件应该怎样打开?
  • @Builder用法
  • @PostConstruct 注解的方法用于资源的初始化