|
最近在做單片機(jī)課設(shè) ds18b20多路溫度計(jì)老師要求我們不要用單總線的方法
代碼貼出來如下:
#include<reg52.h>
#include<intrins.h>
#define bool int
#define true 1
#define false 0
#define uchar unsigned char
#define uint unsigned int
bool flag=true;
uchar code table[]={0xc0,0xf9,//共陽數(shù)碼管普通編碼表
0xa4,0xb0,0x99,
0x92,0x82,0xf8,
0x80,0x90};
uchar code table_1[]={0x40,0x79,//共陽數(shù)碼管帶小數(shù)編碼表
0x24,0x30,0x19,
0x12,0x02,0x78,
0x00,0x10
};
sbit reset=P2^4; //定義復(fù)位鍵 按下復(fù)位鍵之后才可以按其余三個(gè)鍵來選擇溫度
sbit key1=P2^5; //定義三個(gè)獨(dú)立按鍵來選擇用哪一個(gè)ds18b20
sbit key2=P2^6;
sbit key3=P2^7;
sbit DQ1=P1^0; //位定義三個(gè)io口接ds18b20
sbit DQ2=P1^1;
sbit DQ3=P1^2;
/*************數(shù)碼管顯示延時(shí)程序*********************/
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}
/*****************ds18b20精確延時(shí)程序***********/
/******************延時(shí)20us********************/
void time20(void)
{
unsigned char a,b;
for(b=1;b>0;b--)
for(a=16;a>0;a--);
}
/******************延時(shí)60us********************/
void time60(void)
{
unsigned char a,b;
for(b=1;b>0;b--)
for(a=48;a>0;a--);
}
/****************延時(shí)500us********************/
void time500(void)
{
unsigned char a,b,c;
for(c=1;c>0;c--)
for(b=142;b>0;b--)
for(a=2;a>0;a--);
}
/*************初始化程序*********************/
void Init_DS18B20_1()
{
DQ1= 1;
time20();
DQ1= 0;
time500();
DQ1= 1;
time60();
}
/************** DS18B20讀函數(shù),每次讀16位,可以讀出溫度寄存器的數(shù)值********************/
uchar read_1(void)
{
int i=0;
uchar u=0;
for (i=0;i<16;i++)
{
DQ1=0;
u>>=1;
DQ1=1;
if(DQ1) u|=0x8000;
time20();
}
return (u);
}
/*******************DS18B20寫函數(shù),寫指令給芯片,每次寫八位*************/
void write_1(unsigned char ku)
{
int i=0;
for (i=0;i<8;i++)
{
DQ1=0;
DQ1=ku&0x01;
delay(3);
DQ1=1;
ku>>=1;
}
}
/*******************讀取顯示函數(shù) 返回的是16位的溫度數(shù)據(jù)讀取并顯示到數(shù)碼管上***************************/
void Read_and_display_Temperature_1()
{
int num=0;
int aa,bb,cc,dd;
float tm=0;
uchar tp;
write_1(0xcc);//跳過序列號(hào) (0xcc)
write_1(0x44);//啟動(dòng)溫度轉(zhuǎn)換 (0x44)
Init_DS18B20_1();//初始化ds18b20
write_1(0xcc);//跳過序列號(hào)(0xcc)
write_1(0xbe);//開始讀取溫度寄存器(指令0xbe)
tp=read_1();//調(diào)用函數(shù)讀取溫度寄存器
delay(60);
if((tp&0xf800)==0xf800)//判斷正負(fù)數(shù) if成立為負(fù)數(shù)
{
tp=~tp+1;//將tp取反再+1
tm=tp*0.0625;//得到無符號(hào)的真實(shí)溫度值
num=(uint)(tm*10);//將得到的溫度乘以10 以便得到小數(shù)后一位的數(shù)據(jù)
aa=num/1000;//得到溫度百位
bb=num%1000/100; //得到溫度十位
cc=num%1000%100/10; //得到溫度個(gè)位
dd=num%1000%100%10; //得到溫度小數(shù)后一位
while(flag)
{
/*位選 將第一個(gè)數(shù)碼管點(diǎn)亮*/
P2=0Xfe;
/*段選 使第一個(gè)數(shù)碼管顯示負(fù)號(hào)*/
P0=0xbf;
/*延時(shí)*/
delay(6);
P2=0xfd;
P0=table[bb];
delay(6);
P2=0xfb;
P0=table_1[cc];
delay(6);
P2=0xf7;
P0=table[dd];
if (reset==0)
{
delay(6);
if(reset==0){flag = false;} //退出溫度顯示死循環(huán)
}
}
flag=true;//將標(biāo)志位復(fù)原
}
else
{
tm=tp*0.0625;//得到無符號(hào)的真實(shí)溫度值
num=(uint)(tm*10);//將得到的溫度乘以10 以便得到小數(shù)后一位的數(shù)據(jù)
aa=num/1000;//得到溫度百位
bb=num%1000/100; //得到溫度十位
cc=num%1000%100/10; //得到溫度個(gè)位
dd=num%1000%100%10; //得到溫度小數(shù)后一位
while(flag)
{
/*位選 將第一個(gè)數(shù)碼管點(diǎn)亮*/
P2=0xfe;
/*段選 */
P0=table[aa];
/*延時(shí)*/
delay(6);
P2=0xfd;
P0=table[bb];
delay(6);
P2=0xfb;
P0=table_1[cc];
delay(6);
P2=0xf7;
P0=table[dd];
if (reset==0)
{
delay(6);
if(reset==0){flag = false;} //退出溫度顯示死循環(huán)
}
}
flag=true;//將標(biāo)志位復(fù)原
}
}
void main()
{
while(1)
{
if(key1==0) //第一個(gè)按鍵按下選擇第一個(gè)ds18b20
{
delay(5);
if(key1==0)//防抖動(dòng)
{
Read_and_display_Temperature_1();
}
}
}
代碼編譯沒錯(cuò)
仿真和下載到單片機(jī)中都沒效果
還有就是新手寫的程序太復(fù)雜
最想問的是有三個(gè)ds18b20 難道我得把程序?qū)懭閱?/font>
請論壇的大神幫幫我這個(gè)新手
|
|