嗯,我想你可以在这个平台上找到几十个关于如何管道的问题find
输出到sed
,但到目前为止我还没有找到任何相反方向的东西。我想做的是修改我的输入, 和然后将其传递给find
.
假设我想做类似以下的事情,以避免输入那些繁琐的星号通配符,从而使自己的生活更轻松。 (我希望很明显,这里字符串运算符后面的表达式<<<
最终计划被参数替换,例如$1
,在稍后的脚本中。下面的行仅用于演示。)
$ sed 's/ /\*/g' <<< ' foo bar baz ' | find . -type f -iname -
-
这句台词的结尾实际上是应该使用 的输出sed
作为 的输入find
;然而,将该find
部分扩展到
... find -D tree . -type f -iname - ...
显示该参数是不是传递到find
.也许您find
根本无法使用管道传递预处理的输入?
答案1
find
不从标准输入获取参数,而是从命令行获取参数,因此:
find . -iname "$(sed 's/ /\*/g' <<< ' foo bar baz ')"
那将变成:
find . -iname "foo*bar*baz*"
(引号是阻止 shell 扩展通配符 foo*bar*baz* 所必需的)
这可能是也可能不是您希望得到的。例如,如果您确实想要以 foo、bar 或 baz 开头的文件,而不是与模式“foo*bar*baz*”匹配的文件,那么您需要构造一个正则表达式并使用-regex
or-iregex
而不是-iname
。或者构建一个更复杂的查找命令,例如-iname 'foo*' -o -iname 'bar*' -o -iname 'baz*'
或者:
PATTERN='foo bar baz'
PATTERN=$(echo "$PATTERN" | sed -e 's/ /*/g')
# and/or do whatever else you need to do to transform $PATTERN to be what
# you need it to be...
find . -iname "$PATTERN"
这是 bash 脚本中的一行代码。它在脚本中的工作方式与在命令行中的工作方式完全相同。
$ cat ./test.sh
#! /bin/bash
find . -iname "$(sed 's/ /\*/g' <<< ' foo bar baz ')"
$ ls -l
total 4
-rw-r--r-- 1 cas cas 0 Sep 26 16:53 doesntmatch
lrwxrwxrwx 1 cas cas 16 Sep 26 16:59 symlink -> xfoo-ybar-zbaz01
-rwxr-xr-x 1 cas cas 69 Sep 26 16:50 test.sh
-rw-r--r-- 1 cas cas 0 Sep 26 16:50 xfoo-ybar-zbaz01
-rw-r--r-- 1 cas cas 0 Sep 26 16:50 xfoo-ybar-zbaz02
-rw-r--r-- 1 cas cas 0 Sep 26 16:50 xfoo-ybar-zbaz03
$ ./test.sh
./xfoo-ybar-zbaz01
./xfoo-ybar-zbaz03
./xfoo-ybar-zbaz02
$ find . -iname "$(sed 's/ /\*/g' <<< ' foo bar baz ')"
./xfoo-ybar-zbaz01
./xfoo-ybar-zbaz03
./xfoo-ybar-zbaz02
$ find . -iname "*foo*bar*baz*"
./xfoo-ybar-zbaz01
./xfoo-ybar-zbaz03
./xfoo-ybar-zbaz02
答案2
为什么不使用for循环呢?
for n in $(sed 's/ /\*/g' <<< ' foo bar baz '); do find . -iname $n; done