【C++】引用计数写时拷贝

为什么要引入引用计数写时拷贝?

使用浅拷贝不浪费内存空间却容易发生内存泄漏问题,使用深拷贝不会发生内存泄漏但是会不断开辟新的空间,内存利用率低。

因此结合深浅拷贝的优点产生了写时拷贝。

在String类中添加新成员变量_pcount来计算指向同一段内存空间的指针的数目,若果要修改成员变量,当指针数目为小于等于1时就可以释放空间,大于1则另开辟空间来保存新的数据。

代码如下:

#include<iostream>
#include<stdio.h>
#include<string.h>
using namespace std;
class String{
  public:
    String(const char* str=""){
      _str=new char[strlen(str)+1];
      strcpy(_str,str);
      _pcount=new int(1);
    }
    String(const String& s){
      _str=s._str;
      _pcount=s._pcount;
      ++(*_pcount);
    }
    //不能直接释放_str,因为_str指向的空间的指针不止一个
    String& operator=(const String& s){
      if(_str!=s._str) {
        if(--(*_pcount)==0){
          delete[] _str;
          delete _pcount;
        }
        _str=s._str;
        _pcount=s._pcount;
        ++(*_pcount);
      }
      return *this;
    }
    //修改某一变量的值
    //先开辟新的空间,拷贝,修改
    //对某一变量进行修改不会影响其他变量的数据
    void CopyOnWrite(){
      if(*_pcount>1){
        char* tmp=new char[strlen(_str)+1];
        strcpy(tmp,_str);
        --(*_pcount);

        _str=tmp;
        _pcount=new int(1);
      }
    }
    char& operator[](size_t pos){//是一个可读可写的接口
      CopyOnWrite();
      return _str[pos];
    }
    char* c_str(){
      return _str;
    }
    ~String(){
      if(--(*_pcount)){
        delete[] _str;
        delete[] _pcount;
      }
    }
  private:
    char* _str;
    int* _pcount;
};
void Test(){
  String s1("hello");
  String s2(s1);
  s1[0]='x';
  cout<<s1.c_str()<<endl;
  cout<<s2.c_str()<<endl;
}
int main(){
  Test();
}

猜你喜欢

转载自blog.csdn.net/moralin_/article/details/81094592
今日推荐