0

问题:比较特定参数的节点的预检查状态和后检查状态的文件。

在社区的一些帮助下,我编写了以下解决方案,该解决方案根据“节点 ID”(它恰好是唯一的,也将从文件中提取)从目录中的文件中提取信息。从 Pre/post 文件夹中提取数据后,我根据节点 ID 创建了文件夹并将文件转储到文件夹中。

我的代码来提取数据(数据是从 Pre 和 Post 文件夹中提取的)

FILES=$(find postcheck_logs -type f -name *.log)
for f in $FILES
do
    NODE=`cat $f | grep -m 1 ">" | awk '{print $1}' | sed 's/[>]//g'`  ##Generate the node-id
    echo "Extracting Post check information for " $NODE 
    mkdir temp/$NODE-post  ## create a temp directory
    cat $f | awk 'BEGIN { RS=$NODE"> "; } /^param1/ { foo=RS $0; } END { print foo ; }' > temp/$NODE-post/param1.txt ## extract data
    cat $f | awk 'BEGIN { RS=$NODE"> "; } /^param2/ { foo=RS $0; } END { print foo ; }' > temp/$NODE-post/param2.txt
    cat $f | awk 'BEGIN { RS=$NODE"> "; } /^param3/ { foo=RS $0; } END { print foo ; }' > temp/$NODE-post/param3.txt
done

在此之后,我的结构如下:

/Node1-pre/param1.txt
/Node1-post/param1.txt

等等。

现在我坚持比较$NODE-pre$NODE-post归档,

我曾尝试使用递归 grep 来做到这一点,但我没有找到合适的方法来做到这一点。使用 diff 比较这些文件的最佳方法是什么?

此外,我发现上述数据提取程序非常慢。我相信这不是最好的方法(使用最少的资源)这样做。有什么建议么?

4

1 回答 1

3

看看任何实例cat one-file——你可以在管道中的下一个命令上使用 I/O 重定向。

您可以通过以下方式更简单地完成整个操作:

for f in $(find postcheck_logs -type f -name *.log)
do
    NODE=$(sed '/>/{ s/ .*//; s/>//g; p; q; }' $f)  ##Generate the node-id
    echo "Extracting Post check information for $NODE" 
    mkdir temp/$NODE-post
    awk -v NODE="$NODE" -v DIR="temp/$NODE-post" \
        'BEGIN { RS=NODE"> " }
         /^param1/ { param1 = $0 }
         /^param2/ { param2 = $0 }
         /^param3/ { param3 = $0 }
         END {
             print RS param1 > DIR "/param1.txt"
             print RS param2 > DIR "/param2.txt"
             print RS param3 > DIR "/param3.txt"
             }' $f
done

通过单个sed命令完成 NODE 查找过程要比 . 好得多cat | grep | awk | sed,您应该计划在$(...)任何地方使用反引号而不是反引号。

日志文件的主要处理应该做一次;一个awk命令就足够了。脚本被传递给变量——节点和目录名。BEGIN 被清理;之前的$节点可能不是您想要的。主要动作非常相似;每个都查找相关的参数名称并将其保存在适当的变量中。最后,它将保存的值写入相关文件,并用 RS 的值进行修饰。仅当一行中有多个语句时才需要分号;在这个扩展脚本中,每行只有一个语句。它看起来比原版大,但这只是因为我使用的是垂直空间。


至于比较前后文件,您可以通过多种方式进行比较,具体取决于您想知道的内容。如果你有一个 POSIX 兼容的diff(你可能有),你可以使用:

diff -r temp/$NODE-pre temp/$NODE-post

报告两个目录内容之间的差异(如果有)。或者,您可以手动执行此操作:

for file in param1.txt param2.txt param3.txt
do
    if cmp -s temp/$NODE-pre/$file temp/$NODE-post/$file
    then : No difference
    else diff temp/$NODE-pre/$file temp/$NODE-post/$file
    fi
done

显然,您可以将其包装在“for each node”循环中。而且,如果您需要这样做,那么您可能确实希望find在变量中捕获命令的输出(如在原始代码中),这样您就不必重复该操作。

于 2012-07-22T15:04:42.583 回答