#include<reg52.h> #include<intrins.h> #define uchar unsigned char #define uint unsigned int sbit DQ=P3^7; sbit beep=P3^0; void reset(); //DS18B20复位函数 void write_byte(uchar val); //DS18B20写命令函数 uchar read_byte(void); //DS18B20读1字节函数 void read_temp(); //温度读取函数 void LED_display(); void alarm(); uchar tempH,tempL,num; uchar table[10]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90}; //0~9的LED字符编码 uchar setValue_low=15; //设置温度下限 uchar setValue_high=30; //设置温度上限 main() { while(1) { read_temp(); LED_display(); alarm(); } } void delay(uint t) { for(;t>0;t--); } void reset() //DS18B20的复位 { uchar presence=1; while(presence) { while(presence) { DQ=1;_nop_();_nop_(); DQ=0; delay(50); DQ=1; delay(6); presence=DQ; } delay(45); presence=~DQ; } DQ=1; } void write_byte(uchar val) //DS18B20写一个字节 { uchar i; for(i=8;i>0;i--) { DQ=1;_nop_();_nop_(); DQ=0;_nop_();_nop_();_nop_();_nop_();_nop_(); DQ=val&0x01; delay(6); val=val>>1; } DQ=1; _nop_(); } uchar read_byte(void) //DS18B20读一个字节 { uchar i; uchar value=0; for(i=8;i>0;i--) { DQ=1;_nop_();_nop_(); value>>=1; DQ=0; _nop_();_nop_();_nop_();_nop_(); DQ=1;_nop_();_nop_();_nop_();_nop_(); if(DQ) value|=0x80; delay(6); } DQ=1; return(value); } void read_temp() //从DS18B20读取温度值 { uchar ch1,ch2; reset(); write_byte(0xcc); write_byte(0x44); reset(); write_byte(0xcc); write_byte(0xbe); ch1=read_byte(); //DS18B20的温度数值是16位的二进制,精度高,最后四位是温度的小数部分,最高五位为符号位(即正负温度) ch2=read_byte(); num=(ch2<<4)|(ch1>>4); //只取温度值的中间八位,小数部分舍去,符号位舍去四位。 tempH=num/10; //温度的十位 tempL=num-tempH*10; //温度的个位 } void LED_display() //显示检测的温度 { P2=0x0; P2=2; P0=table[tempL]; delay(50); P2=0x0; P2=1; P0=table[tempH]; delay(50); P2=0x0; } void alarm() //报警 { if(setValue_low<=num &&setValue_high>=num) beep=1; //在温度允许范围,不报警 else beep=~beep; }
|