【问题标题】:Function templates and Private Inheritance函数模板和私有继承
【发布时间】:2011-07-04 09:46:57
【问题描述】:

我最近在使用私有继承方案时遇到了一个问题,其中基类定义了一个模板方法,而(私有)派生类通过 public 访问说明符下的 using 声明将该方法公开。该模板旨在获取函数的地址并调用该函数指针。但是,在尝试将函数名称传递给派生类模板方法时,我收到一条错误消息,指出基类方法无法访问派生类中声明的私有成员。这是一个模拟问题的代码段:

class A
{ 
public:
     template<class T> void Funct(T pFunct) { }
};

class B : private A
{
public:
    using A::Funct;
};

void Show(void) { }

int main(void)
{
    B b;
    b.Funct(Show);
}

准确的错误消息是:'A::Funct' : cannot access private member declared in class 'B'

我可以通过以下方式解决问题:

1)在函数参数名称前加上地址运算符:

b.Funct(&Show);

2)显式限定模板类型参数:

b.Funct<void(*)(void)>(Show)

如果Show() 函数也是模板,我需要使用用于实例化Show 的正确模板类型参数显式限定模板。

我的问题不是如何解决问题,而是为什么会生成错误消息。为什么用Show&amp;Show 实例化Funct() 会导致编译器做两件不同的事情。为什么用Show 实例化Funct() 会导致Funct() 方法尝试访问B 类中的私有数据(我假设它是B 类中的A 子对象)?

【问题讨论】:

  • 什么编译器?你的例子用 g++ 4.2 编译得很好。
  • 有趣。我正在使用 Microsoft Visual C++ 2010
  • 这是视觉工作室吗?一些旧版本的模板参数中的成员函数指针存在问题。
  • 是的,是VC。那么可能是某种错误?
  • 使用 Intellisense,如果没有 &amp;Show 或明确指定 void(*)(void) 作为类型,VC 不知道模板的正确类型。如果您有 &amp;Show,当您将鼠标悬停在 Funct&lt;void(*)(void)&gt; 上时,Intellisense 将正确地将其显示为完全限定的函数。

标签: c++ templates function inheritance private


【解决方案1】:

bcc32 给出错误:error bccE2247: 'Funct&lt;void (*)()&gt;(void (*)())' is not accessible in function main()

我相信这是一个编译器错误。

【讨论】:

    【解决方案2】:

    使用 Comeau Online 可以正常编译。因此,编译器错误。举报吧。

    干杯,

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-10-30
      • 2016-12-30
      • 1970-01-01
      • 2023-01-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多