[英]Specify that a non-member function should be called instead of member function
我有一个名为成员的类f
,同时一个通用的自由函数调用f
。 自由函数f
是要从另一个成员(以下称为g
)调用的。
class A{};
int f(A const& a){return 5;} // generic free f
template<class T>
struct B{
void f() const{} // member f
int g(){
T a;
auto i = f(a) + 1; // here (cannot resolve f)
return i;
}
};
int main(){
B<A> b;
int j = b.g();
assert(j == 6);
}
事实证明,我的编译器(GCC和clang)无法解析对f
的调用。
error: no matching function for call to ‘B::f(A&)’
auto i = f(a) + 1; ^
note: candidate: void B::f() const
void f() const{} ^
note: candidate expects 0 arguments, 1 provided
当然,这是因为它与成员f
混淆。 但是,只有::f
才有意义。
如果要强制成员函数,可以说this->f
或B::f
。 但是我不知道有什么语法可以做相反的事情,即强制使用自由函数::f
或实际上是ADL给f
一些外部解析并禁用成员函数(诸如notthis->f
类的东西)。
我可以使用using ::f
:
... int g(){
T a;
using ::f;
auto i = f(a) + 1;
return i;
} ...
但是,这不是通用的,因为我不知道名称空间T
属于哪个名称,并且我想要通用的代码。 (这里是::
但是对于T = A
,但是对于其他名称空间中的其他类,我不知道)。
例如,类B<ns::C>
应该编译为:
namespace ns{
class C{};
int f(C const& a){return 5;} // genetic free f
}
当然,我可以重命名所有内容以避免冲突,但这不是一个可以接受的解决方案,假设同时具有free和member函数f
都是有意义的。
这是GCC和clang的错误,是语言的缺陷,还是我缺少一些明显的方法来指定不使用成员函数?
(该示例使用C ++ 11,但该问题对任何版本的C ++均有效)。
感谢@JohnZwinck,这是当前的解决方法
class A{};
int f(A const& a){return 5;} // genetic free f
class nonmember{
protected:
template<class TT> static decltype(auto) _f(TT&& t){return f(std::forward<TT>(t));}
};
template<class T>
struct B : private nonmember{
void f() const{} // member f
int g(){
T a;
auto i = _f(a) + 1;
return i;
}
};
这是GCC和clang的错误,是语言的缺陷吗?
以上都不是。 语言的设计决定是,名称与调用匹配的成员函数是最匹配的。 如果要避免它们,可以通过中间自由函数调用:
template<class T>
int call_f(const T& arg){
return f(arg);
}
template<class T>
struct B{
void f() const{}
int g(){
T a;
auto i = call_f(a) + 1;
return i;
}
};
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.