关于基本类型的简单赋值和复合赋值运算

转载 2012年03月23日 16:44:53

通过阅读下面转载的文章,Kaiwii学习到以下的内容:

1、需要判断一个变量的类型,可以采用下面的方式完成:

假如我要弄清楚2.0/SAMPLING_COUNT的结果的类型,Kaiwii可以这样做:

Object var=2.0/SAMPLING_COUNT;
System.out.println(var.getClass().getSimpleName());

2、可以通过查看和比较生成的class文件来判断两种写法的实际执行过程是否一样

3、自动提升类型和自动降低类型的理解:

在运算过程中,一般情况下会进行进行自动提升类型,也就是一个低精度的变量为了与高精度的变量进行运算而发生的低精度向高精度类型转换的过程。比如文中提到的:

short s1 = 1; s1 = s1 + 1; 

为什么不正确,是因为1是int类型的,所以S1与其发生运算的过程中会升级为int类型,所以最终生成的结果的类型应该是int的。一个int类型的变量怎么可以赋值到一个shor类型的变量中去呢?除非使用强制转换的方式吧……

另外,只有在直接将一个常量值赋值给一个变量的时候,才可能发生自动降低类型的情况。比如文中提到的情况:

short i=1

分析:1是int类型的常量,可以通过自动降低类型的方式赋值给一个更低精度的变量i

其中,比较特殊的自动降低类型的方式还包括:

short i+=1
好吧,Kaiwii说了那么废话,直接上原文吧……

有一道很经典的面试题是这样的:
short s1 = 1; s1 = s1 + 1; 有什么错? short s1 = 1; s1 += 1;有错吗?

答案很简单:
1. 编译出错。类型不匹配,需要强制类型转换。
2. 没有错误。

有一朋友说不是太明白这是为什么。我在这里分析一下原因。
对于前半部分:

Java代码 复制代码 收藏代码
  1. short s1 = 1; s1 = s1 + 1;

在java语言规范里,如果表达式中, 当对中间值的精确要求有时可能会超过任何一个操作数的范围, JVM会临时自动提升这个操作数的类型。
像我们这个题目的前面部分,s1 + 1, 我们把类型写出来s1(short) + 1(int)这时JVM会自动把s1先提升成int,然后再跟后面的1(int)相加,这样就是int + int的运算了。但是为什么会有编译错误呢?因为int + int的结果还是int。我们看一下这个例子:
Java代码 复制代码 收藏代码
  1. short s1 = 1;
  2. Object result = s1 + 1;
  3. System.out.println(result.getClass().getSimpleName());

结果是:
Integer

从结果可以看出,结果是int的包装类Integer。所以s1 + 1的结果是int类型的。因此把s1 + 1重新赋值给s1,即s1 = s1 + 1,会丢失精度,编译出错。

对于后半部分 s1 += 1,个人认为可以分为两部分,见下面代码:
Java代码 复制代码 收藏代码
  1. short s1 = 1;
  2. s1 = (short)((int) s1 + 1);

这样解释的原因可以再看下面的例子:
Java代码 复制代码 收藏代码
  1. public class Test {
  2. public void test1(){
  3. short s1 = 1;
  4. s1 = (short)((int) s1 + 1);
  5. }
  6. public void test2() {
  7. short s1 = 1;
  8. s1 += 1;
  9. }
  10. }

查看Test.class文件的字节码文件:
Java代码 复制代码 收藏代码
  1. public void test1();
  2. 0 iconst_1
  3. 1 istore_1 [s1]
  4. 2 iload_1 [s1]
  5. 3 iconst_1
  6. 4 iadd
  7. 5 i2s
  8. 6 istore_1 [s1]
  9. 7 return
  10. Line numbers:
  11. [pc: 0, line: 4]
  12. [pc: 2, line: 5]
  13. [pc: 7, line: 6]
  14. Local variable table:
  15. [pc: 0, pc: 8] local: this index: 0 type: Test
  16. [pc: 2, pc: 8] local: s1 index: 1 type: short
  17. public void test2();
  18. 0 iconst_1
  19. 1 istore_1 [s1]
  20. 2 iload_1 [s1]
  21. 3 iconst_1
  22. 4 iadd
  23. 5 i2s
  24. 6 istore_1 [s1]
  25. 7 return
  26. Line numbers:
  27. [pc: 0, line: 9]
  28. [pc: 2, line: 10]
  29. [pc: 7, line: 11]
  30. Local variable table:
  31. [pc: 0, pc: 8] local: this index: 0 type: Test
  32. [pc: 2, pc: 8] local: s1 index: 1 type: short

除了11-13行和28-30行的内的行号不同之外,其余部分都一样。即这两上写法其实是等效的。
s1 = (short)((int) s1 + 1); 可以简化为s1 = (short)(s1 + 1);因为从short到int JVM会自动提升类型。

最后补充一点,JVM会自动提升类型的表达式为:
Java代码 复制代码 收藏代码
  1. short +|-|*|/|% short = (int) short +|-|*|/|% (int) short;
  2. byte +|-|*|/|% byte = (int) byte +|-|*|/|% (int) byte;
  3. char +|-|*|/|% char = (int) char +|-|*|/|% (int) char;

因为这些类型的运算很容易就会越界。它们之间的任意组合都会先转换成int,然后再运算,结果为int类型。但是遇到更高精度的操作数,如float、double,它们也会向float、double自动提升类型。自动提升类型除基本赋值外,都是向精度高的方向进行的。
对于short、byte、char的基本赋值,就像short s1 = 1;是int类型自动降低类型到short的。 


相关文章推荐

js基本类型 引用类型 简单赋值 对象引用

js基本类型 引用类型 简单赋值 对象引用,两个等号与三个等号的区别
  • t_1007
  • t_1007
  • 2016年11月08日 17:08
  • 1656

基本类型 引用类型 简单赋值 对象引用

原文地址:https://segmentfault.com/a/1190000002789651 ECMAScirpt 变量有两种不同的数据类型:基本类型,引用类型。也有其他的叫法,比如原始类型和对...

Java学习笔记-《Java程序员面试宝典》-第四章基础知识-4.4基本类型与运算(4.4.5-4.4.10)

4.4.5强制类型转换的注意事项有哪些Java语言在涉及byte、short和char类型的运算时,首先会把这些类型的变量值强制转换为int类型,然后对int类型的值进行计算,最后得到的结果也是int...

V尼熊的java之旅——基本类型与运算篇

& 和 && 的区别: & 和 && 都可以用作逻辑与的运算符,表示逻辑与(and),当运算符两边的表达式的结果都为 true 时,整个运算结果才为 true,否则,只要有一方为 false,则结果...

在c/c++中的基本类型赋值和初始化

在c/c++中的基本类型赋值和初始化 今天看了一个博客,并且对于c/c++的基础知识做了一个小小的总结,希望可以和大家一起探讨学习。 看如下实例:(来源:http://blog.csdn.ne...

Java 基础知识(四)之基本类型与运算

1.   Java基本数据类型        Java一共提供了8种原始的数据类型(byte、short、int、long、float、double、char、boolean),这些数据类型不是对象...

Java学习笔记-《Java程序员面试宝典》-第四章基础知识-4.4基本类型与运算(4.4.1)

4.4.1 Java提供了哪些基本数据类型Java语言一共提供了8中原始的数据类型(byte、short、int、long、float、double、char、boolean),这些数据类型不是对象,...

Java学习笔记---基本类型、运算优先级的一些知识整理

一、Java提供了8种原始数据类型,其对比见下表: 数据类型 字节长度 范围 默认值 包装类 int 4 [-2147483648,2147483647] ...

编写一个程序实现顺序表的各种基本运算(假设顺序表的元数基本类型为Char)

/* *Copyright (c) 2016, 烟台大学计算机学院 *All rights reserved. *文件名称:main.cpp *作者:张旺华 *完成日期: 2016 年 7 ...

编写一个程序实现链式栈的各种基本运算(假设顺序表的元数基本类型为Char)

/* *Copyright (c) 2016, 烟台大学计算机学院 *All rights reserved. *文件名称:main.cpp *作者:张旺华 *完成日期: 2016 年 7 ...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:关于基本类型的简单赋值和复合赋值运算
举报原因:
原因补充:

(最多只允许输入30个字)