const构造函数
Const constructor
在C 中是否可以实现仅允许创建const
对象的构造函数?
我正在考虑将装饰器类与const
和非const
方法的接口进行。从const
基本对象初始化装饰器只能产生const装饰器,但是从非const初始化应产生功能齐全的装饰器。
struct A
{
virtual void foo(); // requires non-const A
virtual void bar() const; // const method
};
class decorator : public A
{
private:
std::shared_ptr<A> p_impl;
public:
virtual void foo() { p_impl->foo(); }
virtual void bar() const { p_impl->bar(); }
// regular constructor
decorator(std::shared_ptr<A> const & p) : p_impl(p) {}
// hypothetical constructor that makes a const
decorator(std::shared_ptr<A const> const & p) const : p_impl(p) {}
};
void F(std::shared_ptr<A> const & regular_a
, std::shared_ptr<A const> const & const_a )
{
decorator regular_decorator(regular_a);
regular_decorator.foo(); // all good
regular_decorator.bar(); // all good
decorator bad_decorator(const_a); // compiler error
// trying to use a const constructor to init a non-const object
const decorator const_decorator(const_a); // all good
const_decorator.foo(); // compiler error, foo is not const
const_decorator.bar(); // all good
// I have a lot of these in code that is beyond my control
decorator bad_practice(const_cast<decorator&>(const_decorator));
bad_practice.foo(); // all good
}
如何达到类似的效果?
我只能通过没有返回 const
对象的构造函数来获得此工作,而是返回 shared_ptr<const decorator>
的静态函数(a-la命名构造函数)。这是类型中的"编码"构成,并禁止非传播呼叫:
struct A
{
virtual void foo(); // requires non-const A
virtual void bar() const; // const method
};
class decorator : public A
{
private:
std::shared_ptr<A> p_impl;
public:
virtual void foo() { p_impl->foo(); }
virtual void bar() const { p_impl->bar(); }
// regular constructor
decorator(std::shared_ptr<A> const & p) : p_impl(p) {}
static std::shared_ptr<decorator const> constDecorator(std::shared_ptr<A const> const & p) { return std::make_shared<decorator>(std::const_pointer_cast<A>(p)); }
};
void F(std::shared_ptr<A> const & regular_a
, std::shared_ptr<A const> const & const_a )
{
decorator regular_decorator(regular_a);
regular_decorator.foo(); // all good
regular_decorator.bar(); // all good
decorator bad_decorator(const_a); // compiler error
// trying to use a const constructor to init a non-const object
std::shared_ptr<const decorator> const_decorator = decorator::constDecorator(const_a); // all good
const_decorator->foo(); // compiler error, foo is not const
const_decorator->bar(); // all good
// I have a lot of these in code that is beyond my control
decorator bad_practice(const_cast<decorator&>(*const_decorator));
bad_practice.foo(); // all good
}
当然,您也可以通过声明另一个静态功能来将shared_ptr
用于非CONST装饰器,从而获得const和non-const的使用模式相似。
请注意,这将需要您为decorator
删除复制构造函数和operator=
,因为它们会丢失constness。但是,您的版本中存在类似的问题。
我尝试过的另一种方法是使decorator
成为模板类,并且具有两种不同类型:decorator<A>
和decorator<const A>
,希望编译器不使用decorator<const A>::foo()
,除非使用它,否则它即使不使用,也可以继续实例化。
相关文章:
- 如何从构造函数副本 T(const T&)调用对象 T?
- 在 constexpr 构造函数 (c++17) 中赋值到 const char * 在使用 Android NDK 时
- 何时应在构造函数参数中使用 const C++?
- 在 C++ 中声明 const 对象需要用户定义的默认构造函数.如果我有一个可变成员变量,为什么不呢?
- 为什么构造函数 Message(const T&data) 与 Message(T&& data) 冲突,当 T = int&时?
- 如何在构造函数中传递 const 引用时强制编译器不接受右值
- C++将派生类的const值传递给基意外行为的构造函数
- 是否允许使用初始值设定项列表将const数组引用实例化为构造函数参数
- 在C++中,从构造函数中将字符串文本分配给成员const char*变量时会发生什么
- C++:使用委托构造函数时选择"const char *"与"std::string&qu
- 具有字符串文本构造函数的类不适用于 const 引用初始化
- 为什么在使用转换构造函数编译代码时需要 const 复制构造函数?
- C++ 在头文件或构造函数中初始化 const 类成员变量?
- 在没有构造函数的情况下初始化 const c++ 类
- 使用 const T(&x)[N][M] 构造函数类矩阵
- 为什么即使参数标记为"const",也会调用复制构造函数?
- 为什么带有 const 关键字的构造函数可以工作,而没有它就不能工作?
- 在复制构造函数中使用和不使用 const 有什么区别
- 构造函数"const variables"设置的用于表示C++数组的边界?
- 复制构造函数const char*和Shared_ptr