简体   繁体   English

在bash中捕获多个并行的grep输出

[英]Capturing multiple paralleled grep outputs in bash

My quandary lies with piping grep results to a variable for later usage. 我的难题在于将grep结果传递给变量以供以后使用。 Normally, this wouldn't be an issue and I would use $( ) and push the results to the variable as is. 通常,这不是问题,我将使用$( )并将结果按原样推入变量。

The problem comes in when I need to have multiple instances of ping running in parallel using the & operator. 当我需要使用&运算符并行运行多个ping实例时,就会出现问题。 A code snippet: 一个代码片段:

google_ping=$(ping -c 2 www.google.com | grep -oP '\d+(?=% packet loss)') &
bing_ping=$(ping -c 2 www.bing.com | grep -oP '\d+(?=% packet loss)') &
custom_ping=$(ping -c 2 10.1.1.1 | grep -oP '\d+(?=% packet loss)') &

wait

printf "Google Ping: \t\e[32m %3d\e[0m\n " $google_ping
printf "Bing Ping:\t\e[32m %3d\e[0m\n " $bing_ping
printf "Custom Ping:\t\e[32m %3d\e[0m\n " $custom_ping

I have more pings to run, and this has been shortened to make the code less jumbled than it already is. 我有更多的ping命令可以运行,并且已经缩短了此操作,以使代码的混乱程度不如原来。 Essentially, ping each destination twice, retrieve the packet loss for each, and post all results at the same time, rather than as they become available. 本质上,对每个目的地执行两次ping操作,检索每个目的地的数据包丢失,并同时发布所有结果,而不是在它们可用时发布。

The results I get appear to be the error output (which has been 0) rather than the packet loss. 我得到的结果似乎是错误输出(已为0)而不是数据包丢失。 For custom_ping , which is a controlled test (always returns 100% packet loss), the result is still 0 rather than the 100 these greps should be retrieving. 对于custom_ping (这是一个受控测试(总是返回100%的数据包丢失)),结果仍然为0,而不是应检索的100个数据包。

Running the commands in line with the printf like so: 像这样运行与printf一致的命令:

printf "Google Ping: \t\e[32m %3d\e[0m\n " $(ping -c 2 www.google.com | grep -oP '\d+(?=% packet loss)') &
#etc...

Occasionally works, but more often than not distorts the output by placing ping results next to one another or within one another, etc. Not to mention I need to use the values of the results later to perform certain actions based on how high or low the packet loss is, I will eventually need to pull the milliseconds the packets took as well. 偶尔会起作用,但通常会通过将ping结果彼此相邻或彼此放置等方式扭曲输出。更何况,我需要稍后根据结果的高低来使用结果的值来执行某些操作数据包丢失是,我最终还需要拉出数据包花费的毫秒数。

I have tried different methods of running the pings in parallel; 我尝试了多种并行运行ping的方法。 including using the backticks in place of $( ) and redirecting the output via 2>$1 . 包括使用反引号代替$( )并通过2>$1重定向输出。 I want to avoid using temporary files as much as possible, if at all. 我想尽可能避免使用临时文件。

Is there another method that would be more efficient? 还有另一种方法会更有效吗? Or perhaps a way to place all of the ping results from one site into a variable and use a command or function similar to grep to extract the information I need? 还是一种将来自一个站点的所有ping结果放入一个变量,并使用类似于grep的命令或函数来提取我需要的信息的方法?

For reference, the entire script is located on pastebin here . 作为参考,整个脚本位于此处的 pastebin上。

There is simply no way of doing what you want to do without using something like a temporary file. 如果不使用临时文件之类的方法,根本无法做您想做的事情。 (Or similar semi-persistent storage like memcached or redis.) Fortunately, all of those solutions are reasonably fast. (或类似的半永久性存储,如memcached或redis。)幸运的是,所有这些解决方案都相当快。 There's a good chance that your /tmp directory is actually a ramdisk, and if not, you could make one or use one of the in-memory cache solutions. 您的/tmp目录实际上是一个虚拟磁盘,如果没有,您可以制作一个或使用一种内存缓存解决方案。

The command you're using: 您正在使用的命令:

var=$(pipeline) &

causes var=$(pipeline) to be run in a background subshell. 使var=$(pipeline)在后台子shell中运行。 In that shell, the pipeline will be executed and its output captured by the subshell's $var . 在该外壳中,将执行管道,并通过子外壳的$var捕获其输出。 But that's not useful, since the subshell is about to terminate, taking its variables with it. 但这没有用,因为子外壳将要终止,并带有其变量。

You could put the & inside the $(...) , in which case the value will be assigned to $var in the outer shell. 您可以将&放在$(...) ,在这种情况下,值将在外壳中分配给$var But the command substitution $(pipeline&) will wait for pipeline , which pretty well defeats the purpose of running pipeline in the background. 但是命令替换$(pipeline&)wait pipeline ,这完全违背了在后台运行pipeline的目的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM