【问题标题】:Correctly formatting data for I2C (Wire.write)为 I2C 正确格式化数据 (Wire.write)
【发布时间】:2018-12-28 09:39:14
【问题描述】:

我将多个 Arduino Mega 单元连接在一起以创建一组 IO,所有这些 IO 均由 I2C 总线上的主控器控制。

我让它与从机一起使用模拟输入等的状态填充一个字符串,每个用冒号分隔。然后将使用Wire.write 循环该字符串。

最初的reqNo 会告诉master 哪个批次被退回。例如。第 0 批是模拟 0 - 5,第 1 批是模拟 6 - 11 等等。

一切正常,直到进一步阅读使我看到一篇文章,由于内存使用和相关问题而提倡反对使用字符串。我试图重构我的代码以避免使用字符串,但是现在我得到这样的字符串:

:⸮:⸮:⸮:⸮:⸮:⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮⸮W

返回而不是我的预期输出。

我认为这是编码问题或类似问题?任何人都可以就我做错了什么或实现这一目标的其他方式提供建议。设备可以长时间运行而不会重新启动或任何问题非常重要,这就是为什么我非常热衷于删除字符串,如果这可能会导致问题。

主码:

int i=0;
char res[32]="";
while(Wire.available()){
    char c=Wire.read();
    Serial.print(c);
    res[i]=c;
    i++;
}

从机代码:

void requestStatus(){
    int i;
    Wire.write(reqNo);

    if(reqNo==0){
        for(i=0;i<6;i++){
            Wire.write(':');
            Wire.write(analogRead(i));
        }
    }else if(reqNo==1){
        for(i=6;i<12;i++){
            Wire.write(':');
            Wire.write(analogRead(i));
        }
    }else if(reqNo==2){
        for(i=12;i<16;i++){
            Wire.write(':');
            Wire.write(analogRead(i));
        }
    }
    reqNo++;
    if(reqNo==3){
        reqNo=0;
    }
}

【问题讨论】:

  • 你没有在代码的任何地方使用res,请提供完整的例子。

标签: c++ arduino arduino-ide


【解决方案1】:

你的代码有两个问题,第一:

...
// master side
char c=Wire.read();
...
// slave side            
Wire.write(analogRead(i));

您将整数值视为经过ASCII 编码,但它们不是。您必须在某些时候将它们转换为 ASCII(例如主端)。考虑使用sscanfsnprintf 进行转换。

其次,你不是 NUL terminating 一个 C 字符串。

【讨论】:

    【解决方案2】:

    Wire.write(reqNo); 例如将写入代码 0 1 或 2 的字符,而不是字符 '0' 或 '1' 或 '2' 如果这是你所期望的

    【讨论】:

      【解决方案3】:

      一切正常,直到进一步阅读让我看到一篇文章,由于内存使用和相关问题而提倡反对使用字符串。

      我认为它是在谈论 String 对象而不是 c 字符串(以 nul 结尾的字符数组)。
      那些使用动态内存分配并导致堆碎片。 C 字符串通常是静态分配的 (char res[32];),如果它们是在函数中定义的,它们会从堆栈中彻底清除。

      write 仅接受单个字节、具有显式长度的字节(或字符)数组或 c 字符串。
      传递一个 int 只会将其转换为一个字节,并且只保留低 8 位。

      你需要的是˙print˙方法。它即时将整数转换为字符。它不使用 String 或 c-strings。

      您应该将所有Wire.write 替换为Wire.print

      同样在您的主代码中,您没有终止 res 字符数组,这会导致问题,因为字符串没有明确的结尾。您还应该确保,您写入的字符不超过 31 个(nul 终止符也算作一个字符),并导致缓冲区溢出。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2013-02-02
        • 1970-01-01
        • 1970-01-01
        • 2015-01-28
        • 1970-01-01
        • 2014-05-27
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多