包装类和泛型

news2024/11/25 13:10:23

包装类和泛型严格来说算得上是JavaSE的内容,为什么他们要放在数据集合中?

这和集合类有关,我们在集合类中将会用到大量的泛型和包装类。

1. 包装类

基本介绍

包装类(wrapper)是针对八大基本数据类型相应的引用类型。

既然我们叫他包装类,那么类中肯定有方法:

例如:Integer

 那么包装类与基本数据类型的根本区别就在于能够调用方法,与此同时体现了面向对象。

我们先来看看吧大基本类型对应的包装类:

基本数据类型包装类
byteByte
shortShort
intInteger
longLong
floatFloat
doubleDouble
charCharacter
booleanBoolean

除了 Integer 和 Character, 其余基本类型的包装类都是首字母大写。

包装类和基本数据类型的转换

以int和Integer为例

1.jdk5前是手动装箱和拆箱的,装箱:基本类型 ——>包装类型。反之即为拆箱。

2.jdk5(含jdk5)是自动装箱和拆箱的。

3.自动装箱底层调用了valueOf方法。

public class demo {
    public static void main(String[] args) {
        int a = 10;
        Integer val =a;
    }
}

我们来看这段代码,它是如何进行自动拆箱和装箱的。

1. 先运行一遍程序,使之生成字节码文件

2.鼠标右键改Java文件,点击Explorer,如下图:

点击后: 

返回上一级目录,找到进入out目录下:

 再在目录表中输入cmd进入终端:

  3.进入终端后输入指令进入反汇编:javap -c demo(你的.Java文件名) 

 我们在反汇编中找到了valuOf()方法。

4. 在idea上选中Integer 按住ctrl + B 进入底层找到valuOf()方法

 传进来一个参数i ,返回时new 了一个Integer(i)。

 所以:

        int a = 10;
        //Integer val =a;//自动装箱
        Integer val = Integer.valueOf(a);//显示装箱
        Integer val2 = new Integer(a);//显示装箱

我们用这两种方法显示装箱。

我们来看看拆箱:

public static void main(String[] args) {

        Integer val =10;
        int a = val;
        System.out.println(a);

    }

 我们找到intValue :

2. 泛型(Generic)

泛型的引出

泛型的主要目的:就是指定当前的容器,要持有什么类型的对象。让编译器去做检查。此时,就需要把类型,作为参数传递。需要什么类型,就传入什么类型。

比如:在ArrayList(顺序链表下一章就会讲)中添加数据,我们利用之前学的去添加,并不能对添加的数据类型进行约束(不安全)。

例如:在ArrayList中添加多条狗,但是一不小心传递了一只猫,我们再对其进行遍历,调用foreach需要向下转型(转为Dog),这再运行就会报异常

不使用泛型的情况下:

使用泛型后: 

 它就自动检查想要添加进来的类型。

基本介绍

1. 泛型又称参数化类型,是jdk5.0以后出现的新特征,解决数据类型安全问题。

2. 再类声明或实例化时只要指定好需要的具体类型即可。

3.Java泛型可以保证如果程序在编译时没有发出警告,运行时就不会发生类型转换异常,同时代码更加健壮整洁。

4.泛型的作用是:可以在类声明是通过一个标识符表示某个属性的类型,或者某个方法的放回类型或者参数类型。

例如:

public class Main {
    public static void main(String[] args) {
        Person<Integer> integerPerson = new Person<>(123);
        Person<String> bit = new Person<>("bit");
    }
}

class Person<E> {
    E s ;//E表示S的数据类型,该数据类型在定义Person时指定,
    // 即在编译期间确定E是什么类型

    public Person(E s) {
        this.s = s;
    }
    public E f() {
        return s;
    }
}

语法声明

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

interface 接口<T> {

说明:

1. K、T、V不代表值,而是表示类型

2. 可以使用任意字母表示:

E 表示 Element
K 表示 Key
V 表示 Value
N 表示 Number
T 表示 Type
S, U, V 等等 - 第二、第三、第四个类型

3.类名后的 <T> 代表占位符,表示当前类是一个泛型类

泛型的使用细节和注意事项

1.interface 接口<T> { } 和public class HashSet<E>{ } 

T和E只能是同类型的引用

2. 在给泛型指定具体类型后,可以传入该类型或其子类型

例:若指定类型为A类,又需要添加B类,可以B类先继承A类再添加

3.泛型的使用形式

方法1:

ArrayList<Integer> List = new ArrayList<Integer>();

在实际应用中我们一般这么写:

ArrayList<Integer> List = new ArrayList<>();

在我最开始学习面向对象的时候,看起来没有用到,其实默认是Object

Pig pig = new Pig();
//看起来啥都没有写,其实默认是<Objec>
//因为Objec 默认是所有类型的父类
//这也就是个裸类型

裸类型(Raw Type)(了解)

说明:

裸类型是一个泛型类但没有带着类型实参,例如 MyArrayList 就是一个裸类型

MyArray list = new MyArray();

注意: 我们不要自己去使用裸类型,裸类型是为了兼容老版本的 API 保留的机制
下面的类型擦除部分,我们也会讲到编译器是如何使用裸类型的。

泛型的编译

那么,泛型到底是怎么编译的?这个问题,也是曾经的一个面试问题。泛型本质是一个非常难的语法,要理解好他还是需要一定的时间打磨。

代码:以泛型数组为例:

public class demo {
    public static void main(String[] args) {
        MyArray<Integer> myArray = new MyArray<Integer>();

    }
}
class MyArray<E> {
     public E[] obj = (E[])new Object[3];

    public E[] getObj() {
        return obj;
    }

    public void setObj(E[] obj) {
        this.obj = obj;
    }
    
}

我们进入终端,输入指令:javap -c  demo(.java文件名)

 简单讲解一下反汇编的代码:

 那么在程序编译好了以后跑进JVM,就没有了E[ ] 的概念了,我们泛型是在编译时期才存在的,一但程序运行起来以后,就不存在泛型这个概念了。E[ ] 在编译完成以后,就被擦除为了Object。

 泛型在编译期间只做两件事:

1. 存储数据时,帮我们进行自动类型检查

2. 获取元素时,帮我们完成自动类型转换

有关泛型擦除机制的文章截介绍:
Java泛型擦除机制之答疑解惑 - 知乎 (zhihu.com)

自定义泛型

介绍:

1. 一般由单个字母大写表示;

2. 可以有多个大写字母,如: <T,R,M>

3. 普通成员也可以使用泛型

4. 使用泛型的数组不可以初始化(实例化),也就是不可以直接new;因为数组在new时无法确定T的类型,也就无法准确的开辟空间大小。

5. 静态的方法(属性)不可以使用泛型,在类加载时,自定义泛型还未创建(在创建对象时创建),所以JVM无法识别自定义泛型

自定义泛型接口

基本语法:

interface 接口名<T,R> { }

注意细节:

1. 接口中,静态成员也不可以使用泛型(原理如上);

2.泛型接口的类型在继承或者实现接口是确定

3. 如不指定则为默认的Object

自定义泛型方法:

例:

class Car {
    public <T,R> void fly(T t, R r) {
        //实现的代码
    }
}

泛型的继承和通配符说明 

1. 泛型不具备继承性

例如:

 MyArray<Integer> myArray = new MyArray<Object>();

2. 如果需要对传入的类型变量做一定的约束,可以通过类型边界来约束;我们称之为泛型的上界
语法:

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

还可以使用通配符,通配符类型(?)

例如:

<? extends A>//表示支持A类以及A的子类

?的默认是实现是<? extends Object>,表示?是继承Object的任意类型。

3. 有泛型的上界,也就有泛型的下界

例如:

<? super A> // 表示支持A类以及A类的父类,并且不局限于A的直接父类

4. List<?>表示任意泛型类型均可接受

举个例子:

import java.util.ArrayList;
import java.util.List;

public class demo {
    public static void printCollection1(List<?> C) {
        for (Object object:C) {
            System.out.println(object);
        }
    }
    public static void printCollection2(List<? extends AA> C) {
        for (Object object:C) {
            System.out.println(object);
        }
    }
    public static void printCollection3(List<? super BB> C) {
        for (Object object:C) {
            System.out.println(object);
        }
    }

    public static void main(String[] args) {
        ArrayList<Object> list1 = new ArrayList<>();
        ArrayList<String> list2 = new ArrayList<>();
        ArrayList<AA> list3 = new ArrayList<>();
        ArrayList<BB> list4 = new ArrayList<>();
    }
}
class BB {
    
}
class AA extends BB {
    
}

我们的list1、list2、list3、list4均可以放入printCollection1()中;

我们的list3、list4均可以放入printCollection2()中;

我们的list1、list2均可以放入printCollection3()中;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/48570.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

云安全系列4:解析云安全工具集

随着组织越来越多地将数据和应用转移到云端&#xff0c;云安全在确保工作负载安全方面变得至关重要。Gartener 就表示&#xff1a;“云优先战略现在已十分普遍&#xff0c;甚至在不愿承担风险的企业机构中也是如此。但由于缺乏确保安全云计算部署所必需的技能和工具&#xff0c…

pytest文档83 - 把收集的 yaml 文件转 Item 用例并运行

前言 上一篇通过用例收集钩子 pytest_collect_file 把 yaml 文件收集起来的&#xff0c;仅仅只是收集到用例&#xff0c;还不能执行。 接下来详细讲解&#xff0c;如何把yaml 文件的内容&#xff0c;转成Item 用例去执行。 pytest_collect_file 收集钩子 准备一个待执行的YA…

Oracle SQL执行计划操作(12)——DDL及DML相关操作

14. DDL及DML相关操作 该类操作与DDL及DML类SQL语句相关。根据不同的具体SQL语句及其他相关因素,如下各操作可能会出现于相关SQL语句的执行计划。另需注意,该类操作会造成数据库对象或数据的改变。 1)CREATE TABLE STATEMENT 创建数据表。该操作出现于通过create[global …

PHP 开发-XAMPP 安装

开发环境&#xff1a;Windows10&#xff0c;XAMPP&#xff08;x64-7.4.33&#xff09;&#xff0c;Netbeans。 XAMPP 安装 官网下载XAMPP安装包&#xff0c;我下载的版本 x64-7.4.33。安装包中相关软件版本&#xff08;官网上可查询&#xff09;&#xff1a; Apache 2.4.54M…

Java并发编程--变量可见性、避免指令重排,还得是用它

那怎么保证程序里一个线程对共享变量的修改能立马被其他线程看到了&#xff1f;这时候有人会说了&#xff0c;加锁呀&#xff0c;前面不就是因为加锁成本太高才使用的 ThreadLocal的吗&#xff1f;怎么又说回去了&#xff1f; 其实CPU每个核心也都是有缓存的&#xff0c;今天要…

基于el-form实现自动展开/收起的查询条件组件

说明 如果查询条件过多&#xff0c;影响页面的展示效果&#xff0c;网上看了一些实现自动展开/收起的&#xff0c;有根据最小高度控制的&#xff0c;有基于条件的如v-show来控制&#xff0c;下面借助js原生的hidden属性实现要素的显示、隐藏控制。 先一下效果&#xff1a; 优…

web扫码登录

文章目录需求流程交互流程服务交互流程关键思路代码生成二维码&#xff0c;返回给PC展示轮询查询二维码状态APP扫码请求登录总结需求 pc端实现app扫码登录 流程 交互流程 服务交互流程 关键思路 主要问题在于如何识别APP端用户&#xff0c;然后传递给PC端已经登录成功 通过…

小程序瀑布流实现

什么是瀑布流布局 瀑布流布局&#xff0c;一般等宽&#xff0c;不等高的列表排列 原理是找出高度之和最小的那一列&#xff0c;在高度最小列继续添加元素 可以通过 absolute 定位实现&#xff0c;动态计算每一项的 top 和 left 封装瀑布流方法 function getAllRect(context…

HTML期末作业课程设计期末大作业--小米网站开发者平台首页 1页

⛵ 源码获取 文末联系 ✈ Web前端开发技术 描述 网页设计题材&#xff0c;DIVCSS 布局制作,HTMLCSS网页设计期末课程大作业 | 公司官网网站 | 企业官网 | 酒店官网 | 等网站的设计与制| HTML期末大学生网页设计作业&#xff0c;Web大学生网页 HTML&#xff1a;结构 CSS&#x…

MyBatis学习笔记(2022-11-30)

熬过无人问津的日子才会有诗和远方。 文章目录一、MyBatis简述二、快速入门三、MyBatis配置文件详解1. MyBatis核心配置文件1.1 configuration&#xff08;配置&#xff09;1.2 properties&#xff08;属性&#xff09;1.3 environments&#xff08;环境配置&#xff09;1.4 ty…

vue项目 element UI input框扫码枪扫描过快 出现数据丢失问题(已解决二)

项目需求: 输入框要掉两个接口&#xff0c;根据第一个验证接口返回的code&#xff0c;弹不同的框&#xff0c;点击弹框确认再掉第二个接口 根据客户现场反应&#xff0c;扫描枪快速扫描会出现 料号前几位字符丢失 不完整的问题。于是开始了测试之路。 解决方案探索 1.首先考…

数据可视化,销量第一的新能源汽车是什么?比亚迪新能源汽车销量接近60万辆

去年以来&#xff0c;新能源汽车火热度席卷全球&#xff0c;中国的新能源汽车无论制造或者销售&#xff0c;数量增长迅猛。下面小编用一款数据可视化软件&#xff0c;带你用可视化数据解读高端制造背后&#xff0c;中国新能源汽车的具体销售情况。同样如果你工作上有数据报表需…

[附源码]计算机毕业设计springboot酒店物联网平台系统

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

全国省市县 经纬度的 json数据(提供原文件),写Java代码,入库(提供代码)

目录 1 需求2 分析1 需求 有一个全国省市县 经纬度的 json数据,我想要使用代码入库 如何操作,代码咋写 2 分析 首先分析json结构, 一般拿到一个json数据,如果最外层不是 { } 包裹的,那么自己手动加一个 以上这个是自己加的,这个就是key 值就是list 集合 分析完json数…

【并发】深入理解Java线程的底层原理

线程基础知识 线程与进程 进程 操作系统会以进程为单位&#xff0c;分配系统资源&#xff08;CPU时间片、内存等资源&#xff09;&#xff0c;进程是资源分配的最小单位。 当一个程序被运行&#xff0c;从磁盘加载这个程序的代码至内存&#xff0c;这时就开启了一个进程。 线…

LDcad零件新增与导入

LDcad大颗粒小颗粒套装导入方法&#xff0c;以后LDcad也可以用套装搭建模型了。 LDcad大颗粒小颗粒套装导入方法&#xff0c; 以后LDcad也可以用套装搭建模型了。 有个遗憾&#xff0c;就是零件不全。 具体导入方法看下文。 我们可以看到。这些套装都有对应的图标。方便…

环境温湿度在线监测如何实现?有何应用场景?

温度、湿度等环境数据与人们生活生产息息相关。温湿度传感器作为能将温度量和湿度量转换成容易被测量处理的电信号的设备或装置&#xff0c;广泛应用于工农业生产、气象、环保、国防、科研等经常需要对环境或设备的温度与湿度进行测量的领域&#xff0c;因此也产生了对温湿度远…

ASP.NET Core 3.1系列(15)——Entity Framework Core之DB First

1、前言 本文开始介绍一些关于Entity Framework Core的内容。在EFCore中&#xff0c;常用的为DB First模式和Code First模式&#xff0c;下面就来介绍一下如何在EFCore中使用DB First模式生成实体类和数据库上下文。 2、创建测试数据库 在SQL Server中新建一个数据库Dao&…

2016-04《信息资源管理 02378》真卷解析,逐题解析+背诵技巧

本系列博客合计 21 篇&#xff0c;每篇都将解析一张《信息资源管理》真卷&#xff0c;并附带答案解析与背诵技巧。 全国 2016 年 4 月自学考试信息资源管理试题&#xff08;02378&#xff09; 单选题 1、按信息表现形式划分&#xff0c;信息可分为&#xff08;C&#xff09; …

JavaScript的Web api接口

JavaScript的Web api 文章目录JavaScript的Web api选中元素事件操作元素获取/元素内容获取/修改元素属性获取/修改表单元素属性实现一个显示/隐藏 密码的功能实现一个加减计算器复选框全选/全不选获取/修改样式属性点击文字放大字体实现白天模式与夜间模式的切换操作节点新增节…