DS18B20 学习笔记
记忆主线:“一根线聊天(DQ)→ 先让它测(44)→ 再去仓库拿结果(BE)→ 两个字节拼起来 /16”
1. 模块与引脚:把它当成“会说话的温度计”
DS18B20模块
-
DQ:嘴巴(数据线)——所有命令、数据都从这里进出
-
VCC/GND:吃饭和站稳(供电/地)
2. 寄存器:把 DS18B20 当成“带小仓库的温度计”
2.1 高速暂存器(Scratchpad)= “快递柜”
高速暂存器
-
温度转换后,结果会先放进 快递柜(Scratchpad)
-
读温度就是去快递柜取包裹:前两个字节最关键
2.2 温度寄存器 = “包裹内容(原始温度值)”
温度寄存器
-
温度是 16 位:
high(高 8 位)+low(低 8 位) -
常用默认:温度 = 原始值 / 16.0
记法:“右边 4 位是小数” → 所以除以 16
3. 工作流程:背一条线就够了(最重要)
DS18B20工作步骤
口诀(强烈建议直接背)
“叫醒它(复位)→ 免点名(CC)→ 让它去测(44)→ 再叫醒(复位)→ 免点名(CC)→ 去柜子取(BE)”
命令对照(像暗号):
-
0xCC:Skip ROM(免点名:只有一只设备时直接用) -
0x44:Convert T(开始测温) -
0xBE:Read Scratchpad(读快递柜)
4. 代码(不改内容,只加“记忆注释”)
4.1 延时:单总线的“节拍器”
//单总线延时函数
void Delay_OneWire(unsigned int t)//STC89C52RC
{
t*=12;
while(t--);
}
4.2 初始化:先“敲门”,看里面有没有人(应答)
//DS18B20设备初始化
bit init_ds18b20(void)
{
bit initflag=0;
DQ=1;
Delay_OneWire(12);
DQ=0; // 主机拉低:复位/敲门
Delay_OneWire(80);
DQ=1; // 释放:等从机应答
Delay_OneWire(10);
initflag=DQ; // 读应答:判断有没有 DS18B20
Delay_OneWire(5);
}
4.3 写字节:像“从最低位开始一颗一颗喂糖”(LSB first)
//通过单总线向DS18B20写一个字节
void Write_DS18B20(unsigned char dat)
{
unsigned char i;
for(i=0;i<8;i++)
{
DQ=0; // 开始写时隙
DQ=dat&0x01; // 先发最低位(LSB first)
Delay_OneWire(5);
DQ=1; // 释放总线
dat>>=1; // 准备下一位
}
Delay_OneWire(5);
}
4.4 读字节:像“每次抬头看一眼灯亮不亮”,拼成 8 位
//从DS18B20读取一个字节
unsigned char Read_DS18B20(void)
{
unsigned char i;
unsigned char dat;
for(i=0;i<8;i++)
{
DQ=0; // 读时隙开始
dat>>=1; // 给新读到的位腾位置
DQ=1; // 释放,等待从机给出 0/1
if(DQ) // 采样
{
dat|=0x80; // 把“这一位”塞到最高位
}
Delay_OneWire(5);
}
return dat;
}
4.5 读温度:整套流程都在这(最常复习)
//函数名:读取温度函数
//入口参数:无
//返回值:我呢度高低两个字节
//函数功能:完成温度转换,并返回转换之后的温度数据
float rd_temperature(void)
{
unsigned char low,high;//返回的温度数据的高低八位
init_ds18b20();//初始化(叫醒)
Write_DS18B20(0xcc);//跳过ROM(免点名)
Write_DS18B20(0x44);//进行温度转换(去测温)
init_ds18b20();//初始化(再叫醒)
Write_DS18B20(0xcc);//跳过ROM(免点名)
Write_DS18B20(0xbe);//读取温度(去快递柜取)
low=Read_DS18B20();//读取低位(包裹下半)
high=Read_DS18B20();//读取高位(包裹上半)
return((high<<8)|low)/16.0; // 拼成16位原始值,再 /16 得到温度
}
5. 终极记忆卡片(背这一张就够了)
-
CC:免点名(Skip ROM)
-
44:去测温(Convert T)
-
BE:取结果(Read Scratchpad)
-
温度 = (high<<8 | low) / 16.0



