c++11 拷贝构造函数,移动构造函数 调用小结

最近回顾了一下c++11移动语义,结合程序做一下验证。废话不多说,直接上代码。

   1 #include 
   2 using namespace std;
   3 
   4 #define PRINT_FUNC  std::cout << "func: " << __func__ << ":" << __LINE__ << std::endl;
   5 #define PRINT_LINE  std::cout << "================================================================\n"; 
   6 
   7 namespace ns_1                                                                                             
   8 {
   9     class HasPtrMem
  10     {
  11     public:
  12         HasPtrMem()                     {   PRINT_FUNC;         }
  13         ~HasPtrMem()                    {   PRINT_FUNC;         }
  14         HasPtrMem(const HasPtrMem&)     {   PRINT_FUNC;         }
  15         HasPtrMem& operator = (const HasPtrMem&)       {    PRINT_FUNC;        }
  16 
  17         HasPtrMem(HasPtrMem&&)  {   PRINT_FUNC; }       
  18         HasPtrMem& operator = (const HasPtrMem&&)       {    PRINT_FUNC;        }
  19     };
  20 
  21     HasPtrMem test1_help()
  22     {
  23         return HasPtrMem();
  24     }
  25 
  26     void test_1()
  27     {
  28         PRINT_LINE;
  29         {   // block 1
  30             HasPtrMem a = test1_help();     //  block 1
  31         }
  32         PRINT_LINE;
  33         {   // block 2
  34             HasPtrMem a;
  35             a = test1_help();
  36         }
  37         PRINT_LINE;
  38         {   // block 3
  39             std::cout << "with no move constructor const &: \n";
  40             const HasPtrMem& a = test1_help();
  41         }
  42         PRINT_LINE;
  43         {   //block 4
  44             std::cout << "with no move constructor &&: \n";
  45             HasPtrMem&& a = test1_help();
  46         }
  47         PRINT_LINE;
  48     }
  49 };
  50 
  51 
  52 int main()
  53 {
  54     ns_1::test_1();
  55     return 0;
  56 }   

编译指令:g++ 1.cpp -fno-elide-constructors --std=c++11


1)对于block1代码

HasPtrMem a = test1_help(); 

在c++11 之前(即无移动赋值,无移动构造的时候), 调用流程是:构造函数+拷贝构造函数

func: HasPtrMem:12
func: HasPtrMem:14
func: ~HasPtrMem:13
func: HasPtrMem:14
func: ~HasPtrMem:13
func: ~HasPtrMem:13

当加上了移动赋值,移动构造的时候, 调用流程是:构造函数+移动构造函数

func: HasPtrMem:12
func: HasPtrMem:17
func: ~HasPtrMem:13
func: HasPtrMem:17
func: ~HasPtrMem:13
func: ~HasPtrMem:13

2)对于 block 2 的代码

HasPtrMem a;
a = test1_help();

在c++11 之前(即无移动赋值,无移动构造的时候), 调用流程是:构造函数+构造函数+拷贝构造函数+拷贝赋值函数

func: HasPtrMem:12
func: HasPtrMem:12
func: HasPtrMem:14
func: ~HasPtrMem:13
func: operator=:15
func: ~HasPtrMem:13
func: ~HasPtrMem:13

当加上了移动赋值,移动构造的时候, 调用流程是:构造函数+构造函数+移动构造函数+移动赋值函数

func: HasPtrMem:12
func: HasPtrMem:12
func: HasPtrMem:17
func: ~HasPtrMem:13
func: operator=:18
func: ~HasPtrMem:13
func: ~HasPtrMem:13

3)对于 block 3 的代码

const HasPtrMem& a = test1_help();

在c++11 之前(即无移动赋值,无移动构造的时候), 调用流程是:构造函数+拷贝构造函数

func: HasPtrMem:12
func: HasPtrMem:14
func: ~HasPtrMem:13
func: ~HasPtrMem:13

当加上了移动赋值,移动构造的时候, 调用流程是:构造函数+移动构造函数

func: HasPtrMem:12
func: HasPtrMem:17
func: ~HasPtrMem:13
func: ~HasPtrMem:13

4)对于 block 4 的代码

HasPtrMem&& a = test1_help();

在c++11 之前(即无移动赋值,无移动构造的时候), 调用流程是:构造函数+拷贝构造函数

func: HasPtrMem:12
func: HasPtrMem:14
func: ~HasPtrMem:13
func: ~HasPtrMem:13

当加上了移动赋值,移动构造的时候, 调用流程是: 构造函数+移动构造函数

func: HasPtrMem:12
func: HasPtrMem:17
func: ~HasPtrMem:13
func: ~HasPtrMem:13

经过以上测试,可以得出当在类中添加移动构造函数和移动赋值的时候,系统会调用构造函数,移动构造函数, 移动赋值函数; 否则系统会调用 构造函数, 拷贝构造函数, 拷贝赋值构造函数;当添加了移动构造函数
代码块 block3 和 block4 的执行流程是一致的。

你可能感兴趣的:(c++11 拷贝构造函数,移动构造函数 调用小结)