c++面对对象的三大特性:封装,继承和多态
封装的意义:
将属性和行为作为一个整体,表现生活中的事务
将属性和行为加以权限控制
语法:class 类型{访问权限:属性/行为}
访问权限:
1.公共public:类内可以访问,内外也可以访问
2.保护权限protected:类内可以访问,内外也可以访问
3. private:类内可以访问,内外也可以访问
在c++中strcut和class的唯一区别就是默认的访问权限
区别:
strcut:默认为public
class:默认为private;
成员属性设置为私有:
优点1:可以自己控制读写权限
优点2:可以检测数据的有效性
对象的初始化和清理:
构造函数:主要作用在于创建对象时为对象的成员属性赋值,构造函数由编译器自动调用,无需手动调用
析构函数: 主要用于对象销毁前系统自动调用,执行一些清理工作
构造函数语法:类名(){}
1.构造函数,没有返回值,也不写void
2.函数名称与类名称相同
3.构造函数可以有参数,可以发生重载
4.程序在调用对象时会自动调用,无须手动调用,而且只会调用一次
构造函数语法:~类名(){}
1.析构函数,没有返回值,也不写void
2.函数名称与类名称相同
3.析构函数不可以有参数,不可以发生重载
4.程序在对象销毁前自动调用析构,无须手动调用,而且只会调用一次
构造函数的分类:
1.有参构造和无参构造
2.按类型分为:普通构造和拷贝构造
三种调用方法:
1.括号法
2.显示法
3.隐式转换法
#include <iostream> #include <ostream> using namespace std; #include <string> //设置私有后,可以自己控制读写权限 //对于写可以检测数据的有效性 class person { public: //1.1 构造函数 //1.1 没有返回值也没有void //1.2 函数名和类名相同 //1.3 构造函数可以有参数,可以发生重载 //1.4 创建对象的时候,构造函数会自动调用,而且只会调用一次 person() //普通默认构造函数 { cout << "person的默认 构造函数的调用" << endl; } person(int a) //普通有参构造函数 { m_age = a; cout << "person的有参构造函数的调用" << endl; } person(const person &p) //拷构造函数 { m_age = p.m_age; cout << "person的拷贝构造函数的调用" << endl; } //拷贝构造函数 ~person() //默认析构函数 { cout << "person的析构函数的调用" << endl; } int m_age; }; void test01() { //调用 //1.括号法 person p1; person p2(10); person p3(p2); cout << p2.m_age << endl; cout << p3.m_age << endl; //调用默认构造的时候不要加小括号,编译器会认为这是一个函数的声明 //2.显示法 person p4 = person(); person p5 = person(10); person p6 = person(p5); //person(10) 匿名对象 特点:当前行执行完毕后,会立即进行析构 //不要利用拷贝构造函数初始化匿名对象 //编译器会认为这是一个对象的声明 //3.隐式转换法 person p8 = 10; person p9 = p8; } int main() { test01(); system("pause"); return 0; }
拷贝构造函数调用时机:
1.使用一个已经初始化的对象来初始化一个新对象;
2.值传递的方式给函数参数传值
3.以值方式返回局部对象
#include <iostream>
#include <ostream>
using namespace std;
#include <string>
//拷贝构造函数的调用时机:
//1.使用一个已经创建完毕的对象来初始化一个新对象
class person
{
public:
person()
{
cout << "person的默认构造函数" << endl;
}
person(int a)
{
m_age = a;
cout << "person的有参构造函数" << endl;
}
person(const person &p)
{
m_age = p.m_age;
cout << "person的拷贝构造函数" << endl;
}
~person()
{
cout << "person的析构函数" << endl;
}
int m_age;
};
//1.以已经创建的对象创建一个新的对象
void test01()
{
person p1(10);
person p2(p1);
}
//2.值传递的方式给函数参数传值
void test02(person p)
{
cout << "1111" << endl;
}
//3.以值得方式返回局部变量
person test03()
{
person p1(10);
return p1;
}
int main()
{
//test01();
//person p1(10);
//test02(p1);
person p2=test03();
system("pause");
return 0;
}
默认情况下:c++至少给一个类添加3个函数
1.默认构造函数(无参,函数体为空)
2.默认析构函数(无参,函数体为空)
3,默认拷贝构造函数,对属性进行值拷贝
调用规则:
1.如果用户定义有参构造函数,编译器不在提供给默认构造,但是提供拷贝构造函数
2.如果用户定义了一个拷贝构造函数,编译器不在提供其他构造函数
深拷贝和浅拷贝
1.浅拷贝:简单的赋值拷贝操作:带来的问题时堆区的内存重复释放
2.深拷贝:在堆区重新申请空间,进行赋值操作
#include <iostream>
#include <ostream>
using namespace std;
#include <string>
//拷贝构造函数的调用时机:
//1.使用一个已经创建完毕的对象来初始化一个新对象
class person
{
public:
person()
{
cout << "person的默认构造函数" << endl;
}
person(int a,int height)
{
m_age = a;
m_height = new int(height);
cout << "person的有参构造函数" << endl;
}
person(const person &p)
{
m_age = p.m_age;
m_height = new int(*p.m_height);
cout << "person的拷贝构造函数" << endl;
}
~person()
{
//将堆区开发的数据进行释放
if(m_height != NULL)
{
delete m_height;
m_height = NULL;
}
cout << "person的析构函数" << endl;
}
int m_age;
int *m_height;
};
void test01()
{
person p1(18,180);
cout << p1.m_age << endl;
cout << *p1.m_height << endl;
person p2(p1);
cout << p2.m_age << endl;
cout << *p2.m_height << endl;
}
int main()
{
test01();
system("pause");
return 0;
}
初始化列表:
c++提供了初始化列表语法,用来初始化属性
语法:构造函数():属性1(值1),属性2(值2),属性3(值3){}
静态成员:在成员变量和成员函数前加上关键字static,称为静态成员
静态成员分为:
静态成员变量:
1.所有对象共享同一份数据
2.在编译阶段分配内存
3.类内声明,类外初始化
静态成员函数:
1.所有对象共享同一个函数
2.静态成员函数只能访问静态成员变量
#include <iostream>
#include <ostream>
using namespace std;
#include <string>
//拷贝构造函数的调用时机:
//1.使用一个已经创建完毕的对象来初始化一个新对象
class person
{
public:
static void func()
{
m_A = 100; //静态成员函数可以访问静态成员变量
//m_B = 200; 静态成员函数不可以访问非静态成员变量
//无法区分是那个对象上的m_b;
cout << "静态成员函数的运行" << endl;
}
static int m_A;
int m_B;
};
int person::m_A = 10;
int main()
{
person p1;
person p2;
cout << p1.m_A << endl;
cout << p2.m_A << endl;
//通过对象访问:
p1.func();
//通过类名访问:
person::func();
//静态成员不属于某个对象上,所有对象共享同一份数据
//可以通过对象访问
//可以通过类名访问
cout << person::m_A << endl;
system("pause");
return 0;
}
#include <iostream>
#include <ostream>
using namespace std;
#include <string>
class person
{
public:
int m_A; //非静态成员变量:属于类的对象上
static int m_B; //静态成员变量:不属于类的对象上
void func(){} //非静态成员函数:不属于类的对象上
static void func1() {} //非静态成员函数:不属于类的对象上
};
int person::m_B=20;
int main()
{
person p1;
//空对象所占用内存空间为1:
//c++编译器会给每一个空对象也分配一个字节的内存空间;
//是为了区分空对象占内存的位置
//每个空对象也应该有独一无二的内存位置
cout << "size of p=" << sizeof(p1) << endl;
cout << sizeof(p1);
system("pause");
return 0;
}
#include <iostream>
#include <ostream>
using namespace std;
#include <string>
//抽象的cpu类:
class CPU
{
public:
virtual void calculate() = 0;
};
class VideoCard
{
public:
virtual void display() = 0;
};
class Memory
{
public:
virtual void storage() = 0;
};
//电脑类 computer
class Computer
{
public:
Computer(CPU * cpu,VideoCard * vc,Memory *mem)
{
m_CPU = cpu;
m_VideoCard = vc;
m_Memory = mem;
}
~Computer()
{
if(m_CPU != NULL)
{
delete m_CPU;
m_CPU = NULL;
}
if (m_VideoCard != NULL)
{
delete m_VideoCard;
m_VideoCard = NULL;
}
if (m_Memory != NULL)
{
delete m_Memory;
m_Memory = NULL;
}
}
void work()
{
m_CPU->calculate();
m_VideoCard->display();
m_Memory->storage();
}
private:
CPU *m_CPU;
VideoCard *m_VideoCard;
Memory *m_Memory;
};
//具体厂商
class interCpu:public CPU
{
public:
virtual void calculate()
{
cout << "interd的CPU开始计算了" << endl;
}
};
class interVideoCard :public VideoCard
{
public:
virtual void display()
{
cout << "interd的VideoCard开始计算了" << endl;
}
};
class interMemory :public Memory
{
public:
virtual void storage()
{
cout << "interd的Memory开始计算了" << endl;
}
};
class LenovoCpu :public CPU
{
public:
virtual void calculate()
{
cout << "Lenovo的CPU开始计算了" << endl;
}
};
class LenovoVideoCard :public VideoCard
{
public:
virtual void display()
{
cout << "Lenovo的VideoCard开始计算了" << endl;
}
};
class LenovoMemory :public Memory
{
public:
virtual void storage()
{
cout << "Lenovo的Memory开始计算了" << endl;
}
};
void test01()
{
//第一台电脑零件
CPU * interCPU = new interCpu;
VideoCard * videocard = new interVideoCard;
Memory * memory = new interMemory;
//创建第一台电脑
Computer * m_computer = new Computer(interCPU, videocard, memory);
m_computer->work();
delete m_computer;
}
int main()
{
test01();
system("pause");
return 0;
}