打印

请教,如何编写延时函数

[复制链接]
2776|17
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
mcu_lover|  楼主 | 2010-4-6 16:45 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
我有这样的一个函数

void Task(void)
{
    执行一些代码
   .......
   延时50ms
   ......
   再执行一些代码
   ......
   延时10ms
   .....
   执行剩下的代码
}

这个函数中的延时,我不想通过调用DelayMs(50)这样的方式来实现,因为这样就白白的等待了50ms。请问,该如何实现这个函数中的延时功能?

相关帖子

沙发
zq1987731| | 2010-4-6 17:17 | 只看该作者
用定时器做一个时基X,比如每1ms就++
然后设2个变量,前者Y检测到X增加了10次就增1,后者Z检测到Y增加了5次就增1
然后~~
if(Y)
{
    //你的10ms任务
    Y--;
}
if(Z)
{
    //你的50ms任务
    Z--;
}

使用特权

评论回复
板凳
mcu_lover|  楼主 | 2010-4-6 18:46 | 只看该作者
谢谢2L。
用定时器计数我明白,但是就是无法理解如何在一个函数中做到。

void Task()
{
      执行一些代码
    ....
      延时50ms
     .....
}
这里的延时如果用操作系统,可能直接调用一个延时函数就可以了。但是现在是没有操作系统的环境。如果要达到延时的目的,同时又不堵塞CPU的运行?

使用特权

评论回复
地板
cqwangchun| | 2010-4-6 19:11 | 只看该作者
很简单,用定时器做,设置好定时器,开机就启动定时器,在定时器中断函数中,设置一个标志,用的时候才++,到规定的值就置一个标志,就能很好地延时了

使用特权

评论回复
5
mcu_lover|  楼主 | 2010-4-6 19:44 | 只看该作者
LS高手多讲讲。

使用特权

评论回复
6
berg| | 2010-4-6 22:43 | 只看该作者
如果不想用循环延时占用系统资源。
那你只好用中断方式了。
中断加标志位即可。

使用特权

评论回复
7
古道热肠| | 2010-4-7 00:04 | 只看该作者
见我发表在本版的MP3开发板源代码。内有通用定时器的实现,想要几个定时器就能用几个定时器,各是各的。很是方便,不空耗CPU,CPU在忙着Play Music呢。
嘿嘿,也是在本坛的一位网友那儿学来的。

使用特权

评论回复
8
ym2008| | 2010-4-7 13:41 | 只看该作者
各位大侠各抒己见。
fighting!

使用特权

评论回复
9
mcu_lover|  楼主 | 2010-4-7 16:08 | 只看该作者
以下是大虾 machunshui的做法。太赞了。看字面意思可以明白大概是怎么回事。莫非这个就是软件定时器的用法?
void ScanKey(void)
{        
        static ScanKeyStatge = 0;
        
        if(ScanKeyStatge == 0)
        {
                if(RB0 == 0 || RB1 == 0)
                {
                        ScanKeyStatge = 1;
                        SetSysTimer(0,15);//150ms延时
                }        
        }
        else if(ScanKeyStatge == 1)
        {
                if(GetSysTimer(0))
                {
                        GetKey();
                        ScanKeyStatge = 0;
                }        
        }               

}

使用特权

评论回复
10
sharpxcb| | 2010-4-7 16:37 | 只看该作者
给个思路,大循环做得更精细一点,如保持一个周期为1ms,再加上计数单元参与计数, 这们你的程式会更有效率·

使用特权

评论回复
11
冷漠| | 2010-4-7 16:39 | 只看该作者
本帖最后由 冷漠 于 2010-4-7 17:33 编辑

LS是ma老师写的程序?if(ScanKeyStatge==0){  }  else if( ScanKeyStatge == 1) ?
那岂不是跟下面写法一样?( ScanKeyStatge只有2个值)

void ScanKey(void)
{        
        static ScanKeyStatge = 0;
        
        if(ScanKeyStatge == 0)
        {
                if(RB0 == 0 || RB1 == 0)
                {
                        ScanKeyStatge = 1;
                        SetSysTimer(0,15);//150ms延时
                }        
        }
        else     //原写法else if(ScanKeyStatge == 1)
        {
                if(GetSysTimer(0))
                {
                        GetKey();
                        ScanKeyStatge = 0;
                }        
        }               

}

这里的条件表达式 else if(ScanKeyStatge == 1) 是不是写错了?

如果我说错了,也是一次纠正自己常年错误概念的机会。我不怕尴尬,或者被人说装聪明。但是如果我说对了,是不是很得意?哈哈。

使用特权

评论回复
12
mcu_lover|  楼主 | 2010-4-7 17:01 | 只看该作者
11# 冷漠

我是在论坛中一个关于按键扫描的帖子中找到ma老师贴出来的程序,直接copy过来的。至于这种写法可不可以,我也不是很清楚。如果用else if 是不是最后还应该有一个else的语句?麻烦老师们解惑一下。

使用特权

评论回复
13
冷漠| | 2010-4-7 17:29 | 只看该作者
本帖最后由 冷漠 于 2010-4-7 17:36 编辑

刚想了一下,按照概念,else if(条件表达式m ){语句m;}最后一条,可以不是else{语句n;}  默认空else{ }呗。主要是下面的问题:
if(ScanKeyStatge==0)
{......
  ScanKeyStatge = 1;
  SetSysTimer(0,15);//150ms延时
......
}  
else if( ScanKeyStatge == 1)  
{......}   // 这段语句在150ms里要反复进入无效扫描多少次?!表达式(ScanKeyStatge == 1)写错了?

把4楼说的“时间到标志”写在表达式里还差不多。

使用特权

评论回复
14
灰太狼880| | 2010-4-7 17:34 | 只看该作者
假如中断触发时间是50us可以设置自增变量实现啊!!

使用特权

评论回复
15
hondephy| | 2010-4-9 19:00 | 只看该作者
。。。。。。感觉没有那个必要吧,,我觉得写上一个delay就好了吧
delayMs(uchar ucMs)
{
uchar x,y;
for(x=ucMs;x>0,x--)
    for(y=120;y>0;y--)
}

使用特权

评论回复
16
lovewwy| | 2010-4-9 22:07 | 只看该作者
mark,学习

使用特权

评论回复
17
xd54622| | 2011-7-26 10:54 | 只看该作者
mark

使用特权

评论回复
18
xiaoke515| | 2011-7-27 00:03 | 只看该作者
学习

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

10

主题

82

帖子

1

粉丝