Java 包装类与泛型学习笔记:从装箱拆箱到类型擦除与通配符

别再手动点按钮了!用C#给PowerMill做个自动化小助手(附完整源码) 本文详细介绍了如何使用C#进行PowerMill二次开发,打造自动化助手以提升CAM工程师的工作效率。通过实战案例和完整源码,展示了从环境配置到核心功能实现的完整流程,包括智能连接模块、项目批量处理器和刀路智能分析器等高级功能开发。 阅读详情

本文是 Java 集合框架前置知识的整理笔记,覆盖包装类、包装类的自动装箱/拆箱机制,以及泛型的语法、擦除机制、上界与通配符。整理自课程讲义《3. 包装类&泛型》,代码做了格式化与勘误,并补充了讲义中留作思考的面试题答案。

本节目标

  1. 以能阅读 Java 集合源码为目标学习泛型
  2. 了解包装类
  3. 了解泛型

一、包装类

1.1 基本数据类型和对应的包装类

在 Java 中,由于基本类型不是继承自 Object,为了在泛型代码中可以支持基本类型,Java 给每个基本类型都对应了一个包装类型。

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

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

1.2 装箱和拆箱

装箱:把基本类型的数据放进一个包装类对象里。
拆箱:把包装类对象里的值取出来,还原成基本数据类型。

int i = 10;

// 装箱操作:新建一个 Integer 类型对象,将 i 的值放入对象的某个属性中
Integer ii = Integer.valueOf(i);
Integer ij = new Integer(i);

// 拆箱操作:将 Integer 对象中的值取出,放到一个基本数据类型中
int j = ii.intValue();

勘误与提醒:new Integer(i) 这种写法从 Java 9 起已被标记为废弃(deprecated),永远应该使用 Integer.valueOf(i)。原因是 valueOf 会复用缓存对象,而 new 每次都强制创建新对象。

1.3 自动装箱和自动拆箱

可以看到,使用过程中装箱和拆箱会带来不少代码量。为了减少开发者的负担,Java 提供了自动机制。

int i = 10;

Integer ii = i;           // 自动装箱
Integer ij = (Integer) i; // 自动装箱

int j = ii;               // 自动拆箱
int k = (int) ii;         // 自动拆箱

自动装箱/拆箱是编译期的语法糖,本质仍然是调用 valueOf 和 xxxValue()。可以通过 javap -c 查看字节码文件内容,观察装箱和拆箱的操作。

1.4【面试题】下面代码输出什么,为什么?

public static void main(String[] args) {
    Integer a = 127;
    Integer b = 127;

    Integer c = 128;
    Integer d = 128;

    System.out.println(a == b); // true
    System.out.println(c == d); // false
}

答案:a == b 为 true,c == d 为 false。

原因:Integer 内部维护了一个静态的整数缓存数组 IntegerCache,默认缓存范围是 -128 ~ 127。

  • a 和 b 都是 127,在缓存范围内,Integer.valueOf(127) 直接返回缓存中的同一个对象,所以 == 比较引用相等,结果为 true。
  • c 和 d 都是 128,超出了缓存范围,valueOf 会各自 new 一个对象,两个引用不同,所以结果为 false。

想改变上界可以设置 JVM 参数 -XX:AutoBoxCacheMax=<size>(只影响上界,下界固定为 -128)。

结论:包装类比较值的时候,请用 equals(),不要用 ==。


二、泛型

2.1 什么是泛型

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

—— 来源:《Java 编程思想》对泛型的介绍

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

2.2 引出泛型:一个"万能数组"的困境

需求:实现一个类,类中包含一个数组成员,使得数组中可以存放任何类型的数据,也可以根据成员方法返回数组中某个下标的值。

既然所有类的父类默认都是 Object,那我们能不能把数组声明为 Object[]?

class MyArray {
    public Object[] array = new Object[10];

    public Object getPos(int pos) {
        return this.array[pos];
    }

    public void setVal(int pos, Object val) {
        this.array[pos] = val;
    }
}

public class TestDemo {
    public static void main(String[] args) {
        MyArray myArray = new MyArray();
        myArray.setVal(0, 10);
        myArray.setVal(1, "hello"); // 字符串也可以存放

        String ret = myArray.getPos(1); // 编译报错
        System.out.println(ret);
    }
}

问题:以上代码实现后发现

  1. 任何类型数据都可以存放
  2. 1 号下标本身就是字符串,但是却编译报错,必须进行强制类型转换

虽然在这种情况下,当前数组任何数据都可以存放,但是更多情况下,我们还是希望它只能够持有一种数据类型,而不是同时持有这么多类型。所以:

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

2.3 泛型类的语法

基础写法:

class 泛型类名称<类型形参列表> {
    // 这里可以使用类型参数
}

class ClassName<T1, T2, ..., Tn> {
}

其他写法(带继承):

class 泛型类名称<类型形参列表> extends 继承类 /* 这里可以使用类型参数 */ {
    // 这里可以使用类型参数
}

class ClassName<T1, T2, ..., Tn> extends ParentClass<T1> {
    // 可以只使用部分类型参数
}

把上面的 MyArray 改写为泛型版本:

class MyArray<T> {
    public Object[] array = new Object[10];

    public T getPos(int pos) {
        return (T) this.array[pos];
    }

    public void setVal(int pos, T val) {
        this.array[pos] = val;
    }
}

public class TestDemo {
    public static void main(String[] args) {
        MyArray<Integer> myArray = new MyArray<>(); // 1
        myArray.setVal(0, 10);
        myArray.setVal(1, 12);

        int ret = myArray.getPos(1);                // 2
        System.out.println(ret);

        myArray.setVal(2, "bit");                   // 3
    }
}

代码解释:

  1. 类名后的 <T> 代表占位符,表示当前类是一个泛型类
  2. 【规范】类型形参一般使用一个大写字母表示,常用名称有:
    • E 表示 Element
    • K 表示 Key
    • V 表示 Value
    • N 表示 Number
    • T 表示 Type
    • S、U、V 等等 —— 第二、第三、第四个类型
  3. 注释 1 处,类型后加入 <Integer> 指定当前类型
  4. 注释 2 处,不需要进行强制类型转换
  5. 注释 3 处,代码编译报错。因为在注释 2 处已经指定了类当前的类型,所以编译器会在存放元素的时候帮助我们进行类型检查

2.4 泛型类的使用

语法:

泛型类<类型实参> 变量名;                    // 定义一个泛型类引用
new 泛型类<类型实参>(构造方法实参);          // 实例化一个泛型类对象

示例:

MyArray<Integer> list = new MyArray<Integer>();

注意:泛型只能接受类,所有的基本数据类型必须使用包装类!

类型推导(Type Inference):

当编译器可以根据上下文推导出类型实参时,可以省略类型实参的填写。

MyArray<Integer> list = new MyArray<>(); // 可以推导出实例化需要的类型实参为 Integer

2.5 裸类型(Raw Type)(了解)

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

MyArray list = new MyArray();

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

2.6 泛型如何编译:擦除机制

那么,泛型到底是怎么编译的?

1. 基本概念

  • 在编译时,Java 编译器会将泛型类型信息从代码中移除,这个过程就叫做类型擦除。
  • 擦除后,泛型类型会被替换为其边界类型(通常是 Object)或者指定的类型。

2. 擦除过程

  • 将泛型参数替换为其边界或 Object
  • 在必要的地方插入类型转换以保持类型安全
  • 生成桥接方法以保持多态性

3. 示例

擦除前:

class MyArray<T> {
    public Object[] array = new Object[10];

    public T getPos(int pos) {
        return (T) this.array[pos];
    }

    public void setVal(int pos, T val) {
        this.array[pos] = val;
    }
}

擦除后:

class MyArray {
    public Object[] array = new Object[10];

    public Object getPos(int pos) {
        return this.array[pos];
    }

    public void setVal(int pos, Object val) {
        this.array[pos] = val;
    }
}

重要推论:因为擦除后 T 变成了 Object,所以泛型里不能 new T[]、不能 new T(),静态方法中也不能直接使用类的类型形参。

2.7 关于桥接方法

  • 泛型类型擦除可能导致子类方法和父类方法的签名不一致
  • 为了维护 Java 的多态性,需要桥接方法来确保子类方法能够正确覆盖父类方法
public class Node<T> {
    T data;

    public void setData(T data) {
        this.data = data;
    }
}

public class StringNode extends Node<String> {
    @Override
    public void setData(String data) {
        super.setData(data);
    }
}

类型擦除后代码变为:

public class Node {
    Object data;

    public void setData(Object data) {
        this.data = data;
    }
}

public class StringNode extends Node {
    public void setData(String data) {
        super.setData(data);
    }
}

此时 StringNode 的 setData 方法并没有真正覆盖父类的 setData 方法(参数类型不同)。为了解决这个问题,编译器会在 StringNode 中生成一个桥接方法:

// 编译器生成的桥接方法
public void setData(Object data) {
    setData((String) data);
}

2.8 泛型的上界

在定义泛型类时,有时需要对传入的类型变量做一定的约束,可以通过类型边界来约束。

语法:

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

示例:

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

只接受 Number 的子类型作为 E 的类型实参。

MyArray<Integer> l1; // 正常,因为 Integer 是 Number 的子类型
MyArray<String> l2;  // 编译错误,因为 String 不是 Number 的子类型

了解:没有指定类型边界 E,可以视为 E extends Object。

复杂示例:

public class MyArray<E extends Comparable<E>> {
    ...
}
  • E 必须是实现了 Comparable 接口的

2.9 泛型方法

定义语法:

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

示例:

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);

三、通配符

? 用于在泛型的使用中,即为通配符。

3.1 通配符解决什么问题

示例:

package www.bit.java.test;

class Message<T> {
    private T message;

    public T getMessage() {
        return message;
    }

    public void setMessage(T message) {
        this.message = message;
    }
}

public class TestDemo {
    public static void main(String[] args) {
        Message<String> message = new Message<>();
        message.setMessage("比特就业课欢迎您");
        fun(message);
    }

    public static void fun(Message<String> temp) {
        System.out.println(temp.getMessage());
    }
}

以上程序会带来新的问题:如果现在泛型的类型设置的不是 String,而是 Integer:

public class TestDemo {
    public static void main(String[] args) {
        Message<Integer> message = new Message();
        message.setMessage(99);

        fun(message); // 出现错误,只能接收 String
    }

    public static void fun(Message<String> temp) {
        System.out.println(temp.getMessage());
    }
}

我们需要的解决方案:可以接收所有的泛型类型,但是又不能够让用户随意修改。这种情况就需要使用通配符 ? 来处理。

范例:使用通配符

public class TestDemo {
    public static void main(String[] args) {
        Message<Integer> message = new Message<>();
        message.setMessage(55);
        fun(message);
    }

    // 此时使用通配符 "?" 描述的是它可以接收任意类型
    public static void fun(Message<?> temp) {
        System.out.println(temp.getMessage());
    }
}

在 ? 的基础上又产生了两个子通配符:

  • ? extends 类:设置通配符上限
  • ? super 类:设置通配符下限

3.2 通配符上界

语法:

<? extends 上界>
<? extends Number> // 可以传入的实参类型是 Number 或者 Number 的子类

示例:

class Food {
}

class Fruit extends Food {
}

class Apple extends Fruit {
}

class Banana extends Fruit {
}

class Plate<T> { // 设置泛型
    private T data;

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }
}

public class TestDemo {
    public static void main(String[] args) {
        Plate<Apple> plate = new Plate<>();
        plate.setData(new Apple());
        fun(plate);

        Plate<Banana> plate2 = new Plate<>();
        plate2.setData(new Banana());
        fun(plate2);
    }

    // 此时使用通配符 "?" 描述的是它可以接收任意类型,但是需要是 Fruit 或者 Fruit 的子类
    public static void fun(Plate<? extends Fruit> temp) {
        // temp.setData(new Banana()); // error
        // temp.setData(new Apple());  // error
        System.out.println(temp.getData());
    }
}

此时无法在 fun 函数中对 temp 进行添加元素,因为 temp 接收的是 Fruit 和它的子类,此时存储的元素应该是哪个子类无法确定,所以添加会报错!

记忆要点:上界通配符 ? extends T —— 能读不能写。

3.3 通配符下界

语法:

<? super 下界>
<? super Integer> // 代表可以传入的实参的类型是 Integer 或者 Integer 的父类类型

示例:

class Food {
}

class Fruit extends Food {
}

class Apple extends Fruit {
}

class Plate<T> {
    private T plate;

    public T getData() {
        return plate;
    }

    public void setData(T plate) {
        this.plate = plate;
    }
}

public class TestDemo {
    public static void main(String[] args) {
        Plate<Fruit> plate1 = new Plate<>();
        plate1.setData(new Fruit());
        fun(plate1);

        Plate<Food> plate2 = new Plate<>();
        plate2.setData(new Food());
        fun(plate2);
    }

    public static void fun(Plate<? super Fruit> temp) {
        // 此时可以修改!!添加的是 Fruit 或者 Fruit 的子类
        temp.setData(new Apple()); // 这个是 Fruit 的子类
        temp.setData(new Fruit()); // 这个是 Fruit 本身
        // Fruit fruit = temp.getData(); 不能接收,这里无法确定是哪个父类
        System.out.println(temp.getData()); // 只能直接输出
    }
}

记忆要点:下界通配符 ? super T —— 能写不能读(读出来只能当 Object)。

3.4 补充:PECS 原则

Java 泛型通配符的选取可以记成 PECS:Producer Extends, Consumer Super。

  • 如果这个容器是生产者(你主要从它读数据),用 ? extends T
  • 如果这个容器是消费者(你主要往它写数据),用 ? super T

四、小结

  1. 包装类:每个基本类型都有对应包装类;除 Integer 和 Character 外都是首字母大写。
  2. 装箱拆箱:是编译期语法糖;包装类的值比较请用 equals();Integer 缓存范围为 -128 ~ 127。
  3. 泛型:将数据类型参数化,进行传递;使用 <T> 表示当前类是一个泛型类。
  4. 泛型的优点:数据类型参数化,编译时自动进行类型检查和转换。
  5. 类型擦除:编译期泛型信息被擦除,T 被替换为边界类型或 Object,并可能生成桥接方法维持多态。
  6. 上界:<E extends Number> 约束类型实参必须是 Number 的子类型。
  7. 通配符:? 表示任意类型,? extends 是上界(能读不能写),? super 是下界(能写不能读)。

本文整理自课程讲义《3. 包装类&泛型》,代码已重新排版并做了少量勘误与补充说明,仅供个人学习记录使用。

AgentScope 实战训练营-构建元规划智能体(Meta Planner Agent)—— 从 0 到 1 完整实现 本文介绍了基于AgentScope框架开发的元规划智能体(Meta Planner Agent)系统。该系统通过任务拆解和子代理编排机制,实现复杂任务的自动化处理。核心架构分为用户层、规划器层和子代理层,其中规划器作为"项目经理"负责任务分解、创建子代理并协调执行流程。关键技术包括AgentScope多智能体框架、DashScope大语言模型、PlanNotebook计划管理工具等。 阅读详情

相关推荐

STM32F4_DHT11数字温湿度传感器

开机的时候先检测是否有DHT11存在,如果没有,则提示错误。DHT11和DS18B20相同,传感器输出的都是未编码的二进制数字。本节我们将利用STM32F4来读取DHT11的温湿度传感器,获取环境的温度和湿度值。因此:温湿度的读取方式就是整数部分的二进制转换成十进制放在整数部分;小数部分的二进制转换成十进制放在小数部分。DHT11和MCU的一次通讯时间最大3ms,主机连续向DHT11采样的间隔建议不小于100ms。DHT11是广州奥松有限公司生产的一款温湿度一体化的数字传感器。数据分小数部分和整数部分。

light_2025的博客 3432

JAVA SE 包装类和泛型

JAVA SE 包装类和泛型

双吉堡工程专业的一名27届Javaer。 3245

华为MA5626 ONU开局配置实战:从零到业务就绪的完整命令手册

本文详细介绍了华为MA5626 ONU设备的开局配置全流程,包括物理连接、命令行初始化、业务VLAN划分、PoE功能配置及故障排查。通过实战命令手册,帮助网络工程师快速完成从设备上电到业务就绪的完整配置,特别适合FTTB场景部署。

weixin_26934905的博客 561

数据结构(Java版)第二期:包装类和泛型

描述的是使用泛型,创建泛型实例的时候,传入的参数(类型实参)需要满足什么条件。方法限定符 <类型形参列表> 返回值类型 方法名称{

2401_85198927的博客 4790

MATLABGUI读取文件并将路径显示在文本框中

MATLABGUI读取文件并将路径显示在文本框中

m0_50305149的博客 2650

Microsoft Dynamics 365软件二次开发:Dynamics365部署与版本控制策略

在Microsoft Dynamics 365中,自定义实体允许开发者扩展系统以满足特定业务需求。自定义实体可以包含字段、选项集、关系和其他属性,与标准实体类似,但完全由用户定义。1. 登录到Dynamics 365环境。2. 转到“解决方案”区域,选择“自定义”。3. 在“自定义”菜单中,选择“实体”。4. 点击“新建”,输入实体名称,例如“客户反馈”。5. 添加字段,如“反馈类型”、“反馈日期”、“描述”等。6. 设置主键和唯一标识符。7. 定义关系,如与“客户”实体的关联。

kkchenjj的博客 2208

详解Java【泛型】

(1)类名后的叫占位符,意思就是当前的类是泛型类 (2)不需要进行强制类型转化 (3)Java中,不可以new泛型类型的数组 (4)注意中必须要引用类型 (5)泛型类使用中可以省略类型实参的填写 擦除机制就是,在编译的过程中,将泛型T替换为Object,并且擦除机制就是编译时期的一种机制,运行期间没有泛型这个概念 通配符是用来解决泛型无法协变的问题的 通配符的上界,不能进行写入数据,只能进行读取数据。 ...

m0_58761900的博客 5359

深入浅出AXI协议(2)——通道及信号

本文我们继续AXI协议的学习,我们将讨论5个通道的具体内容和相对应的信号。这一部分的内容现在对于大家来说可能很难理解,但是没有关系,随着学习的深入,我们会逐步讲解这里面的所有现在,现在只需要把它们当作一个可以查阅的手册,快速阅读有一个基本的印象即可。

apple_53311083的博客 1800

Java包装类&泛型编程

一般的类和方法,只能使用具体的类型: 要么是基本类型,要么是自定义的类。如果要编写可以应用于多种类型的代码,这种刻板的限制对代码的束缚就会很大。----- 来源**《Java编程思想》**对泛型的介绍。泛型是在JDK1.5就是适用于许多许多类型。从代码上讲,就是对类型实现了参数化。通配符类型语法使用场景特点上界通配符extends T>接受T或其子类的集合只能读取,不能写入(除了null下界通配符super T>接受T或其父类的集合可以写入T或其子类的对象,读取为Object无界通配符。

2401_83429250的博客 1041

MaxScript批量修改材质、贴图名称

MaxScript批量修改材质、贴图名称1 实现效果1.1 修改前材质、贴图名称1.2 修改后2 代码 1 实现效果 1.1 修改前材质、贴图名称 1.2 修改后 2 代码 prefixName = "prefiname" maxFile = "maxfilepath" makeDir "newBitmappath" mapsPath = newbitmappath + "\\" fn formatStr index = ( str = index as string newS

郑德帅 3241

20 硬件工程师笔面试高频考点真题解析——寄存器

摘要: 寄存器是由多个边沿触发的D触发器组成的多位存储单元,用于同步时序电路中的数据暂存、隔离毛刺、跨时钟域同步等。选型需考虑位宽、触发方式(边沿/电平)、异步控制、电气参数等。核心时序参数包括建立时间(Tsu)、保持时间(Thold)和时钟输出延迟(Tco)。寄存器广泛应用于时序逻辑、流水线分割、毛刺消除、跨时钟域同步及计数分频等场景。同步复位依赖时钟边沿,时序易收敛但需时钟支持;异步复位独立于时钟,上电可靠但需注意亚稳态风险。

XU157303764的博客 1342

数据结构预备知识(Java):包装类&泛型

Java数据结构预备知识

2401_83595513的博客 3892

WPF实战案例 | C# WPF实现大学选课系统

WPF实战案例_C# WPF实现大学选课系统, C# WPF实现大学选课系统,大作业,毕业设计,该系统实现多身份登录、修改密码、课程的管理,个人信息的管理等功能。这个源码让你快速搭建自己的应用程序,注释完整,代码规范,各种风格都有,代码上手简单,代码独立,可以直接用程序打开,运行使用。也可直接点击EXE运行程序。

不踩坑,不知道坑有多深;不总结,踩过的坑白踩。 4625

Java-数据结构-包装类与泛型

主要分享了包装类和泛型的知识,希望你能得到帮助

爱是小小的癌的博客 1770

Outlook Express 6 (OE6) for Win7/Win8/Win10

英文版 Outlook Express6.0, 兼容Win7/Win10/WinXP,解压就可用。

SIMATIC S7-1200, S7-1500 PID 控制[手册]

SIMATIC S7-1200, S7-1500 PID 控制[手册]

数据结构---包装类&泛型

本文主要介绍了Java中的包装类和泛型机制。包装类部分讲解了基本数据类型与对应包装类的关系、装箱/拆箱操作及自动装箱拆箱特性。泛型部分详细阐述了泛型定义、语法、优势及使用场景,包括泛型类、泛型方法和通配符的使用。重点分析了泛型的编译机制(类型擦除)和桥接方法的作用,并介绍了泛型上界的概念与应用。文章通过具体代码示例展示了泛型在提高类型安全性、消除强制转换和增强代码复用性方面的优势,同时说明了通配符(无界、上界、下界)的使用限制和适用场景。

2401_88978633的博客 1736

STM32F407中文手册

STM32f407中文手册 本参考手册面向应用开发人员,提供有关使用 STM32F405xx/07xx、STM32F415xx/17xx、 STM32F42xxx 和 STM32F43xxx 微控制器存储器与外设的完整信息。STM32F405xx/07xx、STM32F415xx/17xx、STM32F42xxx 和 STM32F43xxx 构成一个微 控制器系列,各产品具有不同的存储器大小、封装和外设。有关订购信息以及器件的机械与电气特性,请参见数据手册。有关 ARM Cortex™-M4F 内核的信息,请参见《Cortex™-M4F 技术参考手册》。

初识数据结构——Java包装类与泛型:从入门到源码解析

【深入浅出】Java包装类与泛型:从入门到源码解析

此人很懒,什么都留下了...快进来看看吧 1752

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

Java泛型方法的定义和使用、泛型类、泛型接口、泛型方法、通配符、泛型的上界与下界

Java泛型方法的定义和使用、泛型类、泛型接口、泛型方法、通配符、泛型的上界与下界

weixin_49114503的博客 6853

数据结构:包装类和泛型

一般的类和方法,只能使用具体的类型:要么是基本类型,要么是自定义的类。如果要编写可以应用于多种类型的代码,这种刻板的限制对代码的束缚就会很大。泛型,所谓泛型就是适用于许多许多类型。从代码上讲,就是对类型实现了参数化我们来看这样一个例子,在数组中存放各种类型的元素我们知道Object类默认为所有类的父类,所以我们创建的数组为Object类的数组。

zm3rttqs9f的博客 1456

Java 包装类&初识泛型

在Java中,由于基本类型不是继承自Object,为了在泛型代码中可以支持基本类型,Java给每个基本类型都对应了一个包装类型。包装类用于将基本数据类型转换为对象。它们允许在对象上执行额外的操作,例如将基本数据类型作为参数传递给方法,或者在集合类中存储基本数据类型。

2302_79806056的博客 1346

泛型与装箱拆箱

介绍Java中的泛型与包装类

YeZh1Yong 的博客 1185

【java笔记】泛型、包装类、自动装箱拆箱与缓存机制

泛型使用优先使用泛型类/方法,避免原始类型。类型参数命名遵循TE等约定,提高可读性。包装类与缓存小整数(-128~127)直接赋值(利用缓存)。比较包装类时始终用equals(),避免==陷阱。自动装箱拆箱避免在循环中高频使用,优先基本类型。集合操作透明处理,无需显式转换。字符串转换明确需求:基本类型用parseInt,对象用valueOf。处理异常:包裹try-catch处理非数字字符串。

小李同学的博客 1317

Java学习【深入探索包装类和泛型】

包装类,泛型,泛型类,泛型方法,泛型接口,擦除机制

2202_76097976的博客 1370

【Java数据结构】泛型详解+图文,通配符上界、下界

无边界通配符 可以传入任意实参类型,不能写入,不能读取,只能输出。 public static void fun(Food

Original0的博客 3155

【数据结构】泛型

就是适用于许多许多类型。从代码上讲,就是对类型实现了参数化。首先解决这样一个问题:实现一个类,类中包含一个数组成员,使得数组中可以存放任何类型的数据,也可以根据成员方法返回数组中某个下标的值?而且所有类的父类,默认为Object类。数组是否可以创建为Object?//字符串也可以存放//编译报错上述代码中,虽然在 myArray 中任何类型的数据都可以存放,而且1号下标的元素是String类型的,但仍编译报错,此处必须进行强制类型转换。

iLoyo_的博客 1244

【java数据结构】泛型

包装类,java泛型

2303_77535762的博客 1166

数据结构-包装类和泛型

摘要: Java包装类为基本类型提供对象支持,实现自动装箱拆箱(如Integer缓存-128~127)。泛型通过类型参数实现代码复用,编译时进行类型擦除替换为Object或指定类型。泛型类可定义上界约束类型范围(如<E extends Number>),方法也可泛型化。通配符?解决泛型灵活性需求,?extends设置上界(只读),?super设置下界(可写入)。类型擦除会生成桥接方法保持多态性。泛型推导可省略类型实参,但基本类型必须使用包装类。

2301_81261819的博客 1321
上一篇: Java:面向对象编程【继承】
下一篇: Java LinkedList 与链表学习笔记:从 ArrayList 的缺陷到双向链表实现
groot520
博客等级 码龄2年 0粉丝 9原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值