为什么做网站要有自己的服务器,制作衣服的软件app,广东seo推广价格,唐山软件开发公司排名一.浅拷贝和深拷贝
1.引入
从上篇博客拷贝构造我们知道拷贝构造要传引用而不能传值#xff0c;否则会发生无穷递归的情况。 1.若未显示定义拷贝构造函数#xff0c;系统会生成默认的拷贝构造函数。默认的拷贝构造按内存序完成拷贝#xff0c;我们称之为浅拷贝#xff08;…一.浅拷贝和深拷贝
1.引入
从上篇博客拷贝构造我们知道拷贝构造要传引用而不能传值否则会发生无穷递归的情况。 1.若未显示定义拷贝构造函数系统会生成默认的拷贝构造函数。默认的拷贝构造按内存序完成拷贝我们称之为浅拷贝值拷贝。注对内置类型按照字节方式拷贝而自定义类型调用其的拷贝构造函数。 2.浅拷贝就是新拷贝的对象和原对象指向同一块空间新拷贝的对象的值的改变也会引发原对象的值的改变。 3.深拷贝实质是在内存里重新为新拷贝的对象开辟一块空间不指向同一块空间。 2.问题
我们拷贝日期这样的类用浅拷贝是没问题的年月日都是在栈上创建销毁由系统开空间的释放空间的但是如果这样的类呢 class String
{
public:String(const char* str jack){_str (char*)malloc(strlen(str) 1);strcpy(_str, str);}~String(){cout ~String() endl;free(_str);}
private:char* _str;
};
int main()
{String s1(hello);String s2(s1);
}_str是我们malloc出来在堆上的空间需要我们自己调用析构free掉s2拷贝构造s1编译器自动生成的默认拷贝函数会使s2和s1指向同一块空间先定义的对象先析构s1先析构掉这块开好的空间s2再次析构时这块空间已经被释放掉了程序报错。
二.运算符重载
1.概念
C为了增强代码的可读性引入了运算符重载运算符重载是具有特殊函数名的函数也具有其返回值类型函数名字以及参数列表其返回值类型与参数列表与普通的函数类似
函数名字为关键字operator后面接需要重载的运算符符号。 函数原型返回值类型 operator操作符(参数列表) 不能通过连接其他符号来创建新的操作符比如operator 重载操作符必须有一个类类型参数 用于内置类型的运算符其含义不能改变例如内置的整型不 能改变其含义 作为类成员函数重载时其形参看起来比操作数数目少1因为成员函数的第一个参数为隐藏的this .* :: sizeof ?: . 注意以上5个运算符不能重载。这个经常在笔试选择题中出现。 例如以下在.h中声明再cpp中实现的运算符
bool Date::operator(const Date d)const
{return (_year d._year)|| ((_year d._year) (_month d._month))|| (_year d._year) (_month d._month) (_day d._day);
}写一个和就足够了剩下的代码复用就行.
2.赋值运算符重载
2.1注意
赋值运算符主要注意以下几点 1.参数类型const T传递引用可以提高传参效率 2.返回值类型T返回引用可以提高返回的效率有返回值目的是为了支持连续赋值 3.检测是否自己给自己赋值 4.返回*this 要符合连续赋值的含义 //d1d3Date operator(const Date d)//引用作返回值,不用调用拷贝构造存临时变量{_year d._year;_month d._month;_day d._day;return *this;}2.2 赋值运算符只能重载成类的成员函数不能重载成全局函数 原因赋值运算符如果不显式实现编译器会生成一个默认的。此时用户再在类外自己实现一个全局的赋值运算符重载就和编译器在类中生成的默认赋值运算符重载冲突了故赋值运算符重载只能是类的成员数。 用户没有显式实现时编译器会生成一个默认赋值运算符重载以值的方式逐字节拷贝。注意内置类型成员变量是直接赋值的而自定义类型成员变量需要调用对应类的赋值运算符重载完成赋值。 2.3涉及资源管理避免默认生成的拷贝构造
同上浅拷贝和深拷贝的问题
3. 前置和后置的运算符重载
Date Date::operator(int)
{Date ret(*this);*this 1;return ret;
}
Date Date::operator()
{*this 1;return *this;
}前置先加加后使用后置先使用再加加为了区分C规定后置重载时多增加一个int类型的参数但调用函数时该参数不用传递编译器自动传递。