目录

0. 前言

  c++默认赋值构造函数的返回值是引用类型,c++赋值运算符=的本意是返回左值的引用,我们重载赋值构造函数的时候,返回值是否应该设为引用类型呢? 按照《Effective C++》中第10条,最好是设为引用类型。

  本文,通过实验来表述返回值是否为引用类型的区别。

1. 内置类型

  int i= 1,     j=2,    k=3;

  • case1: k = j = i

    i == 1

  j == 1

  k == 1

  • case2: (k = j) = i

    i == 1

  j == 2

  k == 1

2. 自定义类型

  People p1("p1"),     p2("p2"),     p3("p3");

  • case1: p3 = p2 = p1
    • 使用默认赋值构造函数

      p3 == p1

    p2 == p1

    • 返回引用的People

      p3 == p1

  p2 == p1

    • 不返回引用的People

      p3 == p1

    p2 == p1

  • case2: (p3 = p2) = p1
    • 使用默认赋值构造函数

       p3 == p1

    p2 == p2

    • 返回引用的People

  p3 == p1

  p2 == p2

    • 不返回引用的People

      p3 == p2

    p2 == p2

3. 结论

  • case1,是否返回引用没有影响;
  • case2,是否返回引用是有区别的,由于c++内置类型的赋值重载操作符是返回引用的,所以我们应该遵循规则,类的赋值构造函数返回引用类型

4. 实验源码

#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cwchar>
#include <functional>
#include <iostream>
#include <iomanip>
#include <iterator>
#include <string>
#include <vector>
#include <memory> #include <sstream>
#include <utility> using std::cout;
using std::endl;
using std::string;
using std::vector;
using std::stringstream; void test_int()
{
cout << "test_int()" << endl;
int i = , j = , k = ; k = j = i; cout << "\ti=" << i << endl; //
cout << "\tj=" << j << endl; //
cout << "\tk=" << k << endl; //
} void test_int2()
{
cout << "test_int2()" << endl;
int i = , j = , k = ; (k = j) = i; cout << "\ti=" << i << endl; //
cout << "\tj=" << j << endl; //
cout << "\tk=" << k << endl; //
} class People
{
public:
People(const string &_name = "")
: name(_name)
{} People operator=(const People &_p)
{
name = _p.name;
return *this;
} string name;
}; void test()
{
cout << "test(): not reference" << endl;
cout << "\tp3=p2=p1" << endl;
People p1("p1"), p2("p2"), p3("p3"); p3 = p2 = p1; cout << "\t\tp2.name=" << p2.name << endl; // p1
cout << "\t\tp3.name=" << p3.name << endl; // p1
} void test2()
{
cout << "test2(): not reference" << endl;
cout << "\t(p3=p2)=p1" << endl;
People p1("p1"), p2("p2"), p3("p3"); (p3 = p2) = p1; cout << "\t\tp2.name=" << p2.name << endl; // p2
cout << "\t\tp3.name=" << p3.name << endl; // p2
} class PeopleRef
{
public:
PeopleRef(const string &_name = "")
: name(_name)
{} PeopleRef& operator=(const PeopleRef &_p)
{
name = _p.name;
return *this;
} string name;
}; void test_ref()
{
cout << endl;
cout << "test_ref(): reference" << endl;
cout << "\tp3=p2=p1" << endl;
PeopleRef p1("p1"), p2("p2"), p3("p3");; p3 = p2 = p1; cout << "\t\tp2.name=" << p2.name << endl; // p1
cout << "\t\tp3.name=" << p3.name << endl; // p1
} void test_ref2()
{
cout << "test_ref2(): reference" << endl;
cout << "\t(p3=p2)=p1" << endl;
PeopleRef p1("p1"), p2("p2"), p3("p3");; (p3 = p2) = p1; cout << "\t\tp2.name=" << p2.name << endl; // p2
cout << "\t\tp3.name=" << p3.name << endl; // p1
} class PeopleDefault
{
public:
PeopleDefault(const string &_name = "")
: name(_name)
{} string name;
}; void test_default()
{
cout << endl;
cout << "test_default()" << endl;
cout << "\tp3=p2=p1" << endl;
PeopleDefault p1("p1"), p2("p2"), p3("p3"); p3 = p2 = p1; cout << "\t\tp2.name=" << p2.name << endl; // p1
cout << "\t\tp3.name=" << p3.name << endl; // p1
} void test_default2()
{
cout << "test_default2()" << endl;
cout << "\t(p3=p2)=p1" << endl;
PeopleDefault p1("p1"), p2("p2"), p3("p3"); (p3 = p2) = p1; cout << "\t\tp2.name=" << p2.name << endl; // p2
cout << "\t\tp3.name=" << p3.name << endl; // p1
} int main ()
{
test_int();
test_int2(); test();
test2(); test_ref();
test_ref2(); test_default();
test_default2();
}

此文章为 '永无止境'(入驻一点号的媒体名称)原创,特此声明!

c++赋值构造函数为什么返回引用类型?的更多相关文章

  1. C++ 赋值构造函数的返回值到底有什么用?且返回值是否为引用类型有什么区别吗?

    首先定义类Person class Person{ public: string name; Person()=default; //默认构造函数 Person(string nam):name(na ...

  2. c++类大四个默认函数-构造函数 析构函数 拷贝构造函数 赋值构造函数

    每个类只有一个析构函数和一个赋值函数,但可以有多个构造函数(包含一个拷贝构造函数,其它的称为普通构造函数).对于任意一个类A,如果不编写上述函数,C++编译器将自动为A 产生四个缺省的函数,例如: A ...

  3. C++ 赋值函数为什么返回reference to *this?

    赋值操作为什么要返回 reference to *this? 要弄清这个问题之前,先了解函数的返回值类型:返回值类型,返回引用类型 返回值类型:返回的是一个对象的副本. test operator= ...

  4. C++ 为什么拷贝构造函数参数必须为引用?赋值构造函数参数也必须为引用吗?

    之前写拷贝构造函数的时候,以为参数为引用,不为值传递,仅仅是为了减少一次内存拷贝.然而今天看到一篇文章发现自己对拷贝构造的参数理解有误. 参数为引用,不为值传递是为了防止拷贝构造函数的无限递归,最终导 ...

  5. (copy)赋值构造函数的4种调用时机or方法

    第一种调用方法: demo #include <iostream> using namespace std; class Text { public: Text() // 无参数构造函数 ...

  6. C++函数的返回值——返回引用类型&非引用类型

    函数的返回主要分为以下几种情况: 1.主函数main的返回值: 允许主函数main没有返回值就可结束:可将主函数main返回的值视为状态指示器,返回0表示程序运行成功,其他大部分返回值则表示失败. 2 ...

  7. C++类中函数(构造函数、析构函数、拷贝构造函数、赋值构造函数)

    [1]为什么空类可以创建对象呢? 示例代码如下: #include <iostream> using namespace std; class Empty { }; void main() ...

  8. C语言中赋值表达式的返回值是什么?

    我们或多或少都有过,或者见过将赋值表达式参与运算的情况.这通常会伴随着一些意想不到的问题.今天我就见到了一段奇怪的代码: #include<stdio.h> int main() { ; ...

  9. 【opencv 源码剖析】 四、 Mat的赋值构造函数 和 拷贝构造函数

    1.赋值构造函数 右值引用 inline Mat& Mat::operator = (Mat&& m) { if (this == &m) return *this; ...

随机推荐

  1. spring boot 项目启动无任何反应

    遇到的问题 spring boot项目启动后无任何报错,ps有进程,nohub无日志 定位 更换jar包,问题依然存在,将jar包放到其他服务器,运行正常,排除打包问题 同服务器其他系统运行正常,但停 ...

  2. NO.2 安装配置

    检测当前系统下的jdk安装情况: [root@Centos 桌面]# rpm -qa | grep java tzdata-java-2012j-1.el6.noarch java-1.7.0-ope ...

  3. Win8.1,windows10部署 .NET Framework 3.5 安装方式汇总

    .NET Framework,操作系统安装过程中默认安装 .NET Framework 4.5.1.如果程序需要.NET Framework 3.5支持,将自动启用相关功能. 注意: 1. .NET ...

  4. 危险代码:如何使用Unsafe操作内存中的Java类和对象

    危险代码:如何使用Unsafe操作内存中的Java类和对象—Part1 危险代码:如何使用Unsafe操作内存中的Java类和对象—Part2 危险代码:如何使用Unsafe操作内存中的Java类和对 ...

  5. Linux 文件普通权限_011

    一.文件权限10个字符对应类型和权限 二.Linux普通文件和Linux目录读.写.执行权限说明 标注:Linux 中的文件名是存在于父目录的block里面,并指向这个文件的inode节点 1.lin ...

  6. VMware vCenter Server 6.5安装

    实验环境: 数据中心操作系统 :  Windows server 2008 R2(建议配置8G内存) 数据中心安装包版本: VMware vCenter Server 6.5 数据中心数据库:     ...

  7. 浅谈编码Base64、Hex、UTF-8、Unicode、GBK等

    网络上大多精彩的回答,该随笔用作自我总结: 首先计算机只认得二进制,0和1,所以我们现在看到的字都是经过二进制数据编码后的:计算机能针对0和1的组合做很多事情,这些规则都是人定义的:然后有了字节的概念 ...

  8. json转换学习

    文章部分代码实体类可以忽略. 原文:https://www.cnblogs.com/free-dom/p/5801866.html 代码如下: package covert; import java. ...

  9. PPT文件太大时可以考虑另存为PPTX格式

    遇到一个PPT文件有24M,30多页,里面主要有一些图片. 使用自带的图片压缩功能进行压缩,发现没有什么改变,后来找了一些工具软件压缩,最多也只能减少22%. 后来另存为PPTX格式,减小到1.74M ...

  10. ELK之使用heartbeat监控WEB站点

    简介 无论您要测试同一台主机上的服务,还是要测试开放网络上的服务,Heartbeat 都能轻松生成运行时间数据和响应时间数据 Heartbeat 能够通过 ICMP.TCP 和 HTTP 进行 pin ...