# 7-原生類型
[原文鏈接](http://code.google.com/p/guava-libraries/wiki/PrimitivesExplained) [譯文鏈接](http://ifeve.com/google-guava-primitives) 譯者:沈義揚,校對:丁一
## 概述
Java的原生類型就是指基本類型:byte、short、int、long、float、double、char和boolean。
_在從Guava查找原生類型方法之前,可以先查查_[**_Arrays_**](http://docs.oracle.com/javase/1.5.0/docs/api/java/util/Arrays.html)_類,或者對應的基礎類型包裝類,如_[**_Integer_**](http://docs.oracle.com/javase/1.5.0/docs/api/java/lang/Integer.html)**_。_**
原生類型不能當作對象或泛型的類型參數使用,這意味著許多通用方法都不能應用于它們。Guava提供了若干通用工具,包括原生類型數組與集合API的交互,原生類型和字節數組的相互轉換,以及對某些原生類型的無符號形式的支持。
| **原生類型** | **Guava****工具類(都在****com.google.common.primitives****包****)** |
|:--- |:--- |
| byte | [`Bytes`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Bytes.html), [`SignedBytes`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/SignedBytes.html), [`UnsignedBytes`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedBytes.html) |
| short | [`Shorts`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Shorts.html) |
| int | [`Ints`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Ints.html), [`UnsignedInteger`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedInteger.html), [`UnsignedInts`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedInts.html) |
| long | [`Longs`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Longs.html), [`UnsignedLong`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedLong.html), [`UnsignedLongs`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedLongs.html) |
| float | [`Floats`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Floats.html) |
| double | [`Doubles`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Doubles.html) |
| char | [`Chars`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Chars.html) |
| boolean | [`Booleans`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/Booleans.html) |
Bytes工具類沒有定義任何區分有符號和無符號字節的方法,而是把它們都放到了SignedBytes和UnsignedBytes工具類中,因為字節類型的符號性比起其它類型要略微含糊一些。
int和long的無符號形式方法在UnsignedInts和UnsignedLongs類中,但由于這兩個類型的大多數用法都是有符號的,Ints和Longs類按照有符號形式處理方法的輸入參數。
此外,Guava為int和long的無符號形式提供了包裝類,即UnsignedInteger和UnsignedLong,以幫助你使用類型系統,以極小的性能消耗對有符號和無符號值進行強制轉換。
在本章下面描述的方法簽名中,我們用Wrapper表示JDK包裝類,prim表示原生類型。(Prims表示相應的Guava工具類。)
## 原生類型數組工具
原生類型數組是處理原生類型集合的最有效方式(從內存和性能雙方面考慮)。Guava為此提供了許多工具方法。
| **方法簽名** | **描述** | **類似方法** | **可用性** |
|:--- |:--- |:--- |:--- |
| List<Wrapper>?asList(prim… backingArray) | 把數組轉為相應包裝類的List | [Arrays.asList](http://docs.oracle.com/javase/6/docs/api/java/util/Arrays.html#asList%28T...%29) | 符號無關* |
| prim[]?toArray(Collection<Wrapper> collection) | 把集合拷貝為數組,和collection.toArray()一樣線程安全 | [Collection.toArray()](http://docs.oracle.com/javase/6/docs/api/java/util/Collection.html#toArray%28%29) | 符號無關 |
| prim[] concat(prim[]… arrays) | 串聯多個原生類型數組 | [Iterables.concat](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/collect/Iterables.html#concat%28java.lang.Iterable...%29) | 符號無關 |
| boolean contains(prim[] array, prim target) | 判斷原生類型數組是否包含給定值 | [Collection.contains](http://docs.oracle.com/javase/6/docs/api/java/util/Collection.html#contains%28java.lang.Object%29) | 符號無關 |
| int indexOf(prim[] array, prim target) | 給定值在數組中首次出現處的索引,若不包含此值返回-1 | [List.indexOf](http://docs.oracle.com/javase/6/docs/api/java/util/List.html#indexOf%28java.lang.Object%29) | 符號無關 |
| int?lastIndexOf(prim[] array, prim target) | 給定值在數組最后出現的索引,若不包含此值返回-1 | [List.lastIndexOf](http://docs.oracle.com/javase/6/docs/api/java/util/List.html#lastIndexOf%28java.lang.Object%29) | 符號無關 |
| prim?min(prim… array) | 數組中最小的值 | [Collections.min](http://docs.oracle.com/javase/6/docs/api/java/util/Collections.html#min%28java.util.Collection%29) | 符號相關* |
| prim?max(prim… array) | 數組中最大的值 | [Collections.max](http://docs.oracle.com/javase/6/docs/api/java/util/Collections.html#max%28java.util.Collection%29) | 符號相關 |
| String?join(String separator, prim… array) | 把數組用給定分隔符連接為字符串 | [Joiner.on(separator).join](http://code.google.com/p/guava-libraries/wiki/StringsExplained#Joiner) | 符號相關 |
| Comparator<prim[]> ? lexicographicalComparator() | 按字典序比較原生類型數組的Comparator | [Ordering.natural().lexicographical()](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/collect/Ordering.html#lexicographical%28%29) | 符號相關 |
*符號無關方法存在于Bytes, Shorts, Ints, Longs, Floats, Doubles, Chars, Booleans。而UnsignedInts, UnsignedLongs, SignedBytes, 或UnsignedBytes不存在。
*符號相關方法存在于SignedBytes, UnsignedBytes, Shorts, Ints, Longs, Floats, Doubles, Chars, Booleans, UnsignedInts, UnsignedLongs。而Bytes不存在。
## 通用工具方法
Guava為原生類型提供了若干JDK6沒有的工具方法。但請注意,其中某些方法已經存在于JDK7中。
| **方法簽名** | **描述** | **可用性** |
|:--- |:--- |:--- |
| int?compare(prim a, prim b) | 傳統的Comparator.compare方法,但針對原生類型。JDK7的原生類型包裝類也提供這樣的方法 | 符號相關 |
| prim checkedCast(long value) | 把給定long值轉為某一原生類型,若給定值不符合該原生類型,則拋出IllegalArgumentException | 僅適用于符號相關的整型* |
| prim?saturatedCast(long value) | 把給定long值轉為某一原生類型,若給定值不符合則使用最接近的原生類型值 | 僅適用于符號相關的整型 |
*這里的整型包括byte, short, int, long。不包括char, boolean, float, 或double。
_**譯者注:不符合主要是指long值超出prim類型的范圍,比如過大的long超出int范圍。_
注:com.google.common.math.DoubleMath提供了舍入double的方法,支持多種舍入模式。相見第12章的”浮點數運算”。
## 字節轉換方法
Guava提供了若干方法,用來把原生類型按**大字節序**與字節數組相互轉換。所有這些方法都是符號無關的,此外Booleans沒有提供任何下面的方法。
| **方法或字段簽名** | **描述** |
|:--- |:--- |
| int BYTES | 常量:表示該原生類型需要的字節數 |
| prim fromByteArray(byte[] bytes) | 使用字節數組的前Prims.BYTES個字節,按**大字節序**返回原生類型值;如果bytes.length <= Prims.BYTES,拋出IAE |
| prim?fromBytes(byte b1, …, byte bk) | 接受Prims.BYTES個字節參數,按**大字節序**返回原生類型值 |
| byte[] toByteArray(prim value) | 按**大字節序**返回value的字節數組 |
## 無符號支持
JDK原生類型包裝類提供了針對有符號類型的方法,而UnsignedInts和UnsignedLongs工具類提供了相應的無符號通用方法。UnsignedInts和UnsignedLongs直接處理原生類型:使用時,由你自己保證只傳入了無符號類型的值。
此外,對int和long,Guava提供了無符號包裝類([UnsignedInteger](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedInteger.html)和[UnsignedLong](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedLong.html)),來幫助你以極小的性能消耗,對有符號和無符號類型進行強制轉換。
### 無符號通用工具方法
JDK的原生類型包裝類提供了有符號形式的類似方法。
| **方法簽名** | **說明** |
|:--- |:--- |
| [`int?UnsignedInts.parseUnsignedInt(String)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/…ogle/common/primitives/UnsignedInts.html#parseUnsignedInt%28java.lang.String%29)[`long?UnsignedLongs.parseUnsignedLong(String)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/…le/common/primitives/UnsignedLongs.html#parseUnsignedLong%28java.lang.String%29) | 按無符號十進制解析字符串 |
| [`int?UnsignedInts.parseUnsignedInt(String string, int radix)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/…ogle/common/primitives/UnsignedInts.html#parseUnsignedInt%28java.lang.String, int%29)[`long?UnsignedLongs.parseUnsignedLong(String string, int radix)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/…le/common/primitives/UnsignedLongs.html#parseUnsignedLong%28java.lang.String%29) | 按無符號的特定進制解析字符串 |
| [`String?UnsignedInts.toString(int)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedInts.html#toString%28int%29)[`String?UnsignedLongs.toString(long)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedLongs.html#toString%28long%29) | 數字按無符號十進制轉為字符串 |
| [`String UnsignedInts.toString(int ? value, int radix)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedInts.html#toString%28int, int%29)[`String?UnsignedLongs.toString(long value, int radix)`](http://docs.guava-libraries.googlecode.com/git-history/release/javadoc/com/google/common/primitives/UnsignedLongs.html#toString%28long, int%29) | 數字按無符號特定進制轉為字符串 |
### 無符號包裝類
無符號包裝類包含了若干方法,讓使用和轉換更容易。
| **方法簽名** | **說明** |
|:--- |:--- |
| UnsignedPrim?add(UnsignedPrim), subtract, multiply, divide, remainder | 簡單算術運算 |
| UnsignedPrim?valueOf(BigInteger) | 按給定BigInteger返回無符號對象,若BigInteger為負或不匹配,拋出IAE |
| UnsignedPrim?valueOf(long) | 按給定long返回無符號對象,若long為負或不匹配,拋出IAE |
| UnsignedPrim?asUnsigned(prim value) | 把給定的值當作無符號類型。例如,UnsignedInteger.asUnsigned(1<<31)的值為2<sup>31</sup>,盡管1<<31當作int時是負的 |
| BigInteger?bigIntegerValue() | 用BigInteger返回該無符號對象的值 |
| toString(),??toString(int radix) | 返回無符號值的字符串表示 |
- Google Guava官方教程(中文版)
- 1-基本工具
- 1.1-使用和避免null
- 1.2-前置條件
- 1.3-常見Object方法
- 1.4-排序: Guava強大的”流暢風格比較器”
- 1.5-Throwables:簡化異常和錯誤的傳播與檢查
- 2-集合
- 2.1-不可變集合
- 2.2-新集合類型
- 2.3-強大的集合工具類:java.util.Collections中未包含的集合工具
- 2.4-集合擴展工具類
- 3-緩存
- 4-函數式編程
- 5-并發
- 5.1-google Guava包的ListenableFuture解析
- 5.2-Google-Guava Concurrent包里的Service框架淺析
- 6-字符串處理:分割,連接,填充
- 7-原生類型
- 9-I/O
- 10-散列
- 11-事件總線
- 12-數學運算
- 13-反射