51单片机教程(四)- 点亮LED灯

1、项目分析

  • 让输入/输出口的P1.0连接一盏LED灯进行点亮。

2、技术准备

1 LED组成

  • 说明
    • 二极管有 P型 和 N型材料构成,通常是:硅/锗 掺杂其他元素(硼、磷等)
      • 电子是带负电的,是负电荷的载体,电子流是从负极流向正极
      • 电流则从正极流向负极。
    • 当N型材料连接电源负极(正向连接),则电子会从流向P型材料的空穴,则会有电流流过【正向偏置】;
    • 当N型材料连接电源正极(反向连接),由于没有多余的空穴,则不会有电子跃迁至P型材料,则不会有电流流过【反向偏置】;
    • 则说明二极管具有单向导电的特性
  • 扩展
    • 如果二极管是由 硅 制成,需要一个约 0.7V的电压,才会有电流流过,则即便是二极管正向连接,也不会有电流流过。
    • 如果二极管是由 锗 制成,需要一个约 0.3V的电压,才会有电流流过,则即便是二极管正向连接,也不会有电流流过。
    • 如果反向链接,则不同材质的二极管所能承受的电压,可以高达 100V,电流可达 1A

2 介绍

  1. LED发光二极管

    • 它是半导体二极管的一种,可以把电能转化成光能;常简写为LED。发光二极管与普通二极管一样是由一个PN结组成,也具有单向导电性。
  2. LED的工作原理。

    • LED的工作是有方向性的,只有当正级接到LED阳极,负极接到LED的阴极的时候才能工作,如果反接LED是不能正常工作的。

  3. LED的原理图解析

    • 开发板上面LED的原理图如右图,LED的阳极串联一个电阻,然后连接到电源VCC,而LED的阴极连接到单片机的P1口,如果你想点亮一盏LED就对把单片机相对应的IO赋为低电平(0)。

3 C语言知识点

1 标识符

  • 标识符:

    • 用来标识源程序中某个对象的名字,这些对象可以是数据类型名、函数名、变量名、数组名等。
  • 组成

    1. 标识符由字母、数字和下划线组成。
    2. 第一个字符必须是字母或下划线。
    3. 不能使用C语言中的关键字。
    4. 由于C51中有些库函数的标识符是以下划线开头的,所以一般不要以下划线开头命名标识符。
    c 复制代码
    // 正确标识符
    name    Name  num1   oldName
        
    // 错误标识符
    3ku    

2 关键字

  • 标准C语言定义了32个关键字

  • 常用关键字
    • char
    • int
    • unsigned
    • for
    • while
    • if
    • sbit
    • interrupt

3 变量与常量

  • 常量

    • 又称为标量,它的值在程序执行过程中不能改变的量,常量的数据类型有整型、浮点型、字符型和字符串型等。

    • 实际使用中用 #define定义(宏定义)const 在程序中经常用到的常量,这样一方面有助于提高程序的可读性,另一方面也便于程序的修改和维护。

      c 复制代码
       #define PI 3.14		               //以后的编程中用PI代替浮点数常量3.14,便于阅读
       #define SYSCLK 12000000	           //长整型常量用SYSCLK代替12MHz时钟
       #define TRUE  1			           //用字符TRUE,在逻辑运算中代替1
       #define STAR '*'			           //用STAR表示字符 '*'
       #define uint unsigned int	       	   //用uint 代替unsigned int
       
       const int MAX_SIZE = 100;

  • 变量

    • 变量是一种在程序执行过程中,其数值不断变化的量。
  • 注意

    • C51规定变量必须先定义后使用

      c 复制代码
      unsigned int i;
      i = 10;
      printf("i=%d", i);
      
      unsigned int i = 10;

4 数据类型

  • 变量都有相应的数据类型。


  • char 字符类型

    • char 类型的长度是一个字节,通常用于定义处理字符数据的变量或常量。
    • 分无符号字符类型 unsigned char 和有符号字符类型 signed char ,默认值为 signed char 类型。
      • unsigned char 类型用字节中所有的位来表示数值,所能表达的数值范围是 0~255。
      • signed char 类型用字节中最高位字节表示数据的符号,"0"表示正数,"1"表示负数,负数用补码表示。所能表示的数值范围是-128~+127。
      • unsigned char 常用于处理 ASCII 字符或用于处理小于或等于 255 的整型数。

  • int 整型

    • int 整型长度为两个字节,用于存放一个双字节数据。
    • 分有符号 int 、整型数signed int 和无符号整型数 unsigned int,默认值为 signed int 类型。
    • signed int 表示的数值范围是-32768~+32767,字节中最高位表示数据的符号,"0"表示正数,"1"表示负数。
    • unsigned int 表示的数值范围是 0~65535。

  • long 长整型

    • long 长整型长度为四个字节,用于存放一个四字节数据。
    • 分有符号 long 长整型 signed long 和无符号长整型 unsigned long,默认值为 signed long 类型。
    • signed int 表示的数值范围是-2147483648~+2147483647,字节中最高位表示数据的符号,"0"表示正数,"1"表示负数。
    • unsigned long 表示的数值范围是 0~4294967295。
  • float 浮点型

    • float 浮点型在十进制中具有 7 位有效数字,是符合 IEEE-754 标准的单精度浮点型数据,占用四个字节。

  • 指针型

    • 指针型是一种特殊的数据类型,其本身就是一个变量,但在其中存放的是另一个数据的地址。

    • 在C51中,指针的长度一般是3个字节。根据所指向的变量类型的不同指针变量也有不同的类型,指针变量的类型也就表示了该指针指向的地址中的数据的类型。


  • bit 位标量

    • bit 位标量是C51的一种扩充数据类型,利用它可定义一个位标量,但不能定义位指针,也不能定义位数组。

    • 它的值是一个二进制位,不是 0 就是 1,位变量的值可以取0 (false)或1 (true)。对位变量进行定义的语法如下:

      c 复制代码
      bit flag1;
      bit send_en=1;

  • sfr 特殊功能寄存器

    • 单片机内的各种控制寄存器、状态寄存器以及I/O端口锁存器、定时器、串行端口数据缓冲器是内部数据存储器的一部分,离散地分布在80H~FFH的地址空间范围内,这些寄存器统称特殊功能寄存器(SFR,Special Function Registers )。

    • sfr类型的长度为一个字节,其定义方式如下:

      • sfr 特殊功能寄存器名 = 地址常量;
    • 说明

      • "地址常量"就是所定义的特殊功能寄存器的地址。

        c 复制代码
        sfr	TMOD=0x89;		/*定义定时器/计数器方式控制寄存器TMOD的地址为89H*/
        sfr	P1=0x90;	          /*定义P1口的地址为90H*/
    • 注意

      • 在关键字sfr后面必须是一个名字,名字可以任意选取,但应符合一般的习惯。等号后面必须是常数,不允许有带运算符的表达式,而且该常数必须在特殊功能寄存器的地址范围之内(80H~0FFH)。

  • sfr16 16位特殊功能寄存器

    • 在新一代的8051单片机中,特殊功能寄存器在功能上经常组合成16位来使用。

    • 为了有效地访问这种16位的特殊功能寄存器,可采用关键字sfrl6。

    • sfrl6类型的长度为两个字节,其定义语法与8位SFR相同,但16位SFR的低端地址必须作为sfr16的定义地址.

      sfr16 T2=0CCH;       //定义TIMER2,其地址为T2L=0CCH、T2H=0CDH。
      

  • sbit 可寻址位

    • sbit 同样是C51中一种扩充数据类型,利用它能访问芯片内部的 RAM 中的可寻址位或特殊功能寄存器中的可寻址位。例如:

      // PSW是可位寻址的SFR,其中各位可用sbit定义。
      sbit CY=0Xd7;		/*定义进位标志CY的地址为D7H*
      sbit AC=0xD0^6;		/*定义辅助进位标志AC的地址为D6H*/
      sbit RS0=0XD0^3;	/*定义RS0的地址为D3H*/
      
    • 注意

      • sfr和sbit只能在函数外使用,一般放在程序的开头

      • 实际上大部分特殊功能寄存器及其可位寻址的位的定义在reg51.h、reg52.h 等头文件中已经给出 ,使用时只需在源文件中包含相应的头文件,即可使用SFR及其可位寻址的位;而对于未定义的位,使用前必须先定义。例如:

        #include<reg52.h>
        
        sbit P10=P1^0;
        sbit P12=P1^2;
        
        PSW=0x08;
        

3、程序实现

实验1:点亮开发板上的第1个LED灯

  • 从LED原理图上看,只要P1.0输出为低电平就可以点亮LED灯。
c 复制代码
#include <reg52.h>   // 包含头文件,在"reg52.h"上右键单击,并打开,可以看到它里面的定义
                  
sbit led=P1^0;   // 定义一个LED 为P1.0 IO口

void main()     
{  
    led=1;    // 单片机IO P1.0脚输出一个高电平,发光管不亮
	led=0;    // 单片机IO P1.0脚输出一个低电平,点亮发光管。 高电平(1)为5V  低电平为0。
	while(1);
}
  • 实验效果

    • 软件设计不用汇编,一律采用C语言,便于理解和扩展。

实验2:点亮开发板上的4个LED灯(第1、3、5、7个灯)

c 复制代码
#include "reg52.h" 

sbit led1=P1^0;	
sbit led3=P1^2;
sbit led5=P1^4;
sbit led7=P1^6;								  

void main()
{
	led1=0;	   //参照电路图可知,P1^0为低电平,可以让led1点亮。
	led3=0;
	led5=0;
	led7=0;
	while(1);   //此处设置一个死循环,让程序停留在这里,防止跑飞。
}
c 复制代码
#include<reg52.h> 

sbit LED0=P1^0; // 用sbit 关键字 定义 LED到P1.0端口,
sbit LED1=P1^1; 
sbit LED2=P1^2;
sbit LED3=P1^3;
sbit LED4=P1^4;
sbit LED5=P1^5;
sbit LED6=P1^6;
sbit LED7=P1^7;

/*------------------------------------------------
                    主函数
------------------------------------------------*/
void main ()
{
                  //此方法使用bit位对单个端口赋值
	LED0=0;     //将P1.0口赋值 0,对外输出低电平
	LED1=1;
	LED2=0;
	LED3=1;
	LED4=0;
	LED5=1;
	LED6=0;
	LED7=1;
	while (1)         //主循环
	{
	                  //主循环中添加其他需要一直工作的程序
	}
}

实验3:点亮开发板上的4个LED灯(第2、4、6、8个灯)

  • 定义所有端口: P1、P2、P3、P4,用来表示 P1、P2、P3、P4 的 I/O 口。

    IO口 P1.7 P1.6 P1.5 P1.4 P1.3 P1.2 P1.1 P1.0
    取值 0 1 0 1 0 1 0 1
    效果
  • 思考:P1 数据值转为十六进制是多少? ox55

c 复制代码
#include <reg52.h> 

/*------------------------------------------------
                    主函数
------------------------------------------------*/
void main (void)
{
    // 0101 0101 --> 0x55
    P1 = 0x55;       

    while (1)       // 主循环中添加其他需要一直工作的程序
    {}
}

4、提示

  • 为了方便每次程序编译成功后,就自动把 hex 文件烧录到MCU中,则可以勾选图中2个选项。
相关推荐
网易独家音乐人Mike Zhou2 小时前
【卡尔曼滤波】数据预测Prediction观测器的理论推导及应用 C语言、Python实现(Kalman Filter)
c语言·python·单片机·物联网·算法·嵌入式·iot
zy张起灵2 小时前
48v72v-100v转12v 10A大功率转换电源方案CSM3100SK
经验分享·嵌入式硬件·硬件工程
lantiandianzi9 小时前
基于单片机的多功能跑步机控制系统
单片机·嵌入式硬件
哔哥哔特商务网9 小时前
高集成的MCU方案已成电机应用趋势?
单片机·嵌入式硬件
跟着杰哥学嵌入式9 小时前
单片机进阶硬件部分_day2_项目实践
单片机·嵌入式硬件
电子科技圈10 小时前
IAR与鸿轩科技共同推进汽车未来
科技·嵌入式硬件·mcu·汽车
东芝、铠侠总代1361006839311 小时前
浅谈TLP184小型平面光耦
单片机·嵌入式硬件·物联网·平面
lantiandianzi11 小时前
基于单片机中医药柜管理系统的设计
单片机·嵌入式硬件
嵌入式知识大讲堂11 小时前
HDMI数据传输三种使用场景
单片机
黑客呀12 小时前
[系统安全]Rootkit基础
stm32·单片机·系统安全