effective c++条款06:若不想使用编译器自动生成的函数,就该明确拒绝

版权声明:转载请注明出处,谢谢!!! https://blog.csdn.net/qhdhnbd110/article/details/83036777

假如你创建了一个类用来表示世界上的每一个人:

class aPerson
{
    //...
};

每一个人都是独一无二的,所以为一个人做一个副本显得有悖伦理道德,那么我们就应该禁止拷贝构造和copy assignment操作(统称为copying 函数)。

不幸的是,如果我们自己没有实现copying函数,那么编译器会自作多情的为我们实现一份。所以为了覆盖它们,我们需要自己实现copying函数,然而如果自己实现了copying函数,那么和编译器自动生成的又有什么区别呢,那不是多此一举吗?

为了解决这个问题,我们首先

(1). 可以将自己生成的copying函数声明为private,这样当用户企图做一份副本时编译器就会报错。

class MyClass
{
private:
    int SomeValue;
private:
    MyClass(const MyClass &Temp):SomeValue(Temp.SomeValue){}
    MyClass &operator =(const MyClass &Temp)
    {
        SomeValue = Temp.SomeValue ;
        return *this;
    }
};

但当你使用member函数或者是friend函数时,还是有可能调用private函数。

(2). 我们可以仅声明copying函数,而不去定义它们,这样当用户企图做一份副本时链接器也会报错。

class MyClass
{
private:
    int SomeValue;
private:
    MyClass(const MyClass &Temp);
    MyClass &operator =(const MyClass &Temp);
};

如果项目很大,编译过程很长,等到链接器报错岂不是白白编译了半天?能不能把错误提前到编译期呢?

(3). 我们只需要定义一个父类,将父类的copying函数声明为private,然后用类去继承它即可。

class NoCopy
{
//...
private:
    NoCopy(const NoCopy &Temp);
    NoCopy &operator =(const NoCopy &Temp);
//...
};
class MyClass private: NoCopy
{
    //不需要再次实现copying函数
};

这么做的理由是:如果你试图给一个MyClass对象做一个副本,那么编译期自动生成的copying函数就会尝试调用父类中的copying函数(因为子类的copying函数只复制子类成员,父类成员也需要复制),而父类中copying函数为private。

猜你喜欢

转载自blog.csdn.net/qhdhnbd110/article/details/83036777