我们已知74HC138译码器控制了8路输出,那么我们是否可以用一个函数来整合这一部分呢
sbit HC138_A = P2^5; //定义用符号HC138_A来表示P2.5引脚,如果你愿意也可以起P25一类的名字,只要下面程序中也随之更改就行了。
sbit HC138_B = P2^6;
sbit HC138_C = P2^7;
void HC138Init(unsigned char n)
{
switch(n)
{
case 4:
HC138_C = 1;
HC138_B = 0;
HC138_A = 0;//让Y4输出低电平,此时Y4C为高电平
break;
case 5:
HC138_C = 1;
HC138_B = 0;
HC138_A = 1;//让Y5输出低电平,此时Y5C为高电平
break;
case 6:
HC138_C = 1;
HC138_B = 1;
HC138_A = 0;//让Y6输出低电平,此时Y6C为高电平
break;
case 7:
HC138_C = 1;
HC138_B = 1;
HC138_A = 1;//让Y7输出低电平,此时Y7C为高电平
break;
}
}
是不是看起来密密麻麻的?是否还可以使代码进一步更加简洁呢?
HC138_C = 1;
HC138_B = 0;
HC138_A = 0;
这一串东西如果可以用一句来表示是不是好多了
首先如果直接给P2赋值,是这样的
P2 = 0x80;
但是这么操作的话你之前对p2^0,p2^1等等的配置就失效了,会被0覆盖过去
此时我们可以用一个按位与先使得P2的高三位置0
p2 & 0x1f
按位与‘&’,都为1时置1,不都为1时置0.
再通过一个位或运算,把高三位变成0x80的高三位
按位与‘|’,当有一个为1时置1。
所以最终优化结果为:
P2 = (P2 & 0x1f) | 0x80
同理进行优化,就得到了这个:
void HC138Init(unsigned char n)
{
swicth(n)
{
case 4:
P2 = (P2 & 0x1f) | 0x80;//让Y4输出低电平,此时Y4C为高电平
break;
case 5:
P2 = (P2 & 0x1f) | 0xa0;//让Y5输出低电平,此时Y5C为高电平
break;
case 6:
P2 = (P2 & 0x1f) | 0xc0;//让Y6输出低电平,此时Y6C为高电平
break;
case 7:
P2 = (P2 & 0x1f) | 0xe0;//让Y7输出低电平,此时Y7C为高电平
break;
}
}
那我们能不能再写一个函数,使得我们每一次使用的时候都不用再自己去选择通道?
void OutPutP0(unsigned char channel,unsigned char dat)
{
HC138Init(channel);//先进入相应的通道
P0 = dat;//给P0赋值
}
至此,代码优化就完成了,让我们看看用优化后的代码来写蜂鸣器和继电器的使用
优化前:
#include "reg52.h"
sbit HC138_A = P2^5; //定义用符号HC138_A来表示P2.5引脚,如果你愿意也可以起P25一类的名字,只要下面程序中也随之更改就行了。
sbit HC138_B = P2^6;
sbit HC138_C = P2^7;
void Delay(unsigned int t)//延迟函数
{
while(t--);
while(t--);
}
void ULN2003Init()//M74HC573M1R上电连通ULN2003
{
HC138_C = 1;
HC138_B = 0;
HC138_A = 1;
//74HC128三八译码器选通了Y5,也就是Y5置0了
//再通过或非门,此时Y5C置1,M74HC573M1R上电连通ULN2003
}
void main()
{
while(1)
{
ULN2003Init();
P0 = 0x40; //0100 0000 打通蜂鸣器
Delay(60000);
P0 = 0x00;//0000 0000响一会在安静
Delay(60000);
P0 = 0x10; //0001 0000 打通继电器
Delay(60000);
P0 = 0x00;//0000 0000点亮指示灯一会再熄灭
Delay(60000);
}
}
优化后:
#include "reg52.h"
void Delay(unsigned int t)//延迟函数
{
while(t--);
while(t--);
}
void HC138Init(unsigned char n)
{
switch(n)
{
case 4:
P2 = (P2 & 0x1f) | 0x80;//让Y4输出低电平,此时Y4C为高电平
break;
case 5:
P2 = (P2 & 0x1f) | 0xa0;//让Y4输出低电平,此时Y4C为高电平
break;
case 6:
P2 = (P2 & 0x1f) | 0xc0;//让Y4输出低电平,此时Y4C为高电平
break;
case 7:
P2 = (P2 & 0x1f) | 0xe0;//让Y4输出低电平,此时Y4C为高电平
break;
}
}
void OutPutP0(unsigned char channel,unsigned char dat)
{
HC138Init(channel);//先进入相应的通道
P0 = dat;//给P0赋值
}
void main()
{
while(1)
{
OutPutP0(5,0x40);//0100 0000响
Delay(60000);
OutPutP0(5,0x00);//0000 0000安静
Delay(60000);
OutPutP0(5,0x10);//0001 0000亮
Delay(60000);
OutPutP0(5,0x00);//0000 0000熄灭
Delay(60000);
}
}
后续还可以将前面的这些函数封装进一个库中,那样子会更加简洁!!