const引用函数指针

时间:2011-06-30 14:56:00

标签: c++ reference const function-pointers

我有一个函数Foo和一个类CDelegate。

typedef void (*typeFctPtr)(void*);


void Foo(void* dummy)
{
  cout << "Foo\n";
}


class CDelegate 
{ 
  public:

  CDelegate (const typeFctPtr& f_ref_Wrapper, void* f_pvSubscriber) 
    : m_ref_Wrapper(f_ref_Wrapper), m_pvSubscriber(f_pvSubscriber) 
  {
  }

  inline void operator () () const
  {
    (*m_ref_Wrapper)(0);
  }

  inline void operator=(const CInterruptDelegate& D)
  {
  }

private:
  void* m_pvSubscriber;
  const typeFctPtr& m_ref_Wrapper;
};

第二个类有一个静态成员static CDelegate m_Delegate;,我使用这样的构造函数进行初始化:

CInterruptDelegate CSpi1::m_Delegate(FreeFunction, 0);

我想通过调用静态对象的()运算符来调用FooCSpi1::m_Delegate();

我在(*m_ref_Wrapper)(0);收到例外 语法有问题吗?我不太确定我尝试做的事情是否可行。我有一个有效的解决方案,其中CDelegate的构造函数不接受函数指针的const引用,而是函数指针本身。然后我可以在()运算符中调用该函数而不会出现问题。我想使用const引用,因为函数指针调用无法优化,我希望通过const引用调用可以因为所有内容都应该在编译时知道。

2 个答案:

答案 0 :(得分:1)

你持有对函数指针的引用(并且指针是一个临时的,它在你使用它时被破坏了,所以事情出现了严重的错误。)

尝试将typedef更改为函数类型:

typedef void typeFct(void*);
...
const typeFct & m_ref_Wrapper;

然后使用现有的代码,你最终会得到一个函数的引用,你会没事的。或者您可以存储指向函数的指针 - const typeFct *

在任何一种情况下,电话都可以是m_ref_Wrapper(0)

一般来说,我更喜欢使用typedef函数类型而不是指向指针或引用,只是因为语法不那么难看。

答案 1 :(得分:1)

我认为问题在于成员的声明:

const typeFctPtr& m_ref_Wrapper;

相反,请尝试删除&

const typeFctPtr m_ref_Wrapper;

引用必须始终引用另一个现有对象。在这种情况下,它将引用创建的临时对象,以在调用构造函数时保存对指针的引用。

虽然我们正在使用它,但我建议你也应该从构造函数中删除引用。这样做的原因是当你使用标量时没有任何好处:s。

使代码更具可读性的另一件事是你要输入函数的类型,而不是指向函数的指针。这样,很明显你传了一个指针。

以下是一个简化版本,总结了我上面建议的更改:

typedef void (typeFct)(void*);

class CDelegate
{
  public:

  CDelegate (typeFct * f_Wrapper, void* f_pvSubscriber)
    : m_ref_Wrapper(f_Wrapper), m_pvSubscriber(f_pvSubscriber) 
  {
  }

  inline void operator () () const
  {
    (*m_ref_Wrapper)(0);
  }

private:
  void* m_pvSubscriber;
  typeFct * m_ref_Wrapper;
};