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

【Java版数据结构】初识泛型

看到这句话的时候证明:此刻你我都在努力
加油陌生人
微信图片编辑_20240229212205.png
br />个人主页:Gu Gu Study
专栏:Java版数据结构
喜欢的一句话: 常常会回顾努力的自己,所以要为自己的努力留下足迹


喜欢的话可以点个赞谢谢了。
作者:小闭


前言

好久没有更新文章了,大概断更了20天,想着今天就写一下文章吧!最近也是又温习了一下数据结构,其实之前我写过关于数据结构的一个专栏那个专栏是写了顺序表,链表,栈和队列,但是那时是用C语言实现的,虽然数据结构不局限于语言,但是总归在语言的使用上有所不同,毕竟面向不同,一个是面向过程的C语言,一个是面向对象的Java。所以这次我打算起一个数据结构的Java专栏,当然由于之前已经写过有些地方会写得简洁一点,模糊的话大家可以去看一下前面得文章哦。今天是关于泛型的哦!只是简单的认识一下基础,为了更好的理解后面Java使用数据结构的代码。


认识包装类

Java中,包装类(Wrapper Classes)是用来包装原始数据类型的类。Java是一种面向对象的语言,所有的对象都是类的实例,包括基本数据类型。但是基本数据类型并不是对象,它们是Java语言的一部分,而不是Java类。为了将基本数据类型当作对象来处理,Java提供了对应的包装类。
以下是Java中的基本数据类型及其对应的包装类:

  • boolean - Boolean
  • byte - Byte
  • short - Short
  • int - Integer
  • long - Long
  • float - Floa
  • double - Double
  • char - Characte

很容易看出来除了int和char的包装类有些特殊其它基本数据的包装类就是大写其第一个字幕。
包装类的主要作用包括:

  1. 自动装箱和拆箱:Java 5 引入了自动装箱(Autoboxing)和拆箱(Unboxing)的概念,允许自动将基本数据类型转换为对应的包装类对象,反之亦然。
  2. 使用对象的方法:包装类提供了一些有用的方法,比如toString()equals()hashCode()等,这些在基本数据类型中是不可用的。
  3. 集合框架:Java的集合框架只能存储对象,不能直接存储基本数据类型。通过包装类,可以将基本数据类型作为对象存储在集合中。
  4. 方法参数:在定义方法时,如果需要一个可变参数,可以使用包装类,因为基本数据类型是不可变的。

在数据结构中我们主要运用第三点集合框架,集合框架,后面的文章会给大家讲到。

自动装箱和拆箱的使用

以下就是自动装箱和拆箱的使用方法:
如果将num1和num2打印出来,都是一样的值----5。

public class Test {public static void main(String[] args) {Integer num1 = 5; // 自动装箱int num2 = num1; // 自动拆箱System.out.println(num1);System.out.println(num2);}
}

image.png
包装类还提供了一些静态方法,比如Integer.valueOf(int i)用于将基本类型转换为包装类对象,
Integer.parseInt(String s)用于将字符串转换为基本类型。这些方法在处理数值与字符串之间的转换时非常有用。将字符串转化为整形其实我们前面在讲字符串时也是讲过的。
了解完包装类接下来就是我们的泛型学习了。

泛型的概念

泛型是Java中一种强大的特性,它允许程序员在编写代码时指定类型参数,从而使得代码更加灵活和可重用。泛型提供了一种方式,使得编译器可以在编译时检查类型安全,避免了类型转换的错误和运行时的类型检查。


当当看概念可能比较抽象,下面我们引出一个情境:

  1. 我们以前学过的数组,只能存放指定类型的元素,例如:int[] array = new int[10]; String[] strs = new
    String[10];

那么如果我想要一个什么类型都能储存的数组可以吗?
其实这是可以实现的,那么我们这里就要提到object类了。
所有类的父类,默认为Object类。数组是否可以创建为Object?
答案是可以的,如下代码,在自己定义了一个MyArray后,我们就可以在里面储存各种类型的数据了。

class MyArray {Object[] array = new Object[10];public void setVal(int pos, Object val) {array[pos] = val;}public Object getVal(int pos) {return array[pos];}}public class Test {public static void main(String[] args) {MyArray myArray=new MyArray();myArray.setVal(0,2);myArray.setVal(1,"hello world");int ret1=(int)myArray.getVal(0);        //注意这里必须进行强制类型转换String ret2=(String)myArray.getVal(1);   //注意这里必须进行强制类型转换System.out.println(ret1);System.out.println(ret2);}}

但是数组的定义本来就是用来储存同种类型数据的一种集合。像上面这种却又不像是数组呢。
下面我们在引入一个情境:
我在定义一个容器时暂时不知道用什么数据类型怎么办,我在用到时才知道这个容器要用什么类型的数据,这时我们该怎么办呢?这时我们的主角泛型就该出场了。

泛型的主要目的:就是指定当前的容器,要持有什么类型的对象。让编译 器去做检查。此时,就需要把类型,作为参数传递。需要什么类型,就传入什么类型。
那么下面就来细看泛型的使用
语法:
class 泛型类名称<类型形参列表> {
// 这里可以使用类型参数
}

那么类型参数列表是什么呢?
其实我们可以理解为一个占位符,我们用一个字母来代表他是一个类型的数据,至于这具体是什么我们定义这个类时是不知道的,但是这时我们可以在这个类中先使用这个未知的类型进行一系列操作,当我们在实例化new一个对象出来时才可以传入自己想要使用的参数类型。image.png
泛型的使用如下代码:

class Box<T> {private T t;public void set(T t) {this.t = t;}public T get() {return t;}
}public class Test {public static void main(String[] args) {Box<Integer> box=new Box<>();box.set(6);System.out.println(box.get());}}

在上面代码中我们定义一个泛型类Box,在实例化时我们需要如上 Box box=new Box<>();那么这个类中的T,那么全部转化为Integer了,所以在传入类型实参时通常是一个类,即:这里的Integer不能是int,这就是我们为什么要先学习包装类。
这个泛型类就是我们数据结构最常用的泛型知识点。

泛型的上界

首先我们先了解什么是泛型上界
泛型上界是泛型编程中的一个重要概念,它用于指定泛型参数可以继承或实现的类或接口的类型范围。在Java等支持泛型的语言中,上界允许你限制泛型参数必须是某个类或接口的子类或实现。
其语法为:
class 泛型类名称<类型形参 extends 类型边界> {
······
}

代码例子

public class MyArray<E extends Number> {
...
}

那么这时我们的传入的类型变量就必须为Number的子类
MyArray n1; // 正常,因为 Integer 是 Number 的子类型
MyArray n2; // 编译错误,因为 String 不是 Number 的子类型

泛型方法

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

}

代码示例:

 public class Util { 
//静态的泛型方法 需要在static后用<>声明泛型类型参数 
public static<E>  void swap(E[] array, int i, int j) { 
E t = array[i];array[i] = array[j]; 
array[j] = t;} 
} 

那么这时我们使用泛型方法时通常有两种方式:
一、可以自动进行类型推导:

 Integer[] a = { ... }; 
swap(a, 0, 9); String[] b = { ... };swap(b, 0, 9);  

二、 不使用类型推导

 Integer[] a = { ... }; 
Util.<Integer>swap(a, 0, 9); String[] b = { ... }; 
Util.<String>swap(b, 0, 9) 

以上就是泛型的简单介绍,泛型的知识还有很多,但是我们这次只学习一些基础唔。主要是为了后面数据类型的打基础铺垫。

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • OpenKylin 系统中禁用 Win 键
  • html+css前端作业 王者荣耀官网1个页面(带报告)
  • Java面试八股之Spring框架的核心模块
  • Web动画(lottie篇)
  • Unity3D结合AI教育大模型 开发AI教师 AI外教 AI英语教师案例
  • 昇思25天学习打卡营第23天|LSTM+CRF序列标注
  • 图像生成中图像质量评估指标— LPIPS介绍
  • JCR一区级 | Matlab实现TTAO-Transformer-LSTM多变量回归预测
  • 分享几种电商平台商品数据的批量自动抓取方式
  • STM32CubeIDE(CAN)
  • Java设计模式—单例模式(Singleton Pattern)
  • W30-python03-pytest+selenium+allure访问百度网站实例
  • SpringBoot中如何使用RabbitMq
  • NVIDIA Drivers、CUDA、Pytorch安装
  • linux--mount--挂载
  • 2017-08-04 前端日报
  • 2017年终总结、随想
  • Android Volley源码解析
  • CentOS 7 修改主机名
  • crontab执行失败的多种原因
  • github从入门到放弃(1)
  • JavaScript设计模式之工厂模式
  • JAVA之继承和多态
  • JS创建对象模式及其对象原型链探究(一):Object模式
  • Just for fun——迅速写完快速排序
  • leetcode46 Permutation 排列组合
  • React Transition Group -- Transition 组件
  • windows下mongoDB的环境配置
  • 3月7日云栖精选夜读 | RSA 2019安全大会:企业资产管理成行业新风向标,云上安全占绝对优势 ...
  • 7行Python代码的人脸识别
  • 湖北分布式智能数据采集方法有哪些?
  • 我们雇佣了一只大猴子...
  • ​【数据结构与算法】冒泡排序:简单易懂的排序算法解析
  • ​软考-高级-信息系统项目管理师教程 第四版【第23章-组织通用管理-思维导图】​
  • # centos7下FFmpeg环境部署记录
  • # 数论-逆元
  • (02)Unity使用在线AI大模型(调用Python)
  • (160)时序收敛--->(10)时序收敛十
  • (19)夹钳(用于送货)
  • (22)C#传智:复习,多态虚方法抽象类接口,静态类,String与StringBuilder,集合泛型List与Dictionary,文件类,结构与类的区别
  • (30)数组元素和与数字和的绝对差
  • (C++)八皇后问题
  • (floyd+补集) poj 3275
  • (rabbitmq的高级特性)消息可靠性
  • (Spark3.2.0)Spark SQL 初探: 使用大数据分析2000万KF数据
  • (免费领源码)python#django#mysql公交线路查询系统85021- 计算机毕业设计项目选题推荐
  • (五)activiti-modeler 编辑器初步优化
  • (一)C语言之入门:使用Visual Studio Community 2022运行hello world
  • (一)Java算法:二分查找
  • (转)清华学霸演讲稿:永远不要说你已经尽力了
  • (转)如何上传第三方jar包至Maven私服让maven项目可以使用第三方jar包
  • (轉貼) 蒼井そら挑戰筋肉擂台 (Misc)
  • (自适应手机端)响应式新闻博客知识类pbootcms网站模板 自媒体运营博客网站源码下载
  • .[hudsonL@cock.li].mkp勒索病毒数据怎么处理|数据解密恢复
  • .class文件转换.java_从一个class文件深入理解Java字节码结构