我正在编写一个名为perl5i的perl模块。它的目标是在一个模块中修复一系列常见的Perl问题(使用许多其他模块)。
要在命令行中调用它,您可以这样写:perl -Mperl5i -e 'say "Hello"',我认为这太冗长了,所以我想提供一个perl5i包装器,这样您就可以编写perl5i -e 'say "Hello"'了。我还希望人们能够用#!/usr/bin/perl5i编写脚本,所以它必须是编译好的C程序。
我认为我所要做的就是将"-Mperl5i“放在参数列表的前面,然后调用perl。这就是我试过的。
#include <unistd.h>
#include <stdlib.h>
/*
* Meant to mimic the shell command
* exec perl -Mperl5i "$@"
*
* This is a C program so it works in a #! line.
*/
int main (int argc, char* argv[]) {
int i;
/* This value is set by a program which generates this C file */
const char* perl_cmd = "/usr/local/perl/5.10.0/bin/perl";
char* perl_args[argc+1];
perl_args[0] = argv[0];
perl_args[1] = "-Mperl5i";
for( i = 1; i <= argc; i++ ) {
perl_args[i+1] = argv[i];
}
return execv( perl_cmd, perl_args );
}Windows使这种方法变得更加复杂。显然,Windows中的程序没有传递一组参数,它们将所有参数作为单个字符串传递,然后进行自己的解析!因此,像perl5i -e "say 'Hello'"这样的东西就变成了perl -Mperl5i -e say 'Hello',而Windows不能处理缺少引用的问题。
那么,我该如何处理呢?在Windows上用引号和转义符将所有内容括起来?有没有图书馆帮我处理这件事?有没有更好的方法?我能不能不在Windows上生成一个C程序,然后把它写成一个perl包装器,因为它不支持#!不管怎么说?
更新:更清楚的是,这是随附的软件,因此需要使用特定外壳或调整外壳配置(例如alias perl5i='perl -Mperl5i')的解决方案不能令人满意。
发布于 2009-07-07 23:20:52
对于Windows,请使用批处理文件。
perl5i.bat
@echo off
perl -Mperl5i %*%*是减去%0后的所有命令行参数。
在Unixy系统上,一个类似的shell脚本就足够了。
更新:
我认为这是可行的,但我不是shell向导,我也没有现成的*nix系统可供测试。
perl5i
#!bash
perl -Mperl5i $@再次更新:
好了!现在我正确地理解了你的#!注释。我的shell脚本可以从命令行界面运行,但不能在#!行中运行,因为#!foo要求foo是一个二进制文件。
忽略以前的更新。
看起来Windows把一切都复杂化了。我认为你最好是使用一个批处理文件。
你可以use a file association,把.p5i和perl -Mperl5i %*联系起来。当然,这意味着在注册表中胡乱操作,最好避免使用IMO。最好在文档中包含有关如何手动添加关联的说明。
又一次更新
您可能想看看parl是如何做到这一点的。
发布于 2009-07-08 13:15:39
我无法重现你所描述的行为:
/* main.c */
#include <stdio.h>
int main(int argc, char *argv[]) {
int i;
for (i = 0; i < argc; i++) {
printf("%s\n", argv[i]);
}
return 0;
}
C:\> ShellCmd.exe a b c
ShellCmd.exe
a
b
c这是在Visual Studio 2005中实现的。
发布于 2009-07-08 15:20:59
Windows总是奇特的情况。就我个人而言,我不会尝试为Windows环境异常编写代码。一些替代方案是使用"bat包装器“或ftype/assoc注册表hacks作为文件扩展名。
Windows在从DOS命令shell运行时会忽略shebang行,但在Apache for Windows中对Perl执行CGI时却使用它。我厌倦了直接在我的web程序中编写#!c:/perl/bin/perl.exe,因为在迁移到*nix环境时会出现可移植性问题。相反,我在我的工作站上创建了一个c:\usr\bin目录,并从其默认位置复制了perl.exe二进制文件,对于AS Perl,通常是c:\perl\bin,对于Strawberry Perl,通常是c:\strawberry\perl\bin。因此,在Windows的web开发模式下,我的程序在迁移到Linux/UNIX webhost时不会崩溃,而且我可以使用标准的shebang行"#!/usr/bin/perl -w“,而不必在部署之前抓狂。:)
在DOS命令行管理程序环境中,我要么显式地设置路径,要么使用嵌入式开关-Mperl5i创建一个指向实际perl.exe二进制文件的ftype。shebang行被忽略。
ftype p5i=c:\strawberry\perl\bin\perl.exe -Mperl5i %1 %*
assoc .pl=p5i然后,在DOS命令行中,你可以直接调用"program.pl“来代替"perl -Mperl5i program.pl”
因此,只需输入Perl程序本身的名称,"say“语句就可以在5.10中工作,并且它也可以接受数量可变的命令行参数。
https://stackoverflow.com/questions/1095309
复制相似问题