亚洲春色中文字幕久久久-三上亚,一吻二脱三床四吻胸,国产真实伦对白视频全集,在线毛片观看,精品成品入口黄网,国产毛aⅴ片久久久,亚洲AV色香蕉一区二区三区老师,萧皇后A级艳片,色情日本视频更新,99久久亚洲精品日本无码
標題:
簡單51單片機多點18b20溫度測量系統源碼
[打印本頁]
作者:
51greenhand
時間:
2018-1-28 18:21
標題:
簡單51單片機多點18b20溫度測量系統源碼
分享我的期末作業,基于51單片機的多點溫度測量
同時多點溫度測量是在單總線上掛載多個18b20溫度傳感器
單片機源程序如下:
#include <reg51.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
#define MAXNUM 4 //宏定義單總線上最大可掃描DS18B20個數
//*****************************//
//**初始定義管腳、變量與數組***//
//*****************************//
sbit DS=P3^7;
sbit lcden=P2^7;//液晶使能端
sbit lcdrs=P2^6;//液晶數0據命令選擇端
sbit lcdrw=P2^5;
union{
uchar c[2];
uint x;
}temp;
uchar time=0;
uint cc,xs; //變量cc中保存計算出的溫度值的整數部分,xs保存計算出的溫度值的小數部分的第一位
uchar idata disbuffer[6]; //LCD顯示緩存數組
uchar idata ID[4][8]={0};//{{0x28,0xff,0x80,0x2e,0x70,0x16,0x03,0xad},{0x28,0xff,0x95,0xb5,0x81,0x16,0x03,0x50},{0x28,0xff,0x02,0x96,0xa1,0x16,0x04,0x59},{0x28,0xff,0xf0,0xf5,0x62,0x16,0x04,0xd3}};
//{"82FF08E2076130DA","82FF595B18613005","82FF20691A614095","82FF0F5F2661403D"}; //用于記錄各DS18B20的ROM序列號
uchar idata RomID_temp[8]; //匹配DS18B20時臨時記錄要匹配DS18B20的序列號
uchar east[5]=" EAST";
uchar west[5]=" WEST";
uchar south[5]="SOUTH";
uchar north[5]="NORTH";
uchar m=0;
uchar num=0;
//***************************//
//*******18b20時序延時*******//
//***************************//
void delay(uint i) //i*9.62us
{
uint j;
for(j=i;j>0;j--);
}
void delay_ms(uchar i) //(j*2+1+2)*i+5
{ uchar j; //12MHz 0.5*i ms
do{j=248;
do{j--;}while(j);
i--;
}while(i);
}
void delay_2us(uchar i) // 2*i+5 us
{
while(--i);
}
//**************************//
//******18b20子程***********//
//**************************//
uchar DS_init(void) //18B20復位,初始化函數
{
uchar presence;
DS=0; delay_2us(250); //根據DS18B20的復位時序.先把總線拉低555us
DS=1; delay_2us(30); //再釋放總線,65us后讀取DS18B20發出的信號
presence=DS; delay_2us(250); //如果復位成功,則presence的值為0;否則為1
return (presence); //返回0則初始化成功,否則失敗
}
uchar read_byte(void) //讀1字節
{
uchar i,j,dat=0;
for(i=1;i<=8;i++) //作8個循環,讀出的8位組成一個字節
{DS=0; _nop_(); //先將總線拉低1us,
DS=1; delay_2us(2); //再釋放總線,產生讀起始信號,延遲9us后讀取總線上的DS18B20發出的值
j=DS; delay_2us(30); //一位讀完后,延遲65us后讀下一位
dat=(j<<7)|(dat>>1); //讀出的數據最低位在一個字節的最低位,這樣剛好一個字節在DAT里
}
return(dat);
}
uchar read_2bit(void) //讀2位
{
uchar i=0,j=0;
DS=0; _nop_(); //先將總線拉低1us,
DS=1; delay_2us(2); //再釋放總線,產生讀起始信號,延遲9us后讀取總線上的DS18B20發出的值
j=DS; delay_2us(30); //一位讀完后,延遲65us后讀下一位
DS=0; _nop_();
DS=1; delay_2us(2);
i=DS; delay_2us(30);
i=j*2+i; //將讀出的兩位放到變量i中,其中第一個讀出的位處于i的第1位;而第二個讀出的位處于i的第0位
return(i);
}
void write_byte(uchar dat) //寫1字節
{
uchar i;
for(i=0;i<8;i++) //作8個循環,寫入的8位組成一個字節
{DS=0; //先將總線拉低
DS = dat&0x01; //向總線上放入要寫的值
delay_2us(50); //延遲105us,以使DS18B20能采樣到要寫入的值
DS = 1; //釋放總線,準備寫入下一位
dat>>=1; //將要寫的下一位移到dat的最低位
}
}
void write_bit(bit dat) //寫1位
{
DS=0; //先將總線拉低
DS=dat; //向總線上放入要寫的值
delay_2us(50); //延遲105us,以使DS18B20能采樣到要寫入的值
DS = 1; //釋放總線
}
//************************//
//*******1602延時*********//
//************************//
void delay1(uint z)
{
uint i,j;
for(i=z;i>0;i--)
for(j=110;j>0;j--);
}
//************************//
//******1602子程**********//
//************************//
void write_com(uchar com) //寫命令
{
lcdrs=0;//選擇寫命令模式
P0=com;//將要寫的命令字送到數據總線上
delay1(5);//稍作延時以待數據穩定
lcden=1;//使能端給一高電平脈沖,因為初始化函數中已將lcden置零
delay1(5);//稍作延時
lcden=0;//將使能端置零完成高脈沖
}
void write_data(uchar date) //寫數據
{
lcdrs=1;//選擇寫數據操作
P0=date;//將要寫的數據送到數據總線上
delay1(5);//稍作延時
lcden=1;//使能端給一高電平脈沖
delay1(5);
lcden=0;
}
void init() //1602初始化
{
lcdrw=0;
lcden=0;
write_com(0x38);//設置16*2顯示,5*7點陣,8位數據接口
write_com(0x0c);//設置開顯示,不顯示光標
write_com(0x06);//寫一個字節后地址指針加1
write_com(0x01);//顯示清零,數據指針清零
write_com(0x80);//設置數據指針起點
}
//****************************//
//***讀取18b20溫度數據子程 ***//
//****************************//
void Read_Temperature_rom(void) //讀取溫度函數
{ uchar i;
DS_init();
write_byte(0x55); //匹配ROM
for(i=0;i<8;i++) //發出64位ROM編碼
write_byte(RomID_temp[i]);
write_byte(0x44); //開始轉換溫度
DS_init();
write_byte(0x55); //匹配ROM
for(i=0;i<8;i++) //發出64位ROM編碼
write_byte(RomID_temp[i]);
write_byte(0xBE); //發讀溫度命令
temp.c[1]=read_byte(); //讀低字節,之所以c[1]中放低字節,是因為C51采用的是大端格式
temp.c[0]=read_byte(); //讀高字節,之所以c[0]中放低字節,是因為C51采用的是大端格式
//共用體定義
}
void Temperature_cov(void) //溫度轉化
{
cc=temp.x/16; //計算出溫度值的整數部分,這個語句相當于數值乘0.0625再取整數部分
xs=temp.x&0x0f; //取溫度值小數部分的第一位
xs=xs*10; //這兩條語句相當于乘0.625,得小數位的第一位,注意不是乘0.0625
xs=xs/16;
}
//***********************//
//******顯示子程*********//
//***********************//
void display_m(void) //顯示18b20個數或方向
{
uchar i;
write_com(0x8B);
//write_data('0'+m);
if(m==0)
for(i=0;i<5;i++)
{write_data(east[i]);}
if(m==1)
for(i=0;i<5;i++)
{write_data(west[i]);}
if(m==2)
for(i=0;i<5;i++)
{write_data(south[i]);}
if(m==3)
for(i=0;i<5;i++)
{write_data(north[i]);}
}
void display_ROMID(void) //顯示序列號
{
uchar tmp[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,
0x37,0x38,0x39,0x41,0x42,0x43,0x44,0x45,0x46};
uchar k,i;
uchar disbuffer_rom[16];
disbuffer_rom[0]=(ID[m][k]&0x0F);
disbuffer_rom[1]=((ID[m][k]&0xF0)>>4);
disbuffer_rom[2]=(ID[m][k+1]&0x0F);
disbuffer_rom[3]=((ID[m][k+1]&0xF0)>>4);
disbuffer_rom[4]=(ID[m][k+2]&0x0F);
disbuffer_rom[5]=((ID[m][k+2]&0xF0)>>4);
disbuffer_rom[6]=(ID[m][k+3]&0x0F);
disbuffer_rom[7]=((ID[m][k+3]&0xF0)>>4);
disbuffer_rom[8]=(ID[m][k+4]&0x0F);
disbuffer_rom[9]=((ID[m][k+4]&0xF0)>>4);
disbuffer_rom[10]=(ID[m][k+5]&0x0F);
disbuffer_rom[11]=((ID[m][k+5]&0xF0)>>4);
disbuffer_rom[12]=(ID[m][k+6]&0x0F);
disbuffer_rom[13]=((ID[m][k+6]&0xF0)>>4);
disbuffer_rom[14]=(ID[m][k+7]&0x0F);
disbuffer_rom[15]=((ID[m][k+7]&0xF0)>>4);
write_com(0x80+0x40);
for(i=0;i<16;i++)
{
write_data(tmp[disbuffer_rom[i]]); //1602寫入序列號
}
}
void display(void) //溫度顯示
{
disbuffer[0]='+';
disbuffer[1]=cc/10;
disbuffer[2]=cc%10;
disbuffer[3]='.';
disbuffer[4]=xs;
disbuffer[5]='C';
write_com(0x80);
write_data(disbuffer[0]);
write_com(0x81);
write_data('0'+disbuffer[1]);
write_com(0x82);
write_data('0'+disbuffer[2]);
write_com(0x83);
write_data(disbuffer[3]);
write_com(0x84);
write_data('0'+disbuffer[4]);
write_com(0x85);
write_data(disbuffer[5]);
}
void diplay_final(void) //顯示所用到的18b20的實時溫度
{ uint q;
for(q=0;q<8;q++)
{
RomID_temp[q]=ID[m][q]; //給序列號,等待匹配
}
Read_Temperature_rom(); //讀取溫度
Temperature_cov(); //溫度轉換
display(); //顯示溫度
}
//****************************//
//*****多點18b20搜索子程******//
//****************************//
void search_rom(void) //遍歷搜索單線上所連的所有18b20的序列號
{
uchar k,l=0,chongtuwei,m,n,a;
uchar _00web[MAXNUM]={0};
do
{
DS_init(); //復位單總線上的所有DS18B20
write_byte(0xf0); //單片機發布搜索命令
for(m=0;m<8;m++)
{
uchar s=0; //s用來記錄本次循環得到的1個字節(8位)序列號
for(n=0;n<8;n++)
{
k=read_2bit(); //讀第m*8+n位的原碼和反碼,保存在k中
k=k&0x03; //屏蔽掉k中其它位的干擾,為下一步判斷作準備
s>>=1; //s右移一位,即把上一次循環得到的位值右移一位,
//這樣執行完一次n為變量的循環,便可得到一個字節的ROM號
if(k==0x01) //k為01,表明讀到的數據為0,即所有器件在這一位都為0,所以向總線上寫0
//同時對s的值不進行操作,即這位的序列號記為0
{
write_bit (0);
}
else if(k==0x02)//k為02,表明讀到的數據為1,即所有器件在這一位都為1,所以向總線上寫1
{
s=s|0x80; //記錄下此位的值,即s的最高位置1
write_bit (1);
}
else if(k==0x00)
{
chongtuwei=m*8+n+1; //記錄下這個沖突位發生的位置;之所以加1是為了讓_00web數組中的第一位保持0不變,
//便于判斷搜索循環是否結束;
if(chongtuwei>_00web[l])//如果沖突位比標志00位的位高,即發現了新的沖突位,那么這位寫0
{
write_bit (0);
_00web[++l]=chongtuwei; //依次記錄位比沖突標志位高的沖突位在_00web數組中
}
else if(chongtuwei<_00web[l]) //如果沖突位比標志00位的位低,那么把ID中這位所在的字節右移n位,
{ //從而得到這位先前已經寫過的值,如果為0,說明這位先前寫的是0,那么繼續寫0,
// 如果這位先前寫的是1,那么繼續寫1
a=(ID[num-1][m]>>n)&0x01;
s=s|(a<<7); //記錄下此位的值
write_bit(a);
}
else if(chongtuwei==_00web[l])//如果沖突位就是標志00位,那么s的最高位置1,即這位記為1,同時向總線上寫1;
//之所以不寫0,是因為前面已經寫過0,再寫0,就得不到遍歷的效果.
{
s=s|0x80;
write_bit (1);
l=l-1; //改變標志00位的位置,即向前推一個00位,并且是往低位方向推
}
}
}
ID[num][m]=s;
}
num++; //DS18B20的個數加1
}while((_00web[l]!=0)&&(num<MAXNUM));//如果沖突位記錄數組已經前推到0值或是DS18B20的數目已經超過最大允許數目,
//就退出循環
}
//************************//
//*********主程序*********//
//************************//
void main()
{
delay(10);
search_rom();
TMOD = 0x01; //選擇工作方式1
TH0 = 0x3C; //設置初始值,定時50MS
TL0 = 0xB0;
EA = 1; //打開總中斷
ET0 = 1; //打開定時器0中斷
TR0 = 1; //啟動定時器0
init();
while(1)
{
display_ROMID(); //顯示序列號
display_m(); //顯示18b20個數
diplay_final(); //顯示溫度
…………限于本文篇幅 余下代碼請從51黑下載附件…………
復制代碼
完整代碼下載:
多點溫度測量.zip
(53.69 KB, 下載次數: 76)
2018-1-28 18:16 上傳
點擊文件名下載附件
下載積分: 黑幣 -5
作者:
zhangwb055
時間:
2018-12-4 16:07
請問有protues仿真圖么
作者:
竇可以
時間:
2018-12-6 15:44
沒有頭文件代碼嗎,運行不了啊
作者:
flyzhangyong
時間:
2019-12-10 16:36
不錯我覺得可以
作者:
flyzhangyong
時間:
2019-12-10 16:37
zhangwb055 發表于 2018-12-4 16:07
請問有protues仿真圖么
沒得,自己畫
作者:
iloveyou51
時間:
2020-2-14 15:10
溫度是錯的,老是85
作者:
2871436069gy
時間:
2020-2-19 15:04
不錯,很有幫助
歡迎光臨 (http://www.denmoz.com/bbs/)
Powered by Discuz! X3.1