八种基本数据类型和为什么取值范围会减1

八种基本数据类型

在计算机中最小的单位是bit,比特(也就是位,0101的二进制)
在计算机中最小的存储单位是byte字节(1字节等于8位)
计算机中的存储单位(进率是1024)
Kb<Mb<Gb<Tb<Pb<Eb<Zb<Yb

整型
byte 1个字节 -128(-2^7) ~ 127(2^7-1)(取值范围)
short 2个字节 -32768(-2^15) ~ 32767 (-2^15-1)
int 4个字节 -214783648(-2^31) ~ 2147483647 (-2^31-1)
long 8个字节 -9223372036854775808(-2^63) ~ 9223372036854775807(-2^63-1)
浮点型
float 4个字节 (可以用f或F结尾) 1.4E-45 ~ 3.4028235E+38
double 8个字节 (可以用d或D结尾或者不写) 4.940656458412465334E-324 ~
1.7976931348623157E+308
字符型
char 2个字节 (必须用单引号引起来) 0~65535
Java中char不采用ASCII编码,而采用Unicode(统一码、万国码、单一码)

编码大小支持语言
ASCII1个字节英文
Unicode2个字节(生僻字4个)所有语言
UTF-81-6个字节,英文字母1个字节,汉字3个字节,生僻字4-6个字节所有语言
具体解释

最早只有127个字母被编码到计算机里,也就是大小写英文字母、数字和一些符号,这个编码表被称为ASCII编码,比如大写字母A的编码是65,小写字母z的编码是122。
但是要处理中文显然一个字节是不够的,至少需要两个字节,而且还不能和ASCII编码冲突,所以,中国制定了GB2312编码,用来把中文编进去。
你可以想得到的是,全世界有上百种语言,日本把日文编到Shift_JIS里,韩国把韩文编到Euc-kr里,各国有各国的标准,就会不可避免地出现冲突,结果就是,在多语言混合的文本中,显示出来会有乱码。
因此,Unicode应运而生。Unicode把所有语言都统一到一套编码里,这样就不会再有乱码问题了。
Unicode标准也在不断发展,但最常用的是用两个字节表示一个字符(如果要用到非常偏僻的字符,就需要4个字节)。现代操作系统和大多数编程语言都直接支持Unicode。
新的问题又出现了:如果统一成Unicode编码,乱码问题从此消失了。但是,如果你写的文本基本上全部是英文的话,用Unicode编码比ASCII编码需要多一倍的存储空间,在存储和传输上就十分不划算。
所以,本着节约的精神,又出现了把Unicode编码转化为“可变长编码”的UTF-8编码。UTF-8编码把一个Unicode字符根据不同的数字大小编码成1-6个字节,常用的英文字母被编码成1个字节,汉字通常是3个字节,只有很生僻的字符才会被编码成4-6个字节。如果你要传输的文本包含大量英文字符,用UTF-8编码就能节省空间。
UTF-8编码有一个额外的好处,就是ASCII编码实际上可以被看成是UTF-8编码的一部分,所以,大量只支持ASCII编码的历史遗留软件可以在UTF-8编码下继续工作。

布尔型
boolean (true或false)

1、1个bit
理由是boolean类型的值只有true和false两种逻辑值,在编译后会使用1和0来表示,这两个数在内存中只需要1位(bit)即可存储,位是计算机最小的存储单位。

2、1个字节
理由是虽然编译后1和0只需占用1位空间,但计算机处理数据的最小单位是1个字节,1个字节等于8位,实际存储的空间是:用1个字节的最低位存储,其他7位用0填补,如果值是true的话则存储的二进制为:0000 0001,如果是false的话则存储的二进制为:0000 0000。

3、4个字节
理由来源是《Java虚拟机规范》一书中的描述:“虽然定义了boolean这种数据类型,但是只对它提供了非常有限的支持。在Java虚拟机中没有任何供boolean值专用的字节码指令,Java语言表达式所操作的boolean值,在编译之后都使用Java虚拟机中的int数据类型来代替,而boolean数组将会被编码成Java虚拟机的byte数组,每个元素boolean元素占8位”。这样我们可以得出boolean类型占了单独使用是4个字节,在数组中又是1个字节。

String是一种数据类型,是字符串,不属于八种基本数据类型。

String确是对象类型。对象是一种很复杂的数据类型,你要看一个对象具体占多少字节,可以把这个对象序列化后存入一个文本文件来看它具体占用了多少字节,当然这也不是精确的,因为序列化需要写入少量系统信息,但大致是对的。

二进制

众所周知,计算机中的存储都是以0与1来存储的,但是如何区分存储的正负,例如

正数在计算机中表示为原码,最高位为符号位:

原码的最高为0整个数为正数,最高为1整个数为负数

1的原码为0000 0000 0000 0000 0000 0000 0000 0001

2147483647的原码为0111 1111 1111 1111 1111 1111 1111 1111

所以最大的正整数是2147483647

计算机中存储都是以补码的形式存储的,无论正数还是负数。

原码取反就是0变1,1变0,对照换下来就是反码,反码再加1,就是补码

无论正负最高位符号位都不会发生变化。

负数在计算机中表示为补码,最高位为符号位:

-1的原码为1000 0000 0000 0000 0000 0000 0000 0001,

反码为1111 1111 1111 1111 1111 1111 1111 1110,

补码为1111 1111 1111 1111 1111 1111 1111 1111

-2147483647:

原码为1111 1111 1111 1111 1111 1111 1111 1111,

反码为1000 0000 0000 0000 0000 0000 0000 0000,

补码为1000 0000 0000 0000 0000 0000 0000 0001

所以最小的负数是-2147483647吗?错,不是。

在二进制中,0有两种表方法。

+0的原码为0000 0000 0000 0000 0000 0000 0000 0000,

-0的原码为1000 0000 0000 0000 0000 0000 0000 0000,

因为0只需要一个,所以把-0拿来当做一个最小的数-2147483648。
都互相抄,都没想明白吧,看下面,我自己悟出来的

-2147483648的补码表示为1000 0000 0000 0000 0000 0000 0000 0000,第32位为符号位,符号位不能变,所以没有原码,在32位没有原码。
-0的反码为 1111 1111 1111 1111 1111 1111 1111 1111
补码为反码加1
-0的补码为 1 1000 0000 0000 0000 0000 0000 0000 0000

看见没有int是32位,但是超出了,符号位不能变,所以溢出来了。
就只有-2147483647,
但是负的部分因为有-0,所以为-2147483648
正的位置就没有了,因为取得是-0,少了一个
为2147483647个

所以带符号32位int类型整数为-2147483648~2147483647
现在可以看懂了吧,点个赞好吗,再走好吗

  • 21
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值