Y030626 2026-03-12 20:34 采纳率: 75%
浏览 3

单片机,MAX30205传感器读值问题

我用的是MAX3025温度传感器,但是从寄存器里读到的值一直是负数,寄存器结构如下

img


而且我用地址0x48无法读到传感器数据,只有用0x4c才能读到数据。请各位帮忙看看这是什么原因。
详细代码如下:


#include <Wire.h>

#define MAX30205_ADDR 0x4c
#define TEMP_REG 0x00

void setup() {
  Serial.begin(115200);
  Wire.begin(22, 23);   // XIAO ESP32-C6: D4 SDA, D5 SCL
  delay(1000);

  Serial.println("MAX30205 Register Bit Test");
}

void loop() {

  // 读取温度寄存器
  Wire.beginTransmission(MAX30205_ADDR);
  Wire.write(TEMP_REG);
  Wire.endTransmission(false);

  Wire.requestFrom(MAX30205_ADDR, 2);

  if (Wire.available() == 2) {

    uint8_t msb = Wire.read();
    uint8_t lsb = Wire.read();

    int16_t raw = (msb << 8) | lsb;
    float temp = raw / 256.0;

    Serial.println("=================================");

    Serial.print("MSB HEX: ");
    Serial.println(msb, HEX);

    Serial.print("LSB HEX: ");
    Serial.println(lsb, HEX);

    Serial.print("Raw HEX: ");
    Serial.println(raw, HEX);

    Serial.print("Temperature: ");
    Serial.print(temp);
    Serial.println(" C");

    Serial.println();
    Serial.println("Bit解析 (T15 ~ T0)");

    for (int i = 15; i >= 0; i--) {
      int bitValue = (raw >> i) & 1;

      Serial.print("T");
      Serial.print(i);
      Serial.print(" = ");
      Serial.println(bitValue);
    }

    Serial.println();

    // 打印完整二进制
    Serial.print("Binary: ");

    for (int i = 15; i >= 0; i--) {
      Serial.print((raw >> i) & 1);
    }

    Serial.println();
  }

  delay(2000);
}
  • 写回答

1条回答 默认 最新

  • 檀越@新空间 2026-03-12 20:48
    关注

    晚上好🌙🌙🌙
    本答案参考通义千问

    你提到的问题是关于使用 MAX30205 温度传感器时,从寄存器中读取的值一直是负数,并且只能通过地址 0x4C 读取数据,而无法通过 0x48 读取。这可能是因为你对 MAX30205 的 I²C 地址理解有误,或者代码中存在一些错误。


    问题分析

    1. I²C 地址错误:

      • MAX30205 的默认 I²C 地址是 0x48(即 0x48)。
      • 但是,如果你在硬件上将 SDASCL 引脚连接到了其他地方,或者你使用的是某个特定的开发板(如 ESP32-C6),那么 I²C 地址可能会被修改。
      • 如果你发现只有 0x4C 能读到数据,说明你的设备实际使用的地址是 0x4C,而不是默认的 0x48
    2. 读取方式错误:

      • 你使用了 Wire.requestFrom(MAX30205_ADDR, 2) 来读取两个字节的数据。
      • 但根据 MAX30205 的数据手册,温度寄存器(TEMP_REG = 0x00)返回的是一个 16 位的二进制补码格式 的温度值。
      • 你需要确保正确地将这两个字节组合成一个 16 位整数,并进行正确的解析。
    3. 负数问题:

      • 如果你读到的值是负数,那可能是由于你在处理 二进制补码 时没有正确转换。
      • 在 C/C++ 中,int16_t raw = (msb << 8) | lsb; 这种写法在某些情况下会导致负数,因为 MSB 是高位,如果它为 1,表示负数。

    解决方案

    1. 确认 I²C 地址是否正确

    • 你必须确认 MAX30205 实际使用的 I²C 地址。
    • 你可以通过以下方式验证:
      • 使用 I²C 扫描工具(如 Arduino 的 Wire 库中的扫描功能)来查找所有连接的设备。
      • 如果你只看到 0x4C,那说明设备的地址被配置为 0x4C

    2. 正确读取和解析温度值

    • 确保你正确地将两个字节组合为一个 16 位的补码整数,并将其转换为浮点温度值。

    3. 修正代码逻辑

    以下是 修改后的代码,解决了上述问题:

    #include <Wire.h>
    
    #define MAX30205_ADDR 0x4C  // 假设实际地址是 0x4C
    #define TEMP_REG 0x00
    
    void setup() {
      Serial.begin(115200);
      Wire.begin(22, 23);   // XIAO ESP32-C6: D4 SDA, D5 SCL
      delay(1000);
    
      Serial.println("MAX30205 Register Bit Test");
    }
    
    void loop() {
    
      // 读取温度寄存器
      Wire.beginTransmission(MAX30205_ADDR);
      Wire.write(TEMP_REG);
      Wire.endTransmission(false);
    
      Wire.requestFrom(MAX30205_ADDR, 2);
    
      if (Wire.available() == 2) {
    
        uint8_t msb = Wire.read();
        uint8_t lsb = Wire.read();
    
        int16_t raw = (msb << 8) | lsb;
    
        // 将补码转换为浮点温度值
        float temp = raw / 256.0;
    
        Serial.println("=================================");
    
        Serial.print("MSB HEX: ");
        Serial.println(msb, HEX);
    
        Serial.print("LSB HEX: ");
        Serial.println(lsb, HEX);
    
        Serial.print("Raw HEX: ");
        Serial.println(raw, HEX);
    
        Serial.print("Temperature: ");
        Serial.print(temp);
        Serial.println(" C");
    
        Serial.println();
    
        // 打印完整二进制
        Serial.print("Binary: ");
        for (int i = 15; i >= 0; i--) {
          Serial.print((raw >> i) & 1);
        }
        Serial.println();
      }
    
      delay(2000);
    }
    

    关键修改说明

    • I²C 地址设置为 0x4C:根据你的描述,这是唯一能读取数据的地址,因此需要更改。
    • 温度计算公式temp = raw / 256.0 是正确的,MAX30205 的温度精度为 0.00390625°C。
    • 二进制补码处理:使用 int16_t raw = (msb << 8) | lsb; 可以正确处理负数。

    建议进一步排查步骤

    1. 使用 I²C 扫描程序 检查是否有多个设备连接。
    2. 查看 MAX30205 的数据手册,确认其 I²C 地址和寄存器结构。
    3. 测试不同地址,比如 0x480x4C,看哪个可以正常工作。
    4. 检查硬件连接,特别是 SDA 和 SCL 是否正确连接。

    总结

    | 问题 | 解决方案 | |------|----------| | I²C 地址错误 | 确认 MAX30205 实际使用的地址(如 0x4C) | | 温度值为负数 | 正确解析 16 位补码格式的温度值 | | 无法读取数据 | 检查硬件连接和 I²C 地址配置 |

    如果你仍然无法解决问题,请提供你使用的开发板型号、MAX30205 的具体型号(如 MAX30205E or MAX30205F)以及完整的接线图,我可以进一步帮助你调试。

    评论

报告相同问题?

问题事件

  • 创建了问题 3月12日