1. 程式人生 > >C++中的類型轉換

C++中的類型轉換

actually new CA 對象的引用 如果 四種 表達式 clu 方式

在C++語言中,類型轉換分位兩種:隱式類型轉換 和 顯式類型轉換。

1. 隱式類型轉換

隱式轉換就是系統默認的、不需要加以聲明就可以進行的轉換。一般情況下,數據類型的轉換通常是由編譯系統自動進行的,不需要人工幹預,所以被稱為隱式類型轉換。

在以下四種情況下會進行隱式轉換:

1:算術運算式中,低類型能夠轉換為高類型。
2:賦值表達式中,右邊表達式的值自動隱式轉換為左邊變量的類型;
3:函數調用中參數傳遞時,系統隱式地將實參轉換為形參的類型後,賦給形參。
4:函數有返回值時,系統將隱式地將返回表達式類型轉換為返回值類型,賦值給調用函數。

int    itmp = 0;
double dtmp = 10;
dtmp = itmp;  //itmp被隱式轉換為double
if(itmp);        //itmp被隱式轉換為bool
itmp + dtmp;//計算結果被隱式轉換為double

  

2. 顯示類型轉換

2.1舊式類型轉換

舊式類型轉換其實就是C風格轉換,是從C語言中繼承下來的,比如,為了轉換一個類型為doubole的浮點數到整型:

int i;
double d;
i = (int)d;
或
int i;
double d;
i = int(d);

2.2 C++新式類型轉換

上面兩種方式不適用於C++中類(class)和類的指針,最好的解決方法就是不要使用C風格的強制類型轉換,而是使用標準C++的類型轉換符:static_cast, dynamic_cast。標準C++中有四個新式類型轉換符:static_cast、dynamic_cast、reinterpret_cast、和 const_cast。

dynamic_cast

dynamic_cast主要用於於對象的指針和引用。當用於多態類型時, 其將基類類型對象的引用或指針轉換為同一繼承層次中其他類型的引用和指針。

dynamic_cast的轉換格式:dynamic_cast< type> ( expression )

該運算符把expression轉換成type類型的對象。Type必須是類的指針、類的引用或者void*;如果type是類指針類型,那麽expression也必須是一個指針,如果type是一個引用,那麽expression也必須是一個引用。

如果expression是type的基類,使用dynamic_cast進行轉換時,在運行時就會檢查expression是否真正的指向一個type類型的對象,如果是,則能進行正確的轉換,獲得對應的值;否則返回NULL,如果是引用,則在運行時就會拋出異常。例如:

class A  
{  
    virtual void f(){};  
};  
class B : public A  
{  
    virtual void f(){};  
};  
void main()  
{  
    A* pa = new B;    //
    A* pa2 = new A;  
    B* pb = dynamic_cast<B*>(pa);   // ok: pa actually points to a B  
    B* pb2 = dynamic_cast<B*>(pa2);   // pa2 points to a A not a B, now pa2 is NULL  
}

static_cast

static_cast的轉換格式:static_cast< type > ( expression )

該運算符把expression轉換為type類型,但沒有運行時類型檢查來保證轉換的安全性。它主要有如下幾種用法:

①用於類層次結構中基類和子類之間指針或引用的轉換。

進行上行轉換(把子類的指針或引用轉換成基類表示)是安全的;

進行下行轉換(把基類指針或引用轉換成子類表示)時,由於沒有動態類型檢查,所以是不安全的。

②用於基本數據類型之間的轉換。如把int轉換成char,把int轉換成enum。這種轉換的安全性也要開發人員來保證。

③把空指針轉換成目標類型的空指針。

④把任何類型的表達式轉換成void類型。

註意:static_cast不能轉換掉expression的const、volitale、或者__unaligned屬性。

reinpreter_cast

reinpreter_cast的轉換格式reinpreter_cast<type>(expression)

reinterpret_cast 是一種高度危險的轉換,這種轉換僅僅是對二進制位的重新解釋。這個操作符能夠在非相關的類型之間轉換。操作結果只是簡單的從一個指針到別的指針的值的二進制拷貝。在類型之間指向的內容不做任何類型的檢查和轉換。例:

class A{};
class B{};
A* a = new A;
B* b = reinpreter_cast<B*> a;

const_cast

const_cast的轉換格式:const_cast<type> (expression)

該運算符用來修改類型的const或volatile屬性。除了const 或volatile修飾之外, type和expression的類型是一樣的。常量指針被轉化成非常量指針,並且仍然指向原來的對象;常量引用被轉換成非常量引用,並且仍然指向原來的對象;常量對象被轉換成非常量對象。

#include <iostream>  
using namespace std;  
class CA  
{  
public:  
    CA() :m_iA(10){}  
    int m_iA;  
};  
int main()  
{  
    const CA *pA = new CA;  
    // pA->m_iA = 100; // Error 此時通過pA對m_iA賦值會報錯,因為const屬性  
    CA *pB = const_cast<CA *>(pA);  
    pB->m_iA = 100;  
    // 現在pA和pB指向同一個對象,可以通過pB修改m_iA  
    cout << pA->m_iA << endl;  
    cout << pB->m_iA << endl;  
//-------------------------------------//
    const CA &a = *pA;  
    // a.m_iA = 200; // Error  
    CA &b = const_cast<CA &>(a);  
    b.m_iA = 200;  
    // 現在a和b都是同一個對象的引用,可以通過b修改m_iA  
    cout << b.m_iA << endl;  
    cout << a.m_iA << endl;  
}

C++中的類型轉換