Java算是一门很高级的语言了,平时使用一般不会用到位运算这种很低级的特性,但在有些地方有很高的性能或者空间的要求可能会用到,比如说手机平台。今天偶尔看了下,发现一些基础只是很长时间没有搞都忘记了,今天看到相关的东西以至于想了很久才想通。就从今天看到的一段代码来回顾些基础知识,是一段将int转换为byte数组的代码。
———————————————————–
//cout为自己包装的打印方法
int a = 645765765;
cout(a);
cout(Integer.toBinaryString(a));
byte[] b = new byte[4];
b[0] = (byte)((a>>24)&0xff);
cout(Integer.toBinaryString(b[0]&0xff));
b[1] = (byte)((a>>16)&0xff);
cout(Integer.toBinaryString(b[1]&0xff));
b[2] = (byte)((a>>8)&0xff);
cout(Integer.toBinaryString(b[2]&0xff));
b[3] = (byte)((a>>0)&0xff);
cout(Integer.toBinaryString(b[3]&0xff));
int decodeA ;
decodeA = b[0]&0x000000ff;
decodeA = (decodeA<<8) + (b[1]&0xff);
decodeA = (decodeA<<8) + (b[2]&0xff);
decodeA = (decodeA<<8) + (b[3]&0xff);
cout(decodeA);
//自己写的另外一种转换方法
int decodeA2 ;
decodeA2 = ((b[0]&0xff)<<24);
decodeA2 += ((b[1]&0xff)<<16);
decodeA2 += ((b[2]&0xff)<<8);
decodeA2 += ((b[3]&0xff)<<0);
cout(decodeA2);
——————————————————————–
一开始看到的黑体部分。于是写了下面红色的版本,但之前不是现在这个正确版本,之前是这样的。
int decodeA2 ;
decodeA2 = b[0]<<24;
decodeA2 += b[1]<<16);
decodeA2 += b[2]<<8;
decodeA2 += b[3]<<0;
cout(decodeA2);
结果只要a的值一超过128就会出错,百思不得其解,之后查了有关移位的资料。右移在java中有两种方式,一种是带符号的,一种是不带符号的,带符号的会根据最高位的值来判断用1还是0来补足,若最高位为1则用1来补,若为0则用0来补,无符号的则全部用0补,而对于左移则全部用0补。想了很久这个似乎也没有关系,最后偶然间看到byte的最高位是用来表示正负的,就是说byte的值为-128到127,所以只要在遇到了某一byte的最高位为1的情况下就会出现该值变为了一负值,但其实这个时候它里面存的位信息还是对的,用Integer的int到二进制的一个方法将其打出来便可以发现是一个32位的高位全为1的二进制形式,及是一个负数,于是对它在进行一次“与运算”去掉高位的“1”就可以得到正确的结果了。