OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 16320|回复: 11

函数指针作为结构体的成员

[复制链接]

98

主题

408

帖子

3

精华

金牌会员

Rank: 6Rank: 6

积分
1280
金钱
1280
注册时间
2010-12-14
在线时间
0 小时
发表于 2011-1-27 01:33:49 | 显示全部楼层 |阅读模式

     今晚听原子说起函数指针作为结构体成员的用法,很久没去复习过c语言,回来后特地找了个测试程序,发现这种用法有点像java里面的函数调用,思想值得借鉴。
把一些实体定义为结构体变量,而实体的固有属性便是基本数据类型定义的成员变量,而函数指针类型的成员变量可以抽象为你能对这个实体发出的请求,
例如一个遥控器实体,它具备的固有属性为品牌,按键数等等,而你可以发出的请求为按按键发送指令。
#include "stdio.h"   
struct DEMO   //遥控器实体
{  
    char x;   // 按键
    int (*func)(int x,int y); //函数指针    //按按键
};  
 
int add2(int x,int y)   //定义遥控器发送指令
{  
    return x+y;  
}  
 
int dec2(int x,int y)   //定义遥控器发送指令
{  
    return x-y;  
}  
 
struct DEMO demo[2] =   
{  
    {1,add2},       {2,dec2}  
};   
int main(void)
{  
    printf("func%d=%d\n",demo[0].x,demo[0].func(4,3));  
    printf("func%d=%d\n",demo[1].x,demo[1].func(4,3));   
    return 0;  


说明:demo[0],demo[1]可以看做两种不同功能的遥控器实体,
demo[0].x为获取遥控器的固有属性,可以是遥控器的品牌
demo[0].func(4,3)可以抽象为同时按下4,3按键后遥控器的反应;

此源码没有运行过!


希望openedv能给大家提供一个友好的技术交流平台!
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165309
金钱
165309
注册时间
2010-12-1
在线时间
2108 小时
发表于 2011-1-27 08:53:04 | 显示全部楼层

 
我发一个运行过的源码。
在.h文件中,有如下代码:

//TVM控制状态
typedef struct _m_TVM_CTRL
{
 u32(*get_coin_totval)(void); //得到此次投入硬币总金额
 u32(*get_coin_totcnt)(void); //得到此次投入硬币总数目
 void(*clr_coin)(void);   //清空金额和数目,每次新投币开始执行

 u32(*get_coin_totrval)(void);//得到此次找零的总金额
 u32(*get_coin_totrcnt)(void);//得到此次找零的硬币总数目
 void(*clr_rcoin)(void);   //清空金额和数目,每次新找零开始执行

 void(*clr_hpx)(void);      //清空某个hp中的所有硬币
 void(*thp_add_money)(void);  //将钱数汇总到循环找零hp中,当chg_mode为1的时候,可以执行该函数
  u8  cur_cmd;           //当前指令 0X00,无有效指令;0X32,开始收钱;0X33,硬币回收;0X34,找零;
  u16 cmd_prm;         //指令参数
 u8  cmd_sta;                 //指令执行状态
 m_HP_MESSAGE hp_msg[4];   //每个hopper的状态信息
}m_TVM_CTRL;
extern m_TVM_CTRL     TVM_CTRL;    //控制器

在.c文件中,有如下代码:
//TVM主控制器     
m_TVM_CTRL     TVM_CTRL=    //控制器
{
 get_coin_totval,
 get_coin_totcnt,
 clr_coin,

 get_coin_totrval,
 get_coin_totrcnt,
 clr_rcoin,

 clr_hpx,
 thp_add_money,
  0,
 0,
 0,
 0,  
};
get_coin_totva, clr_coinl等都是在.c文件中存在的函数的函数名。
这样,就完成了TVM_CTRL这个结构体的函数指针初始化,
接下来就可以方便应用了。
比如我要清空TVM的金额,我只需要写:TVM_CTRL.clr_coin();即可。
又比如,我要清空某个HOPPER,只需要写:TVM_CTRL.clr_hpx();
这样可以及其方便的管理某些设备的各个状态。

你可以把任何一个外设都定义为一个结构体,然后在这个里面包含了该外设的所有执行函数,及状态变量。从而非常方便的控制该外设。
更好的是,一旦有任何新增功能,只需要在原来的结构体里面塞函数或者变量就可以了。及其方便维护。




我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复 支持 反对

使用道具 举报

98

主题

408

帖子

3

精华

金牌会员

Rank: 6Rank: 6

积分
1280
金钱
1280
注册时间
2010-12-14
在线时间
0 小时
 楼主| 发表于 2011-1-27 10:06:39 | 显示全部楼层
    可以通过这种方法把面向过程(c)和面向对象(java,c++)的思想联系起来!这种思想很实用!
希望openedv能给大家提供一个友好的技术交流平台!
回复 支持 反对

使用道具 举报

7

主题

12

帖子

0

精华

初级会员

Rank: 2

积分
61
金钱
61
注册时间
2010-12-14
在线时间
0 小时
发表于 2011-1-27 11:08:43 | 显示全部楼层
结构体可以看成c++里面的类,只是封装性不好而已。
回复 支持 反对

使用道具 举报

7

主题

12

帖子

0

精华

初级会员

Rank: 2

积分
61
金钱
61
注册时间
2010-12-14
在线时间
0 小时
发表于 2011-1-27 13:55:28 | 显示全部楼层
附上一个详细的用c实现面向对象的文档。

Object-oriented C.pdf

1.2 MB, 下载次数: 3525

回复 支持 反对

使用道具 举报

98

主题

408

帖子

3

精华

金牌会员

Rank: 6Rank: 6

积分
1280
金钱
1280
注册时间
2010-12-14
在线时间
0 小时
 楼主| 发表于 2011-1-27 14:15:26 | 显示全部楼层
回复【5楼】levension:
-------------------------------
谢谢长老!呵呵!回家好好研究一下!!
希望openedv能给大家提供一个友好的技术交流平台!
回复 支持 反对

使用道具 举报

98

主题

408

帖子

3

精华

金牌会员

Rank: 6Rank: 6

积分
1280
金钱
1280
注册时间
2010-12-14
在线时间
0 小时
 楼主| 发表于 2011-1-28 00:25:45 | 显示全部楼层
代码已经测试过了,OK!
希望openedv能给大家提供一个友好的技术交流平台!
回复 支持 反对

使用道具 举报

56

主题

289

帖子

0

精华

高级会员

Rank: 4

积分
865
金钱
865
注册时间
2012-11-16
在线时间
65 小时
发表于 2013-10-30 21:07:12 | 显示全部楼层
谢谢原子 学习了
回复 支持 反对

使用道具 举报

56

主题

289

帖子

0

精华

高级会员

Rank: 4

积分
865
金钱
865
注册时间
2012-11-16
在线时间
65 小时
发表于 2013-10-30 21:10:04 | 显示全部楼层
用这种方法一定好吗 在有些情况下会不会有什么缺陷
回复 支持 反对

使用道具 举报

5

主题

18

帖子

0

精华

初级会员

Rank: 2

积分
63
金钱
63
注册时间
2016-2-6
在线时间
13 小时
发表于 2016-2-28 21:11:53 | 显示全部楼层
学习了
回复 支持 反对

使用道具 举报

5

主题

158

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
200
金钱
200
注册时间
2016-5-29
在线时间
5 小时
发表于 2016-6-1 16:39:54 | 显示全部楼层
学习下
回复 支持 反对

使用道具 举报

1

主题

16

帖子

0

精华

初级会员

Rank: 2

积分
101
金钱
101
注册时间
2013-8-8
在线时间
11 小时
发表于 2016-12-14 17:26:27 | 显示全部楼层
正点原子 发表于 2011-1-27 08:53
 
我发一个运行过的源码。
在.h文件中,有如下代码:

原子哥,我在工程中也是使用了结构体封装函数指针,但是现在出现了一个严重的问题,就是程序很容易跑飞。例如我加一句无关重要的语句到调用了指针函数的普通函数中且导致了程序无法运行。我个人首先判断出现这个现象的原因,是我在指针函数中有调用了指针函数。你觉得有可能是这个原因造成的?求帮助!!
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2024-11-23 09:53

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表