Effective c++学习笔记条款20:宁以 pass-by-reference-to-const替换pass-by-value

详细介绍pytorch重要的API Tensor 是 PyTorch 中最基本的数据结构,提供了多种创建和操作张量的函数。Autograd 提供了自动求导功能,可以跟踪 Tensor 上的操作并计算梯度。损失函数用于衡量模型预测值与真实值之间的差异,提供了多种损失函数。是构建神经网络的基础类,提供了定义网络层和前向传播的方法。提供了 GPU 计算的支持,包括设备管理、内存管理等。提供了一些常用的函数式操作,如激活函数、损失函数等。提供了常用的数据集、模型架构和图像转换工具。提供了数据加载和预处理的工具,包括。 阅读详情
Prefer pass-by-reference-to-const to pass-by-value
        这个问题在在C++是非常常见的。传值和传引用巨大的差别在于你所使用的参数是其本身还是其副本。缺省情况下C++是以by value 传递的。其副本是对象本身的copy 构造函数自动调用的。有关对象自动调用的五个函数请看条款12.下面看一下例子吧    :
 
// refer_value.cpp : 定义控制台应用程序的入口点。
//2011/10/5 by wallwind at sunrise
#include "stdafx.h"
#include <iostream>
using namespace std;
class Base
{
public:
    Base(){cout<<"Base()"<<endl;}
    ~Base(){cout<<"~Base()"<<endl;}
private:
    string str1;
    string str2;
};
class Derived:public Base
{
public:
    Derived(){cout<<"Derived()"<<endl;}
    ~Derived(){cout<<"~Derived()"<<endl;}
    bool retTrue()
    {
        return true;
    }
private:
    string str1;
    string str2;
};
bool validateDerived(Derived d)
{
    return d.retTrue();
}
int _tmain(int argc, _TCHAR* argv[])
{
    Derived d;
    bool bb=validateDerived(d);
    system("pause");
    return 0;
}
运行结果如图:
从结果我们可以看到 构造函数,析构函数都调用了,其实远不止这些,因为上述两个类都含有两个string,他们也相应的调用构造函数,就是说四次string构造动作,还有析构。
总计12次,也就是我们简单的一个调用,动用了这么多函数。很浪费资源。
下面我们用 pass-by-reference-to-const来。
修改代码为
 
bool retTrue() const
    {
        return true;
    } 

bool validateDerived(const Derived& d)
{
    return d.retTrue();
} 

运行的结果:
如图,程序只调用了构造函数。在这里注明书中说没有调用任何构造函数和析构函数,应该是调用了构造函数了吧。跪求高人解释
by-reference避免了对象切割,什么是对象切割,请看下边的例子。
// refer_value.cpp : 定义控制台应用程序的入口点。
//2011/10/5 by wallwind at sunrise
#include "stdafx.h"
#include <iostream>
using namespace std;
class Window
{
public :
    Window(){};
    void name()const;
    
    virtual void display()const;
};
void Window::name()const
{
    cout<<"window name"<<endl;
}
void Window::display()const
{
    cout<<" window display()"<<endl;
}
class WindowWithScrollBars:public Window{
    
public:
    WindowWithScrollBars(){};
    virtual void display() const;
};
void WindowWithScrollBars::display() const
{
    cout<<"WindowWithScrollBars display()"<<endl;
}
void pintNaandWind(Window w)
{
    w.name();
    w.display();
}
int _tmain(int argc, _TCHAR* argv[])
{
    WindowWithScrollBars wwsb;
    pintNaandWind(wwsb);
    return 0;
}

运行的结果如图所示:
 
 
可以看出,我们想得到WindowWithScrollBars display() ,但是我们得到的是上述的。它调用 是window对象,而不是子类的。因为他是by value,WindowWithScrollBars的所有特化信息都会被切除,这就是对象切割。那么解决办法就是 pass-by-reference-to-const,
修改代码如下:
void pintNaandWind(const Window& w)

{

    w.name();

    w.display();
} 

运行结果得到:
 
从中我们看到了通过pass-by-reference-to-const,得到了我们想要的结果。

解释一下:
(1)所谓的slicing问题,也就是如果你把子类的对象赋值给父类的对象,如果用reference和指针,当然是可以的,而且这也是virtual的实现必需品。但是,如果用pass-by-value,就会出现,传进去的总是父类的对象,在传递对象的时候出现了切割问题。


(2)如果窥视c++编译器的底层,你会发现,references往往以指针实现出来,因此pass-by-reference通常意味着这真正传递的是指针。因此如果你有个对象属于内置类型(如int),pass by reference或pass by reference to const时,选择pass by value并非没有道理。这个忠告也适用于STL的迭代器和函数对象,因为习惯上它们都被设计为pass by value。迭代器和函数对象的实践者有责任看看他们是否高效且不受切割问题的影响。


(3)内置类型都相当的小。因此有人认为,所有小类型的types都是pass by value的合格候选人,甚至他们是用户自定义的class亦然。这是个不可靠的推论。对象小并不就意味其copy构造函数不昂贵。许多对象,包括STL容器,内含的东西只比一个指针多一些,但复制这种东西对象却需要承担“复制那些指针的每一样东西”。那将非常昂贵。

即使小型对象拥有并不昂贵的copy构造函数,还是可能有效率上的争议。某些编译器对待“内置类型”和“用户自定义类型”的态度截然不同,总是两者有相同的底层表述。举个例子,某些编译器拒绝把只由一个double组成的对象放进缓存器内,却很乐意在一个正规基础上对光秃秃的double那么做。当这种事发生,你更应该以by reference方式传递此等对象,因为编译器当然会将指针(references的实现体)放进缓存器内,绝无问题。


小型的用户自定义类型并不必然成为pass by value优良候选人的另一个理由是,作为一个用户自定义类型,其大小容易有所改变。甚至当你改用另一个c++编译器都有可能改变type的大小。举个例子,某些标准程序库实现版本中的string类型比其他版本大七倍!

请记住:
▲ 尽量以pass-by-reference-to-const替换pass-by-value.前者通常比较高效,并可避免切割问题(slicing
problem).
▲ 以上规则并不适合与内置类型,以及STL的迭代器和函数对象.对它们而言,pass-by-value往往比较适合.
一层一责,一聚合一包:DDD分层架构下的微服务代码模型、三重边界与服务数据协作 领域模型画得再清楚,落不进代码也是空谈。本文以一个可运行的客户中心微服务为线索,先对比整洁架构、六边形架构与DDD分层架构,指出三者共同守护的那条隔离核心业务的红线;再把DDD分层落成四个一级目录、以聚合为单位分包、一个聚合一个仓储的代码模型,拆解实体、聚合根、值对象、领域事件、领域服务与仓储的设计要点;随后厘清逻辑、物理、代码三重边界,并用检查器实测:干净代码零越界,拆出积分聚合时领域代码无需改动;注入九处越界后,必须先重构才能拆分。最后梳理服务调用三场景与PO、DO、DTO、VO的协作。 阅读详情

相关推荐

EXCEL实现分层自定义比例随机抽样(图+文教程)

EXCEL实现分层自定义比例随机抽样(图+文教程) 单一字段分层自定义比例随机抽样 多字段分层自定义比例随机抽样 单一字段分层自定义比例随机抽样 首先数据源如下,我们想随机抽张三的金额数据10%、李四金额20%、王五5%、哈哈15%、李六10% 首先第一步,添加辅助列,随机数 =RAND() 对数据进行高级排序 升序、降序都可以 添加辅助列...

可乐联盟 2万+

Effective C++之Item 20: 用 pass-by-reference-to-const(传引用给 const)取代 pass-by-value(传值)

1.引用传递提高执行效率; 2.避免切断问题; 缺省情况下,C++ 以传值方式将对象传入或传出函数(这是一个从 C 继承来的特性)。除非你特别指定其它方式,否则函数的参数就会以实际参数(actual argument)的拷贝进行初始化,而函数的调用者会收到函数返回值的一个拷贝。这个拷贝由对象的拷贝构造函数生成。这就使得传值(pass-by-value)成为一个代价不菲的操作。例如,考虑

janeqi1987的专栏 452

国内网络环境下Calico v3.26.4安装避坑指南(附华为云镜像加速脚本)

本文为国内开发者提供Calico v3.26.4的高效部署指南,重点介绍如何通过华为云镜像加速服务解决Kubernetes集群网络插件镜像拉取问题。文章包含详细的镜像加速脚本、部署清单修改方法及深度排错技巧,帮助开发者快速完成Calico网络插件的安装与配置。

brown的博客 289

Effective C++条款20:宁以pass-by-reference-to-const替换pass-by-value

Effective C++条款20:宁以pass-by-reference-to-const替换pass-by-value(Prefer pass-by-reference-to-const to pass-by-value)

CltCj的博客 741

第3章 信息技术服务(一)

对 第三章 《信息技术服务》中第一、二、三节 <内涵与外延、原理与组成、服务生命周期>进行总结、归纳

好好学习,天天向上的博客 733

从光猫到机顶盒:H10G-13融合网关双系统网络配置全解析(含超密获取技巧)

本文详细解析了中国移动H10G-13融合网关的双系统网络配置,涵盖光猫路由与安卓电视盒子的协同工作。通过晶晨S905L3芯片的优化,设备实现高效网络接入与安卓9.0系统的定制化应用,特别适合酒店和民宿行业的智能化改造。文章还提供了超密获取技巧和线刷固件包的实用指南。

weixin_42525264的博客 947

C++经验(七)-- pass by value 和 pass by reference to const 的问题

缺省情况下,C++以 by value 方式传递参数。函数参数都是以实参的副本为初值,如果返回对象的话,返回的也是返回参数的一个副本。而这些副本都是由对象的copy构造函数产出。这也就使得pass by value的操作比较耗时。 那么如果我们传递一个对象的引用或者是返回一个对象的引用呢?会不会降低这些耗时?.........

slowlytalk 817

STK中的传感器、雷达、发射机、接收机、天线

本文根据STK手册介绍了传感器、雷达、发射机、接收机、天线等对象的基本属性,简略分析了它们的不同之处。

wangyulj的专栏 1万+

参数传递:pass by reference to const

1.代码 class complex { public complex (double r=0,double i=0)/*pass by value*/ : re (r), im(i){} complex& operator +=(const complex&); real () const { return re} imag () const{ return im} private: re, im; friend complex&__doapl(co

假正经先生的博客 444

蓝桥杯单片机省一经验分享1:基础篇.含详细代码与应试技巧

含详细代码、驱动修改与应试技巧

qq_53529450的博客 1万+

Python计算时间差的方法

使用datetime模块是Python内置的方法,使用timedelta对象可以更精确地计算时间差,而使用dateutil库则提供了更为灵活和方便的操作方式。我们可以使用datetime模块中的datetime类来表示一个具体的日期和时间,并进行相应的运算。在Python中,我们经常需要计算日期和时间之间的差异,例如计算两个日期之间的天数、小时数、分钟数等。Python提供了多种方法来计算时间差,下面我们将介绍其中的几种常用方法,并附上相应的源代码。在上面的代码中,我们使用了dateutil库中的。

学习使你进步。 2086

条款20:宁以pass-by-reference-to-const替换pass-by-value

缺省情况下C++以by value方式传递对象至函数。除非另外指定了,否则函数参数都是以实际实参的副本为初值,而调用端所获得的亦是函数返回值的一个副本。这些副本是由对象的copy构造函数产出,这导致pass-by-value成为费时的操作。当上述程序代码运行时,发生什么事情呢?首先,Student的copy构造函数会被调用,以plato为蓝本将s初始化。同样明显地,当validateStudent返回,s会被销毁。

依然爱猪的博客 1704

【温室气体数据集】全球总碳柱观测网络 TCCON

【温室气体数据集】全球总碳柱观测网络 TCCON

WW、forever的博客 437

《Effective C++》学习笔记(条款20:宁以 pass-by-reference-to-const 替换 pass-by-value)

最近开始看《Effective C++》,为了方便以后回顾,特意做了笔记。若本人对书中的知识点理解有误的话,望请指正!!! 通常情况下,C++是以值传递(pass-by-value)的方式传递对象至函数,除非你另外指定,否在函数参数都是以实参的复件为初值,而调用函数返回的对象也是函数返回值的一个复件。这些复件是由对象的拷贝构造函数产出的,这使得值传递的成本很高(费时)。 class Person{ public: Person(); virtual ~Person(); //见条款7为什么

ZLX的博客 278

计算机控制技术及应用

《计算机控制技术及应用》通过总结作者的科研成果和吸收国内外的先进理论、方法和技术,以计算机控制系统的网络化、开放化、智能化和集成化发展趋势为主线索,主要介绍计算机控制系统的基本概念和计算机控制系统的典型形式,计算机控制系统的数学描述与基本分析方法,以及数字PID控制器、最少拍控制系统、达林算法、状态变量设计法等设计方法及其各种改进算法。重点突出计算机控制系统输入输出通道接口的设计方法和典型控制系统的设计案例与实现方法等。

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

Effective C++ 学习笔记 条款20 宁以pass-by-reference替换pass-by-value

对内置类型而言,当你有机会选择采用pass-by-value或pass-by-reference-to-const时,选择pass-by-value并非没有道理。当一个derived class对象以by value方式传递并被视为一个base class对象,base class的copy构造函数会被调用,而“造成此对象的行为像个derived对象”的那些特质全被切割掉了,仅仅留下一个base class对象。这是个不可靠的推论。这是正确且值得拥有的行为,毕竟你希望你的所有对象都能够被确实地构造和析构。

tus00000的博客 1074

SIMATIC S7-1200, S7-1500 PID 控制[手册]

SIMATIC S7-1200, S7-1500 PID 控制[手册]

Effective C++ 条款 20:宁以 pass-by-reference-to-const 替换 pass-by-value

然而,这种方式在处理复杂对象时可能引发性能问题,甚至导致。方式传递对象至函数。因此,建议对非内置类型采用。的拷贝构造函数,同时确保。传递对象,避免了调用。

weixin_42255569的博客 505

Effective C++ 条款20:宁以 pass-by-reference-to-const 替换 pass-by-value

深入解析 C++ 函数参数传递方式的选择策略,揭示 pass-by-value 的性能代价与对象切割问题,明确引用传递的适用边界与例外情况。

凡人叶枫的博客 181

[Effective C++]条款20:宁以 pass-by-reference-to-const替换 pass-by-value

在C++中,函数参数与返回值的数据传递的方式,对程序的性能和正确性有着重要影响。C++默认使用pass-by-value(传值)的方式传递参数。但这种方式在某些情况下会导致性能问题和对象切割问题。C++推荐使用pass-by-reference-to-const(传常量引用)的方式来传递参数。

Tim_10的博客 528

【复读EffectiveC++20】条款20:宁以pass-by-reference-to-const替换pass-by-value

尽量以pass-by-reference-to-const替换pass-by-value。前者通常比较高效,并可避免切割问题; 以上规则并不适用于内置类型,以及STL的迭代器和函数对象。对它们而言,传值调用往往比较合适。

weixin_51122602的博客 1047

[Effective C++]条款20 宁以pass-by-reference-to-const替换pass-by-value

我们都知道, pass-by-value(传值传参)是一个费时费力的过程, 它会直接复制一个原件的拷贝, 如果是自定义类就会调用一次拷贝构造来实现复制, 函数结束时还要额外调用一次析构函数, 我们会很有意愿去削减这方面的花销.

tianmu_sama的博客 904

Effective C++ T20:宁以pass-by-reference-to-const 替换 pass-by-value

1. 尽量以pass-by-reference-to-const 替换 pass-by-value。前者通常比较高效,并可避免切割问题。 2. 以上规则并不适用于内置类型,以及STL的迭代器和函数对象。对它们而言pass-by-value往往比较适当。

Ref.Ptr.的博客 318

Effective_C++_条款二十:宁以pass-by-reference-to-const替换pass-by-value

默认情况下,C++的函数调用是传值调用,也就是说形参拷贝实参的内容。举书上的例子: class Person { private: string name; string address; public: Person(){} virtual ~Person(){} }; class Student: public Person { private: ...

Likes的博客 199

Effective C++条款20——宁以pass-by-reference-to-const替换pass-by-value(设计与声明)

对内置类型而言,当你有机会选择采用pass-by-value或pass-by-reference-to-const时,选择pass-by-value并非没有道理。当一个derived class对象以 by value方式传递并被视为一个base class对象,base class 的 copy构造函数会被调用,而“造成此对象的行为像个derived class对象”的那些特化性质全被切割掉了,仅仅留下一个base class对象。即使小型对象拥有并不昂贵的copy构造函数,还是可能有效率上的争议。

StudyWinter的博客 395

【effective c++】条款二十:宁以 pass-by-reference-to-const 替换 pass-by-value

C++中应优先使用const引用传递而非值传递,以提高效率并避免对象切片问题。对于内置类型、STL迭代器和函数对象等小型数据,值传递更合适。对象切片发生在派生类对象按值传递给基类时,导致派生类特有信息丢失。解决方法包括使用引用传递或智能指针存储多态对象。合理选择传递方式能提升性能并保持多态行为。

maybe_Tian_Xia的博客 220

Effective C++ 条款20:宁以pass-by-reference-to-const替换pass-by-value

Effective_C++_20

君鼎的博客 474
上一篇: Effective c++学习笔记条款18:让接口容易被正确使用,不易被误用
下一篇: STL 容器
ctreewang
博客等级 码龄16年 1608粉丝 276原创
评论 9
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值