Dan*_*iel 1 c serial-port arduino char uart
我正在高频采样,需要通过UART从我的Arduino传输10位ADC值.
默认情况下,它每个字符使用一个字节.因此,如果执行analogRead将产生值"612",它将通过UART"6"作为一个字节发送,"1"作为一个字节发送,"2"作为一个字节发送,并将行终止符作为最后一个字节发送.
鉴于我的采样率被这种通信截断,重要的是它尽可能高效和统一,所以我试图强制它使用两个字节来传输那些数据,无论数据实际是什么(通过默认情况下,它将使用三个字节来发送"23",四个字节用于发送"883",五个字节用于发送"1001").
目前,我正在做这样的事情,这是我发现的最好方法:
int a = 600; //Just an example
char high = (char)highByte(a);
char low = (char)lowByte(a);
Serial.print(high);
Serial.println(low);
Run Code Online (Sandbox Code Playgroud)
目前,无论值如何,它都使用三个字节(包括\n).有更有效的方法吗?
只需用类似的东西打印即可
Serial.print(foo, BIN);
Run Code Online (Sandbox Code Playgroud)
根本不起作用.它实际上每foo的二进制表示的每一位使用一个字节,这是非常愚蠢的.
我可能会遗漏一些东西,但你为什么不用Serial.write(byte)
?
你可以使用像这样的方法:
void writeIntAsBinary(int value){
Serial.write(lowByte(value));
Serial.write(highByte(value));
}
Run Code Online (Sandbox Code Playgroud)
您打算如何处理计算机上的数据?
如果您通过串行线路发送二进制数据,则实际上不应该使用文本样式的换行分隔符来混淆所有内容.
另一方面,如果没有某种同步帮助,知道哪个字节是哪一个很难(另一方面).
但是,由于您只有10位有效负载,但发送16位数据,您可以"执行UTF-8"并使用空闲位来发出"值的开始"信号.这将要求你的有效载荷只使用每个8位字节的7位,但这很好,因为7 + 7 = 14超过10.我们可以让第8位表示"这是新对的高字节字节":
const int a = 600;
const unsigned char high = ((a >> 7) & 0x7f) | 0x80;
const unsigned char low = (a & 0x7f);
Serial.print(high);
Serial.print(low);
Run Code Online (Sandbox Code Playgroud)
在上面,传输的两个字节将是:
high == ((600 >> 7) & 0x7f) | 0x80 == 4 | 0x80 == 0x84
low == (600 & 0x7f) == 88 == 0x58
Run Code Online (Sandbox Code Playgroud)
接收方必须反向执行以上操作:
const int value = ((high & 0x7f) << 7) | low;
Run Code Online (Sandbox Code Playgroud)
这应该工作,并使用首先发送的高字节的最高有效位来表示这确实是高字节.低字节永远不会设置MSB.