簡體   English   中英

禁止 C++ 中的類復制

[英]Disallowing class copying in C++

當我想在 C++ 中禁止類復制時,我通常聲明一個私有 operator=和一個復制構造函數,但我不實現它們:

class MyClass
{
  char* _str;
  int _len;
  MyClass(const MyClass& rhs);            //No implementation
  MyClass& operator=(const MyClass& rhs); //No implementation
public:
  MyClass();
  MyClass(const char *);
}

這被認為是一種不好的風格嗎? 還有另一種方法可以做到這一點嗎?

在 C++11 中,您可以顯式刪除這些函數(這比省略實現更可取,因為它更具可讀性,並且它總是會生成編譯器錯誤,而不僅僅是鏈接器錯誤):

class MyClass
{
  char* _str;
  int _len;
  MyClass(const MyClass& rhs) = delete;
  MyClass& operator=(const MyClass& rhs) = delete;
public:
  MyClass();
  MyClass(const char *);
}

在 C++03 中,您可以使用諸如boost::noncopyable之類的基類來實現相同的效果。 這可能更具可讀性(這與您的方法基本相同 - 此基類具有私有復制構造函數和賦值運算符,因此從它繼承將使您的類不可復制):

class MyClass : boost::noncopyable
{
  char* _str;
  int _len;
public:
  MyClass();
  MyClass(const char *);
}

C++ 中淺拷貝和深拷貝之間的區別完全在於你如何實現你的拷貝構造函數(因為你的賦值運算符應該使用你的拷貝構造函數來實現)。 如果你沒有,那么淺拷貝和深拷貝都不可能,如果你有,這取決於它是如何實現的。

您可以創建一個預處理器宏來實現相同的目的,例如

#define DISABLE_COPY_AND_ASSIGN(className) private: \
    className(const className&); \
    className& operator=(const className&);

然后像這樣使用它:

class MyClass
{
   DISABLE_COPY_AND_ASSIGN(MyClass)
public:
   ....
};

您也可以從boost::noncopyable派生:

class MyClass : boost::noncopyable
{
public:
   ....
};

此外,在 C++11 中,您可以使用= delete

MyClass(const MyClass&) = delete;
MyClass& operator=(const MyClass&) = delete;

有兩種方法,兩者都會導致編譯錯誤:

C++11 方式:

class MyClass
{
  char* _str;
  int _len;
  MyClass(const MyClass& rhs) = delete;
  MyClass& operator=(const MyClass& rhs) = delete;
public:
  MyClass();
  MyClass(const char *);
};

C++03方式:

class MyClass
{
  char* _str;
  int _len;
public:
  MyClass();
  MyClass(const char *);

  MyClass(const MyClass& rhs);            //No implementation
  MyClass& operator=(const MyClass& rhs); //No implementation
}

如果你只是將復制構造函數聲明為 public,你會得到鏈接器錯誤,但編譯會通過。 由於編譯發生在鏈接之前,最好中斷編譯,因為您會更快地發現錯誤。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM