发布网友 发布时间:2022-04-22 18:24
共1个回答
热心网友 时间:2023-11-15 06:34
/* 题目:温度采集系统设计
时间:2010年5月14日
作者:杨国宏*/
#include <REGX51.H>
#include<stdio.h>
#define uchar unsigned char
#define uint unsigned int
sbit ds=P3^5; //温度传感器信号线
sbit beep=P3^4; //蜂鸣器引脚
uint temp;
float f_temp ;
uint warn_l1=270;//温度值乘以10的结果
uint warn_l2=250;
uint warn_h1=300;
uint warn_h2=320;
sbit seg1=P2^4;/*数码管一控制*/
sbit seg2=P2^5;
sbit seg3=P2^6;
sbit seg4=P2^7;
sbit led0=P1^0;/*指示灯用于报警控制*/
sbit led1=P1^1;
sbit led2=P1^2;
sbit led3=P1^3;
unsigned char table[]={
0xC0, 0xF9, 0xA4, 0xB0, 0x99,
0x92, 0x82, 0xF8, 0x80, 0x90, //共阳极数码管0到9编码不带小数点
0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0x00,0x10 //共阳极数码管0到9编码带小数点
};
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}
void dsreset()//复位函数(温度传感器)初始化
{
uint i;
ds=0;
i=103;
while(i>0)i--;
ds=1;
i=4;
while(i>0)i--;
}
bit tempreadbit() //读一位数据函数
{
uint i;
bit dat;
ds=0;
i++;
ds=1;
i++;i++; //i++起延时作用
dat=ds;
i=8;
while(i>0)i--;
return(dat);
}
uchar tempread()//读一个字节函数
{
uchar i,j,dat;
dat=0;
for(i=1;i<=8;i++)
{
j=tempreadbit();
dat=(j<<7)|(dat>>1); // 读出的数据最低位在最前面,这样刚好一个字节在DAT里
}
return(dat);
}
void tempwritebyte(uchar dat) //向DS18B20写一个字节数据
{
uint i;
uchar j;
bit testb;
for(j=1;j<=8;j++)
{
testb=dat&0x01;
dat=dat>>1;
if(testb) //写1
{
ds=0;
i++;i++;
ds=1;
i=8;while(i>0)i--;
}
else //写0
{
ds=0;
i=8;while(i>0)i--;
ds=1;
i++;i++;
}
}
}
void tempchange()//获取温度并转换
{
dsreset();
delay(1);
tempwritebyte(0xcc);//写跳过读ROM指令
tempwritebyte(0x44); //写温度转换指令
}
uint get_temp()
{
uchar a,b;
dsreset();
delay(1);
tempwritebyte(0xcc);
tempwritebyte(0xbe);
a=tempread(); // 读低八位;
b=tempread();// 读高八位;
temp=b;
temp<<=8;// 两个字节组合为一个字
temp=temp|a;
f_temp=temp*0.0625;//温度在寄存器中为12位,分辨率为0.0625度
temp=f_temp*10+0.5;//乘以10表示小数点后面只取1位,加0.5是四舍五入
f_temp=f_temp+0.05;//
return temp; //temp是整型
}
void dis_temp(uint t)
{
uchar shuge,shushi,shu;
shu=t/100;//温度数值的十位
shushi=t%100/10; //温度显示的个位
shuge=t%100%10; //温度显示的小数点后一位
seg3=0;
P0=table[shu];
delay(5);
seg3=1;
seg2=0;
P0=table[shushi+10]; //带小数点显示
delay(10);
seg2=1;
seg1=0;
P0=table[shuge];
delay(5);
seg1=1;
}
void warn (uint s,uchar led)//蜂鸣器报警,灯闪烁
{
uchar i;i=s; //S控制音调,LED控制灯
beep=0;
P1=~(led); //控制相应的灯亮
while(i--);
{
dis_temp(get_temp()); //温度函数起延时作用
}
beep=1;//蜂鸣器不响
P1=0xff; //控制相应的灯
i=s;
while(i--);
{
dis_temp(get_temp());//温度函数起延时作用
}
}
void deal(uint t)
{
uchar i;
if((t>warn_l2)&&(t<=warn_l1))//温度处理函数
{
warn(40,0x01); //温度大于25度,小于27度,第一个灯亮,蜂鸣器发出“滴”声
}
else if(t<warn_l2)
{ //温度小于25度
warn(40,0x03); //第一个和第二个灯亮,蜂鸣器发出“滴”声
}
else if(t<warn_h2&&(t>warn_h1)) //温度小于32度而大于30度
{
warn(40,0x04); //第三个灯亮,蜂鸣器发出“滴”声
}
else if(t>warn_h2) //温度大于32度
{
warn(10,0x0c); //第三个灯亮,蜂鸣器发出“滴”声
}
else
{
i=40; //在27到30度之间只是调用显示函数延时
while(i--)
{
dis_temp(get_temp());
}
}
}
void init_com()
{
TMOD=0x20; //串口初始化函数
PCON=0x00;
SCON=0x50;
TH1=0xfd;// 波特率9600
TL1=0xfd;
TR1=1;
}
void comm(char*parr) //串口数据发送
{
do
{
SBUF=*parr++; //发送数据
while(!TI); //等待发送完成标志为1
TI=0; //标志清零
}
while(*parr); //保持循环直到字符为'\0'
}
void main()//主函数
{ //电子表部分
uchar buff[4],i;
init_com();
//温度部分
while(1)
{
tempchange(); //温度转换函数
for(i=10;i>0;i--)
{
dis_temp(get_temp());//获取温度并显示
}
deal(temp); //进行温度处理
sprintf(buff,"%f",f_temp);//浮点型温度格式化为字符型
for(i=10;i>10;i--)
{
dis_temp(get_temp());//温度显示
}
comm(buff); //串口发送数据
for(i=10;i>10;i--)
{
dis_temp(get_temp()); //温度显示
}
}
}
这个你自己修改下好了 我这个是成功的例子,有问题可以详细看完我的注释