songshiqun2010 发表于 2019-6-28 14:57:18

C语言的转换表 C++怎么实现?

1.成员函数指针
转自http://www.cppblog.com/dragon/archive/2010/12/02/135250.html
/*
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif *测试成员函数指针数组的小程序
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif */
http://www.cppblog.com/Images/OutliningIndicators/None.gif#include <iostream>
http://www.cppblog.com/Images/OutliningIndicators/None.gifusing namespace std;
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gifclass Test
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockStart.gif{
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gifpublic:
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    Test();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    ~Test();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gifprivate:
http://www.cppblog.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif    void add5(){ res+=5;}
http://www.cppblog.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif    void add6(){ res+=6;}
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    void (Test::*add)();//这个2至关重要,在VC下没写会报错,但在QT里没报,但析构时出错!
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gifpublic:
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    void DoAddAction();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    void Display();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gifprivate:
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    int res;
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif};
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gifTest::Test()
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockStart.gif{
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    add=&Test::add5;//注意这里的写法
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    add=&Test::add6;
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    res=0;
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif}
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gifTest::~Test()
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockStart.gif{
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif}
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gifvoid Test::DoAddAction()
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockStart.gif{
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    for (int i=0;i<2;i++)
http://www.cppblog.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif    {
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif      (this->*add)();//使用类成员函数指针必须有“->*”或“.*”的调用
http://www.cppblog.com/Images/OutliningIndicators/ExpandedSubBlockEnd.gif    }
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif}
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gifvoid Test::Display()
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockStart.gif{
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    cout<<"The res is:"<<res<<endl;
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif}
http://www.cppblog.com/Images/OutliningIndicators/None.gif
http://www.cppblog.com/Images/OutliningIndicators/None.gifint main()
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockStart.gif{
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    Test * test=new Test();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    test->DoAddAction();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    test->Display();
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    delete test;
http://www.cppblog.com/Images/OutliningIndicators/InBlock.gif    return 0;
http://www.cppblog.com/Images/OutliningIndicators/ExpandedBlockEnd.gif}


2.c++中成员函数指针数组定义和初始化方法

转自http://www.cnblogs.com/sunowfox/p/6875051.html
实际项目中经常遇到很多类似操作,比如命令码对应执行函数等,对于此类操作,比较好的方式是使用const数组,将命令码和操作函数绑定在一起,通过查表方式找到操作函数,并执行操作函数。这样可以简化代码,降低复杂度,在c中这种方式很好实现,在c++中会稍微麻烦一些。以串口命令解析执行为例,首先定义一个结构体,定义操作函数的指针类型:struct T_ShellInfo{    string cmd;    void (* DealFunc)(const vector<string> &vectStr);    string desc;};
定义命令解析执行类,处理函数要定义成static,定义一个const static的数组:http://common.cnblogs.com/images/copycode.gif
class CShell{public:    CShell();    ~CShell();    void RecvCmd();private:       enum{SHELL_INFO_NUM_MAX=10};    void GetCmd(const char *cmdStr, vector<string> &vectStr);    void Deal(const vector<string> &vectStr);      static void CmdHelp(const vector<string> &vectStr);    static void CmdLed(const vector<string> &vectStr);    static void CmdTask(const vector<string> &vectStr);    static void CmdDisk(const vector<string> &vectStr);    static void CmdTime(const vector<string> &vectStr);    static void CmdReboot(const vector<string> &vectStr);       CShell *_self;    const static T_ShellInfo _shellInfo; };http://common.cnblogs.com/images/copycode.gif

实现时,先初始化数组http://common.cnblogs.com/images/copycode.gif
const T_ShellInfo CShell::_shellInfo={    {"?",       CmdHelp,    "show all cmd"},    {"help",    CmdHelp,    "show all cmd"},    {"time",    CmdTime,    "show sys time"},    {"task",    CmdTask,    "show all task info"},    {"disk",    CmdDisk,    "disk cmd "},    {"led",   CmdLed,   "set led "},    {"reboot",CmdReboot,"reboot sys"},      {"",NULL,""}};http://common.cnblogs.com/images/copycode.gif

串口收到命令后,只要遍历此数组,找到相同命令码的执行函数并执行即可http://common.cnblogs.com/images/copycode.gif
void CShell::Deal(const vector<string> &vectStr){    for (u8 i = 0; i< SHELL_INFO_NUM_MAX; i++)    {      if (_shellInfo.cmd.length() == 0)      {            break;      }      if (_shellInfo.cmd == vectStr[0])      {            _shellInfo.DealFunc(vectStr);            return;      }    }    printf("cmd \"%s\" err!\r\n", vectStr[0].c_str());}http://common.cnblogs.com/images/copycode.gif

然后逐个实现对应操作函数:http://common.cnblogs.com/images/copycode.gif
void CShell::CmdTask(const vector<string> &vectStr){    u8 pcWriteBuffer[500]={0};    //u8 *pcWriteBuffer = new u8; //这个值要小心,太小会导致数组溢出,太大会导致堆栈溢出    printf("=================================================\r\n");    printf("任务名      任务状态 优先级   剩余栈 任务序号\r\n");    vTaskList((char *)&pcWriteBuffer);    printf("%s\r\n", pcWriteBuffer);    //delete[] pcWriteBuffer;}http://common.cnblogs.com/images/copycode.gif



3.采用第一节 所述方法keil5编译成功,第二节所述方法未成功。

但成员函数的指针所占内存空间并非,通常的4字节,内存浪费严重。
没想到解决途径,留个疑问。





edmundlee 发表于 2019-6-28 15:55:55

将T_ShellInfo的 两个String 都改为char的指针(char*)然后把String放于const char[][], 就不会浪费了
页: [1]
查看完整版本: C语言的转换表 C++怎么实现?