我编写了python代码和arduino代码的组合来完成这项工作。我正在通过蓝牙(bluetoothsocket(RFCOMM))从python发送一个范围为0-65353的数字数组。它们在arduino中一个接一个地接收,并读入一个数组,该数组会将char数组转换为单个原始int。我想知道这是否应该走的路。理想情况下,整数应该在0-65353之间。
# define ledPinr 4
void setup() {
pinMode(ledPinr, OUTPUT);
digitalWrite(ledPinr, LOW);
Serial.begin(115200);
Serial.setTimeout(10000); // for now, not too important
}
void loop() {
// Read serial input:
char val[5]; //
if (Serial.available()){
digitalWrite(ledPinr, LOW);
Serial.readBytesUntil(',', val, 5);
unsigned int num = atol(val);
}
if (Serial.available()==0){
digitalWrite(ledPinr, HIGH);
}
}
这种方法的问题是,要使其正常工作,我必须首先填充要发送的int,它们的长度均为5,例如,它们的长度均为5,例如:ints2send = ['00001','65353','01000' ]。然后将它们设置为arduino中的char数组,例如:{'0','0','0','0','1'},并且atol在转换为int 1时会忽略前导0。 arduino的新手我想知道是否有一种方法可以将字符读入可变长度的数组中?,例如:{'1'},{'6','5','3 ','5','3'}。 或者是否有一种初始化char数组的方法,如果我仅发送不带填充的值就不会给出错误?还是我想知道是否值得解决这个问题,但我只是好奇我是否可以从改进此代码中学到一些东西。我意识到我真的忽略了Serial.readBytesUntil参数,该参数在找到','后停止读取,但是理想情况下,我希望在某个时间点暂停发送,因此我看不到使ints2send = ['00012,00034']作为解决方案。
答案 0 :(得分:0)
在读取缓冲区时,您需要检查字符是否为数字。然后,您要将其转换为整数左右。
首先要知道的是,arduino上的int
被编码为两个字节,并且被签名。这意味着其值在-2 ^ 15 = -32768和2 ^ 15-1 = 32767之间。 https://www.arduino.cc/reference/en/language/variables/data-types/int/
如果要存储0到65535(2 ^ 16)之间的值,则应使用unsigned int
。 https://www.arduino.cc/reference/en/language/variables/data-types/unsignedint/
然后您可以这样阅读:
unsigned char byte;
unsigned int value = 0;
while (Serial.available() > 0) {
// read the incoming byte:
byte = Serial.read();
//stop if you read a comma
if (byte == ',')
break;
//update the value if you read a digit
if (byte >= '0' && byte <= '9')
value = 10 * value + (byte - '0');
}
该值的计算使用了这样一个事实:每次您读取另一个数字时,这意味着您将移动先前读取的数字。这意味着将10乘以10。然后,要获取字符的值,只需将tu减去0
的ASCII值,因为幸运的是,数字是以正确的顺序编码的。
请注意,只要您不使最大unsigned int
值溢出,此解决方案就可以在字符串中的任何长度下工作。