假设 'identify filename' 本身就是一个命令,那么我认为您需要为此使用 Perl。以最好的 Perl 神秘风格:
while (<>)
{
s/#(\w+)#/my $x = qx%identify $1%; chomp $x; $x/e;
print;
}
这会将一行输入('<>')读入隐式变量'$_';下一行对隐式变量应用替换操作 - 稍后会详细介绍 - 然后 'print' 打印隐式变量。
对于替换操作“s///”,第一部分查找哈希“#”、一系列一个或多个“单词”字符 - 字母数字或下划线 - 以及另一个哈希,使识别的文件名可用作为'$1'。第二部分是替换字符串。第三个斜线之后是修饰符“e”,意思是“将替换作为 Perl 的位执行”。 Perl的相关位是:
my $x = qx%identify $1%; chomp $x; $x
如果哈希标记之间的字符串是“文件名”,则第一部分执行命令“identify filename”,将输出、换行符和所有内容保存在局部变量 $x 中。 'chomp' 操作删除换行符;最后的 '$x' 产生一个值 - 由 'identify' 命令输出的字符串。 (令我惊讶的是,Perl 不允许使用更简单的外观:s/#(\w+)#/chomp qx%identify $1%/e;错误是 'Can't modify quoted execution (``, qx) in chomp at xx.pl line 3, near "qx%identify $1%)"'。)
考虑“识别”命令:
echo "identified file $1 as $PWD/$1"
现在考虑输入行:
abc#def#ghi
输出是:
abcidentified file def as /Users/jleffler/tmp/soq/defghi
(在运行命令时,/Users/jleffler/tmp/soq 恰好是我的当前目录)。
相当不神秘:
while (my $line = <>)
{
if ($line =~ m/#(\w+)#/)
{
my $identity = qx{identify $1};
chomp $identity;
$line =~ s/#\w+#/$identity/;
}
print $line;
}
当然没有那么紧凑,但解释非常相似。
请注意,初始版本可能不是最紧凑的形式。考虑这个版本:
perl -p -e 's/#(\w+)#/my $x = qx%identify $1%; chomp $x; $x/e'
“-p”选项将脚本(“-e”的参数)置于读取、执行、打印循环 (REPL) 中。
这是 Perl 的奇迹之一 - TMTOWTDI(发音为 'tim-toady') - 有不止一种方法可以做到这一点。