本程序为ds18b20 的多路温度采集程序,是我自己参考其他程序后改写而成,可显示 4 路正负温度值,并有上下限温度报警(声音、灯光报警)亲测,更改端口即可使用。
(主要器件:51单片机,ds18b20,lcd 显示器)附有proteus 仿真图,及序列号采集程序/**** 上限62 度下限-20 度****/#include<>#define uchar unsigned char#define uint unsigned intsbit ds=P1A1;sbit rs=P1A4;sbit e=P1A6;sbit sp=P1A0;sbit d1=P1A2;sbit d2=P1A3;uchar lcdrom[4][8]={{0x28,0x30,0xc5,0xb8,0x00,0x00,0x00,0x8e},{0x28,0x31,0xc5,0xb8,0x00,0x00,0x00,0xb9},{0x28,0x32,0xc5,0xb8,0x00,0x00,0x00,0xe0},{0x28,0x33,0xc5,0xb8,0x00,0x00,0x00,0xd7}}; unsigned char code table0[]={"TEMPERARTURE:U "}; int f[4];int tvalue;float ftvalue;uint warnl=320;uint warnh=992;/****lcd 程序****/void delayms(uint ms)// 延时{uint i,j;for(i=ms;i>0;i--) for(j=110;j>0;j--);}void wrcom(uchar com)// 写指令{ delayms(1); rs=0;P3=com; delayms(1); e=1;delayms(1);e=0;}void wrdat(uchar dat)// 写数据{rs=1;e=0;P3=dat;delayms(5);e=1;delayms(5);e=0;}void lcdinit()// 初始化lcd{delayms(15);wrcom(0x38);delayms(5);wrcom(0x0c);delayms(5);wrcom(0x06);delayms(5);wrcom(0x01);delayms(5); }void display(uchar *p)// 显示{while(*p!='\0')wrdat(*p);p++;delayms(1);}}displayinit()// 初始化显示{lcdinit();wrcom(0x80);display(table0);}/****ds18b20 程序****/ void dsrst()//ds18b20 复位{ uint i;ds=0;i=103;while(i>0)i--;ds=1;i=4;while(i>0)i--;bit dsrd0()// 读一位数据{uint i;}bit dat;ds=0;i++;ds=1;i++;i++;dat=ds; i=8;while(i>0)i--; return(dat); }uchar dsrd()// 读1 个字节数据{uchar i,j,dat; dat=0;for(i=8;i>0;i--){j=dsrd0();dat=(j<<7)|(dat>>1);}return(dat);}void dswr(uchar dat)// 写数据uint i;uchar j;bit testb;for(j=8;j>0;j--){testb=dat&0x01;dat=dat>>1;if(testb){{ds=0; i++;i++;ds=1; i=8;while(i>0)i--; }else{ds=0; i=8;while(i>0)i--;ds=1; i++;i++;}}}void tmstart()// 初始化ds18b20{sp=1;d1=1;d2=1;dsrst();delayms(1);dswr(0xcc); dswr(0x44);}void read_dealtemp()// 读取并处理温度{uchar i,j,t;uchar a,b;for(j=0;j<4;j++){dsrst();delayms(1);dswr(0x55);for(i=0;i<8;i++){dswr(lcdrom[j][i]);//发送64 位序列号dswr(0xbe);a=dsrd();}b=dsrd();tvalue=b;tvalue<<=8; tvalue=tvalue|a;if(tvalue<0){d1=1;tvalue=~tvalue+1; wrcom(0xc0);wrdat(0x2d); if(tvalue>warnl){d2=0;sp=0;}else{d2=1;sp=1;}}else{d2=1; wrcom(0xc0); wrdat(' ');if(tvalue>warnh) {d1=0;sp=0;}else{d1=1;sp=1;}}if(j==0){wrcom(0x8e);wrdat('2');}if(j==1)wrcom(0x8e);wrdat('3');}if(j==2){{wrcom(0x8e);wrdat('4');}if(j==3){wrcom(0x8e);wrdat('5');} ftvalue=tvalue*;tvalue=ftvalue*10+;ftvalue=ftvalue+;f[j]=tvalue;// 温度扩大十倍,精确到一位小数tvalue=f[j];t=tvalue/1000;wrcom(0x80+0x41);wrdat(table1[t]);// 显示百位t=tvalue%1000/100; wrdat(table1[t]);// 显示十位t=tvalue%100/10;wrdat(table1[t]);// 显示个位显示小数点儿wrdat(0x2e); //t=tvalue%10/1;显示小数位wrdat(table1[t]);//delayms(5000);}}/**** 主函数****/void main(){d1=1;d2=1;sp=1;displayinit();// 初始化显示while(1){tmstart();// 初始化read_dealtemp();// 读取温度}}/**** 序列号读取程序****/#include <>#define uchar unsigned char#define uint unsigned intsbit DQ = P1A1; // 温度传感器信号线sbit rs = P1A4; //LCD 数据/命令选择端(H/L) 位声明sbit lcden = P1A6; //LCD 使能信号端位声明void delay(uint z);//延时函数void DS18B20_Reset(void); //DQ18B20复位,初始化函数bit DS18B20_Readbit(void);//读 1 位数据函数uchar DS18B20_ReadByte(void);//读 1 个字节数据函数void DS18B20_WriteByte(uchar dat);// 向DQ18B20写一个字节数据函数void LCD_WriteCom(uchar com); //1602 液晶命令写入函数void LCD_WriteData(uchar dat); //1602 液晶数据写入函数void LCD_Init(); //LCD 初始化函数数void Display18B20Rom(char Rom); // 显示18B20 序列号函/********************************************/* 主函数*//********************************************void main(){ uchar a,b,c,d,e,f,g,h;LCD_Init();DS18B20_Reset();delay(1);DS18B20_WriteByte(0x33);delay(1);a = DS18B20_ReadByte();b = DS18B20_ReadByte();c = DS18B20_ReadByte();d = DS18B20_ReadByte();e = DS18B20_ReadByte();f = DS18B20_ReadByte();g = DS18B20_ReadByte();h = DS18B20_ReadByte(); LCD_WriteCom(0x80+0x40);Display18B20Rom(h);Display18B20Rom(g);Display18B20Rom(f);Display18B20Rom(e);Display18B20Rom(d);Display18B20Rom(c);Display18B20Rom(b);Display18B20Rom(a);while(1);}/************************************************* /* 延时函数:void delay()*//* 功能:延时函数*/ /************************************************* void delay(uint z)// 延时函数{uint x,y;for( x = z; x > 0; x-- )for( y = 110; y > 0; y-- );}***********************************************/* DS18B20 函数:void DS18B20_Reset() *//* 功能:复位18B20*/ /***************************************************/ void DS18B20_Reset(void)//DQ18B20 复位,初始化函数uint i;DQ = 0;i = 103;while( i > 0 ) i--;DQ = 1;i = 4;while( i > 0 ) i--;/***************************************************//* DS18B20 函数:void DS18B20_Readbit() *//* 功能:读1 个字节数据函数*//***************************************************/ bitDS18B20_Readbit(void) //读 1 位数据函数{uint i; bit dat; DQ = 0;i++; //i++ 起延时作用 DQ = 1; i++; i++; dat = DQ; i = 8;while( i > 0 )i--; return( dat );}/***************************************************/ /* DS18B20 函数:void DS18B20_ReadByte()*/ /* 功能:读 1 个字节数据函数*/uchar DS18B20_ReadByte(void) //{uchar i,j,dat; dat = 0;for( i = 1; i <= 8; i++ )***********************************************读 1 个字节数据函数j = DS18B20_Readbit(); dat = ( j << 7 ) | ( dat >> 1 ); } return(dat);}/***************************************************/ /* DS18B20 函数:void DS18B20_WriteByte()*/ /* 功能:向DQ18B20写一个字节数据函数*/void DS18B20_WriteByte(uchar dat) // 字节数据函数{uint i; uchar j; bit testb;for( j=1; j<=8; j++) {testb = dat&0x01; dat= dat>>1;if(testb) //写 1***********************************************向 DQ18B20写一个{DQ = 0;i++;i++;DQ = 1;i = 8;while(i>0)i--;}else{DQ = 0; // 写0 i = 8;while(i>0)i--;DQ = 1;i++;i++;}}}/***********************************************//* LCD 函数:void LCD_WriteCom()*//* 功能:向LCD写入命令*/ void LCD_WriteCom(uchar com)*******************************************{rs = 0;P3= com; delay(5);lcden = 0; delay(5);lcden = 1; delay(5);lcden = 0;}/***********************************************//* LCD 函数:void LCD_WriteData(uchar dat) *//* 功能:向LCD写入数据*/ /*********************************************void LCD_WriteData(uchar dat){rs = 1; //择LCD为写入数据状态lcden = 0;P3= dat; // 到总线上将待写入数据放delay(5);lcden = 1; 能端一个脉冲delay(5); // 前放到总线上 lcden = 0; //入 LCDdelay(5);}/***********************************************//* LCD 函数:void LCD_I nit() *//* 功能:初始化LCD 设定LCD 的初始状态 *///给LCD 使******************************************* void LCD_Init(){信号将之的数据写LCD_WriteCom(0x38); //LCDdelay(15);LCD_WriteCom(0x08); delay(3);LCD_WriteCom(0x01); delay(3);// //LCD显示模式设关闭LCD 显示显示清屏针为自动加 1delay(3);LCD_WriteCom(0x0c); // 但不显示光标*/ /* 显示 18B20 序列号*/ /* */void Display18B20Rom(char Rom){uchar h,l;l = Rom & 0x0f; // 取低 4 位 h = Rom & 0xf0; // 取高 4 位 h >>= 4; if( ( h >= 0x00 )&&( h <= 0x09 ) )LCD_WriteData(h+0x30);ASCII 码****************************************** LCD_WriteCom(0x06);//设定光标地址指打开LCD 显示,****************************************** //}/*elseLCD_WriteData(h+0x37); // 取ASCII 码if( ( l >= 0x00 )&&( l <= 0x09 ) )取LCD_WriteData(l+0x30); //ASCII 码elseLCD_WriteData(l+0x37); // 取ASCII 码}。