具体是怎么个不行法。
像你这种按键程序
因为单片机速度非常快,在你按一下按键时,单片机已经循环了很多次程序。
因此这样就会导致,当你按下时,其实k一直==0 一直在执行动作。
所以这种按键需要判断按键是第一次按下(由弹起状态下按下)。而不是一直按着导致的动作。
方法:建一个变量保存上一次按键的值
char LastKeyLastKey = 1
while(1)
{
if(k == 0 && LastKey == 1) //按下,且上一次检测按键时是弹起状态
{ //这样才能保证每次按下时只执行一次,
//而不是一直在执行
Delay1ms(20)
if(k == 0) //确定是第一次按下,执行动作
{
if((n % 2) == 0)
{
LedFlash()
}
else
{
P0 = 0xFF
}
n++
}
}
LastKey = k //保存按键状态
}
看了一下你的要求,单片机里有个GATE位的设置如果你懂得用,编这个程序就不难了。下面是我个人按照你要求刚编的程序:/***********************
功能:内部定时/计数器记录脉冲个数和这些脉冲通过后所用的时间。
硬件:单片机用AT89c51,12M晶振。
原理:当门控位GATE为“1”时,TR0/1=1,INT0/1才能启动定时器。
利用这个特性可以测量外部输入脉冲的宽度。
分析:设外部脉冲由(P3.2)输入,T0工作于定时方式1(16位计数),
GATE设为1.测试时,应在INT0低电平时,设置TR0为1(避免检测
到正在进行的脉冲);当INT0为高电平时,就启动计数,INT0再
次变低时,停止计数。此计数值与机器周期的乘积即为被测正脉
冲的宽度。因晶振为12MHz,机器周期为1us.
************************/
#include <reg51.h>
//sbit INT0=P3^2//INT0在头文件里已定义为P3^2口
#define uint unsigned int
uint pulseWidth[30],num
void init()
{
num=0
TMOD=0x09//选择定时器并设T0为方式1
TH0=0x00//设计数初会为最大值
TL0=0x00
}
main()
{
init()
while(1)
{
if(num<30) //记录30个脉冲
{
while(INT0)//等待INT0变低
TR0=1//应在INT0低电平时,设置TR0为1
while(!INT0)//等待INT0变高,启动定时器开始计数
while(INT0)//等待INT0变低,停止定时器开始计数
TR0=0
pulseWidth[num]=(uint)TL0
pulseWidth[num]|=(uint)(TH0<<8)
//因机器周期为1us,故pulseWidth数组里存的数目加上单位us,
//即为所求的脉冲宽度
num++
}
}
}
另外,虚机团上产品团购,超级便宜