stm32 如何才能使dht11精确到小数点后两位

dht11如何才能精确到小数点后两位啊,还有这里为什么写的是<<8啊

img

img

不知道你这个问题是否已经解决, 如果还没有解决的话:
  • 给你找了一篇非常好的博客,你可以看看是否有帮助,链接:STM32利用滴答定时器实现高精度延时(在DHT11温湿度传感器中的应用)
  • 除此之外, 这篇博客: stm32实现DHT11读取温湿度中的 数据传输的数据 部分也许能够解决你的问题, 你可以仔细阅读以下内容或者直接跳转源博客中阅读:

    一次完整的数据传输为40bits,也就是32位机的5个字节(byte),假如数据为buf[0]~buf[4],每个buf为一个unsigned char,或者其他8位的数据类型,buf[0]就是湿度的整数数据,buf[1]就是其湿度的小数部分,然后buf[2]就是温度的整数部分,buf[3]就是其温度的小数部分,buf[4]是校验和,也就是前面4个buf加起来的和。如果前面四个加起来等于校验和,说明数据传输成功,否则说明数据传输有问题。
    在这里插入图片描述

  • 以下回答来自chatgpt:

    解决方案: 在stm32中实现对dht11读取温湿度值的精确控制,需要对DHT11输出的波形进行解码,从而获取到温湿度数据。在解码波形的过程中,需要计算出低电平持续时间和高电平持续时间,用于将波形转换为二进制数。根据DHT11手册,温湿度数据分为整数和小数两部分,因此需要分别计算出整数和小数部分,再将它们组合成一个完整的数值。

    以下是代码示例:

    // 解码DHT11输出的波形,获取温湿度数据
    // 参数:data 保存温湿度数据的数组,长度为5
    // 返回值:成功返回0,失败返回负数
    int decode_dht11(uint8_t* data)
    {
        // 发送开始信号
        // 设置引脚为输出模式,并输出低电平
        GPIO_InitTypeDef GPIO_InitStruct;
        GPIO_InitStruct.Pin = GPIO_PIN_0;  // 选择引脚
        GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;  // 输出模式
        GPIO_InitStruct.Pull = GPIO_PULLUP;  // 上拉
        GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;  // 低速
        HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
        HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, GPIO_PIN_RESET);  // 输出低电平
        HAL_Delay(20);  // 低电平持续时间至少18ms
        HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, GPIO_PIN_SET);  // 输出高电平
        HAL_Delay(40);  // 高电平持续时间20-40us
    
        // 切换引脚为输入模式,接收DHT11响应信号
        GPIO_InitStruct.Mode = GPIO_MODE_INPUT;  // 输入模式
        HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
        uint32_t t = 0;
        while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_SET) {
            HAL_Delay(1);
            ++t;
            if (t > 80) {
                return -1;  // 响应信号持续时间大于80us,通信失败
            }
        }
        t = 0;
        while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_RESET) {
            HAL_Delay(1);
            ++t;
            if (t > 80) {
                return -2;  // 响应信号持续时间大于80us,通信失败
            }
        }
        t = 0;
        while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_SET) {
            HAL_Delay(1);
            ++t;
            if (t > 80) {
                return -3;  // 响应信号持续时间大于80us,通信失败
            }
        }
    
        // 解码温湿度数据
        uint8_t buffer[5];
        for (int j = 0; j < 5; ++j) {
            uint8_t d = 0;
            for (int i = 7; i >= 0; --i) {
                // 测量低电平持续时间
                t = 0;
                while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_RESET) {
                    HAL_Delay(1);
                    ++t;
                    if (t > 100) {
                        return -4;
                    }
                }
    
                HAL_Delay(40);
    
                // 判断是否有高电平产生
                if (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_SET) {
                    d |= 1 << i;
                    // 测量高电平持续时间
                    t = 0;
                    while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_SET) {
                        HAL_Delay(1);
                        ++t;
                        if (t > 100) {
                            return -5;
                        }
                    }
                }
            }
            buffer[j] = d;
        }
    
        // 数据校验
        uint8_t sum = buffer[0] + buffer[1] + buffer[2] + buffer[3];
        if (sum != buffer[4]) {
            return -6;  // 校验和错误
        }
    
        // 计算温度和湿度值
        int temp_int = (int)buffer[2];
        int temp_dec = (int)buffer[3];
        int humidity_int = (int)buffer[0];
        int humidity_dec = (int)buffer[1];
        data[0] = (uint8_t)(humidity_int * 10 + humidity_dec);
        data[1] = 0;
        data[2] = (uint8_t)(temp_int * 10 + temp_dec);
        data[3] = 0;
        data[4] = sum;
        return 0;
    }
    

    关于参考资料中的 <<8 操作,它是将一个8位的数左移8位,相当于将该数乘以256。在温湿度数据传输过程中,第1个字节表示湿度的整数部分,第2个字节表示湿度的小数部分,而温度的整数部分和小数部分分别在第3个和第4个字节中。为了将整数部分和小数部分组合成一个带小数的数值,需要将小数部分左移8位,相当于将它乘以256,再与整数部分相加。因此,代码中需要进行左移位运算,将小数部分左移8位,再与整数部分相加得到完整的温湿度数值。


如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^

DHT11温湿度传感器只能输出整数,无法精确到小数点后两位。如果需要更高精度的温湿度数据,可以考虑使用DHT22或AM2302等高精度的传感器,它们可以输出小数。或者使用其他类型的温湿度传感器,如SHT30、BME280等,它们可以提供更高的精度和稳定性。但是请注意,在使用更高精度的传感器时,需要进行相应的代码修改,以便正确解析传感器输出的数据。