51单片机C语言程序100例分析(4)外设

发布者:zhaodawei617最新更新时间:2022-12-07 来源: zhihu关键字:51单片机  C语言  外设 手机看文章 扫描二维码
随时随地手机看文章

和我预想的一致,接下来该涉及外设了!


/********************************************************


*********数码管显示*****数码管显示********************


数码管显示****************数码管显示


***************************************************/


//实例60:用LED数码显示数字5


#include//包含51单片机寄存器定义的头文件


void main(void)


{


P2=0xfe;//P2.0引脚输出低电平,数码显示器接通电源准备点亮


P0=0x92;//让P0口输出数字"5"的段码92H


}

说是外设其实就是利用IO引脚而已,可见基础的重要性。


//实例61:用LED数码显示器循环显示数字0~9


#include //包含51单片机寄存器定义的头文件


/**************************************************


函数功能:延时函数,延时一段时间


***************************************************/


void delay(void)


{


unsigned char i,j;


for(i=0;i<255;i++)


for(j=0;j<255;j++)


;


}


/**************************************************


函数功能:主函数


***************************************************/


void main(void)


{


unsigned char i;


unsigned char code Tab[10]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};


//数码管显示0~9的段码表,程序运行中当数组值不发生变化时,


//前面加关键字code,可以大大节约单片机的存储空间


P2=0xfe;   //P2.0引脚输出低电平,数码显示器DS0接通电源工作


while(1)   //无限循环


{


for(i=0;i<10;i++)


{


P0=Tab[i];  //让P0口输出数字的段码92H


delay();   //调用延时函数


}


}


}

//实例62:用数码管慢速动态扫描显示数字"1234"


#include          //   包含51单片机寄存器定义的头文件


void delay(void)          //延时函数,延时一段时间


{


unsigned char i,j;


for(i=0;i<250;i++)


for(j=0;j<250;j++)


;


}


void main(void)


{


while(1)    //无限循环


{


P2=0xfe;   //P2.0引脚输出低电平,DS0点亮


P0=0xf9;  //数字1的段码


delay();


P2=0xfd;   //P2.1引脚输出低电平,DS1点亮


P0=0xa4;  //数字2的段码


delay();


P2=0xfb;   //P2.2引脚输出低电平,DS2点亮


P0=0xb0;  //数字3的段码


delay();


P2=0xf7;   //P2.3引脚输出低电平,DS3点亮


P0=0x99;  //数字4的段码


delay();


P2=0xff;


}



}

注意外设的原理,主要是看引脚的对接和电平的逻辑


//实例63:用LED数码显示器伪静态显示数字1234


#include              //   包含51单片机寄存器定义的头文件


void delay(void)          //延时函数,延时约0.6毫秒


{


unsigned char i;


for(i=0;i<200;i++)


;


}


void main(void)


{


while(1)    //无限循环


{


P2=0xfe;   //P2.0引脚输出低电平,DS0点亮


P0=0xf9;  //数字1的段码


delay();


P2=0xfd;   //P2.1引脚输出低电平,DS1点亮


P0=0xa4;  //数字2的段码


delay();


P2=0xfb;   //P2.2引脚输出低电平,DS2点亮


P0=0xb0;  //数字3的段码


delay();


P2=0xf7;   //P2.3引脚输出低电平,DS3点亮


P0=0x99;  //数字4的段码


delay();


P2=0xff;


}


}

//实例64:用数码管显示动态检测结果

#include     //  包含51单片机寄存器定义的头文件

#include//包含随机函数rand()的定义文件

unsigned char i;//记录中断次数

unsigned int x;//随机检测的数据

unsigned char code Tab[10]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};//数码管显示0~9的段码表

/********************************************************************

函数功能:快速动态扫描延时,延时约0.9毫秒

********************************************************************/

void delay(void)

{

  unsigned int i;

  for(i=0;i<300;i++)

}

/*******************************************************************

函数功能:4位数的数码显示器显示

入口参数:k

出口参数:无

********************************************************************/

void display(unsigned int k)

{

  P2=0xfe;   //即P2=11111110B,P2.0引脚输出低电平,数码显示器DS0接通电源

  P0=Tab[k/1000];          //显示千位

  delay();

  P2=0xfd;   //即P2=11111101B,P2.1引脚输出低电平,数码显示器DS1接通电源

  P0=Tab[(k%1000)/100];            //显示百位

  delay();

  P2=0xfb;   //即P2=11111011B,P2.2引脚输出低电平,数码显示器DS2接通电源

  P0=Tab[(k%100)/10];   //显示十位

  delay();

  P2=0xf7;   //即P2=11110111B,P2.3引脚输出低电平,数码显示器DS3接通电源

  P0=Tab[k%10];//显示个位

  delay();

  P2=0xff;  //关闭所有显示器

}


void main(void)//主函数

{

  TMOD=0x01;//定时器0工作方式一

  TH0=(65536-46083)/256;

  TL0=(65536-46083)%256;

  EA=1;

  ET0=1;

  TR0=1;

  while(1)

  {

    display(x);//调用检测结果的显示程序

  }

}

/********************************************************

函数功能:定时器T0的中断服务程序

*******************************************************/

void Time0(void) interrupt 1 using 1

{

  TR0=0;    //关闭定时器T0

  i++;      //每来一次中断,i自加1

  if(i==20)   //够20次中断,即1秒钟进行一次检测结果采样

  {

    x=rand()/10;      //随机产生一个从0到32767的整数,再将其除以10,获得一个随机4位数,模拟检测结果

    i=0;              //将i清0,重新统计中断次数

  }

  TH0=(65536-46083)/256;    //重新给计数器T0赋初值

  TL0=(65536-46083)%256;

  TR0=1;     //启动定时器T0

}

x在中断中发生改变,通过显示函数显示,这个函数的结构就是一个比较复杂的程序的常用结构了,包括初始化和功能块,注意逻辑分析。


//实例65:数码秒表设计


包含51单片机寄存器定义的头文件


unsigned char code Tab[10]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};//数码管显示0~9的段码表


unsigned char int_time;          //记录中断次数


unsigned char second;          //储存秒


/********************************************************************


***


函数功能:快速动态扫描延时,延时约0.6毫秒


*********************************************************************


***/


void delay(void)


{


unsigned char i;


for(i=0;i<200;i++)


;


}


/********************************************************************


***


函数功能:显示秒


入口参数:k


出口参数:无


*********************************************************************


***/


void Display Second(unsigned char k)

{

  P2=0xfb;          //P2.6引脚输出低电平,DS6点亮

  P0=Tab[k/10];            //显示十位

  delay();

  P2=0xf7;         //P2.7引脚输出低电平,DS7点亮

  P0=Tab[k%10];           //显示个位

  delay();

  P2=0xff;      //关闭所有数码管

}

void main(void)//主函数

{

  TMOD=0x01;//使用定时器T0秒

  TH0=(65536-46083)/256; //将定时器计时时间设定为46083×1.085微=50000微秒=50毫秒

  TL0=(65536-46083)%256;

  EA=1;//开启总中断

  ET0=1;//定时器T0中断允许

  TR0=1;//启动定时器T0开始运行

  int_time=0;//中断次数初始化

  second=0;//秒初始化

  while(1)

  {

     DisplaySecond(second);//调用秒的显示子程序

  }

}

//********************************************************

//函数功能:定时器T0的中断服务程序

//*******************************************************

void interserve(void) interrupt 1 using 1

{

TR0=0;    //关闭定时器T0

int_time++;          //每来一次中断,中断次数int_time自加1

if(int_time==20)    //够20次中断,即1秒钟进行一次检测结果采样

{

int_time=0;     //中断次数清0

second++;     //秒加1

if(second==60)

second=0;//秒等于60就返回0

}

TH0=(65536-46083)/256;    //重新给计数器T0赋初值

TL0=(65536-46083)%256;

TR0=1;     //启动定时器T0

}


//实例66:数码时钟设计

#include//包含51单片机寄存器定义的头文件

unsigned char Tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};//control  shape

unsigned char port[8]={0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f};

unsigned char int_time;//中断次数计数变量

unsigned char second;     //秒计数变量

unsigned char minute;     //分钟计数变量

unsigned char hour;      //小时计数变量

void delay(void)//延时函数,延时约0.6ms

{

  unsigned char j;

  for(j=0;j<200;j++);

}

/******************************************************************

函数功能:显示秒的子程序

入口参数:s

********************************************************************/

void Display Second(unsigned char s)

{

  P2=0xbf;          //P2.6引脚输出低电平,DS6点亮

  P0=Tab[s/10];            //显示十位

  delay();

  P2=0x7f;         //P2.7引脚输出低电平,DS7点亮

  P0=Tab[s%10];           //显示个位

  delay();

  P2=0xff;      //关闭所有数码管

}

/******************************************************************

函数功能:显示分钟的子程序

入口参数:m

********************************************************************/

void Display Minute(unsigned char m)

{

  P2=0xf7;   //P2.3引脚输出低电平,DS3点亮

  P0=Tab[m/10];//显示个位

  delay();

  P2=0xef;   //P2.4引脚输出低电平,DS4点亮

  P0=Tab[m%10];

  delay();

  P2=0xdf;   //P2.5引脚输出低电平,DS5点亮

  P0=0xbf;   //分隔符“-”的段码

  delay();

  P2=0xff;   //关闭所有数码管

}

/******************************************************************

函数功能:显示小时的子程序

入口参数:h

********************************************************************/

void Display Hour(unsigned char h)

{

  P2=0xfe;          //P2.0引脚输出低电平,DS0点亮

  P0=Tab[h/10];            //显示十位

  delay();

  P2=0xfd;         //P2.1引脚输出低电平,DS1点亮

  P0=Tab[h%10];     //显示个位

  delay();

  P2=0xfb;      //P2.2引脚输出低电平,DS2点亮

  P0=0xbf;      //分隔符“-”的段码

  delay();

  P2=0xff;      //关闭所有数码管

}

/******************************************************************

函数功能:主函数

********************************************************************/

void main(void)

{

  TMOD = 0x01;                //使用定时器T0

  EA=1;                      //开中断总允许

  ET0=1;                     //允许T0中断

  TH0=(65536-46083)/256;   //定时器高八位赋初值

  TL0=(65536-46083)%256;   //定时器低八位赋初值

  TR0=1;

  int_time=0;     //中断计数变量初始化

  second=0;       //秒计数变量初始化

  minute=0;      //分钟计数变量初始化

  hour=0;         //小时计数变量初始化

  while(1)

  {

    DisplaySecond(second);     //调用秒显示子程序

    delay();

    DisplayMinute(minute);    //调用分钟显示子程序

    delay();

    DisplayHour(hour);

    delay();

  }

}

/******************************************************************

函数功能:定时器T0的中断服务子程序

********************************************************************/

void interserve(void) interrupt 1 using 1   //usingTime0

{

  int_time++;

  if(int_time==20)

  {

    int_time=0;     //中断计数变量清0

    second++;       //秒计数变量加1

  }

  if(second==60)

 {

   second=0;     //如果秒计满60,将秒计数变量清0

   minute++;     //分钟计数变量加1

[1] [2] [3] [4]
关键字:51单片机  C语言  外设 引用地址:51单片机C语言程序100例分析(4)外设

上一篇:51单片机入门基础知识
下一篇:51单片机C语言程序100例分析(3)串口

推荐阅读最新更新时间:2024-11-17 12:17

51单片机实现音频频谱显示的快速算法研究
1 引言 在家庭影院、卡拉OK等音响系统中,实时显示音乐信号的频谱将为音响系统增添不少色彩。目前实际生产的音响系统产品,大多采用以下两种方法实现音频频谱显示:一是利用硬件滤波器和A/D转换器;二是利用DSP处理频谱显示。前者实现简单,但硬件成本高,后者软件和硬件实现都较复杂。这里针对单片机RAM资源少、运算速度慢的特点,提出一种切实可行的快速傅里叶变换算法实现频谱显示。 2 系统整体设计及原理 该系统设计由单片机SST89V58RD2、音频数据采样电路、A/D转换电路、频谱显示电路等部分组成。图1为系统整体设计原理框图。 该系统从功能上可划分成3部分:(1)音频数据采集电路实现模拟音频信号的采样保持和量化处
[单片机]
<font color='red'>51单片机</font>实现音频频谱显示的快速算法研究
学习51单片机必知的寄存器知识
说起单片机存储器,大家可能知道RAM和ROM,但具体需要怎么用,还需要深入了解下,那今天通程创品就来大家详细了解下51单片机存储器的相关知识,希望对大家有帮助。 程序存储器(又称数据Flash),顾名思义,是用来存储用户的程序,使单片机能够按照编写的代码顺序执行,完成指定的任务。所以程序存储器是只读存储器(只读存储器),我们已经听过很多次了。代码存储在里面,一般有常数、表格、pi值、数码管形状、SCM ID号、内部参考信号源、关机唤醒定时器频率、IRC参数等数据。 注意:单片机每次都是烧录程序,烧录就是为了把代码放到程序存储器中,而我们用的电脑则是把硬盘的数据和程序放到RAM,再用CPU去读取RAM里面的数据和程序 一
[单片机]
51单片机C51毫秒级(ms)精确延时
如下程序能实现ms毫秒级的比较精确的延时 void Delayms(unsigned int n) { unsigned int i,j; for(j=n;j 0;j--) for(i=112;i 0;i--); } 用keil可以看出这个延时的时间,我们先延时1ms(Delayms(1))。 进入Delayms前,sec=0.00042209s 延时后,sec=0.00142253s 可以知道Delayms(1)实际延时0.00142253s—0.00042209s=0.00100044s≈1ms 同样如果想延时15ms的话,用Delayms(15),实际延时0.01480903s≈15m
[单片机]
51单片机控制硬盘的程序
/******************************************************************* * 硬盘控制源程序 * * 编译环境 : KEIL C51 V7.07 支持器件 : AT89C51 * * COPYRIGHT (C) 2004 * /*******************************************************************/ ///////////////////预处理///////////////////////////
[单片机]
用proteus8.0仿真51单片机控制步进电机实验报告与源码
用proteus8.0仿真51单片机控制步进电机,实现简单的正反转、加减速控制。 ps. 该贴仅为获取黑币而法,如有雷同,多多保函 实验内容 掌握KeilC51软件与Protues软件联合仿真调试的方法; 掌握步进电机的工作原理及控制方法; 掌握步进电机控制的不同编程方法。 电路图 实验心得 这次实验让我学到了通过改变延时函数的参数可以实现步进电机的增减速,改变驱动电机的数模可以实现电机的正反转,中途遇到的困难不少,但在老师的指导下总算是完成任务。这两次实验使我能更熟练地运用微机来控制其他器件,获益良多。 单片机源程序如下: #include reg52.h sbit KEY0=P0^0; sbit KE
[单片机]
用proteus8.0仿真<font color='red'>51单片机</font>控制步进电机实验报告与源码
从零开始51单片机教程 —— 单片机条件转移指令
条件转移指令是指在满足一定条件时进行相对转移 判A内容是否为0转移指令 JZ rel JNZ rel 第一指令的功能是:如果(A)=0,则转移,不然次序执行(执行本指令的下一条指令)。转移到什么地方去呢?如果按照传统的办法,就要算偏移量,很麻烦,好在现在我们能借助于机器汇编了。因此这第指令我们能这样理解:JZ 标号。即转移到标号处。下面举一例说明: MOV A,R0 JZ L1 MOV R1,#00H AJMP L2 L1: MOV R1,#0FFH L2: SJMP L2 END 在执行上面这段程序前如果R0中的值是0的话,就转移到L1执行,因此最终的执行结果是R1中的值为0FFH。而如果R0中的值不
[单片机]
从零开始<font color='red'>51单片机</font>教程 —— 单片机条件转移指令
51单片机ADC0832电压测量液晶1602显示的C程序与proteus仿真
很早对AD转换感兴趣,也想自己业余做块单片机开发板,让广大的电子设计爱好者学习使用单片机。 今天通过搜索,整理了proteus 7可以仿真通过的基于51单片机+ADC0832电压采集并通过液晶1602显示电压的C程序及电路连接图,希望对大家有所帮助。 程序是谁写的谁修改的并不主要,主要的是学会并使用单片机AD转换,这才是王道。 电路连接图如下: C程序如下: #include reg52.h #include intrins.h #include math.h /**********************************8/ /**********LCD1602接口程序*********
[单片机]
<font color='red'>51单片机</font>ADC0832电压测量液晶1602显示的C程序与proteus仿真
80C51单片机的内部RAM简介
80C51内部RAM有256个单元,通常在空间上分为两个区。 低128个单元(00H~7FH)的内部数据RAM区和高128个单元(80H~0FFH)的专用寄存器SFR区。 内部RAM低128单元 80C51低128个单元是真正的内部数据RAM区,是一个多功能复用性数据存储器,其按用途可分为3个区域,如下图所示: 1)工作寄存器区(00H~1FH) 工作寄存器区也称为通用寄存器,该区域共有4组寄存器,每组由8个寄存器组成,每个单元8位,各组均以R0~R7作为寄存器编号,共32个单元,单元的地址为00H~1FH。 在任一时刻,CPU只能使用其中一组通用寄存器,称为当前通用寄存器组,具体可由程序状态寄存器PSW中的RS1,RS0
[单片机]
80C<font color='red'>51单片机</font>的内部RAM简介
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved