c++之构造和析构函数

本文详细介绍了C++中的构造函数和析构函数,包括它们的作用、分类和使用场景。此外,还讨论了类的静态成员变量及其初始化,以及`explicit`关键字在防止隐式类型转换中的应用。同时,文章讲解了深拷贝和浅拷贝的区别,强调在对象复制时确保内存管理的正确性。最后,提供了相关练习题以巩固理解。
摘要由CSDN通过智能技术生成

c++之构造函数和析构函数

int a=123;

对于整形变量a=123,创建它分为两个步骤
1、分配内存
2、对其进行初始化。

同样的对于类的对象也分为两个步骤:

People P;

1、分配内存
2、对其进行初始化——构造函数

一、什么是构造函数?

1、类的一种特殊成员函数
2、在每次创建类的新对象时执行
3、构造函数的名称与类的名称是完全相同的,不会返回任何类型

作用:构造函数用于为某些成员变量设置初始值。

二、构造函数的分类

1、默认构造函数
2、有参构造函数
3、拷贝构造函数
在这里插入图片描述

三、构造函数初始化

1、直接进行参数的初始化列表(效率快)

class Point
{
public:
int _x,_y;
Point(): _x(0),_y(0)
{
cout<<" default construct" <<endl;
}
};

2、在构造函数里进行赋值操作(效率慢)

class Point
{
public:
int _x,_y;
Point()
{
_x=0;
_y=0;
cout<<" default construct" <<endl;
}
};

进行构造函数,类已经完成了构造,发生的是赋值操作。

四、析构函数

1、类的一种特殊成员函数
2、在每次删除类对象时执行
3、析构函数的名称与类的名称是相同的,前面有一个~,并且不会返回任何类型。

在这里插入图片描述
作用:析构函数用于释放类对象管理的内存空间。

五、explicit关键字

1、explicit关键字用于修饰构造函数,防止隐式转换
2、针对单参数的构造函数。

class Test {
public:
    Test() {}  // 空构造函数
    explicit Test(double a); // 该构造函数无法进行隐式类类型转换
    ~Test() {}
};

// 调用
Test d1(12.3);  // 正确
Test d2 = 1.2;  // 错误,不能进行隐式类类型转换

在这里插入图片描述

6、类中含有静态变量

在这里插入图片描述
静态变量,是在编译阶段就分配空间,对象还没创建时,已经分配好空间了。

1、静态成员变量必须在类中声明,在类外定义。
2、静态数据成员不属于某个对象,在为对象分配空间中不包括静态成员所占空间。
3、静态数据成员可以通过类名或者对象名来引用。

#include<iostream>
using namespace std;
class Person{
public:
	//类的静态成员属性
	int a;
	static int sNum;
private:
	static int sOther;
};

//类外初始化,初始化时不加static
int Person::sNum = 0;
int Person::sOther = 0;


int main(){

//1. 通过类名直接访问
	Person::sNum = 100;
	cout << "Person::sNum:" << Person::sNum << endl;

	//2. 通过对象访问
	Person p1, p2;
	p1.sNum = 200;

	cout << "p1.sNum:" << p1.sNum << endl;
	cout << "p2.sNum:" << p2.sNum << endl;
	
//3. 静态成员也有访问权限,类外不能访问私有成员
	//cout << "Person::sOther:" << Person::sOther << endl;
	Person p3;
	//cout << "p3.sOther:" << p3.sOther << endl;

		cout<< sizeof(Person)<< <<endl;  //4字节

	return 0;
}


静态成员函数

1、静态成员函数只能访问静态变量,不能访问普通成员变量
2、静态成员函数的使用和静态成员变量一样
3、普通成员函数可访问静态成员变量、也可以访问非静态成员变量
4、静态成员函数也有访问权限。

7、深拷贝和浅拷贝

浅拷贝: 增加一个指针指向已存在的内存地址。
深拷贝: 增加一个指针并申请一个新的内存,增加的指针指向新的内存。

class People
{
public:
 People(int n):name(),age(n)
 {
 	name = new char[20];
 	memset(name,0,20);
 	strcpy(name,"sszzlll");
 	cout<<"int construct" <<endl;
 }
People(const People &p):name(),age(p.age)
{
 	name = new char[20];
 	memset(name,0,20);
 	strcpy(name,"sszzlll");
 	cout<<"int construct" <<endl;	
}
private:
int age;
char* name;

int main()
{
People p(15);
People p2(p);

cout<< "age" << p.age<<"name"<<p.name<<endl;
cout<< "age" << p2.age<<"name"<<p2.name<<endl;
p.name = new char[20];
memset(p1.name,0,20);
strcpy(p.name,"szl");
cout<< "age" << p.age<<"name"<<p.name<<endl;
cout<< "age" << p2.age<<"name"<<p2.name<<endl;
return 0;
}
};

总之深拷贝与浅拷贝的主要区别是:在对象状态中包含其它对象的引用。 当拷贝一个对象时。需要拷贝这个对象引用的对象,则是深拷贝。

练习题:
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值