刚刚学习单片机,谁可以帮忙写个程序3
发布网友
发布时间:2023-10-27 08:11
我来回答
共5个回答
热心网友
时间:2024-04-11 11:13
/*
http://zhidao.baidu.com/question/287237680.html
P1端口P1^0-P1^5端口接的6个独立按键
控制P2的p2^0-p2^5共6个对应的I/O口输出2种状态,
例如
按一下p1^0的按键,那么p2^0接口的LED就长亮,
重复按一下p1^0的按键,p2^0接口的LED就熄灭,
1到6路都如此
P1^6和P1^7也和如上的按键功能相同,
但是对应的P2^6和P2^7输出的是100ms交替闪烁的信号,
例如
按一下P1^6的按键,那么p2^6接口的LED就以100ms的速度闪烁,
重复按一下p1^6的按键,p2^6接口的LED就熄灭,
p2^7都如此
下列程序已经调试通过,可以满足上述要求。
*/
#include <AT89X51.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
//-----------------------------------------------------------
uchar aa, bb, cc, dd; //设定变量.
//-----------------------------------------------------------
void delay(uint ms)
{
uchar t;
while(ms--) for(t = 0; t < 123; t++);
}
//-----------------------------------------------------------
void main(void)
{
TMOD = 0x01; // T0定时方式1
TL0 = (65536 - 50000) % 256; //50ms@12MHz
TH0 = (65536 - 50000) / 256;
TR0 = 1; //启动定时器0
IE = 0x82; //中断允许.
bb = 0x3f;
cc = 0;
while(1) {
aa = P1; //读入按键.
if (aa < 255) { //如果有按下.
delay(10); //延时消抖.
aa = P1; //再读.
if (aa < 255) { //如果仍然按下.
if (aa == 255 - 1) bb ^= 1; //根据按键,分别处理.
if (aa == 255 - 2) bb ^= 2; //这里也可以使用 case 语句.
if (aa == 255 - 4) bb ^= 4;
if (aa == 255 - 8) bb ^= 8;
if (aa == 255 - 16) bb ^= 16;
if (aa == 255 - 32) bb ^= 32;
if (aa == 255 - 64) bb ^= 64;
if (aa == 255 - 128) bb ^= 128;
P2 = (cc & 0xc0) + (bb & 0x3f);//输出.
while(aa < 255) aa = P1; //等待按键松开.
} } }
}
//-----------------------------------------------------------
void T0_INT() interrupt 1
{
TL0 = (65536 - 50000) % 256; //50ms@12MHz
TH0 = (65536 - 50000) / 256;
dd++;
dd %= 4; //4,代表200ms
if (dd == 0) { //如果时间到了.
if ((bb & 64) == 64) cc ^= 64; //按照指定位取反.
else cc |= 64; //关闭指定位.
if ((bb & 128) == 128) cc ^= 128;
else cc |= 128; //关闭指定位.
P2 = (cc & 0xc0) + (bb & 0x3f); //输出.
}
}
//-----------------------------------------------------------
热心网友
时间:2024-04-11 11:17
留下qq联系
热心网友
时间:2024-04-11 11:16
org 00h
ajmp main
org 30h
main:mov 20h,#0h
mov p1,#0FFh
mov p2,#0h
loop:jnb p1.0,kzp20
jb 00h,szp20
jcp11:jnb p1.1,kzp21
jb 01h,szp21
jcp12:jnb p1.2,kzp22
jb 02h,szp22
jcp13:jnb p1.3,kzp23
jb 03h,szp23
jcp14:jnb p1.4,kzp24
jb 04h,szp24
jcp15:jnb p1.5,kzp25
jb 05h,szp25
jcp16:jnb p1.6,kzp26
jb 06h,szp26
jcp17:jnb p1.7,kzp27
jb 07h,szp27
ajmp loop
kzp20:setb 00h
ajmp jcp11
szp20:cpl p2.0
clr 00h
ajmp jcp11
kzp21:setb 01h
ajmp jcp12
szp21:cpl p2.1
clr 01h
ajmp jcp12
kzp22:setb 02h
ajmp jcp13
szp22:cpl p2.2
clr 02h
ajmp jcp13
kzp23:setb 03h
ajmp jcp14
szp23:cpl p2.3
clr 03h
ajmp jcp14
kzp24:setb 04h
ajmp jcp15
szp24:cpl p2.4
clr 04h
ajmp jcp15
kzp25:setb 05h
ajmp jcp16
szp25:cpl p2.5
clr 05h
ajmp jcp16
kzp26:setb 06h
ajmp jcp17
szp26:cpl p2.6
clr 06h
ajmp jcp17
kzp27:setb 07h
ajmp loop
szp27:cpl p2.7
clr 07h
ajmp loop
end
;P1的8个口都是一样的,如果你需要100ms的速度闪烁,得需要编写定时器中断,不编写中断会造成在延时闪烁的时候按键没有反映的情况,这只是一个实现你大致功能的简单的程序,实际使用时还得加按键延时去抖等提高稳定性的功能
热心网友
时间:2024-04-11 11:14
既然是初学 那从最简单的开始 你整这么复杂 还说难
热心网友
时间:2024-04-11 11:15
我写了个小程序,已经经过调试,满足楼主要求,硬件上P1^0-P1^5及P2^6和P2^7接按键接的同时,分线与门,经过与门后接到P3.3,触发INT1中断,我用的是查询中断方法,希望楼主有所收获
希望楼主能从中学习到查询中断的方法
#include <reg52.h> //选用晶振12MHz
unsigned char n,m;
sbit a=P0^0; //对映点符号表示
sbit b=P0^1;
sbit c=P0^2;
sbit d=P0^3;
sbit e=P0^4;
sbit f=P0^5;
sbit aa=P2^0;
sbit bb=P2^1;
sbit cc=P2^2;
sbit dd=P2^3;
sbit ee=P2^4;
sbit ff=P2^5;
sbit g=P1^6;
sbit h=P1^7;
sbit gg=P2^6;
sbit hh=P2^7;
void delay50ms(unsigned int i) //延时50MS
{
unsigned int j;
for (i;i>0;i--)
for(j=50000;j>0;j--);
}
main()
{
P0=0x00; //根据需要,对3个口初始化
P1=0x00;
P2=0x00;
EA=1; //总中断允许
EX1=1; //外部中断1开
while(1)
{
if(m==200) //m复位
m=0;
if(n==200) //n复位
n=0;
if(n%2)
{
delay50ms(2); //延时100ms后换状态
gg=~gg;
}
else gg=0;
if(m%2)
{
delay50ms(2); //延时100ms后换状态
hh=~hh;
}
else hh=0;
}
}
void T1zd(void) interrupt 2 //3 为定时器1的中断号 1 定时器0的中断号 0 外部中断1 2 外部中断2 4 串口中断
{
if(a==1)
aa=~aa; //对当前状态取反
if(b==1)
bb=~bb;
if(c==1)
cc=~cc;
if(d==1)
dd=~dd;
if(e==1)
ee=~ee;
if(f==1)
ff=~ff;
if(g==1)
n++;
if(h==1)
m++;
}