我必须创建三到四个类的对象,所有这些对象都继承自一个基类,但是一些对象需要具有不同的行为 - 比如完全改变一个函数;我可以通过更多的继承和多态来做到这一点,但这似乎不是一个好主意。
我的第一个解决方案是使用专门的模板(对于每个非标准的情况),但后来我将lambdas作为模板参数(例如:Can we use a lambda-expression as the default value for a function argument?)并使用它们代替类方法(如下所示:C++11 lambda and template specialization ) - 对我来说这是更好的解决方案,因为我只需要为每种奇怪的情况传递lambda:
auto default_lambda = [&]() -> int {return this->Sth;};
template<typename functor = decltype(default_lambda)>
class SomeClass{
...
问题在于这个指针 - 我想要更改的方法需要访问非静态方法,而lambda是在非静态方法之外定义的。而且,我不能将类的引用传递给lambda,因为它是一个模板类(或者我错了?)。
当然,我可以使用专门的模板或只是函数指针,但我真的很喜欢lambdas的解决方案,我认为它比我的其他想法更好。
有没有办法“避免”这个问题?或许我的想法一直很糟糕?
答案 0 :(得分:2)
您的方法至少存在三个明显的问题:
SomeClass
无法访问私人会员,即使用this
是不可能的。this
,但没有任何上下文,即没有任何绑定。您必须传递对象以处理函数参数。那就是说,似乎你可以使用自定义函数对象类型的类型而不是一些lambda函数(当然,这绝对是不合理的,但实际上它确实有效):
struct default_lambda {
template <typename T>
int operator()(T const& o) const { return o.x(); }
};
template <typename F = default_lambda>
class SomeClass {
...
};
答案 1 :(得分:0)
如果您需要完全更改一个功能,您有两个选择:
std::function
,如果你愿意,可以稍后反弹。第一个解决方案的示例代码(您甚至可以将其设为模板):
std::unique_ptr<my_base2> get_an_object()
{
class impl : public my_base2
{
void my_virtual_function() { blah blah; }
};
return std::unique_ptr<my_base2>(new impl);
}
在这种情况下,两者通常都优于模板(但没有上下文,很难分辨)。