Java原始碼之路---基礎資料型別
阿新 • • 發佈:2019-01-22
Java原始碼基礎資料型別
1、Java與數先關的基礎資料型別主要分整數與浮點數,整數:byte,short,int,long,浮點數:float,double
2、資料範圍
型別 | 範圍 |
---|---|
byte | -128~127(2^7-1) |
short | -32768~32767(2^15-1) |
int | -2147483648~2147483647(2^31-1)21億(10位) |
long | -9223372036854775808~9223372036854775807(2^63-1)19位 |
float | +/-2^−149,+/-2^128 |
double | +/-2^−1074,+/-2^1024 |
3、六個型別均繼承自Number,Number類為抽象類
public abstract class Number implements java.io.Serializable {
public abstract int intValue();
public abstract int longValue();
public abstract int floatValue();
public abstract int doubleValue();
public byte byteValue () {
return (byte)intValue();
}
public short shortValue() {
return (short)intValue();
}
}
4、整數的byte、short、int、long對於的封裝類,都有相關的快取操作,具體實現是通過內部類
private static class LongCache {
private LongCache(){}
static final Long cache[] = new Long[-(-128) + 127 + 1];
static {
for(int i = 0; i < cache.length; i++)
cache[i] = new Long(i - 128);
}
}
Byte對應ByteCache,Integer對應IntegerCache,Short對應ShortCache,Long對應LongCache,它們的快取範圍都是從-128~127。其中IntegerCache提供了可通過屬性設定“java.lang.Integer.IntegerCache.high”設定快取的最大值。
舉個有趣的栗子
Integer c = 3;
Integer d = 3;
int e = 321;
Integer g = 321;
Integer h = 321;
// 使用了快取
System.out.println(c == d); // true
System.out.println(e == g); // true
System.out.println(h == g); // false
5、都提供了不同進位制的數表示
6、toString()
public static String toString(int i) {
if (i == Integer.MIN_VALUE)
return "-2147483648";
// 1、獲取數的位數
int size = (i < 0) ? stringSize(-i) + 1 : stringSize(i);
char[] buf = new char[size];
// 2、int轉化成char[]陣列
getChars(i, size, buf);
return new String(buf, true);
}
final static int [] sizeTable = { 9, 99, 999, 9999, 99999, 999999, 9999999,
99999999, 999999999, Integer.MAX_VALUE };
//
// Requires positive x
static int stringSize(int x) {
for (int i=0; ; i++)
if (x <= sizeTable[i])
return i+1;
}
final static char [] DigitTens = {
'0', '0', '0', '0', '0', '0', '0', '0', '0', '0',
'1', '1', '1', '1', '1', '1', '1', '1', '1', '1',
'2', '2', '2', '2', '2', '2', '2', '2', '2', '2',
'3', '3', '3', '3', '3', '3', '3', '3', '3', '3',
'4', '4', '4', '4', '4', '4', '4', '4', '4', '4',
'5', '5', '5', '5', '5', '5', '5', '5', '5', '5',
'6', '6', '6', '6', '6', '6', '6', '6', '6', '6',
'7', '7', '7', '7', '7', '7', '7', '7', '7', '7',
'8', '8', '8', '8', '8', '8', '8', '8', '8', '8',
'9', '9', '9', '9', '9', '9', '9', '9', '9', '9',
} ;
final static char [] DigitOnes = {
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
} ;
static void getChars(int i, int index, char[] buf) {
int q, r;
int charPos = index;
char sign = 0;
if (i < 0) {
sign = '-';
i = -i;
}
// Generate two digits per iteration
while (i >= 65536) {
q = i / 100;
// really: r = i - (q * 100);
r = i - ((q << 6) + (q << 5) + (q << 2));
i = q;
buf [--charPos] = DigitOnes[r];
buf [--charPos] = DigitTens[r];
}
// Fall thru to fast mode for smaller numbers
// assert(i <= 65536, i);
for (;;) {
// q = i / 10
q = (i * 52429) >>> (16+3);
r = i - ((q << 3) + (q << 1)); // r = i-(q*10) ...
buf [--charPos] = digits [r];
i = q;
if (i == 0) break;
}
if (sign != 0) {
buf [--charPos] = sign;
}
}
- 關鍵點
- 移位的效率比直接乘除的效率要高
- 乘法的效率比除法的效率要高
- 通過查詢陣列,實現快速訪問,避免除法計算
- 重複利用計算結果:在獲取r(i%100)時,充分利用了除法的結果,結合位移避免重複計算。
- 位運算
- 負數的補碼:符號位:1,其餘絕對值的原碼按位取反+1
- 按位與(&)
- 按位或(|)
- 按位非(~)
- 按位異或(^):相同為0,不同為1,異或0具有保持的特點,而異或1具有翻轉的特點
- 左位移(<<)理解為乘法,如900 << 6 : 900 * 2 ^ 6 = 900 * 64
- 右位移(>>)理解為除法, 如900 >> 6 : 900 / 2 ^ 6 = 900 / 64
- 無符號右移(>>>)
7、浮點數(實現的原始碼:FloatingDecimal),如要進行精確的運算,要使用BigDecimal