基本型別分類與規格(32/64 位常見實現)
| 型別 | 位元組 | 範圍(帶號) | 範圍(無號) | 備註 |
| `char` / `signed char` | 1 | -128 ~ 127 | 0 ~ 255 | 字元/最小整數 |
| `unsigned char` | 1 | - | 0 ~ 255 | 位元操作、原始位元組 |
| `short` / `short int` | 2 | -32,768 ~ 32,767 | 0 ~ 65,535 | 至少 16 位 |
| `int` | 4 | -2,147,483,648 ~ 2,147,483,647 | 0 ~ 4,294,967,295 | 自然字長,通常 32 位 |
| `long` / `long int` | 4/8 | 同 int 或 64 位 | 同 unsigned int 或 64 位 | Windows 64 位為 4,Linux 64 位為 8 |
| `long long` (C++11) | 8 | -9.22e18 ~ 9.22e18 | 0 ~ 1.84e19 | 保證至少 64 位 |
| `float` | 4 | ±1.2e-38 ~ ±3.4e38 | - | IEEE-754 單精度,~7 位有效數字 |
| `double` | 8 | ±2.2e-308 ~ ±1.8e308 | - | IEEE-754 雙精度,~15 位有效數字,預設浮點字面值型別 |
| `long double` | 8/10/16 | 擴展精度 | - | 平台相關,x86 為 80 位擴展精度 |
| `bool` | 1 | `true`/`false` | - | 條件判斷,轉整數為 1/0 |
| `wchar_t` / `char16_t` / `char32_t` | 2/4 | - | - | 寬字元/UTF-16/UTF-32(C++11) |
關鍵差異與避坑
- `int` vs `long`:32 位環境相同,64 位 Linux `long` 為 8 位元組。**跨平台代碼請用 `` 固定寬度型別**(`int32_t`、`int64_t`、`uintptr_t`)。
- 有號/無號混用:`-1 < 0u` 為 `false`(`-1` 隱式轉為巨大無號數)。**避免混用**,或用 `gsl::narrow_cast` 顯式轉換並檢查。
- 浮點精度:`0.1 + 0.2 != 0.3`。貨幣計算用整數(分)或定點數庫。
- 隱性縮窄轉換:`int x = 3.75;` → `x==3`(截斷非四捨五入)。啟用 `-Wnarrowing` / `/W4` 捕獲。
- `char` 有號性未定義:攜帶字元值時用 `unsigned char` 或 `uint8_t`;攜帶文字時用 `char` 配合 `std::string`。
型別別名與固定寬度型別
// 傳統 typedef
typedef unsigned long ulong;
typedef int32_t Int32; // 需 #include
// C++11 using 別名(支援模板)
template using Vec = std::vector;
using StringMap = std::unordered_map;
字面值後綴
123 // int
123u // unsigned int
123L // long
123LL // long long
123.0 // double
123.0f // float
123.0L // long double
'c' // char (單引號)
"str" // const char* (雙引號)
u8"str" // UTF-8 字串字面值 (C++17)
類型推導與 `auto`
- `auto x = 42;` → `int`
- `auto& ref = x;` → `int&`
- `auto* ptr = &x;` → `int*`
- 範圍 for:`for (auto& e : vec)` 自動推導元素型別。
實戰建議
- 預設用 `int` 計數/索引,需固定寬度用 `int32_t`/`int64_t`。
- 指標差值、陣列大小用 `std::size_t`(無號,匹配位址寬度)。
- 位元操作、原始緩衝區用 `std::byte` (C++17) 或 `uint8_t`。
- 浮點預設用 `double`,記憶體/頻寬敏感才用 `float`。
- 布林語境只用 `bool`,避免整數隱性轉換驚喜。
- 啟用編譯器警告(`-Wall -Wextra -Wconversion` / `/W4`),視警告為錯誤(`-Werror` / `/WX`)。