【发布时间】:2017-03-10 10:00:54
【问题描述】:
Scott Meyer 的“Effective Modern C++”讨论了 std::unique_ptr 与自定义删除器的使用并指出:
作为函数指针的删除器通常会导致
std::unique_ptr的大小从 1 增长 两个字。对于作为函数对象的删除器,大小的变化取决于函数对象中存储了多少状态。无状态函数对象(例如,来自没有捕获的 lambda 表达式)不会产生大小损失,这意味着当自定义删除器可以实现为函数或无捕获 lambda 表达式时,lambda 更可取。
举个例子:
auto delInvmt1 = [](Investment* pInvestment) {
makeLogEntry(pInvestment);
delete pInvestment;
};
template<typename... Ts>
std::unique_ptr<Investment, decltype(delInvmt1)>
makeInvestment(Ts&&... args);
比这更好:
void delInvmt2(Investment* pInvestment) {
makeLogEntry(pInvestment);
delete pInvestment;
}
template<typename... Ts>
std::unique_ptr<Investment, void (*)(Investment*)>
makeInvestment(Ts&&... params);
我可以看到,在第二种情况下,需要将指向删除函数的指针存储在 unique_ptr 中,但是为什么对于 lambda 情况不需要存储任何类似的东西呢?
【问题讨论】:
-
std::unique_ptr正在使用空基优化,它允许存储空对象(即没有数据成员的类)而不会产生额外的大小开销。 -
在第一种情况下,逻辑是 type 的一部分,在第二种情况下,它是 value 的一部分。
标签: c++ unique-ptr