int i = 6;
i = 4.5 + i; // 警告:double → int 截斷
// 過程:i→double → 相加 → 10.5 → 截斷為 10 → 賦值給 i
編譯器自動插入轉換,可能丟失精度/符號,建議開啟警告 -Wconversion。
int(11.1) // 函數式風格
static_cast(11.1) // C++ 風格,推薦
(int)11.1 // C 風格,不推薦
單參數構造函數(或除第一參數外全有默認值),隱式用於類型轉換。
class Complex {
double re, im;
public:
Complex(double r, double i) : re(r), im(i) {} // 初始化構造
Complex(double r) : re(r), im(0) {} // 轉換構造:double → Complex
};
Complex c(0,0);
c = c + 2.5; // 錯誤:無 operator+(Complex, double)
// 方案 A:重載 operator+(double)
Complex operator+(double r) const { return Complex(re+r, im); }
// 方案 B:利用轉換構造函數
Complex operator+(const Complex& rhs) const { return Complex(re+rhs.re, im+rhs.im); }
Complex c1(2.5); // 隱式轉換
c = c + c1; // 調用 operator+(Complex)
class Teacher {
public:
Teacher(const Student& s) { // Student → Teacher
num = s.num; name = s.name; sex = s.sex;
}
};
class Complex {
double re, im;
public:
operator double() const { return re; } // Complex → double
// 無返回類型、無參數、隱式調用
};
Complex c(3.0, 4.0);
double d = c + 2.5; // c → double(3.0) → 3.0+2.5=5.5 → d=5.5
class Ptr {
int* p;
public:
explicit operator bool() const { return p != nullptr; } // 僅在布爾上下文隱式調用
};
Ptr ptr = ...;
if (ptr) { ... } // OK
int x = ptr; // Error
int y = ptr + 1; // Error
防止意外算術轉換,保留條件判斷語義。
class NonConvertible {
public:
operator int() const = delete; // 禁止轉換為 int
};
| 機制 | 方向 | 隱式性 | 定義位置 | 典型用途 |
|---|---|---|---|---|
| 隱式標量轉換 | 內建類型間 | 自動 | 語言內建 | 數值運算混合類型 |
| 顯式轉換 | 內建類型間 | 程序員指定 | 使用點 | 明確意圖、窄化轉換 |
| 轉換構造函數 | 其他 → 類 | 隱式(非 explicit) | 目標類 | 數值包裝、字面值構造 |
| 類型轉換函數 | 類 → 其他 | 隱式(非 explicit) | 源類 | 智能指針 bool、數值提取 |
| explicit 轉換函數 | 類 → 其他 | 僅語境隱式 | 源類 | 安全布爾、受控轉換 |
explicit,除非確需隱式語義(如 string(const char*))。toDouble())。explicit operator bool() 實現安全布爾語境。A→B 和 B→A 同時存在)。