具有带空格的命令行参数的 Perl 脚本
Posted
技术标签:
【中文标题】具有带空格的命令行参数的 Perl 脚本【英文标题】:Perl script that has command line arguments with spaces 【发布时间】:2009-08-12 18:19:29 【问题描述】:我觉得我在这里遗漏了一些非常明显的东西,但我似乎无法弄清楚发生了什么。我有一个从 C 代码调用的 perl 脚本。脚本 + 参数是这样的:
my_script "/some/file/path" "arg" "arg with spaces" "arg" "/some/other/file"
当我在 Windows 中运行它时,Perl 正确地将它识别为 5 个参数,而当我在 SunOS Unix 机器上运行它时,它识别出 8 个,将带有空格的 arg 分割成单独的 args。
不确定它是否有任何区别,但在 Windows 中我的运行方式如下:
perl my_script <args>
在 Unix 中,我只是将其作为可执行文件运行,如上所示。
知道为什么 Unix 没有正确管理该参数吗?
编辑:
下面是调用perl脚本的代码:
char cmd[1000];
char *script = "my_script";
char *argument = "\"arg1\" \"arg2\" \"arg3 with spaces\" \"arg4\" \"arg5\"";
sprintf( cmd, "%s %s >1 /dev/null 2>&1", script, arguments);
system( cmd );
不完全是这样,因为我更动态地构建参数字符串,但这就是要点。
另外,这是我读取参数的代码:
($arg1, $arg2, $arg3, $arg4, $arg5) = @ARGV;
我知道这太天真了,但是这个脚本只能从 C 应用程序中运行,所以不需要更复杂的。
【问题讨论】:
请提供在 Unix 中用于从 C 代码调用 perl 脚本的确切代码。 请提供更多关于如何加载参数字符串的细节。我相信您的问题出在该代码中。 我很确定它不是...我在其中放置了一些调试代码,它会在调用系统之前输出该 cmd,这正是我最初发布的内容。 【参考方案1】:大概
system("my_script \"/some/file/path\" \"arg\" \"arg with spaces\" \"arg\" \"/some/other/file\");
导致一切都通过 bash (因为需要解释 shebang 行,吃掉你传递的引号)。同样,据推测,可以通过直接调用 perl
而不是依靠 shell 来找到它来避免该问题(尽管如果路径上的 perl
与 shebang 行上提供的不同,这可能是一个问题) .
更新:
鉴于您的:
char *argument = "\"arg1\" \"arg2\" \"arg3 with spaces\" \"arg4\" \"arg5\"";
你可能想试试:
char *argument = "\\\"arg1\\\" \\\"arg2\\\" \\\"arg3 with spaces\\\" \\\"arg4\\\" \\\"arg5\\\"";
另一个更新:
感谢您接受我的回答,但是,我的整个理论可能是错误的。
我在GNU bash, version 4.0.28(2)-release (i686-pc-linux-gnu)
中尝试了上述argument
的双重反击版本,结果通过了
而原来的 argument
就像一个魅力。我对此感到有些困惑。也许 SUN 上的 shell 不是 bash
或者可能有其他事情发生。
【讨论】:
嗯,这似乎是问题所在。当我更新 Unix cmd 以实际调用 perl 时,它完全符合我的预期。我仍然不确定为什么它不起作用,尤其是考虑到 Juliano 的复制尝试。那好吧。至少它有效。【参考方案2】:您是否忘记了 SunOS 上的引号?
如果你这样做
perl script arg1 arg2 "arg3 with spaces" arg4 arg5
你应该很好。否则,请尝试切换 shell。
【讨论】:
【参考方案3】:现在问题已更新,我仍然无法重现您的结果:
~% cat test.c
#include <stdio.h>
#include <stdlib.h>
int main(void)
char cmd[1000];
char *script = "./my_script";
char *arguments = "\"arg1\" \"arg2\" \"arg3 with spaces\" \"arg4\" \"arg5\"";
sprintf( cmd, "%s %s", script, arguments);
system( cmd );
return 0;
~% cat my_script
#!/usr/bin/perl
($arg1, $arg2, $arg3, $arg4, $arg5) = @ARGV;
print "arg1 = $arg1\n";
print "arg2 = $arg2\n";
print "arg3 = $arg3\n";
print "arg4 = $arg4\n";
print "arg5 = $arg5\n";
~% gcc test.c
~% ./a.out
arg1 = arg1
arg2 = arg2
arg3 = arg3 with spaces
arg4 = arg4
arg5 = arg5
~%
您的配置还有其他问题。
上一个答案:
Unix shell 解释带引号的参数 作为一个单一的论点。你可以做一个 快速测试:
for i in a b "c d e" f; do echo $i; done
结果如你所愿 be: "c d e" 被视为一个单一的 论据。
我认为你有问题 脚本,在参数处理中 逻辑。
【讨论】:
【参考方案4】:SunOS 内核对 shebang 解释器的处理是否可能非常糟糕?尝试将其作为“/path/to/perl script args
”而不是“script args
”运行,看看是否有任何变化。
【讨论】:
以上是关于具有带空格的命令行参数的 Perl 脚本的主要内容,如果未能解决你的问题,请参考以下文章