玩命加载中 . . .

13.2-拷贝控制与资源管理


13.2 拷贝控制与资源管理

13.2.1 行为像值的类

行为像值的类拷贝时要先拷贝源对象的资源,再释放当前对象的资源,再指向新的资源

class Person {
private:
    string *ptr;
    int age;

public:
    Person(const string &s = string()) : ptr(new string(s)), age(0) {}
    Person(const Person &p) : ptr(new string(*p.ptr)), age(p.age) {}
    Person& operator=(const Person& rhs) {
        cout << "copy assignment" << endl;
        auto newptr = new string(*rhs.ptr); // 拷贝资源
        delete ptr;     // 释放当前对象的资源
        ptr = newptr;   // 指针指向新的资源
        age = rhs.age;
        return *this;
    }
    ~Person() { delete ptr; }
};

int main(int argc, char const *argv[]) {
    Person p1("kavin");
    Person p2;
    p2 = p1;
    return 0;
}
// copy assignment

13.2.2 行为像指针的类

行为像指针的类拷贝时两个对象的指针指向同一块资源,使用计数器统计资源的用户数量,当用户数量为0时释放资源,类似于shared_ptr

class Person
{
private:
    string *ptr;
    int age;
    size_t *use;

public:
    Person(const string &s = string()) : ptr(new string(s)), age(0), use(new size_t(1)) {}
    Person(const Person &p) : ptr(p.ptr), age(p.age), use(p.use) { *use++; }
    Person& operator=(const Person& rhs) {
        ++*rhs.use;         // 先递增左侧对象的引用计数
        if (--*use == 0) {  // 再递减右侧对象的引用计数
            delete ptr;
            delete use;
        }
        ptr = rhs.ptr;
        age = rhs.age;
        use = rhs.use;
        return *this;
    }
    ~Person() {
        if (--*use == 0) {  // 引用计数为0就释放资源
            delete ptr;
            delete use;
        }
    }
    void info() { cout << *use << endl; }
};

int main(int argc, char const *argv[])
{
    Person p1("kavin");
    Person p2;
    p2 = p1;
    p2.info();
    return 0;
}
2

文章作者: kunpeng
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 kunpeng !
  目录