第十四届蓝桥杯单片机第二场模拟赛程序

这篇具有很好参考价值的文章主要介绍了第十四届蓝桥杯单片机第二场模拟赛程序。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

第十四届蓝桥杯单片机第二场模拟赛程序(少量bug)

题目来源于4T评测网 www.4t.wiki

赛题:

一、基本要求


使用大赛组委会提供的国信长天单片机竞赛实训平台,完成本试题的程序设计与调试。程序编写、调试完成后,选手需通过考试系统提交以准考证号命名的hex文件。不符合以上文件提交要求的作品将被评为零分或者被酌情扣分。

硬件设置:

将IAP15F2K61S2单片机内部振荡器频率设定为12MHz,串口通信波特率为9600bps

键盘工作模式跳线J5配置为KBD矩阵按键模式。

扩展方式跳线J13配置为IO模式。

请注意:选手需严格按照以上要求配置竞赛板,编写和调试程序,不符合以上配置要求的作品将被评为零分或者被酌情扣分。

二、硬件框图


第十四届蓝桥杯单片机第二场模拟赛程序

图1 系统硬件框图

三、功能描述 


3.1 基本功能描述

1)通过串口控制数码管显示界面:“温度显示界面”或“电压显示界面”;也可以返回当前数码管显示的数据。  

2)通过读取DS18B20温度传感器,获取环境温度。

3)通过 PCF8591 的 ADC 通道测量电位器 RB2 的输出电压。

4)通过数码管显示获取的温度数据和采集的电压数据,显示界面可以通过串口切换。

5)通过LED指示灯完成题目要求的指示功能。

6)根据题目要求完成继电器和蜂鸣器的控制功能。

3.2 性能要求

1)按键动作响应时间:≤0.2 秒

2)指示灯动作响应时间:≤0.1 秒

3.3 显示功能

温度显示界面

温度显示界面如图2所示,显示内容包括界面提示符(U1)和温度数据,单位为℃。

第十四届蓝桥杯单片机第二场模拟赛程序

图2 温度显示界面(27.5℃)

使用3位数码管显示温度数据,温度数据保留小数点后1位有效数字。

电压显示界面

电压显示界面如图3所示,显示内容包括界面提示符(U2)和电压数据,单位为V。

第十四届蓝桥杯单片机第二场模拟赛程序

图3 电压显示界面(1.35V)

使用3位数码管显示温度数据,电压数据保留小数点后2位有效数字。

3.4 按键功能

1)按键S4定义为“锁定”按键,按下S4按键,能够锁定当前界面“温度显示界面”或“电压显示界面”,串口切换界面指令失效。

2)按键S5定义为“解锁”按键,在界面锁定时,按下S5按键,可取消界面锁定,串口指令恢复控制。

3)按键S12定义为“发送”按键,每次按下,串口将当前数码管显示的数据发送给PC端的串口调试工具。

注意:

(1)按键S5仅在界面锁定时有效。

(2)判断按键是否按下时,需进行消抖操作,避免单次按键操作,触发多次结果。

3.5 串口功能

1)串口发送指令字符‘A’,进入温度显示界面。

2)串口发送指令字符‘B’,进入电压显示界面。

3)串口返回数据格式:

                                       “TEMP:27.5℃”或“Voltage:1.35V”

注意: 注意区分字母大小写。

3.6 LED指示灯功能

当前界面处于温度显示界面时,L1指示灯点亮,否则熄灭。

当前界面处于电压显示界面时,L2指示灯点亮,否则熄灭。

当前界面处于锁定状态时,L3指示灯以0.1s的时间间隔亮、灭,否则熄灭。

其余指示灯均处于熄灭状态。

3.7 继电器控制功能

继电器状态受温度控制,将采集的温度数据记为T,若当前采集的温度满足下列条件时,继电器吸合,否则,继电器断开。

                                          T≥28℃

3.8 蜂鸣器控制功能

蜂鸣器状态受电压控制,将采集的电压数据记为V,若当前采集的电压满足下列条件时,蜂鸣器发声,否则蜂鸣器静音。

                                         V>3.6V

3.9 初始化

上电数码管默认处于温度显示界面。

界面切换处于解锁状态。

指示灯全部熄灭。

程序 :

main.c

#include <STC15F2K60S2.h>
#include <onewire.h>
#include <iic.h>
#include <stdio.h>

#define uchar unsigned char
#define uint unsigned int
	
sbit R3=P3^2;
sbit R4=P3^3;
sbit C1=P4^4;
sbit C2=P4^2;
sbit C3=P3^5;
sbit C4=P3^4;

code uchar tab[12]=
{0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0xff,0xc1}; // U 1 1 0 0  0 0 0 1 即0xc1
// 0    1    2     3   4     5    6    7    8   9    灭   U

uchar dspbuff[8]={10,10,10,10,10,10,10,10};
uchar dspcom=0;           //数码管位选标志位
uchar ad_value;          //AD采集
uchar state=1;              //界面切换标志位
uchar x=0xff;             //LED标志
uint v_value;            //AD显示
uint intr=0,intr1=0,intr2=0;
float temperature;           //温度(浮点数)
uint temper;                //温度(整数)
code uchar s1[]={"TEMP:"};
code uchar s2[]={"Voltage:"};
code uchar s3[]={"℃"};
uchar str[20];
uchar str1[10];
uchar str_re='A';
uchar rxcnt=0;          //串口标志位
uchar Control;

bit flag,flag1,flag2;
bit rxc = 0;   /数据接收标志位

void InitAll()              //初始化,关闭所有LED,蜂鸣器,继电器
{
	P2=(P2&0x1f)|0x80;
	P0=0xff;
	P2=(P2&0x1f)|0xa0;
	P0=0x00;
	P2=(P2&0x1f);
}

void Timer0Init(void)		//2毫秒@12.000MHz        定时器初始化,软件自动生成
{
	AUXR &= 0x7F;		//定时器时钟12T模式
	TMOD &= 0xF0;		//设置定时器模式
	TL0 = 0x30;		//设置定时初值
	TH0 = 0xF8;		//设置定时初值
	TF0 = 0;		//清除TF0标志
	TR0 = 1;		//定时器0开始计时
	
	ET0=1;
	EA=1;
}

void UartInit(void)		//9600bps@12.000MHz         串口初始化,软件自动生成
{
	SCON = 0x50;		//8位数据,可变波特率
	AUXR &= 0xBF;		//定时器1时钟为Fosc/12,即12T
	AUXR &= 0xFE;		//串口1选择定时器1为波特率发生器
	TMOD &= 0x0F;		//设定定时器1为16位自动重装方式
	TL1 = 0xE6;		//设定定时初值
	TH1 = 0xFF;		//设定定时初值
	ET1 = 0;		//禁止定时器1中断
	TR1 = 1;		//启动定时器1
	ES = 1;
	EA = 1;
}

void SendDate(uchar dat)        //串口发送字符
{
	SBUF=dat;
	while(TI==0);
	TI=0;
	
}

void SendString(uchar *s)       //串口发送字符串
{
    unsigned char *p;
      
    p = s;
    while(*p != '\0')
    {
        SBUF = *p;
		while(TI == 0);  //等待发送标志位置位
		TI = 0;
        p++;
    }
}

void DisplaySMG()         //数码管显示设置
{
	P2=(P2&0x1f)|0xe0;
	P0=0xff;            //消隐
	P2=P2&0x1f;            
	P2=(P2&0x1f)|0xc0;
	P0=1<<dspcom;
	P2=(P2&0x1f)|0xe0;
	P0=tab[dspbuff[dspcom]];
	P2=P2&0x1f;
	if(state==1)
	{
		if(dspcom==6)
	   {
		P2=(P2&0x1f)|0xe0;
		P0=tab[dspbuff[dspcom]]&0x7f;     //小数点
		P2=P2&0x1f;
	   }
	}
	if(state==2)
	{
		if(dspcom==5)
	   {
		P2=(P2&0x1f)|0xe0;
		P0=tab[dspbuff[dspcom]]&0x7f;         //小数点
		P2=P2&0x1f;
	   }
	}
	if(++dspcom==8)
	{
		dspcom=0;
	}
}

void displayWD()         //数码管温度显示
{
	
	dspbuff[0]=11;
	dspbuff[1]=1;
	
	dspbuff[5]=temper/100;
	dspbuff[6]=temper%100/10;
	dspbuff[7]=temper%10;
}
void displayAD()          //数码管ADC显示
{
	dspbuff[0]=11;
	dspbuff[1]=2;
	
	dspbuff[5]=v_value/100;
	dspbuff[6]=v_value%100/10;
	dspbuff[7]=v_value%10;
}

void displayL3()       //LED闪烁
{
	if(flag2)
	{
		flag2=0;
		P2=(P2&0x1f)|0x80;
		x=x^0x04;
		P0=x;
		P2=(P2&0x1f);
	}
}

void Delay5ms()		//@12.000MHz      软件延时,自动生成
{
	unsigned char i, j;

	i = 10;
	j = 183;
	do
	{
		while (--j);
	} while (--i);
}

void Key_scan()              //键盘扫描
{
	C3=1;C1=0;C2=1;C4=1;
	R3=1;R4=1;
	if(R3==0)     //S5
	{
		Delay5ms();
		if(R3==0)
		{
			ES=1;
			Control=0;
			if(state==1)
			{
				P2=(P2&0x1f)|0x80;
			    P0=0xfe;
			    P2=P2&0x1f;
			}
		else if(state==2)
			{
				P2=(P2&0x1f)|0x80;
			    P0=0xfd;
			    P2=P2&0x1f;
			}
		}
		while(!R3); 
	}
	else if(R4==0)     //S4
	{
		Delay5ms();
		if(R4==0)
		{
			ES=0;
			Control=1;
		}
		while(!R4); 
	}
	C3=0;C1=1;C2=1;C4=1;
	R3=1;R4=1;
	if(R4==0)     //S12
	{
		Delay5ms();
		if(R4==0)
		{
			if(state==1)
			{
				sprintf(str,"%s",s1);
				sprintf(str1,"%s",s3);
				SendString(str);
				SendDate(0x30+temper/100);
				SendDate(0x30+temper%100/10);
				SendDate('.');
				SendDate(0x30+temper%10);
				SendString(str1);
				SendDate('\r');
				SendDate('\n');
			}
			if(state==2)
			{
				sprintf(str,"%s",s2);
				SendString(str);
				SendDate(0x30+v_value/100);
				SendDate('.');
				SendDate(0x30+v_value%100/10);
				SendDate(0x30+v_value%10);
				SendDate('V');
				SendDate('\r');
				SendDate('\n');
			}
			
		}
		while(!R4); 
	}
}

void main()  
{
	InitAll();
	Timer0Init();
	UartInit();	
	while(1)
	{
		if(flag)
		{
			flag=0;
			temperature= rd_temperature(); 
			temper=temperature*10;
			
		}
		if(flag1)
		{
			flag1=0;
			Init_pcf8591(0x03);
			ad_value= Read_pcf8591();
			v_value=ad_value*100/51;
			
		}
		if(state==1)
		{
			
			displayWD();
		}
		else if(state==2)
		{
			
			displayAD();
		}
		if(rxc == 1)
		{
			rxc = 0;
			switch(str_re){
				case 'A':
				{
					state=1;
					P2=(P2&0x1f)|0x80;
			        P0=0xfe;
					P2=P2&0x1f;
				}
				break;		
				case 'B':
				{
					state=2;
					P2=(P2&0x1f)|0x80;
					P0=0xfd;
					P2=P2&0x1f;
				}
				break;
			}
			ES = 1;
		}
		Key_scan();
		if(Control==1)
		{
			P2=(P2&0x1f)|0x80;
			P0=0xff;
			displayL3();
		}
		if(temper>=280)
		{
			P2=(P2&0x1f)|0xa0;
			P04=1;
			P2=P2&0x1f;
		}
		else 
		{
			P2=(P2&0x1f)|0xa0;
			P04=0;
			P2=P2&0x1f;
		}
		if(v_value>=360)
		{
			P2=(P2&0x1f)|0xa0;
			P06=1;
			//P2=P2&0x1f;
		}
		else 
		{
			P2=(P2&0x1f)|0xa0;
			P06=0;
			//P2=P2&0x1f;
		}
		
	}
}

void intr_InitTimer() interrupt 1
{
	DisplaySMG();
	
	if(++intr==50)
	{
		intr=0;
		flag=1;
	}
	if(++intr1==60)
	{
		intr1=0;
		flag1=1;
	}
	if(++intr2==50)
	{
		intr2=0;
		flag2=1;
	}
}
void isr_uart(void) interrupt 4
{
    if(RI)
    {
	    RI = 0;  //清除接收标志位 
	    str_re=SBUF;
		ES = 0;
		rxc = 1;
	  }
}

iic.c

/*
  程序说明: IIC总线驱动程序
  软件环境: Keil uVision 4.10 
  硬件环境: CT107单片机综合实训平台 8051,12MHz
  日    期: 2011-8-9
*/

#include "STC15F2K60S2.h"
#include "intrins.h"

#define DELAY_TIME 5

#define SlaveAddrW 0xA0
#define SlaveAddrR 0xA1

//总线引脚定义
sbit SDA = P2^1;  /* 数据线 */
sbit SCL = P2^0;  /* 时钟线 */

void IIC_Delay(unsigned char i)
{
    do{_nop_();}
    while(i--);        
}
//总线启动条件
void IIC_Start(void)
{
    SDA = 1;
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SDA = 0;
    IIC_Delay(DELAY_TIME);
    SCL = 0;	
}

//总线停止条件
void IIC_Stop(void)
{
    SDA = 0;
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SDA = 1;
    IIC_Delay(DELAY_TIME);
}

//发送应答
void IIC_SendAck(bit ackbit)
{
    SCL = 0;
    SDA = ackbit;  					// 0:应答,1:非应答
    IIC_Delay(DELAY_TIME);
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SCL = 0; 
    SDA = 1;
    IIC_Delay(DELAY_TIME);
}

//等待应答
bit IIC_WaitAck(void)
{
    bit ackbit;
	
    SCL  = 1;
    IIC_Delay(DELAY_TIME);
    ackbit = SDA;
    SCL = 0;
    IIC_Delay(DELAY_TIME);
    return ackbit;
}

//通过I2C总线发送数据
void IIC_SendByte(unsigned char byt)
{
    unsigned char i;

    for(i=0; i<8; i++)
    {
        SCL  = 0;
        IIC_Delay(DELAY_TIME);
        if(byt & 0x80) SDA  = 1;
        else SDA  = 0;
        IIC_Delay(DELAY_TIME);
        SCL = 1;
        byt <<= 1;
        IIC_Delay(DELAY_TIME);
    }
    SCL  = 0;  
}

//从I2C总线上接收数据
unsigned char IIC_RecByte(void)
{
    unsigned char i, da;
    for(i=0; i<8; i++)
    {   
    	SCL = 1;
	IIC_Delay(DELAY_TIME);
	da <<= 1;
	if(SDA) da |= 1;
	SCL = 0;
	IIC_Delay(DELAY_TIME);
    }
    return da;    
}

void Init_pcf8591(unsigned char channel)
{
	IIC_Start();
	IIC_SendByte(0x90);
	IIC_WaitAck();
	IIC_SendByte(channel);
	IIC_WaitAck();
	IIC_Stop();
}

unsigned char Read_pcf8591()
{
	unsigned char temp;
	IIC_Start();
	IIC_SendByte(0x91);
	IIC_WaitAck();
	temp=IIC_RecByte();
	IIC_SendAck(1);
	IIC_Stop();
	return temp;
}

onewire.c文章来源地址https://www.toymoban.com/news/detail-412937.html

/*
  程序说明: 单总线驱动程序
  软件环境: Keil uVision 4.10 
  硬件环境: CT107单片机综合实训平台(外部晶振12MHz) STC89C52RC单片机
  日    期: 2011-8-9
*/
#include "STC15F2K60S2.h"

sbit DQ = P1^4;  //单总线接口

//单总线延时函数
void Delay_OneWire(unsigned int t)  //STC89C52RC
{
	char i;
	while(t--)
		for(i=0;i<12;i++);
}

//通过单总线向DS18B20写一个字节
void Write_DS18B20(unsigned char dat)
{
	unsigned char i;
	for(i=0;i<8;i++)
	{
		DQ = 0;
		DQ = dat&0x01;
		Delay_OneWire(5);
		DQ = 1;
		dat >>= 1;
	}
	Delay_OneWire(5);
}

//从DS18B20读取一个字节
unsigned char Read_DS18B20(void)
{
	unsigned char i;
	unsigned char dat;
  
	for(i=0;i<8;i++)
	{
		DQ = 0;
		dat >>= 1;
		DQ = 1;
		if(DQ)
		{
			dat |= 0x80;
		}	    
		Delay_OneWire(5);
	}
	return dat;
}

//DS18B20设备初始化
bit init_ds18b20(void)
{
  	bit initflag = 0;
  	
  	DQ = 1;
  	Delay_OneWire(12);
  	DQ = 0;
  	Delay_OneWire(80);
  	DQ = 1;
  	Delay_OneWire(10); 
    initflag = DQ;     
  	Delay_OneWire(5);
  
  	return initflag;
}

unsigned int temp;


float rd_temperature(void)
{
	unsigned char LSB,MSB;
	float tempature;
	init_ds18b20();
	Write_DS18B20(0xCC);
	Write_DS18B20(0x44);
	while(!DQ);
	init_ds18b20();
	Write_DS18B20(0xCC);
	Write_DS18B20(0xBE);
	LSB= Read_DS18B20();
	MSB= Read_DS18B20();
	
	temp=MSB&0x0f;
	temp=temp<<8;
	temp=temp|LSB;
	tempature=temp*0.0625;
	
	return tempature;
}

到了这里,关于第十四届蓝桥杯单片机第二场模拟赛程序的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 第十四届蓝桥杯(电子类)单片机开发——赛题源代码分享

          需要源代码一键三联,私聊我哦

    2024年02月05日
    浏览(62)
  • 蓝桥杯十四届单片机省赛

    【失败的博主】蓝桥杯最后一文 感想 : 练完省赛题就去练国赛题!!! 1.B站小蜜蜂老师(基础模块 )(容易听懂) 2.做一套省赛题、你会发 现无法把模块结合起来。 3.学整体代码的思想(关键!!!) 来源:电子设计工坊、四梯科技、官方源代码、其他人做的题; 4.形成自

    2023年04月10日
    浏览(64)
  • 蓝桥杯十四届单片机国赛试题及代码

        今年十四届单片机国赛试题在程序题设计方面难度有所下降,但选择题没有了以往可以在手册中可以找到的单片机类选择题,选择题难度较高,因此想获得一个不错的成绩,需要在选择题方面有所加强 此次国赛采用了温度传感器DS18B20模块,LED模块,按键模块,Pcf8591DAC模

    2024年02月13日
    浏览(41)
  • 2023年第十四届蓝桥杯单片机开放与设计省赛微析与经验分享

    前言:        2023年4月8日, 就在昨天,本人刚参与了第十四届蓝桥杯单片机开放与设计省赛。         整体做下来,且不谈客观题,今年的程序题,个人感觉有点像大杂烩,题量大,细节多,而且有些要求定义不够清晰,所以本人这次做的不够完美,并且因为时间问题有

    2024年02月08日
    浏览(56)
  • 【第十四届蓝桥杯单片机组客观题1】

    以下客观题来自4T测评的模拟题,希望可以帮助到大家,加油丫 1、C 若希望将IAP15F2K61S2单片机的IO口输出电流能力较强,应将IO配置为( )模式。 IAP15F2K61S2单片机的IO口输出电流能力较强,应将IO配置为推挽输出模式。 2、A 当下列IAP15F2K61S2单片机的中断源同时发出中断请求时

    2023年04月09日
    浏览(40)
  • 蓝桥杯单片机 第十二届 国赛

    蓝桥杯第十二届,模块都比较常规,感觉都和省赛差不多,主要是麻烦在数据处理上,而我们处理的数据又要在界面中显示出来。 对比之前的第十届,其实题目差不多,并且少了串口收发这一比较难的模块。但是多了max,min,avg三个超声波数据的处理。所以按道理时间方面应该

    2023年04月08日
    浏览(51)
  • 蓝桥杯单片机第十三届国赛客观题(深夜学习——单片机)

    1.填空题 (2)不同的地址范围: data:0x00-0xff idata:0x0000-0xffff xdata:0x0000-0xffff pdata:0x00-0xff code:0x0000-0xffff 2.选择题 (3)模电——》多级放大电路 (6)DS18B20 (7)模电——》二极管  (8)单片机      

    2024年02月11日
    浏览(66)
  • 第十二届蓝桥杯单片机省赛

    直接复制粘贴然后运行 然后打开stc烧录到开发板上面就能用 程序哪里不懂的话问我,我闲的蛋疼! #include STC15F2K60S2.H #include intrins.h unsigned char tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0x00,0x10,0xff,0xc6,0x8c,0x88}; unsigned char yi,er,san,si,wu,liu,qi,ba; l

    2023年04月09日
    浏览(59)
  • 蓝桥杯单片机学习14——第十三届省赛题

    上期我们学习了NE555方波发生器频率测量,讲到我会更新之后省赛的题目,那么,他来了。 首先声明:我还没有参加蓝桥杯单片机比赛,也没有拿过奖,所以我写的代码注定不会那么完美,存在BUG是必然的,我写这个系列的目的纯粹是为了记录我的学习………… 关于功能描述

    2024年02月06日
    浏览(56)
  • 蓝桥杯单片机学习15——第十二届省赛题

    书接上文,上期我们基本完成了十三届省赛题,但还是存在一些问题,本期我将对上期存在的一些问题,提出一些解决方案,并加以实践验证可行性,废话少说,让我们往下看。 上期我们提到,数码管和LED在使用的时候会存在外设之间相互干扰的问题,在我们不断的探索之下

    2024年01月25日
    浏览(61)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包