这个指向成员的指针转换有什么问题

what is wrong with this pointer to member conversion?

本文关键字:转换 什么 问题 指针 成员      更新时间:2023-10-16

此代码有什么问题?我想我可以转换由于这个答案:

安全吗;upcast";方法指针,并将其与基类指针一起使用?

struct B
{
  void f(){}
};
struct D : B
{
  virtual ~D(){}
};
template <typename FP, FP fp>
void g()
{
}
int main()
{
  g<void (D::*)(), &B::f>();
  return 0;
}

错误:

t.cpp:18:27: error: could not convert template argument '&B::f' to 'void (D::*)()'
   g<void (D::*)(), &B::f>();

这也不起作用:

g<void (D::*)(), static_cast<void (D::*)()>(&B::f)>();

这是标准(C++11,[temp.arg.notype]§5)不允许的:

对用作非类型模板参数的每个表达式执行以下转换如果非类型的模板参数无法转换为相应的模板参数的类型,则程序格式错误。

  • 对于指向成员函数的指针类型的非类型模板参数,如果模版参数则,不应用任何转换。如果模板参数表示一组重载的成员函数,则从该集合中选择匹配的成员函数(13.4)

(强调矿)

由于[temp.arg.notype]§1:,也不允许铸造

非类型、非模板的模板参数template自变量应为以下之一:

  • 指向如5.3.1中所述的成员的指针

其中5.3.1§4为:

只有当使用显式&并且其操作数是不包含在括号中的限定id时,才形成指向成员的指针。

这意味着不允许将强制转换表达式作为非类型模板参数。

因此,虽然这种转换在运行时是可能的,但似乎没有办法将它们用作模板参数。