Arduino串行数据解析

Sol*_*oid 5 arduino

我正在编写一个应用程序,用我的Android手机通过蓝牙控制我的机器人,一切顺利,数据得到回应和验证,但我在协议上遇到了一些麻烦,特别是我希望机器人的轮子在发送时转动一个命令,如s,10,100s,-30,-10...(以百分比表示的值).

我的问题是,当我想在我的Arduino的解析我的车轮转速命令我必须解析最多4分开bytesint,例如s,-100,-100使我的机器人全速倒退,但我要如何解析这个,所以我可以打电话setSpeed(left, right);leftright平等到-100?

我知道我可以单独分析每个字节并将它们放在一起得到一个整数,但它不是很优雅,而且可能已经有了更好的解决方案,不幸的是我还没有找到它.

编辑

这是我用于解析命令的Arduino函数:

void parseCommand(char* command, int* returnValues)
{
  // parsing state machine
  byte i = 2, j = 0, sign = 0;
  int temp = 0;
  while(*(command + i) != '\0')
  {
    switch(*(command + i))
    {
      case ',':
        returnValues[j++] = sign?-temp:temp;
        sign = 0;
        temp = 0;
        break;
      case '-':
        sign = 1;
        break;
      default:
        temp = temp * 10 + *(command + i) - 48;
    }
    i++;
  }
  // set last return value
  returnValues[j] = sign?-temp:temp;
}
Run Code Online (Sandbox Code Playgroud)

在解析像s,100,-100(必须\0终止)之类的东西时你这样称呼它:

char serialData[16];
void loop()
{
  if(Serial.available() > 0)
  {
    Serial.readBytesUntil('\0', serialData, 15);
    switch(serialData[0])
    {
      case 's':
        int speed[2];
        parseCommand(serialData, speed);
        setSpeed(speed[0], speed[1]);
        break;
    }
    // always echo
    Serial.write(serialData);
    // end of message is maked with a \0
    Serial.print('\0');

    // clear serialData array
    memset(serialData, 0, sizeof(serialData));
  }
}
Run Code Online (Sandbox Code Playgroud)

Dav*_*rtz 9

只需逐个字符地读入状态机.它简单而有效.

要逐位读取数字,请执行以下操作:从零开始.对于每个数字,将数字乘以10并添加数字的值.因此,例如,阅读97将如下工作:

  1. 你读一个没有前一个数字的数字,你从0开始.

  2. 你读入9并计算(0*10)+9 - > 9

  3. 你读入7并计算(9*10)+7 - > 97

  4. 你读了一个非数字,你输出97.

这是一个更全面的例子s,10,100:

  1. 您从"准备读取命令状态"开始.

  2. 你读"s","s"是命令.您切换到"准备好先读取逗号"状态.

  3. 你读了第一个逗号,你切换到"准备找出第一个参数的符号"状态.

  4. 你读了一个数字.由于这不是" - ",因此第一个参数是正数.您将第一个数字设置为数字的值,1.您现在处于"读取第一个数字"状态.

  5. 您读取一个数字,0.您将第一个数字设置为1*10 + 0 - > 10.您仍处于"读取第一个数字"状态.

  6. 你读了一个逗号.您现在处于"准备找出第二个参数的状态"状态.

  7. 您阅读1.第二个数字是正数(因为这不是" - ").您将第二个数字设置为1.您处于"读取第二个数字"状态.

  8. 您读取0.第二个数字现在设置为1x10 + 0 - > 10.您仍处于"读取第二个数字"状态.

  9. 您读为0.第二个数字现在设置为10x10 + 0 - > 100.您仍处于"读取第二个数字"状态.

  10. 你读了一行的结尾.执行结果:命令为"s",第一个数字为正数,第一个数字为10,第二个数字为正数,第二个数字为100.

  11. 您切换回"准备读取命令"状态.