我的命令行有很大的性能问题。如果我输入:
hcidump -a
我得到以下输出:
> HCI Event: LE Meta Event (0x3e) plen 42
LE Advertising Report
ADV_IND - Connectable undirected advertising (0)
bdaddr 78:A5:04:17:9F:66 (Public)
Flags: 0x06
Unknown type 0xff with 25 bytes data
RSSI: -26
> HCI Event: LE Meta Event (0x3e) plen 41
LE Advertising Report
SCAN_RSP - Scan Response (4)
bdaddr 78:A5:04:17:9F:66 (Public)
Complete local name: 'BEACON 17:9F:66'
TX power level: 0
Unknown type 0x16 with 7 bytes data
RSSI: -26
每一块信息都会在屏幕上实时显示。但由于我只需要RSSI的值,我使用此命令来获取它:
hcidump -a | egrep 'RSSI|bdaddr' | grep -A1 --no-group-separator 'bdaddr 78:A5:04:17:9F:66' | grep -Po 'RSSI:\s+\K.*'
它完美无缺,但我有很大的性能问题。由于两位数值不是在屏幕上逐个显示,而是以块为单位。 12-15秒没有发生任何事情,然后我一次得到40个值。有什么机构知道问题是什么吗?
pipe-command是否使用缓冲区? 或者有人知道如何缩短命令,如上所示?提高性能?
最好的问候阿德里安
答案 0 :(得分:3)
性能问题是由grep
命令检测到它们的输出不是终端设备,因此在打印输出时使用块缓冲。如果你正在使用GNU grep
,你可以使用它的--line-buffered
缓冲区而不是 block 的数据。
如果您只需要RSSI值,则可以使用一个grep
命令替换管道sed
命令:
hcidump -a | sed -n 's/[ \t]*RSSI: //p'
-n
选项告诉sed
不打印每一行。它在每一行中搜索前面有任意数量的空白字符的字符串RSSI:
,并用空字符串替换整个批次。最终p
指示sed
在替换完成后打印该行。
由于sed
命令直接打印到终端设备,因此不应阻止缓冲区输出。如果您希望将其打印到终端以外的其他内容并使用GNU sed
,则可以使用其-u, --unbuffered
选项
从输入文件加载最少量的数据并更频繁地刷新输出缓冲区
当程序将文本打印到输出流时,打印将被缓冲。 有两种类型:
stdin
始终是块缓冲的。stderr
是行缓冲的。stdout
取决于输出设备:
stdout
连接,则使用块缓冲
管道中另一个程序的stdin
。Grep and Output Buffering提供 对这个问题的正确介绍。
PádraigBrady写了一篇很好的文章来解释内核发生了什么 级别:buffering in standard streams
Jonathon Perkin解释了如何为许多程序解决此问题: How to fix stdio buffering
这个Unix& Linux Stack Exchange问题涵盖了许多解决方案: Turn off buffering in pipe