1. 隱式(自動)型別轉換
在 Java(與其他語言相同)中,變數有嚴格的型別——如果變數宣告為 int,就只能存放整數;如果是 double,就只能存放浮點數。但在實際程式中,常會需要把一個變數的值「放到」另一個不同型別的變數中。例如:
- 從方法得到 int,但想當作 double 使用以進行小數運算。
- 以數值(int)存放字元的碼位,想要取得字元本身(char)。
- 運算結果是 double,但我們需要整數結果(int),例如要輸出整顆蘋果的數量。
在 Java 中有兩種主要的型別轉換方式:隱式(自動)與顯式(手動)。
這是什麼?
隱式轉換是指在安全且不會遺失資料時,Java 會自動將值從一種型別轉成另一種型別,無需你的介入。
當你把較小範圍的型別指定給較大範圍的型別變數時就會發生。例如,從 int 到 double、從 char 到 int、從 float 到 double。
類比:想像你有一杯水(int)和一個水桶(double)。把水從杯子倒進水桶——不會溢出,全部都裝得下。Java 在這些情況下允許自動轉換。
範例:int → double
int apples = 5;
double applesWeight = apples; // int 會自動變成 double
System.out.println(applesWeight); // 5.0
範例:char → int
在 Java 中,每個字元其實就是 Unicode 表中的一個數值。因此,char 轉成 int 會自動進行:
char letter = 'A';
int code = letter; // 'A' 會變成 65(在 Unicode 中的碼位)
System.out.println(code); // 65
隱式轉換對照表
| 來源 | 可隱式轉到 |
|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
重要:隱式轉換只會朝「擴張」方向(由較小到較大)。
2. 顯式(手動)型別轉換(type casting)
顯式轉換是在你想把值從較大的型別轉成較小的型別,或是在不相容型別之間轉換時所需要。這種情況下,Java 要求你明確表示你了解可能會遺失資料。
類比:把水從水桶(double)倒進杯子(int)——有些水可能會溢出,而 Java 要求你說:「是的,我明白可能會遺失一部分資料!」
語法
tip_naznacheniya peremennaya = (tip_naznacheniya) vyrazhenie;
範例:double → int
double price = 12.99;
int roundedPrice = (int) price; // 小數部分會直接被丟棄!
System.out.println(roundedPrice); // 12
注意:這不是四捨五入!只是把小數點後面的部分「切掉」。要四捨五入請使用 Math.round()。
範例:int → char
int code = 66;
char letter = (char) code; // 66 是字元 'B'
System.out.println(letter); // B
範例:double → float
double d = 3.1415926535;
float f = (float) d; // 會喪失一部分精度
System.out.println(f); // 3.1415927(小數位較少)
3. 數值與字元(char)之間的轉換
為什麼可行?
在 Java 中,字元(char)其實就是 Unicode 表中的數值。因此,它們可以自由地與 int 相互轉換。
範例:char → int
char ch = '\u0416';
int code = ch;
System.out.println(code); // 1046
範例:int → char
int code = 8364;
char symbol = (char) code;
System.out.println(symbol); // €
實作:輸出字母表
for (int i = 65; i < 65 + 26; i++) {
System.out.print((char) i + " ");
}
// 輸出:A B C D ... Z
4. 整數與浮點數之間的轉換
int → double(隱式)
int count = 10;
double avg = count; // 隱式擴張
System.out.println(avg); // 10.0
double → int(顯式)
double score = 8.75;
int rounded = (int) score;
System.out.println(rounded); // 8
如何依數學規則四捨五入?
如果需要的不是單純「丟棄」小數部分,而是四捨五入到最接近的整數,請使用 Math.round():
double price = 8.75;
int rounded = (int) Math.round(price);
System.out.println(rounded); // 9
5. 當型別「縮小」時會發生什麼?資料遺失
範例:int → byte
int big = 300;
byte small = (byte) big;
System.out.println(small); // 44(!)
為什麼是 44?因為 byte 的範圍是從 -128 到 127,若數值超出範圍——就會依 256 的模(取餘數)進行「截斷」。
範例:double → int
double d = 1e20;
int i = (int) d;
System.out.println(i); // -2147483648(int 的最小值)
數值太大超出 int 的範圍,結果就會變得「怪異」。
6. 運算中的轉換:「混合」型別
範例:int + double
int a = 3;
double b = 2.5;
double result = a + b; // int 會自動變成 double
System.out.println(result); // 5.5
範例:char + int
char ch = 'A'; // 65
int offset = 2;
char next = (char) (ch + offset); // char 會自動變成 int
System.out.println(next); // C
7. 數字與字串之間的轉換
雖然嚴格來說這不算是「型別轉換」,但常常需要把數字與字串互轉。
int → String
int x = 123;
String s = Integer.toString(x);
// 或者更簡單:String s = "" + x;
String → int
String s = "456";
int x = Integer.parseInt(s);
8. 常見錯誤與細節
錯誤 №1:在 double → int 時遺失小數部分。 新手常以為(int)3.99 會得到 4。其實結果是 3,小數部分會被丟棄。要正確四捨五入請使用 Math.round()。
錯誤 №2:隱式「縮小」不起作用。 不能直接寫 int x = 300; byte b = x; —— 編譯器會報錯。必須明確寫出(byte)x,但如果數值超出 byte 的範圍,結果可能很奇怪。
錯誤 №3:在不相容型別之間轉換。 不能寫(int)"123"——字串要轉成數字,應透過 Integer.parseInt()。
錯誤 №4:char 與 int 的問題。 將 int 轉成 char 只對 Unicode 中實際存在的碼位有效。若傳入過大的數值,結果可能是意想不到的符號。
錯誤 №5:運算式中的混合型別。 如果運算式同時包含 int 與 double,結果會永遠是 double。如果你預期得到整數,這可能會對程式邏輯造成意外影響。
錯誤 №6:四捨五入不是型別轉換!(int)x 並非四捨五入,而是直接丟棄小數部分。要四捨五入請使用 Math.round()。
GO TO FULL VERSION