鱼C论坛

 找回密码
 立即注册
查看: 1358|回复: 6

[已解决]89C51延时函数看不懂

[复制链接]
发表于 2020-8-16 22:15:22 | 显示全部楼层 |阅读模式
5鱼币
  1. #include <reg51.h>
  2. #include <intrins.h>
  3. #define  NOP() _nop_()  /* 定义空指令 */         
  4. void delay(unsigned int i);      //函数声明


  5. // 此表为LED字模         
  6. unsigned char code LED7Code[] = {0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90};
  7.                                /*  { ~0x01,~0x02,~0x04,~0x08,~0x10,~0x20,~0x40,~0x80}*/

  8. main()
  9. {  
  10.    unsigned int LedNumVal=1 ,C ;  //定义变量
  11.    
  12.   while(1)
  13.   {         
  14.            if (++C>= 300)
  15.                   { LedNumVal++ ;         //每隔300个扫描周期加1
  16.                   C =0;                 //每隔300个扫描周期清0
  17.                  }       
  18.            // 将字模送到P0口         
  19.                 P0 = LED7Code[LedNumVal%10];     //LED7
  20.                  
  21.                              
  22.                 delay(150);          //调用延时函数
  23.          
  24.   }   
  25. }
  26.        
  27. /*****************************************************************
  28. *                                                                                                                                 *
  29. *                         延时函数                                                                                 *
  30. *                                                                                                                                 *
  31. *****************************************************************/
  32. void delay(unsigned int i)
  33. {
  34.     char j;
  35.     for(i; i > 0; i--)
  36.         for(j = 200; j > 0; j--);
  37. }
复制代码



以上程序为89C51 8位数码管显示程序,延时看不懂。delay(150),这个150啥意思,与下面的相乘还是搞啥?下面的 for 语句,第一个,i没初始化,定义无符号的i,想不通,i--为啥值?下面的for,后面有分号,初始化j=200,条件判断j已经大于0,应该不循环,百思不得其解。。。。百度无果。自己转程序,打delay 的值,2个都为4199866,改delay(150)里面的值,明显数码管刷新变快,但打印值还是4199866。
最佳答案
2020-8-16 22:15:23
第一个,i没初始化,定义无符号的i,想不通 其实是已经初始化了,就是函数传入的参数 150

下面的for,后面有分号,初始化j=200,条件判断j已经大于0,应该不循环,百思不得其解。。。。 的解答是:
分号就是运行一句空语句
因为后面还有j--所以当j减到0的时候再下一次循环就不满足条件了,那时才停止循环

最好delay函数的作用就是单词的含义,延迟的作用让单片机执行领个嵌套的for循环。因为每一个语句的执行都需要时间,这样就达到延时的效果

最佳答案

查看完整内容

第一个,i没初始化,定义无符号的i,想不通 其实是已经初始化了,就是函数传入的参数 150 下面的for,后面有分号,初始化j=200,条件判断j已经大于0,应该不循环,百思不得其解。。。。 的解答是: 分号就是运行一句空语句 因为后面还有j--所以当j减到0的时候再下一次循环就不满足条件了,那时才停止循环 最好delay函数的作用就是单词的含义,延迟的作用让单片机执行领个嵌套的for循环。因为每一个语句的执行都需要时间,这 ...
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2020-8-16 22:15:23 | 显示全部楼层    本楼为最佳答案   
第一个,i没初始化,定义无符号的i,想不通 其实是已经初始化了,就是函数传入的参数 150

下面的for,后面有分号,初始化j=200,条件判断j已经大于0,应该不循环,百思不得其解。。。。 的解答是:
分号就是运行一句空语句
因为后面还有j--所以当j减到0的时候再下一次循环就不满足条件了,那时才停止循环

最好delay函数的作用就是单词的含义,延迟的作用让单片机执行领个嵌套的for循环。因为每一个语句的执行都需要时间,这样就达到延时的效果
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2020-8-16 22:16:08 | 显示全部楼层
  1. #include <stdio.h>
  2. void delay(unsigned int i);  
  3. unsigned char  LED7Code[10] = {0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90};
  4. main()
  5. {  
  6.    unsigned int LedNumVal=1 ,C ;   
  7.   while(1)
  8.   {         
  9.            if (++C>= 3000)
  10.                   { LedNumVal++ ;         
  11.                   C =0;                
  12.                  }                           
  13.                 printf("LED此时状态:%X\n",LED7Code[LedNumVal%10]);              
  14.                 delay(150);         
  15.                 break ;
  16.   }   
  17.   printf ("delay=%d\n",delay);
  18. }



  19. void delay(unsigned int i)
  20. {
  21.     char j;
  22.     for(i; i > 0; i--)
  23.         for(j = 200; j > 0; j--);
  24.         printf ("delay=%d\n",delay);
  25. }
复制代码


这个是我自己修改打印delay  的程序。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2020-8-17 01:22:49 | 显示全部楼层
首先,感谢 jhanker 兄弟答惑,明白了 i  的值,也明白了  delay(150)的含义,哎,谭浩强视频,写的C程序跟羊子拉屎一样,函数东扯一下,西扯一下,郁闷。。。。反复打印  J   的值,一直是 -56,根本没看见  J--  循环,最后发现,定义的是   char j  ,for  循环里面给的值是  200  ,已超出范围。。。。。光坑。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2020-8-17 09:05:07 | 显示全部楼层
本帖最后由 SHRS23 于 2020-8-17 09:10 编辑
喝水卡牙 发表于 2020-8-17 01:22
首先,感谢 jhanker 兄弟答惑,明白了 i  的值,也明白了  delay(150)的含义,哎,谭浩强视频, ...


51单片机的C语言编程只推荐一个老师的书和视频,金沙滩工作室http://www.qdkingst.com/cn/download

视频教程,教材PDF,工具软件全部可以在官网直接下载

另外你说的是郭天祥吧,程序确实一言难尽,变量全是abc,像是刚学C语言的人写的。。

你的问题:
单片机的这种延时函数就是用循环空语句的方式占用CPU时间,正常里面没有printf只有两层循环,在更短时间的延时中一层循环就够了,每执行一次delay函数延迟多久取决于外部晶振频率,你这个程序我目测大概是11.0592MHz晶振下的1ms延时吧,STC单片机的下载程序STC-ISP有生成延时代码的功能可以试一下。

不同平台运行这段代码得到的时间是不同的,如果你尝试在电脑上编译这段代码,时间肯定不对,即使是在不同的51单片机里时间也是有些差别,而且这种延时实际上是
让CPU做没有意义的工作来实现延时,是阻塞CPU的程序,浪费了CPU的性能,所以这种延时程序只适合初学单片机做一些简单的示例程序,或者实际应用时一些很短的小延时
以后用的更多的是用定时器中断来产生延时效果,中断能让CPU更高效。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2020-8-17 22:45:33 | 显示全部楼层
感谢4楼兄弟的回复,以及推荐的网站,感谢。
另外也帮分析了一下MCU延时的一些特性,谢谢。再次慢慢学习,
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2020-8-17 22:46:15 | 显示全部楼层
嗯,应该是5楼,说错了
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

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

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-5-21 21:47

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

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