【问题标题】:Suppress output to StdOut when piping echo管道回声时抑制输出到 StdOut
【发布时间】:2012-04-24 19:20:21
【问题描述】:

我正在制作一个 bash 脚本,它会爬取目录并将特定类型的所有文件输出到文本文件中。我已经开始工作了,它还会向控制台输出一堆我不想要的输出(文件名)

这是到目前为止的相关代码,tmpFile 是我正在写入的文件:

for DIR in `find . -type d` # Find problem directories
do
        for FILE in `ls "$DIR"` # Loop through problems in directory
        do
                if [[ `echo ${FILE} | grep -e prob[0-9]*_` ]]; then
                        `echo ${FILE} >> ${tmpFile}`
                fi
        done
done

我放入文本文件的文件采用正则表达式 prob[0-9]*_ 描述的格式(类似于 prob12345_01)

我将 echo ${FILE} 的输出通过管道传输到 grep 中,它仍然输出到 stdout,这是我想避免的。我认为这是一个简单的解决方法,但它正在逃避我。

【问题讨论】:

  • 迭代find 输出的安全方法是find ... -print0 | while read -r -d "" DIRDon't parse ls,使用for FILE in "$DIR"/*。从echo ${FILE} >> ${tmpFile} 行中删除反引号。

标签: bash unix echo pipe


【解决方案1】:

所有这些都可以在一个 find 命令中完成。考虑一下:

find . -type f -name "prob[0-9]*_*" -exec echo {} >> ${tmpFile} \;

编辑:

更简单:(感谢 @GlennJackman

find . -type f -name "prob[0-9]*_*" >> $tmpFile

【讨论】:

  • 我很喜欢这个解决方案,并且我看到了它是如何工作的,但是它生成了两个文件,两个文件都不包含正确的数据。 tmpfile var 实际上只是 TMP_COUNTER,我得到的文件是 TMP_COUNTER 和 TMP_COUNTER; (唯一的区别是分号) 编辑:忽略上述,修复。现在文件只是空的。
  • 你可以试试:find . -type f -name "prob[0-9]*_*" -exec echo {} >> ${tmpFile} \;
  • 你甚至不需要-exec: find . -type f -name "prob[0-9]*_*" -print >> $tmpFile
  • @glennjackman:同意,我不应该在那里使用 exec。已编辑。
  • @glennjackman:我什至删除了-print,因为它默认就在那里。
【解决方案2】:

要回答您的具体问题,您可以将-q 传递给 grep 以进行静默输出。

if echo "hello" | grep -q el; then
  echo "found"
fi

但由于您已经在使用 find,因此只需一个命令即可完成:

find . -regex ".*prob[0-9]*_.*" -printf '%f\n' >> ${tmpFile}

find 的正则表达式在整个路径上都是匹配的,这就是为什么需要前导和尾随 .*

-printf '%f\n' 打印不带目录的文件名,以匹配您的脚本正在执行的操作。

【讨论】:

    【解决方案3】:

    你想要做的是,readfind 命令的输出,
    对于返回的每个条目 find,您希望获取该位置下的所有 (*) 文件
    然后您要检查该文件名是否与您想要的模式匹配
    如果匹配,则将其添加到 tmpfile

    while read -r dir; do
        for file in "$dir"/*; do  # will not match hidden files, unless dotglob is set
            if [[ "$file" =~ prob[0-9]*_ ]]; then
                echo "$file" >> "$tmpfile"
            fi
    done < <(find . -type d)
    

    但是 find 可以单独做到这一点
    阿努巴瓦把我带到了那里;)
    所以看看他的回答是怎么做的

    【讨论】: