完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
|
|
相关推荐
1个回答
|
|
提示:该菜单程序通过按键选择不同的功能,依托于某电设电子秤的题目要求。
一、循环链表 说到循环链表,必须要提到节点,循环链表是有节点组成的,而节点分为两部分,第一部分为数据域,存储着该节点的各项数据信息(以菜单来说,该节点就是菜单的某一项,存储着这一项的名称、属性、功能等),第二部分为指针域,可以把它理解为带有方向的箭头,他是指向另外一个节点的位置。 下图为一个单向链表,先不看h,后面的部分,每一个节点的指针域连接着下一个节点的,直到最后一个节点,其指针域为空,不指向任何一个节点。那么,访问任何一个节点,都可以通过遍历该链表实现。 其中,h为一个指针,指向该链表的头节点,那么,我们可以通过移动h,来访问任何一个节点的数据。 如果,我们把最后一个节点的指针域指向第一个节点,那么该链表首尾相连,就成为了一个循环链表。 二、菜单程序设计思路 现在我们只考虑一级菜单(即无子菜单),将该菜单类比于一个循环链表,菜单里的每一项都相当于一个节点。 那么,我们现在只需要定义好一个节点,并将每个节点连接起来,就可以完成一个一级菜单的制作。 三、节点定义、添加 前文提到。定义一个节点需要两部分,一部分为数据域,另一部分为指针域。指针域,我们暂且定义为一个,作用为指向下一个节点的地址。数据域,根据我们的需要,可以添加任何我们想要添加的内容,比如名称、属性、功能等。 如下: 其中,next_Menu指向下一级菜单,link指向下一项菜单(同级)。 typedef struct Menus* Menu; struct Menus { unsigned char* name; //Menu name unsigned char position;//name of positon unsigned int font_num;//number of name float price; unsigned char function_mode;//Menu function 0:self check 1:Cal 2:Add 3:... unsigned char price_mode; Menu next_Menu;//the second Menu Menu link; //the next Menu }; 这时,我们需要新的添加节点函数,因为原先的添加节点函数变量初始化是基于第一级菜单的。 注意:根据你的需要,你需要自定义你的数据域! unsigned char *Menu_price_name[]={(unsigned char *)"1.5",(unsigned char *)"2.5",(unsigned char *)"3.5",(unsigned char *)"4.5",(unsigned char *)"5.5",(unsigned char *)"6.5"}; //price of Menu unsigned char Menu_price_num[]={1.5 , 2.5 , 3.5 , 4.5 , 5.5 , 6.5}; unsigned int price_font_num[]={3,3,3,3,3,3}; //number of Menu Menu Attach_Menu_Price(Menu* pRear,int i,int mode) { Menu P; P = (Menu)malloc(sizeof(struct Menus)); P->link = NULL; P->next_Menu=NULL; P->name = Menu_price_name; P->font_num= price_font_num; P->price=Menu_price_num; P->function_mode=mode; P->price_mode=1; (*pRear)->link = P; *pRear = P; return P; } 我们还需要新的二级菜单初始化程序,暂定为价格菜单初始化程序,其原理是在当前节点的next_Menu创建一个新的菜单(循环链表)。 void Menu_Price_Init(Menu price,int mode) { Menu Start, Rear, t, End; int num; num= sizeof(Menu_price_num)/ sizeof(Menu_price_num[0]); Start = (Menu)malloc(sizeof(struct Menus)); Start->link = NULL; Rear = Start; for (int i = 0; i < num-1; ++i) { Attach_Menu_Price(&Rear, i,mode); } End= Attach_Menu_Price(&Rear, num-1,mode); t = Start; Start = Start->link; free(t); End->link = Start; price->next_Menu=Start; } 那么,我们还需要在一级菜单的初始化程序中,修改一下,添加一个if判断在哪项菜单添加二级菜单: Menu Menu_Init(void) { Menu Start, Rear, t, End; int num=5; num= sizeof(Menu_name)/ sizeof(Menu_name[0]); Start = (Menu)malloc(sizeof(struct Menus)); Start->link = NULL; Rear = Start; for (int i = 0; i < num-1; i++) { Attach_Menu(&Rear, i); if (! strcmp((const char *)Rear->name,"Cal_Price")||! strcmp((const char *)Rear->name,"Add_Price")) { Menu_Price_Init(Rear,i); } } End= Attach_Menu(&Rear, num-1); t = Start; Start = Start->link; free(t); End->link = Start; return Start; } 至此,一个完整的二级菜单创建完毕,如果需要三级菜单,则需要在二级菜单的初始化程序中,假如if判断,步骤同二级菜单建立过程一样。 那么,在按键菜单功能中,如何进行菜单的选择呢? 如果按键为菜单、选择、确认。 我们需要定义两个Menu全局变量,第一个为Start,第二个为pRear,Start指向的菜单的第一项,pRear 指向的是当前选择的菜单,默认为第一项。 通过按键中断,如果是Select可以移动pRear移动到当前指向菜单的下一项(pRear=pRear->link),pRear指向哪一项,就执行pRear所指的菜单的功能函数。当需要重新选择功能时(即再次进入菜单时,将pRear复位,令pRear=Start即可),令pRear指向开头的节点即可。如果是确认按键,先判断当前所指菜单是否有子菜单,如果有,进入子菜单,如果没有,再执行相应的函数即可。 |
|
|
|
只有小组成员才能发言,加入小组>>
2512 浏览 0 评论
1082浏览 2评论
696浏览 1评论
452浏览 0评论
192浏览 0评论
326浏览 0评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-11-21 01:33 , Processed in 1.259904 second(s), Total 78, Slave 60 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号