-
本人经过摸索实验,并总结,大致应用程序的架构有三种:
1.
简单的前后台顺序执行程序,
这类写法是大多数人使用的方法,不需用思考程序的具体
架构,直接通过执行顺序编写应
用程序即可。
2.
时间片轮询法,此方法是介于顺序执行与操作系统之间的一种方法。
3.
操作系统,此法应该是应用程序编写的最高境界。
下面就分别谈谈这三种方法的利弊和适应范围等。
。
。
。
。
。
。
。
。
。
。
。
。
1.
顺序执行法:
这种方法,
这应用程序比较简单,
实时性,
< br>并行性要求不太高的情况下是不错的方法,
程序设计简单,
思路比较清晰。
但是当应用程序比较复杂的时候,
如果没有一
个完整的流程
图,
恐怕别人很难看懂程序的运行状态,
而且随着程序功能的增加,
编写应用程序的工程师
的大脑也开始混乱。
即不利于升级维护,
也不利于代码优化。
本人写个几个比较复杂一点的
应用程序,
刚开始就是使用此法,
最终虽然能够实现功能,
但是自己的思
维一直处于混乱状
态。导致程序一直不能让自己满意。
这种方法大多数人都会采用,而且我们接受的教育也基本都是使用此法。对于我们这
p>
些基本没有学习过数据结构,
程序架构的单片机工程师来说,
无疑很难在应用程序的设计上
有一个很大的提高,也导致了不同工程师
编写的应用程序很难相互利于和学习。
本人建议,如果喜欢使用此法的网友,如果编写比较复杂的应用程序,一定要先理清
p>
头脑,
设计好完整的流程图再编写程序,
否
则后果很严重。
当然应用程序本身很简单,
此法
还是一个非常必须的选择。
下面就写一个顺序执行的程序模型,方面和下面两种方法对比:
复制内容到剪贴板
代码
:
/************
**************************************************
*********
***************
*
FunctionName
: main()
*
Description
:
主函数
*
EntryParameter : None
* ReturnValue
: None
********
**************************************************
**************
**************/
int main(void)
{
uint8
keyValue;
InitSys();
//
初始化
while (1)
{
T
askDisplayClock();
keyValue
= TaskKeySan();
switch (keyValue)
{
case x:
T
askDispStatus(); break;
...
default:
break;
}
}
}
2.
时间片轮询法
时间片轮询法
,在很多书籍中有提到,而且有很多时候都是与操
作系统一起出现,也
就是说很多时候是操作系统中使用了这一方法。
不过我们这里要说的这个时间片轮询法并不
是挂在操作系统下,而是在前后台程序中
使用此法。也是本贴要详细说明和介绍的方法。
对于时间片轮询法,虽然有不少书籍都有介绍,但大多说得并不系统,只是提提概念
而
已。
下面本人将详细介绍本人模式,
并参考别人的代码建立的一
个时间片轮询架构程序的
方法,我想将给初学者有一定的借鉴性。
记得在前不久本人发帖
《
1
个定时器多处复用的问题》
,
由于时间的问题,
并没有详细
说明怎样实现
1
个定时器多处复用。在这里我们先介绍一下定时器的复用功能。
。
。
使用
1
个定时器,可以是任意的定时器,这里不做特
殊说明,下面假设有
3
个任务,那么
我
们应该做如下工作:
1.
初始化定时器,这里假设定时器的定时中断为
1ms(
当然你可以改成
10ms
,这个和操作
系统一样,
中断过于频繁效率就低,中断太长,实时性差
2.
定义一个数值:
复制内容到剪贴板
代码
:
#define
TASK_NUM
(3)
//
这里定义的任务数为
3
,表示有三个任务会使
用此定时器定
时。
uint16 T
askCount[TASK_NUM]
//
这里为三个任务定义三个变量来存放定时值
uint8
T
askMark[TASK_NUM];
//
同样对应三个标志位,为
0<
/p>
表示时间没到,为
1
表示定时时间到。<
/p>
3.
在定时器中断服务函数中添加:
复制内容到剪贴板
代码
:
/************
**************************************************
***
******
***************
* FunctionName : TimerInterrupt()
* Description :
定时中断服务函数
*
EntryParameter : None
* ReturnValue :
None
**********************************
**************************************
*
*************/
void
TimerInterrupt(void)
{
uint8 i;
定时中断服务函数, <
br>时器或此定时器已经完成定时,
for (i=0;
i
{
if (TaskCount[i])
{
TaskCount[i]--;
if (T
askCount[i] == 0)
{
T
askMark[i] = 0x01;
}
}
}
}
代码解释:
在中断中逐个判断,
如果定时值为
p>
0
了,
表示没有使用此定
不着处理。
否则定时器减
一,
知道为零时,
相应标志位值
1
p>
,
表示此任务的定时值到了。
4.
在我们的应用程序中,在需要
的应用定时的地方添加如下代码,下面就以任务
1
为例:
复制内容到剪贴板
代码
:
T
askCount[0] = 20;
//
延时
20ms