3、常用传感器详解(上):DHT11/DHT22温湿度传感器、DS18B20温度传感器,数据手册解读与接线

好,咱们进入实战环节。前面聊了那么多理论,今天终于要上手摸传感器了。这一章我挑了两个最常用的家伙——DHT11/DHT22 和 DS18B20。说实话,这两个传感器我用了不下几百个,从早期的智能家居项目到工业环境监测,到处都有它们的身影。

你想想看,一个项目里最基础的需求是什么?无非就是知道环境温度多少、湿度如何。这两个传感器就能搞定。但怎么选、怎么接线、怎么读数据手册,这里头门道不少。我今天就把自己踩过的坑、总结的经验,一股脑倒给你。

3.1 DHT11 与 DHT22:温湿度测量的入门之选

先说说 DHT11 和 DHT22。这俩长得几乎一模一样,四个引脚,方方正正的小模块。但性能差别还挺大。

3.1.1 数据手册怎么看?

拿到一个新传感器,我习惯先翻数据手册。别怕,不用全看,抓住几个关键参数就行。

参数 DHT11 DHT22 (AM2302)
温度范围 0~50°C -40~80°C
温度精度 ±2°C ±0.5°C
湿度范围 20~90%RH 0~100%RH
湿度精度 ±5%RH ±2%RH
采样周期 1秒 2秒
通信方式 单总线 单总线

看到没?DHT22 精度高、范围广,但贵一些。DHT11 便宜,精度凑合。我个人习惯:做原型验证用 DHT11,正式产品用 DHT22。为什么?因为我在一个智能花盆项目里吃过亏——DHT11 在高温高湿环境下数据飘得厉害,后来全换成 DHT22 才稳定。

核心要点:选型时别只看价格,要看你的应用场景。室内环境监测 DHT11 够用,户外或工业场景必须上 DHT22。

3.1.2 引脚定义与接线

这两个传感器引脚定义完全一样。从正面看(有网格那面朝自己),从左到右:

  1. VDD:电源正极(3.3V~5V)
  2. DATA:数据线
  3. NC:空脚,不用接
  4. GND:电源负极

接线其实很简单:

DHT11/DHT22      Arduino/ESP32
    VDD  ----------- 3.3V 或 5V
    DATA ----------- GPIO 引脚 (比如 D4)
    GND  ----------- GND

注意:DATA 引脚需要接一个 4.7kΩ~10kΩ 的上拉电阻到 VDD。为什么?因为 DHT 用的是开漏输出,没有上拉电阻信号拉不起来。我曾经偷懒没接,结果数据全是 0,排查了半天。

3.1.3 通信协议简析

DHT 用的是单总线协议,但和 DS18B20 的单总线不太一样。它的时序更严格,对时间精度要求高。

基本流程是这样的:

  1. 主机拉低总线至少 18ms(启动信号)
  2. 主机拉高 20~40μs
  3. DHT 响应:拉低 80μs,再拉高 80μs
  4. 开始传输 40 位数据(16位湿度 + 16位温度 + 8位校验)

每个 bit 的传输:

  • 0:拉低 50μs,拉高 26~28μs
  • 1:拉低 50μs,拉高 70μs

嗯,这里要注意。用 Arduino 的 DHT 库或者 ESP32 的 DHT sensor library 可以省去自己写时序的麻烦。但我建议你至少看一遍底层代码,理解原理。我在调试一个低功耗项目时,就是因为库的时序在睡眠唤醒后不对,最后自己重写了驱动才搞定。

// Arduino 示例代码
#include <DHT.h>

#define DHTPIN 2     // 数据引脚
#define DHTTYPE DHT22   // DHT 11 或 DHT22

DHT dht(DHTPIN, DHTTYPE);

void setup() {
    Serial.begin(9600);
    dht.begin();
}

void loop() {
    delay(2000);  // DHT22 采样周期至少 2 秒
    
    float h = dht.readHumidity();
    float t = dht.readTemperature();
    
    if (isnan(h) || isnan(t)) {
        Serial.println("读取失败!");
        return;
    }
    
    Serial.print("湿度: ");
    Serial.print(h);
    Serial.print(" %\t");
    Serial.print("温度: ");
    Serial.print(t);
    Serial.println(" *C");
}

小技巧:读取间隔一定要大于采样周期。DHT11 至少 1 秒,DHT22 至少 2 秒。读太频繁传感器会不响应,我刚开始做的时候就被这个坑过。

3.2 DS18B20:数字温度传感器的经典之作

DS18B20 是我个人非常喜欢的一个传感器。它精度高、支持多点测量、而且通信距离远。说白了,它就是温度测量领域的「老兵」,从 2000 年左右开始用到现在,依然活跃在一线。

3.2.1 数据手册关键参数

参数 DS18B20
温度范围 -55~125°C
精度 ±0.5°C(-10~85°C)
分辨率 9~12 位可配置
转换时间 最大 750ms(12位)
通信方式 1-Wire(单总线)
供电方式 寄生供电或外部供电

这里有个亮点——寄生供电。什么意思?就是传感器可以从数据线上「偷」电,不需要单独的电源线。这在长距离布线时特别有用。我记得在一个温室大棚项目里,用了 20 多个 DS18B20 挂在一条总线上,只用了三根线(数据、地、电源),省了不少线材成本。

3.2.2 引脚与接线

DS18B20 有三种封装:TO-92(像三极管)、SOIC(贴片)、和封装好的不锈钢探头。最常用的是 TO-92 封装。

引脚定义(平面朝自己,引脚朝下):

  1. GND:地
  2. DQ:数据线
  3. VDD:电源(寄生供电时可接地)

标准接线(外部供电模式):

DS18B20           Arduino/ESP32
    VDD  ----------- 3.3V 或 5V
    DQ   ----------- GPIO 引脚 (比如 D2)
    GND  ----------- GND

同样,DQ 引脚需要接一个 4.7kΩ 上拉电阻到 VDD。

寄生供电接线:VDD 引脚直接接 GND,数据线 DQ 既传数据又供电。但要注意,这种模式下转换时间会变长,而且总线上传感器数量不宜超过 8 个。

3.2.3 多点测量:一条总线挂多个传感器

DS18B20 最大的优势就是每个芯片都有一个唯一的 64 位 ROM 编码。你可以把多个传感器并联在同一条数据线上,通过 ROM 编码来寻址。

我做过一个项目,在一条 50 米长的总线上挂了 30 个 DS18B20,用来监测冷库不同位置的温度。效果很好,就是布线要小心,线太长信号会衰减。

// Arduino 多点测量示例
#include <OneWire.h>
#include <DallasTemperature.h>

#define ONE_WIRE_BUS 2

OneWire oneWire(ONE_WIRE_BUS);
DallasTemperature sensors(&oneWire);

void setup() {
    Serial.begin(9600);
    sensors.begin();
    
    // 获取总线上传感器数量
    int deviceCount = sensors.getDeviceCount();
    Serial.print("发现 ");
    Serial.print(deviceCount);
    Serial.println(" 个 DS18B20");
}

void loop() {
    sensors.requestTemperatures(); // 发起温度转换
    
    for (int i = 0; i < sensors.getDeviceCount(); i++) {
        float tempC = sensors.getTempCByIndex(i);
        Serial.print("传感器 ");
        Serial.print(i);
        Serial.print(": ");
        Serial.print(tempC);
        Serial.println(" °C");
    }
    
    delay(1000);
}

避坑指南:我曾经在一条总线上混用了不同批次的 DS18B20,结果寻址时偶尔会冲突。后来发现是某些国产兼容芯片的 ROM 编码有重复。建议从正规渠道采购,或者用之前先扫描一遍所有 ROM 地址,确认没有重复。

3.3 两个传感器的对比与选型建议

好,咱们来总结一下。这两个传感器虽然都能测温度,但定位完全不同。

对比项 DHT11/DHT22 DS18B20
测量参数 温度 + 湿度 仅温度
温度精度 DHT11: ±2°C, DHT22: ±0.5°C ±0.5°C
多点测量 不支持(每个传感器独立引脚) 支持(一条总线挂多个)
通信距离 短(20米以内) 长(100米以上)
价格 DHT11: 极低, DHT22: 中等 中等
典型应用 室内环境监测、气象站 工业测温、冷链物流

我的建议很简单:

  • 如果你需要同时测温度和湿度,选 DHT22(预算够)或 DHT11(预算紧)
  • 如果你只需要测温度,或者需要多点测量,选 DS18B20
  • 如果项目要求高可靠性、长距离传输,DS18B20 是更好的选择

个人经验:我做过一个智能鱼缸项目,用了 DHT22 测环境温湿度,DS18B20 测水温。两个传感器各司其职,配合得很好。你想想看,一个项目里完全可以同时用它们,取长补短。

好了,这一章的内容就到这儿。下一章我们会继续聊其他常用传感器,包括光照、气压、气体传感器等。到时候我会分享更多实战中的坑和技巧。记住,看数据手册是基本功,接线是体力活,真正考验人的是调试和排错。别怕犯错,我犯过的错比你多得多,重要的是从中学到东西。