我一般不使用 Solaris,但今天我需要编写一个 find 命令来使用 shell 对已识别的文件执行操作。我发现这些{}
角色没有被替换,也找不到替代品。
例如:
bash-3.2# find / -exec sh -c "echo {}" \;
这会导致它打印{}
每个文件而不是文件名。
答案1
唯一标准的使用方法是作为单独的参数find -exec …
传递。{}
参数包含时的行为{}
不是标准化的。看来您已经习惯了{}
在子字符串中替换的 GNU 行为。find
Solaris 上的命令仅当{}
参数仅包含 时才进行替换{}
。
GNU 行为并不是特别有用,有时甚至很烦人,因为在参数中替换文件名很脆弱。除非您知道文件名的限制,否则无法知道文件名的开始和结束位置。例如,使用 GNU find,find / -exec sh -c "echo {}" \;
确实不是一般打印文件名。它仅在文件名不包含任何 shell 特殊字符时打印文件名。如果您在包含名为 的文件的目录中运行它;rm -r ~
,请与您的文件说再见。
调用 shell 的可靠(且可移植)方法find -exec
是将文件名作为参数传递给 shell。
find … -exec sh -c 'echo "$0"' {} \;
在大多数情况下,您可以批量传递参数并在 shell 中迭代参数。速度有点快了。请注意,shell 代码后面的第一个参数是$0
which 不包含在"$@"
.
find … -exec sh -c 'for x; do echo "$x"; done' _ {} +
答案2
正如手册页和标准中所写,{}
必须位于单独的参数中。
find / -exec sh -c 'echo $1' dummy '{}' \;
按预期工作。
请注意,该参数dummy
是必需的,因为 shell 会在命令参数sh -c cmd
变为 to之后分配第一个参数$0
,而下一个参数则变为$1
。