浅拷贝:简单来说就是值拷贝,数据的拷贝。一般是默认构造函数
深拷贝:地址的拷贝,数据之间相互独立
写时拷贝:指用浅拷贝的方法拷贝其他对象,多个指针指向同一块空间,只有当对其中一个对象修改时,才会开辟一个新的空间给这个对象,和它原来指向同一空间的对象不会收到影响。一个对象的值改变与之相对应的也改变
#include<iostream>
#include<vld.h> //一个检查内存泄露的工具vld
using namespace std;
class String; //声明string类
ostream& operator<<(ostream &out, const String &s);//申明重载输出流<<
class String_rep
{
friend ostream& operator<<(ostream &out, const String &s); //友元函数
friend class String;
public:
String_rep(const char *str) : use_count(0) //构造函数
{
data = new char[strlen(str)+1];
strcpy(data, str);
}
String_rep(const String_rep &rep) : use_count(0)//拷贝构造函数
{
data = new char[strlen(rep.data)+1];
strcpy(data, rep.data);
}
String_rep& operator=(const String_rep &rep)//赋值语句
{
if(this != &rep) //自对比“这里牵扯到一个概念叫做 异常安全性! 大家可以去查找一下”
{
String_rep tmp = rep;
char *ptmp = data; //首先创建一个临时变量 然后使原有的data与临时data所交换
data = tmp.data; //并且不需要释放空间,因为是临时变量出了这个区域就会被系统默认析构
tmp.data = ptmp;
}
return *this;
}
~String_rep() //析构函数
{
delete []data;
data = NULL;
}
public:
void increment() //引用技术增加
{
++use_count;
}
void decrement() //引用技术减少
{
if(--use_count == 0)
delete this;
}
private:
char *data;
int use_count;
};
class String
{
friend ostream& operator<<(ostream &out, const String &s);
public:
String(const char *str="") //构造函数
{
rep = new String_rep(str);
rep->increment();
}
String(const String &s) : rep(s.rep) //拷贝构造函数
{
rep->increment();
}
String& operator=(const String &s)//赋值语句
{
if(this != &s)
{
rep->decrement();
rep = s.rep;
rep->increment();
}
return *this;
}
~String()
{
rep->decrement();
rep = NULL;
}
public:
void toupper()
{
String_rep *new_rep = new String_rep(rep->data);
rep->decrement();
rep = new_rep;
rep->increment();
char *ch;
for(ch=rep->data; *ch!='\0'; ++ch)
(*ch) -= 32;
}
private:
String_rep *rep; //句柄
};
ostream& operator<<(ostream &out, const String &s)
{
out<<s.rep->data;
return out;
}
void main()
{
String s("hello");
String s1 = s;
String s2("linux");
s2 = s1;
cout<<"s = "<<s<<endl;
cout<<"s1 = "<<s1<<endl;
s.toupper();
cout<<"s = "<<s<<endl;
cout<<"s1 = "<<s1<<endl;
}