《C++文章匯總》
上一篇介紹了引用和匯編《06-封裝、內存布局、堆、構造和析構》,本文介紹內存管理、命名空間和繼承。
1.內存管理:自己創建的自己釋放,自己惹的禍,自己承擔
struct Car {
int price;
Car(){
cout << "Car::Car()" << endl;
}
~Car(){
cout << "Car::~Car()" << endl;
}
};
struct Person {
int m_age;
Car *car;
//用來做初始化的工作
Person(){
m_age = 0;
car = new Car;
cout << "Person::Person()" << endl;
}
//用來做內存清理的工作
~Person(){
delete car;
cout << "Person::~Person()" << endl;
}
};
int main(){
//內存泄露:該釋放的內存沒有得到釋放
{
Person person;
}
getchar();
return 0;
}
//輸出
Car::Car()
Person::Person()
Car::~Car()
Person::~Person()
image
圖片.png
image
圖片.png
2.聲明和實現分離
//Person.hpp文件
class Person {
private:
int m_age;
public:
void setAge(int age);
int getAge();
Person();
~Person();
};
//Person.cpp文件
#include "Person.hpp"
void Person::setAge(int age){
m_age = age;
}
int Person::getAge(){
return m_age;
}
Person::Person(){
m_age = 0;
}
Person::~Person(){
};
調用
#include "Person.hpp"
int main(){
Person person;
person.setAge(10);
cout << "age is " << person.getAge() << endl;
getchar();
return 0;
}
//輸出
age is 10
3.命名空間:命名空間可以用來避免命名沖突
3.1 命名空間的基本用法
class Person{
int m_age;
};
namespace Cloud {
int m_age;
void func(){
cout << "Cloud::func" << endl;
};
class Person{
int m_age;
int m_name;
};
}
int main(){
Cloud::m_age = 10;
Cloud::func();
// Cloud::Person person;
// cout << sizeof(person) << endl;
getchar();
return 0;
}
//輸出
Cloud::func
二義性:不同命名空間相同名字函數
image
外部和命名空間同時有相同名字函數func,要調用func,此時存在全局默認的命名空間,沒有名字,要調用函數用::
有個默認的全局命名空間,我們創建的命名空間默認都嵌套在它里面
圖片.png
class Person{
int m_age;
};
namespace Cloud {
int m_age;
void func(){
cout << "Cloud::func" << endl;
};
class Person{
int m_age;
int m_name;
};
}
void func(){
cout << "func()" << endl;
}
namespace Fish {
int m_age;
void func(){
cout << "Fish::func()" << endl;
};
}
int main(){
using namespace Cloud;
using namespace Fish;
// m_age = 1;//二義性,Cloud和Fish里面均有m_age
Fish::func();
::func();
::Cloud::func();
// Cloud::m_age = 10;
// Cloud::func();
// Cloud::Person person;
// cout << sizeof(person) << endl;
getchar();
return 0;
}
//輸出
Fish::func()
func()
Cloud::func
3.2 命名空間的合并
以下兩種寫法是等價的
namespace ManKind {
int m_name;
}
namespace ManKind {
int m_sex;
}
合并
namespace ManKind {
int m_name;
int m_age;
}
.h和.cpp文件中的命名空間
namespace A {
class Person{
int m_age;
int m_name;
Person();
~Person();
};
}
namespace A {
Person::Person(){};
Person::~Person(){};
}
3.3 其他編程語言的命名空間
? Java
Package
? Objective-C
類前綴
4.繼承
4.1繼承的基本特性
? 繼承,可以讓子類擁有父類的所有成員(變量\函數)
? 關系描述
? Student是子類(subclass,派生類) ? Person是父類(superclass,超類)
? C++中沒有像Java、Objective-C的基類 Java:java.lang.Object Objective-C:NSObject
struct Person {
int m_age;
void run(){};
};
struct Student:Person{
int m_score;
void study(){};
};
struct Worker:Person{
int m_salary;
void work(){};
};
int main(){
return 0;
}
4.2 繼承的成員變量在內存布局
? 父類的成員變量在前,子類的成員變量在后
image
5.成員訪問權限
? 成員訪問權限、繼承方式有3種
public:公共的,任何地方都可以訪問(struct默認)
protected:子類內部、當前類內部可以訪問
private:私有的,只有當前類內部可以訪問(class默認)
struct Person {
public:
int m_age;
};
struct Student:private Person{
};
struct GoodStudent:Student{
void work(){
m_age = 10;//會報錯,因為Person是私有繼承,無法在子類中直接訪問m_age
}
};
? 子類內部訪問父類成員的權限,是以下2項中權限最小的那個
成員本身的訪問權限
上一級父類的繼承方式
? 開發中用的最多的繼承方式是public,這樣能保留父類原來的成員訪問權限
? 訪問權限不影響對象的內存布局
struct Person {
private:
int m_age;
public:
void setAge(int age){
m_age = age;
}
int getAge(){
return m_age;
}
};
struct Student:public Person{
};
struct GoodStudent:Student{
void work(){
setAge(10);
getAge();
}
};
通過class定義一個類,繼承的默認方式為private
通過struct定義一個類,繼承的默認方式為public