如何将方法作为函数指针存储在地图容器中?

时间:2018-11-16 11:22:52

标签: c++ function pointers

我希望能够基于从文件中读取的数据来调用函数。 因此,对于每种项目类型,我想调用所需的reader方法。 我写了这段代码,但是无法在要向地图添加函数指针的地方编译。怎么了?

#include <vector>
#include <map>
#include <iostream>
class reader
{

  std::map< std::string, void(*)()> functionCallMap; // function pointer
  void readA(){ std::cout << "reading A\n";};
  void readB(){ std::cout << "reading B\n";};;
public:
  reader()
  {
    *functionCallMap["A"] = &reader::readA;*
    *functionCallMap["B"] = &reader::readB;*
  }

  void read()
  {
   auto (*f) = functionCallMap["A"];
   (*f)();
  }



};

我正在构造器上填写地图。

4 个答案:

答案 0 :(得分:20)

您可以将vue-router与lambda或std::function结合使用:

std::bind

答案 1 :(得分:17)

您需要使用指向成员函数的指针,如下所示:

class reader
{
    using FuncPtr = void(reader::*)(); // function pointer
    std::map< std::string, FuncPtr> functionCallMap;
    void readA(){ std::cout << "reading A\n"; }
    void readB(){ std::cout << "reading B\n"; }
public:
    reader()
    {
        functionCallMap["A"] = &reader::readA;
        functionCallMap["B"] = &reader::readB;
    }

    void read()
    {
        auto f = functionCallMap["A"];
        (this->*f)();
    }
};

int main()
{
    reader r;
    r.read();
}

答案 2 :(得分:9)

到目前为止,有两个答案,thisthis

明显的区别是,一个使用UIAlertAction,另一个使用函数指针。这不是重要的区别!

关键是成员函数是非静态成员函数。因此,它们是std::function类型的 不是

它们的类型为void()。因此,只有给定类型为reader的对象时,才能调用它们;可以将其理解为隐藏参数。

first answer仅通过指定 正确 类型来解决该问题。可以使用功能指针(如所示)使用void(reader::*)()来完成(后者要贵得多!)。

second answer通过 绑定 指向类的特定实例的函数指针解决了该问题。绑定后,类型实际上就是std::function。不能使用原始函数指针来完成此操作(因为它们只能指向一个函数,而不能指向对象/函数对!)。

答案 3 :(得分:1)

我最终得到了这个解决方案。它确实可以完成工作,但是我对其美学还是有些怀疑。总之,总而言之,我得到了以下代码:

#include <map>
#include <iostream>
#include <functional>
class reader
{
    std::map< std::string, std::function<void(std::string tableName)>> functionCallMap; // function pointer
    void readA(const std::string tableName){ std::cout << "reading:" << tableName<< "\n"; }
    void readB(const std::string tableName){ std::cout << "reading:" << tableName <<"\n"; }
public:
    reader()
    {
      functionCallMap["A"] = std::bind(&reader::readA, this, std::placeholders::_1);
      functionCallMap["B"] = std::bind(&reader::readA, this, std::placeholders::_1);
    }

    void read()
    {
      const std::string table_name = "A";
      functionCallMap[table_name](table_name);
    }
};

int main()
{
    reader r;
    r.read();
}

我将表名传递给读取器,使用 bind placeholder 可以很好地完成。