实用C++学习笔记5

37 类的静态成员

https://www.cctry.com/thread-290010-1-1.html

例如:Student类,加一个变量:校长master。如果定义为普通的成员变量,每个对象都要开个内存放master,而且如果换一个校长了,每个对象的master都要一个个修改。
这时可以定义为静态成员,在前面加static,这样这个成员就是属于类的而不是属于某个对象的(类似全局变量,但作用域是在整个类当中)

①、这样所有对象都可以直接访问这个静态成员变量,而且值是一样的;
②、静态成员变量在内存中只占用一份存储空间;
③、静态成员变量的值对于所有对象来说都是一样的。如果其中一个对象调用函数将其改变了,那么其他成员在访问这个静态成员变量的时候的值都是改变之后的;
④、只要在类中定义了类的静态成员变量,那么就占用存储空间了,不管有没有定义这个类的对象,因为静态成员变量不属于任何类对象,而是属于该类;
⑤、静态数据成员需要在类外进行声明或声明并初始化,否则在使用的时候会报链接的错误;例:int CStudent::master = 0;
⑥、类的静态成员在定义的时候需要加 static,在类外声明的时候不需要加 static 关键字;
⑦、不能用构造函数的参数初始化表的形式对静态成员进行初始化操作;
⑧、静态数据成员既可以通过对象名引用,也可以通过类名来直接引用,(一般都用类名引用,用以和普通成员区分开)CStudent::master
⑨、public 公有类型的静态数据成员,可以被类的对象引用,也可以直接用类名来引用。但如果静态数据成员被定义成private私有的,那么通过对象或者类名来引用都是不可以的,必须通过类的public类型的静态成员函数来引用了。

38 运算符重载

https://www.cctry.com/thread-290018-1-1.html

例:
之前在用对象赋值那里提到的,会让两个指针指向同一块内存的情况,可以重载等号=

CStudent& CStudent::operator=(const CStudent& stud)  //"operator="是函数名
//operator这个关键字不能变,后面跟着什么运算符就是重载什么运算符
//原来是stud2 = stud1;  在这里,相当于stud2是本对象,stud1是目标对象(参数的那个stud)
{
    if (p_name)
    {
        delete[] p_name;
        p_name = NULL;
    }

    int name_len = strlen(stud.p_name) + 1;
    p_name = new char[name_len];
    memset(p_name, 0, name_len);

    strcpy(p_name, stud.p_name);
    sex = stud.sex;
    num = stud.num;
    age = stud.age;
    return *this;
}

重载运算符的规则:

①、C++不允许用户自己定义新的运算符,只能对已有的C++运算符进行重载:
例如,在VB中可能有的人会使用运算符,例如:35,表示3的5次方,如果你想在C++中创建**运算符并实现重载,那是不行的。

②、C++允许与不允许重载的运算符如下图:

在这里插入图片描述

③、重载运算符不能改变运算符操作对象的个数:例如 > 和 < 运算符,本身是比较用的双目运算符,也就是说要有2个操作数,如果你重载完了之后变成不是2了,那肯定不行;
④、重载运算符不能改变运算符的优先级别,乘除 */ 运算符的优先级别大于±,如果你重载完了之后导致优先级改变了,那肯定也不行;
⑤、重载运算符不能改变运算符的结合性,例如,赋值运算符=是从右向左开始结合的,如果你重载完了之后导致从左往右了,那肯定也不行;
⑥、重载运算符的函数不能有默认的参数:不然就改变了运算符参数的个数,与第③点矛盾了;
⑦、重载运算符的函数参数至少有一个是本类的对象或引用,不能全部都是C++的基本类型,例如:CStudent& CStudent::operator+(int a, int b) 这种也是不行的;
⑧、重载运算符应该遵循运算符原有的含义,不能把+重载之后变成-的功能,虽然语法上没有错误,但是违背了重载运算符的初衷!

小作业:
为 CStudent 类重载 ==运算符,判断两个 CStudent 对象是否相等,或者说是否是同一个学生的数据。

#include <iostream>
#include <string>
using namespace std;

class CStudent
{
public:
	char* p_name;
	char sex;
	int num;
	int age;

public:

	CStudent() 
	{
		p_name = NULL;
	}

	CStudent(const char* t_name, char t_sex, int t_num, int t_age);

	CStudent& operator=(const CStudent& stud);

	bool operator==(const CStudent& stud);

	~CStudent();
};

CStudent::CStudent(const char* t_name, char t_sex, int t_num, int t_age) :sex(t_sex), num(t_num), age(t_age)
{
	int n_len = strlen(t_name) + 1;
	p_name = new char[n_len];
	memset(p_name, 0, n_len);

	strcpy_s(p_name, n_len, t_name);
}

CStudent& CStudent::operator=(const CStudent& stud)
{
	sex = stud.sex;
	num = stud.num;
	age = stud.age;

	if (p_name)
	{
		delete[] p_name;
		p_name = NULL;
	}

	int name_len = strlen(stud.p_name) + 1;
	p_name = new char[name_len];
	memset(p_name, 0, name_len); //初始化函数。作用是将某一块内存中的内容全部设置为指定的值, 这个函数通常为新申请的内存做初始化工作。
	strcpy_s(p_name, name_len, stud.p_name);
	return *this;
}

bool CStudent::operator==(const CStudent& stud)
{
	int flag = 1;
	if (*p_name != *stud.p_name)
	{
		flag = 0;
	}
	if (sex != stud.sex)
	{
		flag = 0;
	}
	if (num != stud.num)
	{
		flag = 0;
	}
	if (age != stud.age)
	{
		flag = 0;
	}
	if (flag == 1)
	{
		return true;
	}
	if (flag == 0)
	{
		return false;
	}
}

CStudent::~CStudent()
{
	if (p_name)
	{
		delete[] p_name;
		p_name = NULL;
	}
	cout << "CStudent::~CStudent()" << endl;
}

void test()
{
	CStudent stud_1("zhangsan", 'f', 1001, 20),stud_2;
	stud_2 = stud_1;
	if (stud_1 == stud_2)
	{
		cout << "是同一个学生" << endl;
	}
	else
	{
		cout << "不是同一个学生" << endl;
	}
}

int main()
{
	test();
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值