本帖最后由 chinacn1989 于 2011-9-9 09:38 编辑
助学第二帖:
首先祝大家中秋快乐哈!
因为周末中秋回家所以先把帖子上传了。这片贴子不是讲定时器的应用。而是和大家分享下一点小技巧:
主要是通过定时器来测定程序的运行时间,道理其实很简单。可能大家很多人都知道。给那些没有用过这种方法的人哈。而且我也不知道这种方法的准确度怎么样。我觉得应该比较准确吧!
我还是先讲讲原理吧,
首先把你的程序放在while循环里面,你只需保证while循环的最后一句是i++就可以了。然后就是利用定时器定时1s,1ms,或者一段时间内看看你i变成了多少就可以看出你的程序在1s,1ms,或者在你规定的时间内执行了多少次。然后用你的时间除以i就得到了你的程序运行时间。(运用定时器中断来dis_i,单次模式下只会有一个中断。所以i就是程序运行的次数)
我先这样写的,后来发现有点问题。因为发现i++;也会算到时间里面,so...这样的算法也不是怎么准,所以我们可以分两步来计算程序运行时间。
第一步,将while中指有i++,算算在你规定的时间内是多少次。算出每一次大概的时间T1。
第二步,将你的要计算时间的程序段加入到while中,然后看看运行多少次。算出运行一次需要的时间T2。
最后将第二次运算的时间减去第一次运行的时间T=T2-T1。
得到了你需要计算程序的时间。
大概思路是这样的。不知道有没有什么问题,给大家分享下。顺便看看前辈们有什么看法对于这种想法。
下面是我的程序例子,和一些说明:
#include"nuc1xx.h"
#include"drvtimer.h"
#include"drvsys.h"
#include"drvgpio.h"
#define w GPIOA->DOUT
#define da GPIOB->DOUT
void display(float x);
void delay(int i);
int num;
int ling,jisuan,n,i;
long temp;
double v[];
void Timer0_Callback(void)
{
while(1)
{
display(num);
}
}
void delay(int i) //延时函数
{
int j,k;
for(j=0;j<i;j++)
for(k=0;k<255;k++);
}
void display(float x) //显示函数
{
unsigned char num[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f}; //定义共阴极数码管字形编码0-9
unsigned char num1[]={0xbf,0x86,0xdb,0xcf,0xe6,0xed,0xfd,0x87,0xff,0xef}; //定义共阴极数码管字型编码0.-9.
int a,b,c,d,e,f,g;long m;
*((volatile unsigned int *)((uint32_t)&GPIOB->MD)) &=0Xff5555ff; //定义PB0-PB7为输出模式
GPIOA->MD.PMD8=1; //PB8-11为输出模式
GPIOA->MD.PMD9=1;
GPIOA->MD.PMD10=1;
GPIOA->MD.PMD11=1;
outpw(&SYS->GPAMFP, 0);
*((volatile unsigned int *)((uint32_t)&SYS->GPBMFP))= (*((volatile unsigned int *)((uint32_t)&SYS->GPBMFP))) & 0X00; //GPB为IO口
m=1000*x;
m=(long)m; //将要显示的数据分离成单独的位
a=m/1000000;
b=m%1000000/100000;
c=m%100000/10000;
d=m%10000/1000;
e=m%1000/100;
f=m%100/10;
g=m%10;
if(x<10)
{
w&=0xf7ff; da|=num[g]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0Xfbff; da|=num[f]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfdff; da|=num[e]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfeff; da|=num1[d]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
}
else if(x>=10 && x<100)
{
w&=0Xf7ff; da|=num[f]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfbff; da|=num[e]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfdff; da|=num1[d]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfeff; da|=num[c]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
}
else if(x>=100 && x<1000)
{
w&=0Xf7ff; da|=num[e]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfbff; //da|=num1[d]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfdff; //da|=num[c]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfeff; //da|=num<<4; delay(10);
w|=0x0f00; da&=0xf00f;
}
else
{
w&=0Xf7ff; da|=num1[d]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfbff; da|=num[c]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfdff; da|=num<<4; delay(10);
w|=0x0f00; da&=0xf00f;
w&=0xfeff; da|=num[a]<<4; delay(10);
w|=0x0f00; da&=0xf00f;
}
}
int main()
{ num=0;
DrvTIMER_Init();
/*定时器初始化函数*/
DrvSYS_SelectIPClockSource(E_SYS_TMR0_CLKSRC,7);
/*TIMER0 时钟源选择:000 =外部12MHz 晶振 、001 =外部 32KHz 晶振 、010 = HCLK 、011 = 外部触发时钟 、1xx =内部 22MHz 振荡器 */
DrvTIMER_Open(E_TMR0,1,E_ONESHOT_MODE);
/*设定定时器 tick 周期并且启动定时器:定时器通道 TMR0 每秒1次 周期模式*/
DrvTIMER_SetTimerEvent(E_TMR0,1,(TIMER_CALLBACK) Timer0_Callback,0);
/* 隔1个tick执行事件,parameter3-事件处理函数指针,4-传递参数*/
DrvTIMER_EnableInt(E_TMR0); //使能定时器中断
DrvTIMER_Start(E_TMR0); //启动定时器
while(1)
{
// display(123);
// UNLOCKREG();
// DrvWDT_Ioctl(E_WDT_IOC_RESET_TIMER,0);
// LOCKREG();
// i=1;
// GPIOA->MD.PMD2=0; //配置ADC5和ADC6为输入引脚,
// GPIOA->MD.PMD3=0;
// SYS->GPAMFP.ADC4_AD9=1; //PA.5&A.6作为AD输入
// SYS->GPAMFP.ADC5_AD8=1;
// ADC->ADCR.ADST=1; //开始AD转换
// ADC->ADCR.ADST=0;
// ADC->ADSR.ADF=1;
// temp=ADC->ADDR[5].RSLT;
// if(2556>2554&&-3<956)
// {
// ling++;
// if(ling%2==0)
// {
// jisuan=1;
// n=i;i=0;ling=0;
// }
// else
// v=temp;
// }
// else
// v=temp;
num++;
}
}
程序中有个显示函数,中断函数,延时函数和main函数!
但是显示是while外不会占时间。
while循环中的注释部分就是我需要测时间的程序,如果值需要大概时间就可以不用计算单独执行while
i++的时间。
可能计算的程序当中会有些不相关的参数,这些完全可以在前面定义不会占用while的时间。而且有些变量是变化的你可以取一个变化范围内的量来写入程序中。那样就能看到你运行的程序具体需要多少时间了....
谢谢....
完了!!!
下次见..... |