- 博客(85)
- 收藏
- 关注
原创 图说设计模式:状态模式
状态模式(State Pattern) :允许一个对象在其内部状态改变时改变它的行为,对象看起来似乎修改了它的类。其别名为状态对象(Objects for States),状态模式是一种对象行为型模式。状态模式允许一个对象在其内部状态改变时改变它的行为,对象看起来似乎修改了它的类。其别名为状态对象,状态模式是一种对象行为型模式。
2024-07-01 09:30:00 1089
原创 图说设计模式:策略模式
策略模式(Strategy Pattern):定义一系列算法,将每一个算法封装起来,并让它们可以相互替换。策略模式让算法独立于使用它的客户而变化,也称为政策模式(Policy)。策略模式是一种对象行为型模式。在策略模式中定义了一系列算法,将每一个算法封装起来,并让它们可以相互替换。策略模式让算法独立于使用它的客户而变化,也称为政策模式。策略模式是一种对象行为型模式。策略模式包含三个角色:环境类在解决某个问题时可以采用多种策略,在环境类中维护一个对抽象策略类的引用实例;
2024-07-01 09:30:00 849
原创 图说设计模式:观察者模式
观察者模式(Observer Pattern):定义对象间的一种一对多依赖关系,使得每当一个对象状态发生改变时,其相关依赖对象皆得到通知并被自动更新。观察者模式又叫做发布-订阅(Publish/Subscribe)模式、模型-视图(Model/View)模式、源-监听器(Source/Listener)模式或从属者(Dependents)模式。观察者模式是一种对象行为型模式。观察者模式定义对象间的一种一对多依赖关系,使得每当一个对象状态发生改变时,其相关依赖对象皆得到通知并被自动更新。
2024-06-30 09:15:00 913
原创 图说设计模式:中介者模式
中介者模式(Mediator Pattern)定义:用一个中介对象来封装一系列的对象交互,中介者使各对象不需要显式地相互引用,从而使其耦合松散,而且可以独立地改变它们之间的交互。中介者模式又称为调停者模式,它是一种对象行为型模式。中介者模式用一个中介对象来封装一系列的对象交互,中介者使各对象不需要显式地相互引用,从而使其耦合松散,而且可以独立地改变它们之间的交互。中介者模式又称为调停者模式,它是一种对象行为型模式。中介者模式包含四个角色:抽象中介者用于定义一个接口,该接口用于与各同事对象之间的通信;
2024-06-30 09:00:00 698
原创 图说设计模式:代理模式
代理模式(Proxy Pattern) :给某一个对象提供一个代 理,并由代理对象控制对原对象的引用。代理模式的英 文叫做Proxy或Surrogate,它是一种对象结构型模式。其他问题。如果按照这种方法使用代理模式,那么真实主题角色必须是事先已经存在的,并将其作为代理对象的内部成员属性。如果一个真实主题角色必须对应一个代理主题角色,这将导致系统中的类个数急剧增加,因此需要想办法减少系统中类的个数,此外,如何在事先不知道真实主题角色的情况下使用代理主题角色,这都是动态代理需要解决的问题。
2024-06-29 10:30:00 653
原创 图说设计模式:命令模式
命令模式(Command Pattern):将一个请求封装为一个对象,从而使我们可用不同的请求对客户进行参数化;对请求排队或者记录请求日志,以及支持可撤销的操作。命令模式是一种对象行为型模式,其别名为动作(Action)模式或事务(Transaction)模式。在命令模式中,将一个请求封装为一个对象,从而使我们可用不同的请求对客户进行参数化;对请求排队或者记录请求日志,以及支持可撤销的操作。命令模式是一种对象行为型模式,其别名为动作模式或事务模式。
2024-06-29 10:30:00 608
原创 图说设计模式:享元模式
享元模式(Flyweight Pattern):运用共享技术有效地支持大量细粒度对象的复用。系统只使用少量的对象,而这些对象都很相似,状态变化很小,可以实现对象的多次复用。由于享元模式要求能够共享的对象必须是细粒度对象,因此它又称为轻量级模式,它是一种对象结构型模式。享元模式运用共享技术有效地支持大量细粒度对象的复用。系统只使用少量的对象,而这些对象都很相似,状态变化很小,可以实现对象的多次复用,它是一种对象结构型模式。享元模式包含四个角色:抽象享元类声明一个接口,通过它可以接受并作用于外部状态;
2024-06-28 21:47:56 1181
原创 图说设计模式:外观模式
外观模式(Facade Pattern):外部与一个子系统的通信必须通过一个统一的外观对象进行,为子系统中的一组接口提供一个一致的界面,外观模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。外观模式又称为门面模式,它是一种对象结构型模式。在外观模式中,外部与一个子系统的通信必须通过一个统一的外观对象进行,为子系统中的一组接口提供一个一致的界面,外观模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。外观模式又称为门面模式,它是一种对象结构型模式。
2024-06-28 21:45:56 581
原创 图说设计模式:装饰模式
装饰模式(Decorator Pattern) :动态地给一个对象增加一些额外的职责(Responsibility),就增加对象功能来说,装饰模式比生成子类实现更为灵活。其别名也可以称为包装器(Wrapper),与适配器模式的别名相同,但它们适用于不同的场合。根据翻译的不同,装饰模式也有人称之为“油漆工模式”,它是一种对象结构型模式。装饰模式用于动态地给一个对象增加一些额外的职责,就增加对象功 能来说,装饰模式比生成子类实现更为灵活。它是一种对象结构型模 式。
2024-06-24 09:49:07 948
原创 图说设计模式:桥接模式
桥接模式(Bridge Pattern):将抽象部分与它的实现部分分离,使它们都可以独立地变化。它是一种对象结构型模式,又称为柄体(Handle and Body)模式或接口(Interface)模式。桥接模式将抽象部分与它的实现部分分离,使它们都可以独立地变化。它是一种对象结构型模式,又称为柄体(Handle and Body)模式或接口(Interface)模式。桥接模式包含如下四个角色:抽象类中定义了一个实现类接口类型的对象并可以维护该对象;
2024-06-24 09:47:29 971
原创 图说设计模式:适配器模式
适配器模式(Adapter Pattern) :将一个接口转换成客户希望的另一个接口,适配器模式使接口不兼容的那些类可以一起工作,其别名为包装器(Wrapper)。适配器模式既可以作为类结构型模式,也可以作为对象结构型模式。结构型模式描述如何将类或者对象结合在一起形成更大的结构。适配器模式用于将一个接口转换成客户希望的另一个接口,适配器模式使接口不兼容的那些类可以一起工作,其别名为包装器。适配器模式既可以作为类结构型模式,也可以作为对象结构型模式。
2024-06-18 09:05:35 1047
原创 图说设计模式:单例模式
单例模式(Singleton Pattern):单例模式确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例,这个类称为单例类,它提供全局访问的方法。单例模式的要点有三个:一是某个类只能有一个实例;二是它必须自行创建这个实例;三是它必须自行向整个系统提供这个实例。单例模式是一种对象创建型模式。单例模式又名单件模式或单态模式。单例模式确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例,这个类称为单例类,它提供全局访问的方法。单例模式的要点有三个:一是某个类只能有一个实例;
2024-06-18 09:01:33 1110 1
原创 图说设计模式:建造者模式
造者模式(Builder Pattern):将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。建造者模式是一步一步创建一个复杂的对象,它允许用户只通过指定复杂对象的类型和内容就可以构建它们,用户不需要知道内部的具体构建细节。建造者模式属于对象创建型模式。根据中文翻译的不同,建造者模式又可以称为生成器模式。建造者模式将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。
2024-06-13 09:30:00 584
原创 图说设计模式:单例模式
单例模式(Singleton Pattern):单例模式确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例,这个类称为单例类,它提供全局访问的方法。单例模式的要点有三个:一是某个类只能有一个实例;二是它必须自行创建这个实例;三是它必须自行向整个系统提供这个实例。单例模式是一种对象创建型模式。单例模式又名单件模式或单态模式。单例模式确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例,这个类称为单例类,它提供全局访问的方法。单例模式的要点有三个:一是某个类只能有一个实例;
2024-06-13 09:06:03 832
原创 图说设计模式:工厂方法模式
工厂方法模式(Factory Method Pattern)又称为工厂模式,也叫虚拟构造器(Virtual Constructor)模式或者多态工厂(Polymorphic Factory)模式,它属于类创建型模式。在工厂方法模式中,工厂父类负责定义创建产品对象的公共接口,而工厂子类则负责生成具体的产品对象,这样做的目的是将产品类的实例化操作延迟到工厂子类中完成,即通过工厂子类来确定究竟应该实例化哪一个具体产品类。工厂方法模式又称为工厂模式,它属于类创建型模式。
2024-06-12 09:30:00 555
原创 图说设计模式:抽象工厂模式(Abstract Factory)
抽象工厂模式(Abstract Factory)模式动机模式定义模式结构时序图代码分析模式分析实例优点缺点适用环境模式应用模式扩展“开闭原则”的倾斜性工厂模式的退化总结抽象工厂模式(Abstract Factory Pattern):提供一个创建一系列相关或相互依赖对象的接口,而无须指定它们具体的类。抽象工厂模式又称为Kit模式,属于对象创建型模式。抽象工厂模式提供一个创建一系列相关或相互依赖对象的接口,而无须指定它们具体的类。
2024-06-12 09:30:00 845
原创 图说设计模式:简单工厂模式( Simple Factory Pattern )
简单工厂模式(Simple Factory Pattern):又称为静态工厂方法(Static Factory Method)模式,它属于类创建型模式。在简单工厂模式中,可以根据参数的不同返回不同类的实例。简单工厂模式专门定义一个类来负责创建其他类的实例,被创建的实例通常都具有共同的父类。创建型模式对类的实例化过程进行了抽象,能够将对象的创建与对象的使用过程分离。简单工厂模式又称为静态工厂方法模式,它属于类创建型模式。在简单工厂模式中,可以根据参数的不同返回不同类的实例。
2024-06-11 09:20:16 567
原创 Effective ModernC++条款42:考虑使用置入代替插入
然后,如果值已经存在,置入操作取消,创建的节点被销毁,意味着构造和析构时的开销被浪费了。在当前标准库的实现下,有些场景,就像预期的那样,置入执行性能优于插入,但是,有些场景反而插入更快。这种场景不容易描述,因为依赖于传递的实参的类型、使用的容器、置入或插入到容器中的位置、容器中类型的构造函数的异常安全性,和对于禁止重复值的容器(即。但是移动赋值需要一个源对象,所以这意味着一个临时对象要被创建,而置入优于插入的原因就是没有临时对象的创建和销毁,所以当通过赋值操作添加元素时,置入的优势消失殆尽。
2024-05-24 09:19:40 989
原创 Effective Modern C++ 条款41:对于移动成本低且总是被拷贝的可拷贝形参,考虑按值传递
(这样的句子就说明有一个术语来区分拷贝操作制作的副本,和移动操作制作的副本,是非常好的。对于特殊的场景,可拷贝且移动开销小的类型,传递给总是会拷贝他们的一个函数,并且切片也不需要考虑,这时,按值传递就提供了一种简单的实现方式,效率接近传递引用的函数,但是避免了传引用方案的缺点。结论是,使用通过赋值拷贝一个形参进行按值传递的函数的额外开销,取决于传递的类型,左值和右值的比例,这个类型是否需要动态分配内存,以及,如果需要分配内存的话,赋值操作符的具体实现,还有赋值目标占的内存至少要跟赋值源占的内存一样大。
2024-05-24 09:18:41 1605
原创 Effective Modern C++ 条款40:对于并发使用std::atomic,对于特殊内存使用volatile
但是它们通常做出一些没有数据竞争的程序中才有效的优化,这些优化在存在数据竞争的程序中会造成异常和不可预测的行为。但是在编译器拿到看起来合理的代码,执行了模板实例化,内联和一系列重排序优化之后,结果会出现冗余访问和无用存储,所以编译器需要摆脱这样的情况并不少见。)这意味对我们的代码,对象被构建,在其上的操作表现得像操作是在互斥锁保护的关键区内,但是通常这些操作是使用特定的机器指令实现,这比锁的实现更高效。那些不那么相同,但是如果我们暂时忽略它,只关注编译器执行的操作,则概念上可以说,编译器看到这个,
2024-05-23 10:22:40 854
原创 Effective Modern C++ 条款39:对于一次性事件通信考虑使用void的futures
互斥锁被用于保护共享数据的访问,但是可能检测任务和反应任务可能不会同时访问共享数据,比如说,检测任务会初始化一个全局数据结构,然后给反应任务用,如果检测任务在初始化之后不会再访问这个数据结构,而在检测任务表明数据结构准备完了之前反应任务不会访问这个数据结构,这两个任务在程序逻辑下互不干扰,也就没有必要使用互斥锁。不好的一点是反应任务中轮询的开销。这样,反应线程占用了可能能给另一个任务使用的硬件线程,每次启动或者完成它的时间片都增加了上下文切换的开销,并且保持核心一直在运行状态,否则的话本来可以停下来省电。
2024-05-23 10:21:52 944
原创 Effective Modern C++ 条款38:关注不同线程句柄的析构行为
最后,决定先不改变,所以C++11和C++14中这里的行为是一致的。满足上面条件的任意一条(比如由于程序逻辑造成的不满足),你就可以确定析构函数不会执行“异常”行为。因为与被调用者关联的对象和与调用者关联的对象都不适合存储这个结果,所以必须存储在两者之外的位置。阻塞了它们的析构函数”。我们真正要处理的是一个简单的“正常”行为以及一个单独的例外。的数据成员(当然,还做了另一件事,就是递减了共享状态中的引用计数,这个共享状态是由引用它的。创建的共享状态才有资格执行“异常”行为,但是有其他创建共享状态的方式。
2024-05-22 08:17:14 1081
原创 Effective ModernC++ 条款37:使std::thread在所有路径最后都不可结合
如果同时进行调用,那肯定是有竞争的,但是不在析构函数中,是在客户端代码中试图同时在一个对象上调用两个成员函数(析构函数和其他函数)。在这个类中,这个顺序没什么特别之处,但是通常,可能一个数据成员的初始化依赖于另一个,因为。的可结合性如此重要的原因之一就是当可结合的线程的析构函数被调用,程序执行会终止。比如,假定有一个函数。可以视作状态保存的对象,保存的状态可能也包括可调用对象,有没有具体的线程承载就是有没有连接),然后选择析构执行的动作,这比反过来更合理),但是成员初始化列表设计的匹配成员声明的顺序。
2024-05-22 08:14:52 956
原创 EffectiveModernC++ 条款36:如果有异步的必要请指定std::launch::async
那些是使机器资源超额或者线程耗尽的条件,此时任务推迟执行才最有可能发生。毕竟,如果硬件没有资源耗尽,没有理由不安排任务并发执行。的默认启动策略——你不显式指定一个策略时它使用的那个——不是上面中任意一个。相反,是求或在一起的。作为启动策略的工具,拥有它会非常方便,而且编写起来很容易也使它看起来很棒。和标准库的线程管理组件承担线程创建和销毁的责任,避免资源超额,以及平衡负载。执行函数时(或者其他可调用对象),你通常希望异步执行函数。的循环使用超时机制,因为在一个延时的任务(参见[Item35])上调用。
2024-05-20 21:39:34 1052
原创 Effective ModernC++ 条款35:优先考虑基于任务的编程而非基于线程的编程
避免资源超额很困难,因为软件线程之于硬件线程的最佳比例取决于软件线程的执行频率,那是动态改变的,比如一个程序从IO密集型变成计算密集型,执行频率是会改变的。此外,硬件线程的数量和CPU缓存的细节(比如缓存多大,相应速度多少)取决于机器的体系结构,即使经过调校,在某一种机器平台避免了资源超额(而仍然保持硬件的繁忙状态),换一个其他类型的机器这个调校并不能提供较好效果的保证。遇到负载不均衡问题时,对机器内发生的事情,运行时调度程序比你有更全面的了解,因为它管理的是所有执行过程,而不仅仅个别开发者运行的代码。
2024-05-20 21:38:18 829
原创 Effective Modern C++ 条款34:考虑lambda而非std::bind
无论如何,这样的理解都是值得的,因为你永远不知道何时会在阅读或维护的代码库中遇到。这是可以理解的,但是在这种情况下,改变是更好的,因为在C++11中,在C++14中,通常可以省略标准运算符模板的模板类型实参,因此无需在此处提供。进一步假设,在程序的某个时刻,我们已经确定需要设置一个小时后响30秒的警报器。(答案是传递给bind对象的所有实参都是通过引用传递的,因为此类对象的函数调用运算符使用完美转发。)等简化在C++14中的代码,其中标准后缀基于C++11对用户自定义常量的支持。的调用是通过一个函数指针。
2024-05-18 08:31:00 786
原创 Effective Modern C++ 条款33:对auto&&形参使用decltype以std::forward它们
Item28解释过如果一个左值实参被传给通用引用的形参,那么形参类型会变成左值引用。传递的是右值,形参就会变成右值引用。时,惯例决定了类型实参是左值引用时来表明要传进左值,类型实参是非引用就表明要传进右值。是非传统的,不过它产生的实例化结果与传统类型相同。去实例化产生的结果,它们完全相同。一般来说,当你在使用完美转发时,你是在一个接受类型参数为。这个特性的实现是非常直截了当的:即在闭包类中的。的类型来确定传递进来的实参是一个左值还是右值,如果传递的是一个右值,指定为右值引用,这会发生什么。
2024-05-18 08:30:11 695
原创 Effective ModernC++ 条款32:使用初始化捕获来移动对象到闭包中
如果你要复制的对象复制开销非常高,但移动的成本却不高(例如标准库中的大多数容器),并且你希望的是宁愿移动该对象到闭包而不是复制它。表达式要多,但这并不难改变这样一个事实,即如果你希望使用一个C++11的类来支持其数据成员的移动初始化,那么你唯一要做的就是在键盘上多花点时间。这清楚地表明了,这个C++14的捕获概念是从C++11发展出来的的,在C++11中,无法捕获表达式的结果。这种移动构造是模仿移动捕获的关键,因为将右值移动到bind对象是我们解决无法将右值移动到C++11闭包中的方法。
2024-05-17 09:14:50 605
原创 Effective ModernC++ 条款31:避免使用默认捕获模式
但默认按引用捕获模式可能会带来悬空引用的问题,而默认按值捕获模式可能会诱骗你让你以为能解决悬空引用的问题(实际上并没有),还会让你以为你的闭包是独立的(事实上也不是独立的)。在这种情况下,你可能会争论说,没有悬空引用的危险,就不需要避免使用默认的引用捕获模式。使用默认的按值捕获还有另外的一个缺点,它们预示了相关的闭包是独立的并且不受外部数据变化的影响。,这和默认的按值捕获表示的含义有着直接的矛盾。捕获并没有默认的捕获模式,因此在C++14中,本条款的建议——避免使用默认捕获模式——仍然是成立的。
2024-05-17 09:13:44 951
原创 Effective Modern C++ 条款30:熟悉完美转发失败的情况
在大多数情况下,完美转发工作的很好。你基本不用考虑其他问题。但是当其不工作时——当看起来合理的代码无法编译,或者更糟的是,虽能编译但无法按照预期运行时——了解完美转发的缺陷就很重要了。同样重要的是如何解决它们。在大多数情况下,都很简单。当模板类型推导失败或者推导出错误类型,完美转发会失败。导致完美转发失败的实参种类有花括号初始化,作为空指针的0或者NULL,仅有声明的整型数据成员,模板和重载函数的名字,位域。
2024-05-16 09:56:24 1223
原创 EffectiveModern C++ 条款29:假定移动操作不存在,成本高,未被使用
为了升级到C++11,C++98的很多标准库做了大修改,为很多类型提供了移动的能力,这些类型的移动实现比复制操作更快,并且对库的组件实现修改以利用移动操作。的确,C++11倾向于为缺少移动操作的类生成它们,但是只有在没有声明复制操作,移动操作,或析构函数的类中才会生成移动操作(参考Item17)。Item14解释了原因,标准库中的某些容器操作提供了强大的异常安全保证,确保依赖那些保证的C++98的代码在升级到C++11且仅当移动操作不会抛出异常,从而可能替换操作时,不会不可运行。但是传说总有些夸大成分。
2024-05-16 09:55:23 888
原创 Effective Modern C++ 条款28:理解引用折叠
存在两种类型的引用(左值和右值),所以有四种可能的引用组合(左值的左值,左值的右值,右值的右值,右值的左值)。如果一个上下文中允许引用的引用存在(比如,模板的实例化),引用根据规则。通用引用的概念是有用的,因为它使你不必一定意识到引用折叠的存在,从直觉上推导左值和右值的不同类型,在凭直觉把推导的类型代入到它们出现的上下文中之后应用引用折叠规则。和通用引用之前,必须明确在C++中引用的引用是非法的。会产生对左值引用的右值引用,然后引用折叠规则告诉我们结果就是左值引用。第一,也是最常见的就是模板实例化。
2024-05-15 07:40:12 785
原创 Effective Modern C++ 条款27:熟悉通用引用重载的替代方法
更多C++学习笔记,关注 wx公众号:cpp读书笔记中说明了对使用通用引用形参的函数,无论是独立函数还是成员函数(尤其是构造函数),进行重载都会导致一系列问题。但是也提供了一些示例,如果能够按照我们期望的方式运行,重载可能也是有用的。这个条款探讨了几种,通过避免在通用引用上重载的设计,或者通过限制通用引用可以匹配的参数类型,来实现所期望行为的方法。讨论基于中的示例,如果你还没有阅读那个条款,请先阅读那个条款再继续。
2024-05-15 07:39:13 730
原创 Effective Modern C++ 条款26:避免在通用引用上重载
中说明,在适当的条件下,C++会生成拷贝和移动构造函数,即使类包含了模板化的构造函数,模板函数能实例化产生与拷贝和移动构造函数一样的签名,也在合适的条件范围内。如同注释表示的,派生类的拷贝和移动构造函数没有调用基类的拷贝和移动构造函数,而是调用了基类的完美转发构造函数!根据正常的重载解决规则,精确匹配优先于类型提升的匹配,所以被调用的是通用引用的重载。确实我们是这样想的,但是编译器严格遵循C++的规则,这里的相关规则就是控制对重载函数调用的解析规则。使用通用引用的函数在C++中是最贪婪的函数。
2024-05-14 08:57:20 649
原创 Effective Modern C++ 条款25:对右值引用使用std::move,对通用引用使用std::forward
对标准中教条的(也可以说是有毒的)絮叨做些解释,这个特定的好事就是说,编译器可能会在按值返回的函数中消除对局部对象的拷贝(或者移动),如果满足(1)局部对象与函数返回值的类型相同;增加的开销根据实现不同而不同,这些开销是否值得担心也跟应用和库的不同而有所不同,但是事实上,将通用引用模板替换成对左值引用和右值引用的一对函数重载在某些情况下会导致运行时的开销。一些人将RVO的应用区分为命名的和未命名的(即临时的)局部对象,限制了RVO术语应用到未命名对象上,并把对命名对象的应用称为。而是设计的可扩展性差。
2024-05-14 08:56:53 742
原创 EffectiveModern C++ 条款24:区分通用引用与右值引用
如果初始值是一个右值,那么通用引用就会是对应的右值引用,如果初始值是一个左值,那么通用引用就会是一个左值引用。,它们依赖于右值引用和通用引用的区别。就像牛顿的力学定律(本质上不正确),比起爱因斯坦的广义相对论(这是真相)而言,往往更简单,更易用。”),并且,当你在和你的合作者交流时,它会帮助你避免歧义(“在这里我在用一个通用引用,而非右值引用”)。它们的二重性使它们既可以绑定到右值上(就像右值引用),也可以绑定到左值上(就像左值引用)。”的另一种意思是,它既可以是右值引用,也可以是左值引用。
2024-05-13 09:07:18 794
原创 Effective Modern C++ 条款23:理解std::move和std::forward
前者是典型地为了移动操作,而后者只是传递(亦为转发)一个对象到另外一个函数,保留它原有的左值属性或右值属性。的吸引力在于它的便利性:减少了出错的可能性,增加了代码的清晰程度。是移动操作的候选者。接受一个对象的引用(准确的说,一个通用引用(universal reference),见。的,因为我们可以到处直接写转换代码,但是我希望我们能同意:这将相当的,嗯,让人恶心。返回的真的是右值引用,这很重要,因为函数返回的右值引用是右值。,你能确保的唯一一件事就是将它应用到一个对象上,你能够得到一个右值。
2024-05-13 09:06:50 684
原创 Effective Modern C++ 条款22:当使用Pimpl惯用法,请在实现文件中定义特殊成员函数
凭借这样一种技巧,你可以将类数据成员替换成一个指向包含具体实现的类(或结构体)的指针,并将放在主类(primary class)的数据成员们移动到实现类(implementation class)去,而这些数据成员的访问将通过指针间接访问。而言,删除器的类型不是该智能指针的一部分,这让它会生成更大的运行时数据结构和稍微慢点的代码,但是当编译器生成的特殊成员函数被使用的时候,指向的对象不必是一个完整类型。这样的做法会导致同样的错误,和之前的声明一个不带析构函数的类的错误一样,并且是因为同样的原因。
2024-05-11 09:18:19 896
原创 Effective Modern C++ 条款21:优先考虑使用std::make_unique和std::make_shared,而非直接使用new
源代码中的重复增加了编译的时间,会导致目标代码冗余,并且通常会让代码库使用更加困难。但是,因为控制块和对象被放在同一块分配的内存块中,直到控制块的内存也被销毁,对象占用的内存才被释放。这种优化减少了程序的静态大小,因为代码只包含一个内存分配调用,并且它提高了可执行代码的速度,因为内存只分配一次。这些函数的存在意味着对这些类型的对象的全局内存分配和释放是不合常规的。中的两个:接收任意的多参数集合,完美转发到构造函数去动态分配一个对象,然后返回这个指向这个对象的指针。函数中,完美转发使用小括号,而不是花括号。
2024-05-11 09:17:50 646
空空如也
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人