但是從沒聽說過轉換構造函數,隱式轉換函數也是一樣,C++的確是夠博大精深的,再次嘆服!
其實我們已經在C/C++中見到過多次標準類型數據間的轉換方式了,這種形式用于在程序中將一種指定的數據轉換成另一指定的類型,也即是強制轉換,比如:int a = int(1.23),其作用是將1.23轉換為整形1.然而對于用戶自定義的類類型,編譯系統并不知道如何進行轉換,所以需要定義專門的函數來告訴編譯系統改如何轉換,這就是轉換構造函數和類型轉換函數!
一、轉換構造函數
轉換構造函數(conversion constructor function) 的作用是將一個其他類型的數據轉換成一個類的對象?
當一個構造函數只有一個參數,而且該參數又不是本類的const引用時,這種構造函數稱為轉換構造函數。
轉換構造函數是對構造函數的重載。
例如:
[cpp]
Complex(double r)
{
real=r;
imag=0;
}
其作用是將double型的參數r轉換成Complex類的對象,將r作為復數的實部,虛部為0?用戶可以根據需要定義轉換構造函數,在函數體中告訴編譯系統怎樣去進行轉換?
那么如何使用轉換構造函數進行類型轉換呢?我們看如下的例子:
[cpp]
// TypeSwitch.cpp : 定義控制臺應用程序的入口點。
//
#include "stdafx.h"
#include <iostream>
using namespace std;
class Complex
{
public:
Complex():real(0),imag(0){};
Complex(double r, double i):real(r),imag(i){};
Complex(double r):real(r),imag(0){}; // 定義轉換構造函數
void Print(){
cout《"real = " 《 real 《" image = "《imag《endl;
}
Complex& operator+(Complex c){
return Complex(this->real + c.real, this->imag + c.imag);
}
private:
double real;
double imag;
};
int main(int argc, _TCHAR* argv[])
{
Complex c;
c = 1.2; // 調用轉換構造函數將1.2轉換為Complex類型
c.Print();
Complex c1(2.9, 4.2);
Complex c2 = c1 + 3.1; // 調用轉換構造函數將3.1轉換為Complex類型
c2.Print();
return 0;
}
不僅可以將一個標準類型數據轉換成類對象,也可以將另一個類的對象轉換成轉換構造函數所在的類對象?如可以將一個學生類對象轉換為教師類對象,可以在Teacher類中寫出下面的轉換構造函數:
[cpp]
Teacher(Student& s)
{
num=s.num;
strcpy(name,s.name);
sex=s.sex;
}
使用方法同上!
注意:
1.用轉換構造函數可以將一個指定類型的數據轉換為類的對象?但是不能反過來將一個類的對象轉換為一個其他類型的數據(例如將一個Complex類對象轉換成double類型數據)?
2.如果不想讓轉換構造函數生效,也就是拒絕其它類型通過轉換構造函數轉換為本類型,可以在轉換構造函數前面加上explicit!例如sat答案
[cpp]
// TypeSwitch.cpp : 定義控制臺應用程序的入口點。
//
#include "stdafx.h"
#include <iostream>
using namespace std;
class Complex
{
public:
Complex():real(0),imag(0){};
Complex(double r, double i):real(r),imag(i){};
explicit Complex(double r):real(r),imag(0){}; // explicit禁止構造函數的轉換功能
void Print(){
cout《"real = " 《 real 《" image = "《imag《endl;
}
private:
double real;
double imag;
};
int main(int argc, _TCHAR* argv[])
{
Complex c1(1.2, 2.3), c2;
double d;
d = c1 + 1.1; // 調用類型轉換函數將c1轉換為double,編譯出錯!
cout《d《endl;
return 0;
}
二、類型轉換函數
用轉換構造函數可以將一個指定類型的數據轉換為類的對象?但是不能反過來將一個類的對象轉換為一個其他類型的數據(例如將一個Complex類對象轉換成double類型數據)?而類型轉換函數就是專門用來解決這個問題的!
類型轉換函數的作用是將一個類的對象轉換成另一類型的數據?
如果已聲明了一個Complex類,可以在Complex類中這樣定義類型轉換函數:
[cpp]
operator double( )
{
return real;
}
類型轉換函數的一般形式為:
operator 類型名( )
{
實現轉換的語句
}
注意事項:
1.在函數名前面不能指定函數類型,函數沒有參數?
2.其返回值的類型是由函數名中指定的類型名來確定的?
3.類型轉換函數只能作為成員函數,因為轉換的主體是本類的對象,不能作為友元函數或普通函數?
4.從函數形式可以看到,它與運算符重載函數相似,都是用關鍵字operator開頭,只是被重載的是類型名?double類型經過重載后,除了原有的含義外,還獲得新的含義(將一個Complex類對象轉換為double類型數據,并指定了轉換方法)?這樣,編譯系統不僅能識別原有的double型數據,而且還會把Complex類對象作為double型數據處理托福答案
[cpp]
// TypeSwitch.cpp : 定義控制臺應用程序的入口點。
//
#include "stdafx.h"
#include <iostream>
using namespace std;
class Complex
{
public:
Complex():real(0),imag(0){};
Complex(double r, double i):real(r),imag(i){};
Complex(double r):real(r),imag(0){}; // 定義轉換構造函數
void Print(){
cout《"real = " 《 real 《" image = "《imag《endl;
}
operator double(){ // 定義類型轉換函數
return real;
}
private:
double real;
double imag;
};
int main(int argc, _TCHAR* argv[])
{
Complex c1(1.2, 2.3);
double d;
d = c1 + 1.1; // 調用類型轉換函數將c1轉換為double
cout《d《endl;
return 0;
}
本例中,對于d = c1 + 1.1;先調用類型轉換函數將c1轉為double類型,然后在與1.1相加!
那么程序中的Complex類對具有雙重身份,既是Complex類對象,又可作為double類型數據?Complex類對象只有在需要時才進行轉換,要根據表達式的上下文來決定?轉換構造函數和類型轉換運算符有一個共同的功能: 當需要的時候,編譯系統會自動調用這些函數,建立一個無名的臨時對象(或臨時變量)?