Arduino实战:从零到一构建DHT11/DHT22温湿度监测系统

张开发
2026/4/13 2:05:14 15 分钟阅读

分享文章

Arduino实战:从零到一构建DHT11/DHT22温湿度监测系统
1. 硬件选型DHT11与DHT22深度对比第一次接触温湿度传感器时我也曾被DHT11和DHT22搞得晕头转向。这两兄弟长得像双胞胎价格差不了几块钱但性能差异却直接影响项目效果。实测下来DHT22的精度确实更胜一筹但具体选哪个还得看实际需求。先看温度测量范围DHT11只能覆盖0-50℃而DHT22可以做到-40到80℃。去年我给冰柜做监控时就踩过坑用DHT11在零下环境直接罢工换成DHT22才解决问题。精度方面更明显DHT22温度误差±0.5℃湿度误差±2%比DHT11的±2℃和±5%精准不少。不过要注意DHT22的采样间隔是2秒比DHT11的1秒慢一倍。价格方面国内市场上DHT11约5-8元DHT22约15-25元。如果只是做室内温湿度监测DHT11完全够用。但要是做农业大棚、冷链监控这类对精度要求高的场景多花点钱上DHT22更稳妥。有个小技巧买带PCB板的型号已经内置了上拉电阻接线能省事不少。2. 硬件连接详解与避坑指南很多新手第一次连接DHT传感器都会遇到读数不稳定的问题其实八成是电路没接对。我拆过十几个不同厂家的模块发现引脚定义虽然相同但细节处理差异很大。这里分享几个实测可用的接线方案。基础接法中传感器1脚接5V4脚接GND2脚接数字引脚比如D2。关键是要在数据脚和VCC之间加4.7kΩ上拉电阻我用过从1k到10k的电阻都能工作但4.7k最稳定。有个容易忽略的细节如果使用三线制模块通常已经内置了10k电阻这时外接电阻反而会导致读数异常。遇到信号干扰时可以尝试这些方案在VCC和GND之间加0.1μF去耦电容数据线长度控制在20cm以内避免与电机、继电器等干扰源共用一个电源最近发现个有趣的现象用某些品牌的Arduino板时3.3V供电比5V更稳定。特别是在ESP8266这类开发板上建议先用万用表测实际电压偏离标准值太多的话要考虑加稳压电路。3. 开发环境搭建与库配置装库看似简单但版本兼容性问题坑过不少开发者。去年给学校实验室配置时就遇到过同样的代码在不同电脑上一个能跑一个报错折腾半天发现是库版本作祟。现在推荐使用Arduino IDE 2.0以上版本库管理更稳定。安装时务必按这个顺序先装Adafruit Unified Sensor库最新版1.1.7再装DHT sensor library最新版1.4.3有个隐藏坑点某些第三方库会依赖旧版Unified Sensor库导致冲突。这时可以在Arduino\libraries目录下手动删除旧版本。如果遇到Adafruit_Sensor.h not found错误八成是库路径有问题试试把库文件直接拷贝到项目目录下。调试时建议先跑这个最小测试代码#include DHT.h #define DHTPIN 2 #define DHTTYPE DHT22 DHT dht(DHTPIN, DHTTYPE); void setup() { Serial.begin(115200); dht.begin(); } void loop() { float h dht.readHumidity(); float t dht.readTemperature(); Serial.print(Humidity: ); Serial.print(h); Serial.print(% Temperature: ); Serial.print(t); Serial.println(°C); delay(2000); }4. 代码优化与实战技巧官方示例代码虽然能用但缺乏错误处理和稳定性设计。经过多个项目迭代我总结出一套增强版代码框架加入了这些实用功能温度单位自动转换float getTemp(bool isFahrenheit) { float t dht.readTemperature(); return isFahrenheit ? t * 1.8 32 : t; }带超时机制的读取函数bool readDHT(float h, float t, uint32_t timeout3000) { uint32_t start millis(); while((millis()-start) timeout) { h dht.readHumidity(); t dht.readTemperature(); if(!isnan(h) !isnan(t)) return true; delay(100); } return false; }移动平均滤波算法#define FILTER_SIZE 5 float tempFilter[FILTER_SIZE] {0}; float filteredTemp() { float sum 0; for(int iFILTER_SIZE-1; i0; i--) { tempFilter[i] tempFilter[i-1]; sum tempFilter[i]; } tempFilter[0] dht.readTemperature(); sum tempFilter[0]; return sum/FILTER_SIZE; }实际项目中建议把采样间隔设为传感器极限值的1.5倍DHT11用1.5秒DHT22用3秒。太频繁的读取会导致传感器发热影响测量精度。曾有个温室监控项目因为设置500ms读取间隔导致长期运行后温度偏高0.8℃。5. 数据可视化与扩展应用光在串口看数据太原始了我常用这些方法提升实用性OLED本地显示方案#include U8g2lib.h U8G2_SSD1306_128X64_NONAME_F_HW_I2C u8g2(U8G2_R0); void displayData(float h, float t) { u8g2.clearBuffer(); u8g2.setFont(u8g2_font_ncenB14_tr); u8g2.setCursor(0, 20); u8g2.print(Temp: ); u8g2.print(t); u8g2.print(C); u8g2.setCursor(0, 50); u8g2.print(Humi: ); u8g2.print(h); u8g2.print(%); u8g2.sendBuffer(); }结合Blynk实现手机监控#define BLYNK_PRINT Serial #include BlynkSimpleEsp8266.h char auth[] YourAuthToken; char ssid[] YourWiFiSSID; char pass[] YourWiFiPassword; void setup() { Blynk.begin(auth, ssid, pass); dht.begin(); } void loop() { Blynk.run(); float h dht.readHumidity(); float t dht.readTemperature(); Blynk.virtualWrite(V0, t); Blynk.virtualWrite(V1, h); delay(3000); }数据持久化方案用SD卡模块存储CSV格式数据通过ESP8266上传到Thingspeak搭配0.96寸LCD做实时曲线显示最近做的智能衣柜项目就整合了这些功能DHT22监测温湿度超标时启动风扇除湿数据同时上传云端和本地存储整套系统成本不到50元。6. 常见问题排查手册遇到传感器抽风时按这个检查清单逐步排查电源问题测量VCC-GND间电压是否在3.3-5V之间检查电源波纹最好用示波器看尝试单独供电避免与其他模块共电信号问题确认上拉电阻值在4.7kΩ左右检查数据线是否接触不良缩短数据线长度或改用屏蔽线环境干扰远离电磁干扰源在潮湿环境要给传感器做防水处理高温环境要考虑散热问题代码问题确认定义了正确的DHT类型检查引脚编号是否与实际一致采样间隔是否满足传感器要求有个经典案例某实验室的传感器每周一准时失灵最后发现是保洁阿姨用带静电的抹布擦拭设备。后来给传感器加了防静电罩就再没出过问题。

更多文章