通过名称在父级中调用子类方法

时间:2018-03-21 08:11:52

标签: c++

如何实施invoke功能?

class Args {};

class NoSuchMethod {};

class Base {
        public:
                Args invoke(std::string name, Args a) {
                        //get method and call it or
                        //throw NoSuchMethod()
                }
};

class One: public Base {
                int q;
        public:
                One(int q_): q(q_) {};
                Args test(Args a) {
                        printf("One::test() -> q = %d", q);
                };
};

class Two: public Base {
                std::string s;
        public:
                Two(std::string s_): s(s_) {};
                Args test2(Args a) {
                        printf("Two::test2() -> t = %s", s.c_str());
                };
};

std::vector<Base*> objs = {new One(123), new One(321), new Two("ha"), new One(0)};

int main() {
        objs[0]->invoke("test", Args());
        objs[1]->invoke("test", Args());
        objs[2]->invoke("test2", Args());
        objs[3]->invoke("test", Args());
}

1 个答案:

答案 0 :(得分:0)

您无法直接从字符串中调用方法。如果基本方法无法访问基本方法,则也无法从基本方法调用父方法。

实现这一目标的一种方法是设置一个包含所需功能的地图。

类似的东西(代码未编译,但它应该给你一个想法):

    class Base {
            public:
                    Args invoke(std::string name, Args a) {
                            auto foundMethod = methods_.find(name);

                            if (foundMethod == methods_.end())
                            {
                                    throw NoSuchMethod();
                            }

                            (*foundMethod)(a);
                    }
            protected:
                    std::map<std::string, std::function<void(Args)>> methods_;
    };

    class One: public Base {
                    int q;
            public:
                    One(int q_): q(q_)
                    {
                            methods_["test"] = std::bind(&One::test, this, std::placeholders::_1);
                    };

                    Args test(Args a) {
                            printf("One::test() -> q = %d", q);
                    };
    };

    class Two: public Base {
                    std::string s;
            public:
                    Two(std::string s_): s(s_)
                    {
                            methods_["test2"] = std::bind(&Two::test, this, std::placeholders::_1);
                    };

                    Args test2(Args a) {
                            printf("Two::test2() -> t = %s", s.c_str());
                    };
    };
相关问题