2017年計算機二級C++輔導實例編程(8)

字號:


    C++重載類型轉換操作符(type cast operator)
    boost::ref和boost::cref使用了重載“類型轉換(type cast)”操作符來實現使用引用類型來替換模版參數,本文就介紹一下這種操作符的重載方法。
    函數原型
    T1::operator T2() [const];   //T1的成員函數,重載"(T2)a"操作符
    1. 類型轉換重載函數的返回值是隱含的,并且不能顯示聲明,返回值是與轉換的類型相同的,即為上面原型中的T2。
    2. 不能有參數;
    3. 支持繼承,可以為虛函數;
    4. 支持使用typedef定義的類型;
    先通過一個簡單的例子來說明如何使用類型轉換重載
    1 #include
    2
    3 class D {
    4 public:
    5 D(double d) : d_(d) {}
    6
    7 /* 重載“(int)D” */
    8 operator int() const {
    9 std::cout << "(int)d called!" << std::endl;
    10 return static_cast(d_);
    11 }
    12
    13 private:
    14 double d_;
    15 };
    16
    17 int add(int a, int b) {
    18 return a + b;
    19 }
    20
    21 int main() {
    22 D d1 = 1.1;
    23 D d2 = 2.2;
    24 std::cout << add(d1, d2) << std::endl;
    25
    26 return 0;
    27 }
    28
    29
    在24行執(zhí)行add(d1,d2)函數時“(int)D”重載函數將被調用,程序運行的輸出為:
    (int)d called!
    (int)d called!
    3
    類型轉換操作符 vs 類型轉換構造函數(conversion constructor)
    有時候使用conversion constructor就能實現類型轉換,這種方式效率更高而且也更直觀,下面舉例說明:
    1 #include
    2
    3 class A
    4 {
    5 public:
    6 A(int num = 0) : dat(num) {}
    7
    8 /* 重載"(int)a" */
    9 operator int() { return dat; }
    10
    11 private:
    12 int dat;
    13 };
    14
    15
    16 class X
    17 {
    18 public:
    19 X(int num = 0) : dat(num) {}
    20
    21 /* 重載"(int)a" */
    22 operator int() { return dat; }
    23
    24 /* 重載"(A)a" */
    25 operator A() {
    26 A temp = dat;
    27 return temp;
    28 }
    29
    30 private:
    31 int dat;
    32 };
    33
    34
    35 int main()
    36 {
    37 X stuff = 37;
    38 A more = 0;
    39 int hold;
    40
    41 hold = stuff; // convert X::stuff to int
    42 std::cout << hold << std::endl;
    43
    44 more = stuff; // convert X::stuff to A::more
    45 std::cout << more << std::endl; // convert A::more to int
    46
    47 return 0;
    48 }
    49
    上面這個程序中X類通過重載“operator A()”來實現將X類型對象轉換成A類型,這種方式需要先創(chuàng)建一個臨時A對象再用它去賦值目標對象;更好的方式是為A類增加一個構造函數:
    A(const X& rhs) : dat(rhs) {}
    同時,請注意上面程序的第45行more的類型在調用std::cout時被隱式地轉成了int!
    一個簡單boost::ref實現
    通過重載type cast operator,我們就可以自己實現一個簡版的boost::ref。
    1 #include
    2
    3 template
    4 class RefHolder
    5 {
    6 public:
    7 RefHolder(T& ref) : ref_(ref) {}
    8
    9 /* 重載“(T&)A”操作符 */
    10 operator T& () const {
    11 return ref_;
    12 }
    13
    14 private:
    15 T& ref_;
    16 };
    17
    18
    19 template
    20 inline RefHolder ByRef(T& t) {
    21 return RefHolder(t);
    22 }
    23
    24 int inc(int& num) {
    25 num++;
    26 return num;
    27 }
    28
    29
    30 int main() {
    31 int n = 1;
    32 std::cout << inc(ByRef(n)) << std::endl; //RefHolder被轉換成了"int&"類型
    33
    34 return 0;
    35 }