c++ 05
構(gòu)造函數(shù)
無(wú)參構(gòu)造函數(shù)
有參構(gòu)造函數(shù)
//無(wú)參構(gòu)造函數(shù),書寫格式
#include <iostream>
using namespace std;
class Pet
{
public:
//函數(shù)聲明
void exer1();
int exre2();
private:
//函數(shù)聲明
}
void Pet::exer1(){}
int Pet::exer2(){}
int main(void)
{
Pet pet;
return 0;
}
//有參構(gòu)造函數(shù),書寫模板
#include <iostream>
using namespace std;
class Pet
{
public:
Pet();
//函數(shù)和聲明
private:
//函數(shù)和聲明
};
int main(void)
{
Pet pet();
return 0;
}
//有參構(gòu)造函數(shù),實(shí)例
#include <iostream>
#include <string>
using namespace std;
class Pet
{
public:
//構(gòu)造函數(shù):用來(lái)初始化成員變量
//在生成對(duì)象的時(shí)候自動(dòng)被調(diào)用
//函數(shù)需要的參數(shù)通過(guò)定義對(duì)象時(shí)
//在對(duì)象的后面括號(hào)中進(jìn)行指定
//若沒(méi)有自定義構(gòu)造函數(shù)
//則默認(rèn)自動(dòng)會(huì)生成一個(gè)無(wú)參的構(gòu)造函數(shù)
//若自定義了構(gòu)造函數(shù)
//則不會(huì)生成一個(gè)無(wú)參的構(gòu)造函數(shù)
Pet(string name, string voice
, string skill, int attack);
//無(wú)參構(gòu)造函數(shù)
Pet()
{
cout << "call Pet()..." << endl;
}
void info();
private:
string m_strName;
string m_strVoice;
string m_strSkill;
int m_iAttack;
};
Pet::Pet(string name, string voice
, string skill, int attack)
{
m_strName = name;
m_strVoice = voice;
m_strSkill = skill;
m_iAttack = attack;
cout << "call Pet construct..." << endl;
}
void Pet::info()
{
cout << "戰(zhàn)寵:" << m_strName
<< " 賣萌:" << m_strVoice
<< " 技能:" << m_strSkill
<< " 攻擊力:" << m_iAttack
<< endl;
}
int main(void)
{
//生成對(duì)象pet時(shí),自動(dòng)調(diào)用構(gòu)造函數(shù)
//構(gòu)造函數(shù)需要的數(shù)據(jù)通過(guò)對(duì)象后面的括號(hào)進(jìn)行指定
Pet pet("九尾狐", "叮叮叮", "魅惑", 20000);
pet.info();
//若生成對(duì)象時(shí),沒(méi)有傳參,則默認(rèn)調(diào)用無(wú)參構(gòu)造函數(shù)
//若沒(méi)有參數(shù),則不需要在對(duì)象后面加括號(hào)
Pet pet2;
return 0;
}
拷貝構(gòu)造函數(shù)
淺拷貝
深拷貝
#include <iostream>
#include <string.h>
using namespace std;
class MyString
{
public:
MyString()
{
m_pData = NULL;
}
MyString(const char *pData)
{
if (NULL != pData)
{
m_pData = new char[strlen(pData)+1];
if (NULL != m_pData)
{
strcpy(m_pData, pData);
}
}
cout << "called MyString(const char *pData)\n";
}
//若沒(méi)有自定義拷貝構(gòu)造函數(shù)
//則默認(rèn)會(huì)生成一個(gè)拷貝構(gòu)造函數(shù)
//默認(rèn)生成的拷貝構(gòu)造函數(shù)只是
//使用舊對(duì)象的成員變量依次對(duì)新對(duì)象的成員變量賦值
//將這種拷貝稱之為淺拷貝
//在自定義的拷貝構(gòu)造函數(shù)中
//若不僅僅拷貝變量的值,還拷貝額外的相關(guān)資源
//將這種拷貝稱之為深拷貝
MyString(const MyString &other)
{
m_pData = NULL;
if (NULL != other.m_pData)
{
m_pData = new char[strlen(other.m_pData)+1];
if (NULL != m_pData)
{
strcpy(m_pData, other.m_pData);
}
}
cout << "called MyString(const MyString &other)\n";
}
const char *data()
{
return m_pData;
}
//析構(gòu)函數(shù)
//在對(duì)象消亡的時(shí)候自動(dòng)調(diào)用
//用來(lái)釋放相關(guān)資源
//若沒(méi)有自定義析構(gòu)函數(shù)
//則會(huì)默認(rèn)生成一個(gè)析構(gòu)函數(shù)
//默認(rèn)生成的析構(gòu)函數(shù)什么都不做
~MyString()
{
if (NULL != m_pData)
{
delete []m_pData;
}
cout << "~MyString()...\n";
}
void myDelete()
{
if (NULL != m_pData)
{
delete []m_pData;
}
cout << "myDelete()...\n";
}
private:
char *m_pData;
};
int main(void)
{
MyString str("HelloWorld");
cout << str.data() << endl;
//使用舊對(duì)象的成員變量依次對(duì)新對(duì)象的成員變量賦值
//MyString str2 = str; //初始化
//調(diào)用拷貝構(gòu)造函數(shù)
MyString str2(str);
cout << str2.data() << endl;
#if 0
str.myDelete();
str2.myDelete();
#endif
return 0;
}
類的成員變量
四類特殊的成員變量
// const 必須寫在初始化成員列表中,值不可改
#include <iostream>
#include <string>
using namespace std;
class Person
{
public:
Person(): m_strName("newPerson")
, m_strDate("1999-11-17")
, m_strAddress("beijing")
{
}
Person(string name, string date
, string address)
: m_strDate(date)
{
m_strName = name;
m_strAddress = address;
}
void info()
{
cout << m_strName << ' ' << m_strDate
<< ' ' << m_strAddress << endl;
}
private:
string m_strName;
//const成員變量的初始化必須在初始化列表中進(jìn)行
const string m_strDate;
string m_strAddress;
};
int main(void)
{
Person p1;
p1.info();
Person p2("aa", "1999-11-11", "beijing");
p2.info();
return 0;
}
//static 初始化在類外,不獨(dú)立屬于任何一個(gè)對(duì)象,為所有成員共有
#include <iostream>
#include <string>
using namespace std;
class Product
{
public:
Product(string name, float price, int num)
{
m_strName = name;
m_fPrice = price;
iNum = num;
}
void info()
{
cout << m_strName << ' ' << m_fPrice
<< ' ' << iNum << endl;
}
void setNum(int num)
{
iNum -= num;
}
private:
string m_strName;
float m_fPrice;
int iNum;
};
class Saller
{
public:
Saller(string name)
{
m_strName = name;
}
void sell(int num)
{
cout << m_strName << "賣了" << num << "瓶\n";
m_product.setNum(num);
}
void showWork()
{
cout << m_strName
<< ":";
m_product.info();
}
private:
string m_strName;
//靜態(tài)的成員變量不獨(dú)立屬于某個(gè)對(duì)象
//為所有對(duì)象所共有
//類的大小不包括靜態(tài)的成員變量
//也不包括函數(shù)
static Product m_product;
};
//靜態(tài)的成員變量的初始化必須在類外進(jìn)行
Product Saller::m_product("可口可樂(lè)", 3, 100);
int main(void)
{
Saller s1("zhangsan");
Saller s2("lisi");
s1.sell(23);
s1.showWork();
s2.sell(30);
s2.showWork();
cout << "product size:" << sizeof(Product) << endl;
cout << "saller size:" << sizeof(Saller) << endl;
return 0;
}
//& 引用 初始化必須在成員列表中
#include <iostream>
#include <string>
using namespace std;
class Product
{
public:
Product(string name, float price, int num)
{
m_strName = name;
m_fPrice = price;
iNum = num;
}
void info()
{
cout << m_strName << ' ' << m_fPrice
<< ' ' << iNum << endl;
}
void setNum(int num)
{
iNum -= num;
}
private:
string m_strName;
float m_fPrice;
int iNum;
};
class Saller
{
public:
//若成員變量為引用
//則初始化必須在初始化列表中進(jìn)行
Saller(string name, Product &ref)
: m_product(ref)
{
m_strName = name;
}
void sell(int num)
{
cout << m_strName << "賣了" << num << "瓶\n";
m_product.setNum(num);
}
void showWork()
{
cout << m_strName
<< ":";
m_product.info();
}
private:
string m_strName;
Product &m_product;
};
class SuperMarket
{
public:
SuperMarket(): m_product("kele", 2, 100)
, m_saller("zhangsan", m_product)
, m_saller2("lisi", m_product)
{
}
void work()
{
m_saller.sell(20);
m_saller.showWork();
m_saller2.sell(18);
m_saller2.showWork();
}
private:
//如果一個(gè)類的對(duì)象作為另外一個(gè)類的成員變量
//那么將該對(duì)象稱之為子對(duì)象
//該對(duì)象的初始化必須在初始化列表進(jìn)行
Product m_product;
Saller m_saller;
Saller m_saller2;
};
int main(void)
{
SuperMarket sm;
sm.work();
cout << "product size:" << sizeof(Product) << endl;
cout << "saller size:" << sizeof(Saller) << endl;
cout << "supermarket size:"
<< sizeof(SuperMarket) << endl;
return 0;
}
//子對(duì)象 若類中有子對(duì)象,則先執(zhí)行子對(duì)象,再執(zhí)行父對(duì)象,析構(gòu)函數(shù)執(zhí)行順序相反
#include <iostream>
#include <string>
using namespace std;
class A
{
public:
~A()
{
cout << "called ~A()..." << endl;
}
A()
{
m_i = 0;
cout << "called A()..." << endl;
}
A(int i)
{
m_i = i;
cout << "called A(int i)..." << endl;
}
int m_i;
};
class B
{
public:
~B()
{
cout << "called ~B()...\n";
}
//B()
B():m_a(189)
{
cout << "called B()...\n";
}
//B(int j)
B(int j):m_a(90)
{
m_j = j;
cout << "called B(int j)...\n";
}
private:
//如果沒(méi)有在初始化列表中顯式的調(diào)用子對(duì)象的構(gòu)造函數(shù)
//那么會(huì)自動(dòng)默認(rèn)調(diào)用子對(duì)象的無(wú)參構(gòu)造函數(shù)來(lái)初始化
A m_a;
int m_j;
};
int main(void)
{
//若類中含有子對(duì)象,則先執(zhí)行子對(duì)象的構(gòu)造函數(shù)
//在執(zhí)行該類的構(gòu)造函數(shù)
//析構(gòu)函數(shù)的執(zhí)行順序和構(gòu)造函數(shù)的相反
// B b1;
B b2(12);
return 0;
}