关于C语言for循环延时函数

voiddelay(uintx){ucharj;uinti;for(i=0;i<x;i++)for(j=0;j<100;j++);}我用的是12M的晶振,给x的值是500... void delay(uint x)
{
uchar j;
uint i;
for(i=0;i<x;i++)
for(j=0;j<100;j++);
}
我用的是12M的晶振,给x的值是500,理论上应该是延时500毫秒,为什么我实际观察的时候延时的时间200毫秒都不到?晶振误差不会这么大吧!!
展开
 我来答
椴iejdhifghj
推荐于2017-09-04 · TA获得超过4701个赞
知道小有建树答主
回答量:622
采纳率:0%
帮助的人:138万
展开全部
for循环实现C语言精确延时
(晶振12MHz,一个机器周期1us.)
一. 500ms延时子程序
程序:
void delay500ms(void){
unsigned char i,j,k;
for(i=15;i>0;i--)
for(j=202;j>0;j--)
for(k=81;k>0;k--);
}
产生的汇编:
C:0x0800 7F0F MOV R7,#0x0F
C:0x0802 7ECA MOV R6,#0xCA
C:0x0804 7D51 MOV R5,#0x51
C:0x0806 DDFE DJNZ R5,C:0806
C:0x0808 DEFA DJNZ R6,C:0804
C:0x080A DFF6 DJNZ R7,C:0802
C:0x080C 22 RET
计算分析:
程序共有三层循环
一层循环n:R5*2 = 81*2 = 162us DJNZ 2us
二层循环m:R6*(n+3) = 202*165 = 33330us DJNZ 2us + R5赋值 1us = 3us
三层循环: R7*(m+3) = 15*33333 = 499995us DJNZ 2us + R6赋值 1us = 3us
循环外: 5us 子程序调用 2us + 子程序返回 2us + R7赋值 1us = 5us
延时总时间 = 三层循环 + 循环外 = 499995+5 = 500000us =500ms
计算公式:延时时间=[(2*R5+3)*R6+3]*R7+5

二. 200ms延时子程序
程序:
void delay200ms(void){
unsigned char i,j,k;
for(i=5;i>0;i--)
for(j=132;j>0;j--)
for(k=150;k>0;k--);
}
产生的汇编
C:0x0800 7F05 MOV R7,#0x05
C:0x0802 7E84 MOV R6,#0x84
C:0x0804 7D96 MOV R5,#0x96
C:0x0806 DDFE DJNZ R5,C:0806
C:0x0808 DEFA DJNZ R6,C:0804
C:0x080A DFF6 DJNZ R7,C:0802
C:0x080C 22 RET

三. 10ms延时子程序
程序:
void delay10ms(void){
unsigned char i,j,k;
for(i=5;i>0;i--)
for(j=4;j>0;j--)
for(k=248;k>0;k--);
}
产生的汇编
C:0x0800 7F05 MOV R7,#0x05
C:0x0802 7E04 MOV R6,#0x04
C:0x0804 7DF8 MOV R5,#0xF8
C:0x0806 DDFE DJNZ R5,C:0806
C:0x0808 DEFA DJNZ R6,C:0804
C:0x080A DFF6 DJNZ R7,C:0802
C:0x080C 22 RET

四. 1s延时子程序
程序:
void delay1s(void){
unsigned char h,i,j,k;
for(h=5;h>0;h--)
for(i=4;i>0;i--)
for(j=116;j>0;j--)
for(k=214;k>0;k--);
}
产生的汇编
C:0x0800 7F05 MOV R7,#0x05
C:0x0802 7E04 MOV R6,#0x04
C:0x0804 7D74 MOV R5,#0x74
C:0x0806 7CD6 MOV R4,#0xD6
C:0x0808 DCFE DJNZ R4,C:0808
C:0x080A DDFA DJNZ R5,C:0806
C:0x080C DEF6 DJNZ R6,C:0804
C:0x080E DFF2 DJNZ R7,C:0802
C:0x0810 22 RET

在精确延时的计算当中,最容易让人忽略的是计算循环外的那部分延时,在对时间要求不高的场合,这部分对程序不会造成影响.
lujin925619
2010-07-25
知道答主
回答量:21
采纳率:0%
帮助的人:0
展开全部
工作环境没说清,但基本能排除OSC的问题。是什么系统?51单片机还是其他内核的?内核不同,指令执行的速度不一样。另外,c语言的指令周期是不准的,具体时延这和你的编译器还有关,在延时问题上,通常是不采用c来做精确延时函数的,而采用汇编来实现。要排除问题很简单,你用示波器观测时钟源的频率就知道OSC的误差大概多少了。同时用示波器观测来调整x的值以实现500毫秒的延时。
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
woshizzza
推荐于2017-09-03 · TA获得超过252个赞
知道小有建树答主
回答量:271
采纳率:0%
帮助的人:209万
展开全部
完全不对- -~这个是C 你要看汇编里面到底有多少条指令的。。。
看看编译出来的汇编代码,然后看看一个时钟要执行多少条指令。
还要算上入入栈出栈时间等等等。。。要是可以 最好是用编译器
调试一下,看看时间多少就行了,以后作为一个子函数调用。。
本回答被提问者采纳
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
栩箭
2010-07-25 · TA获得超过5311个赞
知道大有可为答主
回答量:3036
采纳率:0%
帮助的人:1665万
展开全部
1, 没有这种简单的对应关系.
2, 就算有这种简单的对应关系. 12MHz * 500ms = 6000000. x给500能满足这么华丽丽的0么
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
收起 更多回答(2)
推荐律师服务: 若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询

为你推荐:

下载百度知道APP,抢鲜体验
使用百度知道APP,立即抢鲜体验。你的手机镜头里或许有别人想知道的答案。
扫描二维码下载
×

类别

我们会通过消息、邮箱等方式尽快将举报结果通知您。

说明

0/200

提交
取消

辅 助

模 式