【问题标题】:Calling a method with an array of pointers to class::method使用指向 class::method 的指针数组调用方法
【发布时间】:2018-11-20 03:22:09
【问题描述】:

我想调用一个方法,该方法将接受一个指向类列表的指针作为参数:方法指针:

void dispatch ( int cmdCount, methodFunction *pointer [] ) {
...
}

这个typedef创建methodFunction:

typedef void ( ClassName::*methodFunction )( char, char );

但我看不到如何使 ClassName 成为传递给调度的东西。我认为这需要某种形式的模板,但我还不清楚模板。

这是我的全部代码(将代码放入 TemplateTest.ino 和 code.h:

    //  Template Test
    #include "code.h"

    Dispatcher *dispatcher;
    Example1 ex1;
    Example2 ex2;

    void setup() {
        Serial.begin ( 115200 );

        ex1.execute ( 'a', '+' );
        ex1.execute ( 'b', '-' );
        ex2.execute ( 'y', '?' );
    }

    void loop() {}

    <<<<<<<<<< NEW FILE: code.h >>>>>>>>>>>>

#pragma once

class Dispatcher {
public:
    template<class T>

    void dispatch ( T& instance, void(T::*func)(char sel, char act), char def [][2], int cmdCount ) {
        //  Walk through the array containing sel,act pairs.
        //  When we find a match, launch the function from
        //  tPointer with the same index value.
        for (int i = 0; i < cmdCount; i++) {
            char _sel = def [i] [0];
            char _act = def [i] [1];
            if (( sel == _sel ) && ( act == _act )) {
                ( *T [i] )( sel, act );
                return;
            }
        }
    }
};

//  Example 1 Code
char ex1Array [] [2] = {
    {'a','+'},
    {'a','-'},
    {'b','+'},
    {'b','-'},
};

class Example1 {
public:

    char *_name = "Template Example 1";

    Dispatcher disp;

    static const int cmdCount = sizeof ( ex1Array ) / sizeof ( ex1Array [0] );

    typedef void ( Example1::*FunctionPointer )( char sel, char act );

    //  Function dispatch table
    FunctionPointer cmdMethods [cmdCount] = {
        &Example1::alphaPlus,
        &Example1::alphaMinus,
        &Example1::betaPlus,
        &Example1::betaMinus,
    };

    Example1 () {
    }

    void alphaPlus ( char sel, char act ) {
        Serial.println ( F ( "Alpha +" ) );
    }
    void alphaMinus ( char sel, char act ) {
        Serial.println ( F ( "Alpha -" ) );
    }
    void betaPlus ( char sel, char act ) {
        Serial.println ( F ( "Beta +" ) );
    }
    void betaMinus ( char sel, char act ) {
        Serial.println ( F ( "Beta -" ) );
    }

    void execute ( char sel, char act ) {
        disp.dispatch ( *this, cmdMethods [0], 'a', 'b', ex1Array[0], cmdCount );
    }

};

//  Example 2 
char ex2Array [] [2] = {
    {'x','?'},
    {'y','?'},
    {'z','?'},
};

class Example2 {
public:

    char *_name = "Template Example 2";

    Dispatcher disp;

    static const int cmdCount = sizeof ( ex2Array ) / sizeof ( ex2Array [0] );

    typedef void ( Example2::*FunctionPointer )( char sel, char act );

    //  Function dispatch table
    FunctionPointer cmdMethods [cmdCount] = {
        &Example2::x,
        &Example2::y,
        &Example2::z,
    };

    Example2 () {
    }

    void x ( char sel, char act ) {
        Serial.println ( F ( "X" ) );
    }
    void y ( char sel, char act ) {
        Serial.println ( F ( "Y" ) );
    }
    void z ( char sel, char act ) {
        Serial.println ( F ( "Z" ) );
    }

    void execute ( char sel, char act ) {
        disp.dispatch ( *this, cmdMethods [0], 'a', 'b', ex2Array [0], cmdCount );
    }
};

【问题讨论】:

    标签: c++ templates arduino typedef


    【解决方案1】:

    dispatch 应该使用实例调用。

    template<class T>
    void dispatch(T& instance, void(T::*func)(char, char), char param1, char param2  )
    {
      instance.*func(param1, param2);
    }
    

    呼叫调度:

    dispatch(*this, cmdMethods[0], 'a', 'b');
    

    【讨论】:

    • 谢谢,潘艾敏。您的意见有所帮助。我已根据您的建议更新了发布的代码,但仍有五个编译错误。
    • @BobJones 例如,您不能使用来自void(T::*func)(char sel, char act)selact。你怎么会通过呢?您拥有的唯一变量是func。另一个错误是关于向调度传递的参数过多(可能与以前有关)。
    猜你喜欢
    • 2020-09-02
    • 2015-06-17
    • 1970-01-01
    • 2011-01-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-01-04
    相关资源
    最近更新 更多