假设我有一个 c++ 类,其成员函数为 const 重载,如下所示:
Type* DoSomething();
const Type* DoSomething() const;
如果这是一个更大、更复杂的成员,如何防止必须编写两次相同的代码?不能从 const 调用任何非常量函数。并且从非常量调用 const 版本会导致 const 指针必须强制转换为非常量(这有点 imo 的味道)。
假设我有一个 c++ 类,其成员函数为 const 重载,如下所示:
Type* DoSomething();
const Type* DoSomething() const;
如果这是一个更大、更复杂的成员,如何防止必须编写两次相同的代码?不能从 const 调用任何非常量函数。并且从非常量调用 const 版本会导致 const 指针必须强制转换为非常量(这有点 imo 的味道)。
您可以委托给模板静态成员函数,如下所示:
class Widget
{
Type member;
template<typename Result, typename T>
static Result DoSomethingImpl(T This)
{
// all the complexity sits here, calculating offsets into an array, etc
return &This->member;
}
public:
Type* DoSomething() { return DoSomethingImpl<Type*>(this); }
const Type* DoSomething() const { return DoSomethingImpl<const Type*>(this); }
};
在 C++11 中,您甚至可以摆脱非推断模板参数,使用:
static auto DoSomethingImpl(T This) -> decltype(This->member)
你做了一次,第二次用类上的 const 属性做,你可以使用const_cast
:
class Foo
{
Type* DoSomething()
{
// Lots of stuff
}
const Type* DoSomething() const
{
return const_cast<Foo*>(this)->DoSomething();
}
}
使用模板方法模式从中提取公共代码。例如。
inline const T* prev(size_t i) const
{
return &FBuffer[ AdjustIndex(i) ];
}
inline T* prev(size_t i)
{
return &FBuffer[ AdjustIndex(i) ];
}
inline size_t AdjustIndex( size_t i ) const
{
return Math::ModInt( static_cast<int>( FHead ) - 1 - i, static_cast<int>( FBuffer.size() ) );
}
这种技术可以应用于许多情况(但不是所有情况,即如果行为显着不同)。