Java 基础 基础数据类型与包装器类型

基础数据类型

java 中包含哪些基础数据类型,默认值分别是多少?

基础数据类型 byte short int long double float char boolean
默认值 0 0 0 0l 0.0 0.0f null false

基础数据在 JVM 中的存储模型

Java 中的基础模型因为其长度可知、生命周期(存活时间)可知,为了追求速度,基础数据都是存放在栈中的。另外栈有一个特点,就是栈中的数据可以共享。

例如:

// int a = 3;
// int b = 3;

经过查证,上面的说法是不准确的。

基本数据类型的存储分为三种情况:

  1. 基本数据类型的局部变量
  2. 基本数据类型的成员变量
  3. 基本数据类型的常量

基本数据类型的局部变量

定义基本数据类型的局部变量以及数据都是直接存储在内存中的栈上,也就“虚拟机栈”,数据本身的值就是存储在栈空间里面。

这么说好像有点模糊,举个例子吧。

public class baseDemo {

    public static void main(String[] args) {

       int weight = 50;
int hight = 50;
int age = 18;
Person per = new Person(); } }

这段代码中所有的基本类型都是局部变量,我们从第一个开始看

int weight = 50;
// 这段代码可以分解为
int weight; // 定义局部变量
weight = 50; // 为局部变量赋值

首先在栈帧的局部变量中创建一个局部变量 weight,然后在栈中寻找有没有字面量为 50 的,如果有就直接指向,就当前代码来看,显然是没有,那么 JVM 会在栈中创建一个字面量为 50 的空间,并将 weight 变量指向这个地址。因此我们可以得知:

我们创建的基本数据类型的局部变量,变量名以及字面值都是存放在栈中的。而且是真实的内容。

然后我们接着往下看:

int hight = 50;
// 这段代码可以分解为
int hight; // 定义局部变量
hight = 50; // 为局部变量赋值

这里也是一样的,创建局部变量 hight,从栈中寻找有没有字面量为 50 的内容,刚好我们之前创建 weight 的时候已经创建过字面量为 50 的内容,所以hight直接指向这个地址。由此可见:

栈中的数据在当前线程下是共享的

基本数据类型的数据本身是不会改变的,当局部变量重新赋值时,并不是在内存中改变字面量内容,而是重新在栈中寻找已存在的相同的数据,若栈中不存在,则重新开辟内存存新数据,并且把要重新赋值的局部变量的引用指向新数据所在地址。

基本数据类型的成员变量

成员变量,也就是在类中声明的变量。例如:

public class Person {

    private int age;
private String name;
private int sex;
private long idCard; }
// 通用方法
Person per = new Person();

age、name、sex、idCard被存储到了堆中为per对象开辟的一块空间中。因此可知:基本数据类型的成员变量名和值都存储于堆中,其生命周期和对象的是一致的。

基本数据类型的常量

JVM 中方法区用来存储一些共享数据,因此基本数据类型的静态变量名以及值存储于方法区的运行时常量池中,静态变量随类加载而加载,随类消失而消失

基础数据类型的自动转换

基础类型的自动转换规则包括自动、强制、提升三种

自动类型转换是指:数字范围小的数据类型可以自动转换成数据范围大的类型

int a = 100;
long b = a;

具体可以残照下面这张图:

实线表示自动转换时不会造成数据丢失,虚线则可能会出现数据丢失问题。

在自动转换的过程中也需要考虑溢出问题,例如:

int a = Integer.MAX_VALUE;
int b = 2;
long c = a + b;
System.out.println(c); // out -2147483647

在这种情况下编译器不会报错,但是打印出来的结果是负数(溢出)。因为jvm 中对其进行计算的时候,是先计算两个 int 的和,再将其自动转换为 long,但是在计算过程中,a和 b的和已经大于 int 的最大值,也就是说在自动转换之前结果已经是负数了,所以转换成 long 之后依然是负数。

另外,向下转换的时候可以直接将 int 的常量直接赋予给char、short、byte,只要常量的数字小于这些基础类型的最大上限,所以可以自动转换

short d = 3;
char e = 4;
byte f = 1;

下图中的 g 报错了,是因为int 的常量超过了 byte 的最大限度。

short d = 3;
char e = 4;
byte f = 1;
byte g = 128;

包装器类型

包装器类型与基础数据类型对应关系

包装器类型 byte char short int long double float boolean
基础数据类型 Byte Character Short Integer Long Double Float Boolean

自动装/拆箱何时触发

这里情况比较多,所以我们直接在代码中体现吧

// 自动装箱
Integer num1 = 1;
Integer num2 = 2;
Integer num3 = 3;
// num1 + num2 触发自动拆箱,然后因为要和 Integer 类型的num3 进行 equals 比较,所以又触发自动装箱
// Integer.equals 返回的是 boolean,但是我们是使用 Boolean 类型接收的,这里又触发了自动装箱
Boolean flag = num3.equals(num1 + num2);

Integer 的 equals源码

 /**
* Compares this object to the specified object. The result is
* {@code true} if and only if the argument is not
* {@code null} and is an {@code Integer} object that
* contains the same {@code int} value as this object.
*
* @param obj the object to compare with.
* @return {@code true} if the objects are the same;
* {@code false} otherwise.
*/
public boolean equals(Object obj) {
if (obj instanceof Integer) {
return value == ((Integer)obj).intValue();
}
return false;
}

包装器类型在 JVM 内存中的存储模型

包装器类型的对象存储在堆中,引用存储在栈中,通过栈来操作对象。但是部分是直接从存放在常量池中的比如 Integer 的 -128 ~ 127

基础数据类型和包装器类型的适用场景

  1. 基础数据类型适合用于方法内部的局部变量,随着方法的调用创建在栈中,随着方法一起被回收销毁。
  2. 包装器有一个基础数据类型没有的优点,就是默认值是 null,可以通过是否为 null 直观的判断这个数据是不是被赋值过。比如:使用 Mybatis 从数据库中获取数据的时候,如果这个是 int类型,但是其实这条数据这个字段是空,就会出问题。
  3. 基本类型与对象类型最大的不同点在于,基本类型基于数值,对象类型基于引用

Java 基础复习 基础数据类型与包装器类型的更多相关文章

  1. Java中基本数据类型和包装器类型的关系

    在程序设计中经常用到一系列的数据类型,在Java中也一样包含八中数据类型,这八种数据类型又各自对应一种包装器类型.如下表: 基本类型 包装器类型 boolean Boolean char Charac ...

  2. Java基础之基本数据类型的包装类型

    Java的基本数据类型的包装数据类型有多种: int Integer,short Short,boolean Boolean,float Float,double Double等等. Java包装类数 ...

  3. Java基础(八)对象包装器与自动装箱

    1.对象包装器 有时候,需要将int这样的基本类型转换为对象.所有的基本类型都有一个与之对应的类.通常,这些类被称为包装器(wrapper). 这些对象包装类分别是:Integer.Long.Floa ...

  4. C# 基础复习 一 数据类型

    数据类型分为:值类型和引用类型 值类型:byte.short/char.int.long.float.double.decimal.enum.struct 引用类型:string.object.int ...

  5. ndk学习之C语言基础复习----基本数据类型、数组

    关于NDK这个分类在N年前就已经创建了,但是一直木有系统的记录其学习过程,当然也没真正学会NDK的技术真谛,所以一直也是自己的一个遗憾,而如今对于Android程序员的要求也是越来越高,对于NDK也是 ...

  6. python基础复习-1-2 数据类型-str、list、tuple、dict

    数据类型 数字 引号: 123 数值 '123' 字符串 整数:ini long 范围:(-2**31 - 2**31) num = 123 长整型 long (L) num = 123L 浮点型:f ...

  7. Java基础的基础,花1h看这一篇就够了!

    ------------恢复内容开始------------ Java笔记 ​ 一直以来,总想着Java会点基础就可以写后端程序了,但越到后来越发现Java基础的重要性.更不必说在面试时,Java基础 ...

  8. java面试| 精选基础题(2)

    关注微信公众号"java从心",置顶公众号 每天进步一点点,距离大腿又近一步! 阅读本文大概需要6分钟 继续挖掘一些有趣的基础面试题,有错望指出来哈,请赐教~ 1.包装类的装箱与拆 ...

  9. Java基本数据类型与包装类型(转)

    基本数据类型的包装类 为什么需要包装类? Java并不是纯面向对象的语言.Java语言是一个面向对象的语言,但是Java的基本数据类型却不是面向对象的.但是我们在实际使用中经常需要将基本数据转化成对象 ...

随机推荐

  1. Flask开发成语接龙游戏,闲来无事手机玩玩自己写的游戏吧!

    英语单词学习应用 周五发布的文章Flask开发天气查询软件,带你掌握pipenv的使用与手机Termux下的部署发布后,看到喜欢的人比较多.本来周末打算照着扇贝/极光单词,写一个英语单词自测工具.但苦 ...

  2. MySQL必知必会(使用子查询)

    SELECT cust_name, cust_contact FROM customers WHERE cust_id IN (SELECT cust_id FROM orders #单独写多个分句, ...

  3. MySQL必知必会(数据分组,Group by和Having子句, Select子句的顺序)

    SELECT vend_id, COUNT(*) AS num_prods FROM products #GROUP BY子句可以包含任意数目的列,多行NULL值将分为一组 GROUP BY vend ...

  4. Unity3d 与 Objective-C 数据交互,持续更新中

    Unity 3D是用于3D游戏编程的语言,它是一个用C\C++编写的强大的库.而在游戏中经常要接入用OC编写的SDK,这就涉及到了Unity3d 和 OC之间的数据交互.XCode是完成兼容C语言的. ...

  5. ZooKeeper初步

    ZooKeeper 简介: 顾名思义 zookeeper 就是动物园管理员,他是用来管 hadoop(大象).Hive(蜜蜂).pig(小猪)的管理员, Apache Hbase 和 Apache S ...

  6. 数据库Oracle的子查询练习

    1.写一个查询显示与 Zlotkey 的 在同一部门的雇员的 last name和 hire date,结果中不包括 Zlotkey --1.写一个查询显示与 Zlotkey 的 在同一部门的雇员的 ...

  7. python输出日志到文件(每天一个日志)

    import logging from logging.handlers import TimedRotatingFileHandler logger = logging.getLogger('sim ...

  8. 从FPGA搞定OV7670 VGA显示 移植到 STM32F10x TFT显示 总结及疑问(高手请进)

    OV7670不愧是最便宜的摄像头了最大显示像素:640*480(在VGA显示器上显示效果还不赖,用usb模块采集显示依然显著) 第一步:VGA显示 视频图像(实时)FPGA+SDRAM+OV7670= ...

  9. 反射从入门到精通之深入了解Class类

    .katex { display: block; text-align: center; white-space: nowrap; } .katex-display > .katex > ...

  10. python 中 and or

    在Python 中,and 和 or 执行布尔逻辑演算,如你所期待的一样,但是它们并不返回布尔值:而是,返回它们实际进行比较的值之一. 一.and: 在布尔上下文中从左到右演算表达式的值,如果布尔上下 ...