1-java的变量和数据类型的转换

本文详细介绍了Java中的变量,包括变量的作用、声明与赋值。讨论了Java的两种数据类型:基本数据类型(如整数、浮点数、字符、布尔)和引用数据类型。着重讲解了基本数据类型的自动和强制类型转换,强调了溢出风险及其可能导致的错误。此外,还探讨了Java中为什么给float类型赋值需要加F,以及byte和short类型可以直接用int字面量赋值的原因。
摘要由CSDN通过智能技术生成

变量概述
变量:常量是固定不变的数据,那么在程序中可以变化的量称为变量。
变量:计算机要进行运算必须能够保持住参加运算的数据,首先数据要进入内存存放在内存中,为了方便找到并使用这些数据,那么必须要对它们进行标示,这种标识符所表示的数据就成为变量。因此变量用来标示内存中的一份数据。变量表示的数据可以在程序执行过程中进行改变,变量一旦改变就使用改变后的值。

变量的使用:
1.变量的声明:指明变量的名称及所属的数据类型。基本语法:数据类型 变量名;
2.变量的赋值,把一份数据指定给某个变量去表示,赋值可以改变变量的值。基本语法:变量名=值;
规范:JAVA语言是“强类型的语言”,它要求变量必须具有明确的数据类型,主要是因为在编译期需要给变量精确的分配内存,也需要确定表达式的精确的结果类型等。

数据类型:就是对程序中所使用数据的分类,数据就是用来标示信息的。作为信息的描述来看,不同种类的信息表达方式是不同的,比如人的 名称应归类为 字符串,比如菜的重量归类为小数,人的年龄应归类为正数等。

Java的数据类型分为两大类: 基本数据类型:包括 整数 、 浮点数 、 字符 、 布尔 。
引用数据类型 有四种:包括 类类型 、 接口类型 、类型变量(泛型) 、数组类型、还有一个特殊的空类型


null类型,即表达式的类型null,没有名称。

由于空类型没有名称,因此无法声明空类型的变量或将其强制转换为空类型。

空引用是空类型表达式的唯一可能的值。

空引用总是可以被分配或浇铸任何引用类型。

在实践中,程序员可以忽略null类型,而只是假装这null只是可以是任何引用类型的特殊文字。

基本数据类型

基本数据类型 有八个 :四个是 整数,两个是小数,其他的 是字符和布尔。

四类八种基本数据类型

了解各类型数据的表示范围,有利于给不同的数据声明为不同类型的合适的变量。

在这里插入图片描述

补充:JAVA是面向对象的,原本没有基本数据类型,只是代码中有很多数据用基本类型来表示更加简单直接,所以得以保留。但是,所有的基本类型的数据都可以用它对应的引用类型(包装类型,java中的八个基本类型有八个对应的包装类型,它们之间可以方便地进行互相转换,这种转换操作表示为“装箱”和拆箱)来表示。

代码展示

public static void main(String[] args) {
        System.out.println("byte的表示范围从"+Byte.MIN_VALUE+"至"+Byte.MAX_VALUE);
        System.out.println("short的表示范围从"+Short.MIN_VALUE+"至"+Short.MAX_VALUE);
        System.out.println("int的表示范围从"+Integer.MIN_VALUE+"至"+Integer.MAX_VALUE);
        System.out.println("long的表示范围从"+Long.MIN_VALUE+"至"+Long.MAX_VALUE);
        System.out.println("float的表示范围从"+Float.MIN_VALUE+"至"+Float.MAX_VALUE);
        System.out.println("double的表示范围从"+Double.MIN_VALUE+"至"+Double.MAX_VALUE);
        System.out.println("char的表示范围从"+'\u0000'+"至"+'\uffff');
        System.out.println("boolean的表示范围从"+Boolean.FALSE+"至"+Boolean.TRUE);
        }

在这里插入图片描述

Java中的默认类型:整数类型是 int 、浮点类型是 double

 //在代码 中使用直接量 的 一些 注意点
        int i=100;  //整数的直接量的  类型就是int
        short s=100;   //这里 执行了 自动类型转换,在赋值前 把int 转换成short
        short s1=(short)9999;// 可能会发生 数据溢出
        long l=100;      //也执行了 自动类型转换,而且不会损失数据
        long l2=233333334324;  //为什么表示不了.     该数 超过了 int的表示范围,需要后面加L明确的表示它是Long类型
        float f=2.5;   //为什么有错误。  小数的直接量属于double类型,所以需要在后面加上F明确的表示它是Float类型
        double d=2.5;
  //大转小  会自动的类型转换    ,小转大 会报错 需要 强制类型转换 ,
        char c='*';
        int ic=c;    //为什么可以这样做。字符类型内部表示为一份两字节的整数,这种赋值没有问题
        char c2=12; //数字赋值给字符,只要数字在字符的表示范围内,就没问题。

似乎 代码块 不能把错误表示出来,下面 有截图。
在这里插入图片描述

自动类型转换:把表示范围小的数据转换为表示范围大的数据,java采用的是自动类型转换,这种情况不需要在表达式中明确的指出结果类型。

long result; int c1=2,c2=4; result=c1+c2;

这里 int 类型 c1和c2可以直接自动类型转换成 标示范围更大的long类型。

八大类型从小至大的排列关系: byte  short  int  long  float  double  
                                 char
int result;  long c1=2;  result=c1;

在这里插入图片描述

这里的 long类型 想要给 int 赋值 就会 报错,因为long的表示范围是大于int的,把long类型值直接赋给int类型会有溢出的风险

这是 软件自身的 为你可能的错误进行的 报错提示,但是这种提示也不是万能、什么时候都会出现的。

比如

//溢出判断
    int result=2147483647+2147483647+2147483647+2147483647;
    int test;
    test=result;
    System.out.println(test);

在这里插入图片描述
在这里插入图片描述

在上方的 代码中,int 类型的result变量已经承载了远超int范围大小的数值,并且输出时,发生溢出,但是,并没有报错提示

强制类型转换,如果把表示范围大的类型数据转换为表示范围小的类型的数据,必须进行强制类型转换。
强制类型转换的语法:目标类型变量=(目标类型)源类型变量.

long l=10; int i=5  i=(int)l;  

当然 强制类型转换 也是有可能会发生 溢出的。

注意;自动类型转换会发生溢出吗?会的,而且编译器不报错。
强制类型转换会发生溢出吗?会的,但是编译器会提前报错。

Java中为什么给float类型变量赋值需要加F,而给byte、short赋值的时候却不需要呢?
JVM规范中所说,并没有说float,int,byte等占多少个字节,而是真正的有效位是多少。比如byte的有效位是1个字节,也就是-128到127。使用Java编程的时候,就只能用byte表示-128到127之间的数,而真正JVM实现,一般byte还是占用和int一样大小:4个字节。
也就说在JVM看来,short,byte,int都是同一个东西。
这也就解释了为什么byte,short使用int字面量赋值的时候会不用强制转型。
在这里插入代码描述

short a=3;
byte b=2;

因为编译器在编译的只需要根据字面值3,字面值2来确定是否超过有效值即可,并不用做深入的检查,因为他们在JVM存在的类型也是一样的。
在这里插入图片描述

 byte b=128;//error

同时在通过JVM在操作byte,short,int都是用的相同的指令:iconst,bipush等也能证明。

然而double和float在JVM中存储是不一样的。

System.out.println(3.2f==3.2d);//false

因此在使用double给float赋值的时候,会报错的。

参考博客:https://blog.csdn.net/cgb1804great/article/details/103545545?utm_medium=distribute.pc_relevant_bbs_down.none-task-blog-baidujs-2.nonecase&depth_1-utm_source=distribute.pc_relevant_bbs_down.none-task-blog-baidujs-2.nonecase

short s1=1,s2=2,s3=3;
      s3=s1+s2;  //报错

还有

char s1=1,s2=2,s3=3;
     s3=s1+s2;  //报错

还有

 byte s1=1,s2=2,s3=3;
      s3=s1+s2;  //报错

一些原因已经被指出。例如,事实上“…(几乎)所有关于byte,short的操作都会将这些原语提升为int”。然而,下一个明显的问题是:为什么这些类型被提升为int?

因此,更深入一层:答案可能仅仅与Java虚拟机指令集有关。正如Java虚拟机规范中的表所总结的那样,所有的整数运算,如加法、除法等,只适用于int和long类型,而不适用于较小的类型。

(顺便说一句:较小的类型(byte和short)基本上只用于数组。像new byte[1000]这样的数组需要1000个字节,像new int[1000]这样的数组需要4000个字节)

当然,现在有人可以说“……下一个明显的问题是:为什么这些指令只提供给int(和long)。

上面提到的JVM规范中提到了一个原因:

如果每个类型化指令都支持Java虚拟机的所有运行时数据类型,那么将有比用字节表示更多的指令

另外,Java虚拟机可以看作是一个真实处理器的抽象。为小型型号引入专用的算术逻辑单元是不值得的:它需要额外的晶体管,但它仍然只能在一个时钟周期内执行一个加法运算。JVM设计时的主流架构是32位,正好适合32位int(涉及64位长值的操作作为特殊情况实现)。

(注意:最后一段有点过于简单,考虑到可能的矢量化等,但应该给出基本思想,而不要深入研究处理器设计主题)

编辑:一个简短的附录,集中在问题中的例子上,但从更一般的意义上讲:人们还可以问,使用较小的类型存储字段是否有益。例如,有人可能认为可以通过存储来保存内存日历日作为一个字节。但在这里,Java类文件格式发挥了作用:类文件中的所有字段至少占据一个“slot”,其大小为一个int(32位)。(“宽”字段,双字段和长字段,占据两个插槽)。所以显式地将字段声明为short或byte也不会节省任何内存。

参考博客:
https://stackoverflow.com/questions/27122610/why-does-the-java-api-use-int-instead-of-short-or-byte/27122853#27122853

有什么不懂的,建议直接看官方文档
https://docs.oracle.com/javase/specs/index.html

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值