[Java源碼]Byte

此次咱們來看看Byte類的源代碼,基於 jdk1.8.0_181.jdk 版本 。html

概要

Java的Byte類主要是對byte基本數據類型的封裝,有着一個字段存放着對應的byte數據值,另外提供了一些方法方便對byte進行相關的操做。java

類定義

public final class Byte extends Number implements Comparable<Byte> 複製代碼

Byte類帶有關鍵字final,也就是不能夠繼承的,另外繼承了Number類,實現了Comparable接口,也就是能夠進行比較。數組

屬性

public static final byte   MIN_VALUE = -128;

public static final byte   MAX_VALUE = 127;
複製代碼

定義了Byte的範圍大小,因爲補碼的關係,負數會比正數多一個值,MIN_VALUE能取的值爲 -2**8,而MAX_VALUE能取的值爲2**8 - 1,具體原碼和補碼的邏輯,能夠參考下原碼、反碼、補碼的產生、應用以及優缺點有哪些? - 知乎用戶的回答 - 知乎,我的以爲講解的不錯。oracle

public static final int SIZE = 8;
複製代碼

定義了byte值的二進制補碼格式的bit位數,固定8位。ide

public static final int BYTES = SIZE / Byte.SIZE;
複製代碼

定義了byte值的二進制補碼格式的字節數,計算值固定爲1。post

@SuppressWarnings("unchecked")
public static final Class<Byte>     TYPE = (Class<Byte>) Class.getPrimitiveClass("byte");
複製代碼

獲取Byte的類信息,Byte.TYPE == byte.class,二者是等價的。性能

private final byte value;
複製代碼

Byte由於是byte的包裝類,因此這裏包含了對應的byte基本類型數據的變量。學習

private static final long serialVersionUID = -7183698231559129828L;
複製代碼

內部類

private static class ByteCache {
  private ByteCache(){}

  static final Byte cache[] = new Byte[-(-128) + 127 + 1];

  static {
    for(int i = 0; i < cache.length; i++)
      cache[i] = new Byte((byte)(i - 128));
  }
}
複製代碼

這裏定義了一個靜態的嵌套類,內部定義了一個數組,大小爲-(-128)+127+1=256,包含了-128~127之間的值。靜態塊中初始化了數組的值。這裏補充一個知識點,Java類的加載順序,靜態變量/代碼塊 -> 非靜態變量/代碼塊 -> 構造方法,相同部分裏面是按照代碼順序進行加載,詳細的內容能夠自行搜索學習。優化

關於內部類的相關說明,能夠參考官方的文檔 Nested Classes 進行進一步的瞭解學習。this

方法

構造方法

public Byte(byte value) {
  this.value = value;
}

public Byte(String s) throws NumberFormatException {
  this.value = parseByte(s, 10);
}

複製代碼

存在兩個對應的構造方法,一個傳入byte值,一個是傳入字符串解析,轉換成10進制整數處理(注意的是這個方法可能會拋出異常,須要注意處理),對應的解析方法下面介紹。

parseByte 方法

public static byte parseByte(String s, int radix) throws NumberFormatException {
  int i = Integer.parseInt(s, radix);
  if (i < MIN_VALUE || i > MAX_VALUE)
    throw new NumberFormatException(
    "Value out of range. Value:\"" + s + "\" Radix:" + radix);
  return (byte)i;
}

複製代碼

傳入字符串和進制數,調用了Integer.parseInt方法獲取轉換後的整數,判斷整數範圍是否符合Byte的範圍。若是是,強制轉換byte類型返回;否,拋出NumberFormatException異常。

public static byte parseByte(String s) throws NumberFormatException {
  return parseByte(s, 10);
}

複製代碼

存在一個單參數的parseByte方法,經過調用上面的方法實現,默認10進制數。

toString 方法

public static String toString(byte b) {
  return Integer.toString((int)b, 10);
}

public String toString() {
  return Integer.toString((int)value);
}

複製代碼

直接將byte類型值強制轉換成int,而後調用了Integer.toString方法進行操做。

valueOf 方法

public static Byte valueOf(byte b) {
  final int offset = 128;
  return ByteCache.cache[(int)b + offset];
}

複製代碼

對於byte類型參數,直接經過計算偏移量,讀取ByteCache內部類的靜態變量數組對應值來操做,提高了對應的空間和時間性能。

public static Byte valueOf(String s, int radix) throws NumberFormatException {
  return valueOf(parseByte(s, radix));
}

public static Byte valueOf(String s) throws NumberFormatException {
  return valueOf(s, 10);
}

複製代碼

這兩個方法是針對string類型參數的,只是進制設定的問題。使用parseByte方法將字符串轉換成byte類型值,而後直接使用第一個valueOf方法操做。

decode 方法

public static Byte decode(String nm) throws NumberFormatException {
  int i = Integer.decode(nm);
  if (i < MIN_VALUE || i > MAX_VALUE)
    throw new NumberFormatException(
    "Value " + i + " out of range from input " + nm);
  return valueOf((byte)i);
}

複製代碼

針對字符串解碼,將字符串轉換成Byte類型值。主要邏輯是調用了Integer.decode方法獲取解碼後的數字,而後判斷對應返回是否符合byte要求,調用valueOf返回最終結果。

除去+/-符號,會根據實際狀況進行特定的解碼,默認會處理成十進制。0x,0X,#開頭的會處理成16進制,0開頭的會處理成8進制。

xxxValue 方法

public byte byteValue() {
  return value;
}

public short shortValue() {
  return (short)value;
}

public int intValue() {
  return (int)value;
}

public long longValue() {
  return (long)value;
}

public float floatValue() {
  return (float)value;
}

public double doubleValue() {
  return (double)value;
}

複製代碼

經過強制類型轉換,擴大了原有值類型範圍,返回結果。

hashCode 方法

@Override
public int hashCode() {
  return Byte.hashCode(value);
}

public static int hashCode(byte value) {
  return (int)value;
}

複製代碼

直接返回了對應的int類型值,做爲其hashCode。

equals 方法

public boolean equals(Object obj) {
  if (obj instanceof Byte) {
    return value == ((Byte)obj).byteValue();
  }
  return false;
}

複製代碼

首先判斷傳入參數obj是否是Byte的實例,是的話比較二者的值是否相等;不然直接返回false。從這裏能夠看出來,咱們在使用時也不須要對傳入參數進行null == obj的判斷,能夠忽略。

compare 方法

public static int compare(byte x, byte y) {
  return x - y;
}

複製代碼

比較二者的值,x小於y時返回負數,x等於y時返回0,x大於y時返回正數。

compareTo 方法

public int compareTo(Byte anotherByte) {
  return compare(this.value, anotherByte.value);
}

複製代碼

內部調用compare方法。

toUnsignedInt 方法

public static int toUnsignedInt(byte x) {
  return ((int) x) & 0xff;
}

複製代碼

byte轉換成無符號整數。x強制轉換成int類型值,經過與0xff進行位運算,保留低8位值,高24位設置成0。總體結果,0和正數保持不變,負數等於原來的值 + 2**8。

toUnsignedLong 方法

public static long toUnsignedLong(byte x) {
  return ((long) x) & 0xffL;
}

複製代碼

過程同上,只是long爲64位,低8位保持原值,高56位設置成0。

總結

經過閱讀源碼發現,Byte類大量使用了Integer的方法,另外使用了內部類、位運算等方式進行了必定的邏輯優化。本身在看的過程對於內部類,補碼,類的加載順序也加深了了解,繼續加油!

最後

對應博客地址:blog.renyijiu.com/post/java源碼…

相關文章
相關標籤/搜索