从 Bourne Shell 执行 TCL 脚本时出现问题(重定向问题)

发布于 2024-07-29 02:35:21 字数 880 浏览 2 评论 0原文

我正在使用 VMD(分子动力学可视化包),我想从 Perl 脚本打开 VMD,运行 Tcl 脚本,将输出打印到日志文件,然后关闭 VMD 并返回到 Perl 脚本。 执行此操作的普通语法是:

system("vmd -dispdev text -eofexit < program.tcl > LOG");

据我所知,其分解如下:

  • system("");:执行引号
  • vmd 中包含的 Bourne Shell 命令:调用 VMD
  • -dispdev text:以文本模式打开 VMD
  • -eofexit:当达到 STDIN 上的 EOF 时终止 VMD
  • prog.tcl:将prog.tcl设置为STDIN; 时终止
  • vmd 将在 prog.tcl 完成> LOG:将 STOUT 写入文件

现在,这可以完美工作,只是我的 Tcl 脚本需要参数。 我想要做的事情是这样的:

system("vmd -dispdev text -eofexit < program.tcl string1 string2 > LOG");

但是,在这种情况下,shell 尝试将 string1 和 string2 作为文件读取。 由于我对重定向的理解有限,我不确定第一行到底发生了什么,第二行到底出了什么问题,或者什么是好的解决方案。 任何帮助,将不胜感激。

I am working with VMD (a molecular dynamics visualization package) and I want to open VMD from a Perl script, run a Tcl script, print the output to a log file, then close VMD and return to the Perl script. The ordinary syntax to do this is:

system("vmd -dispdev text -eofexit < program.tcl > LOG");

which breaks down as follows, as best as I understand:

  • system("");: executes Bourne Shell commands contained in quotes
  • vmd: calls VMD
  • -dispdev text: opens VMD in text mode
  • -eofexit: terminates VMD when EOF on STDIN is reached
  • < prog.tcl: sets prog.tcl as STDIN; vmd will terminate when prog.tcl completes
  • > LOG: writes STOUT to file <LOG>

Now this would work perfectly, except that my Tcl script takes arguments. What I'd like to do is something like:

system("vmd -dispdev text -eofexit < program.tcl string1 string2 > LOG");

however, in this case the shell tries to read string1 and string2 as files. With my limited understanding of redirection, I'm not sure exactly what is going in the first line, what exactly goes wrong in the second, or what a good solution would be. Any help would be appreciated.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

话少情深 2024-08-05 02:35:21

抱歉,当 Tcl 脚本在另一个程序(如 vmd)中执行时,您不认为可以直接将参数传递给 Tcl 脚本。 我建议通过文件传递参数作为解决方法。 例如。
在 Perl 脚本中,在调用 vmd 之前,使用 Tcl 语法将参数写入文件:

open PARAMS, '>myparams.tcl';
print PARAMS "set arg1 $string1; set arg2 $string2";
close PARAMS;

然后在 program.tcl 的开头,不使用命令行参数 ($argv),而是读取参数文件以获取参数价值观:

source myparams.tcl

Sorry, don't think you can pass arguments to your Tcl script directly when its being executed within another program like vmd. I would suggest passing the parameters via a file as a workaround. Eg.
In the Perl script, before calling vmd, write the parameters to a file in Tcl syntax:

open PARAMS, '>myparams.tcl';
print PARAMS "set arg1 $string1; set arg2 $string2";
close PARAMS;

Then at the start of program.tcl, instead of using command line arguments ($argv), have it read the parameter file to pick up the argument values:

source myparams.tcl
2024-08-05 02:35:21

将参数直接传递给 VMD 。

system(vmd -dispdev text -e program.tcl -args string1 string2 > LOG);

您可以通过执行类似确保在 program.tcl 末尾添加 quit 语句的操作,

You can pass the arguments directly to VMD by doing something like

system(vmd -dispdev text -e program.tcl -args string1 string2 > LOG);

Make sure to add a quit statement at the end of program.tcl.

高冷爸爸 2024-08-05 02:35:21

您所做的是将program.tcl 文件的内容发送到vmd,而不是执行程序的输出。 如果我理解你的意思,你想用管道将 Tcl 程序连接到 vmd:

system("program.tcl arg1 arg2 | vmd -... > output.file");

编辑:

因此,如果 vmd 在 stdin 上读取 Tcl 代码,你仍然可以在不使用临时文件的情况下传递参数:

system("( echo 'set arg1 str1; set arg2 str2'; cat program.tcl; ) | vmd ... > output_file");

或者

open my $fh, '<', 'program.tcl';
my @tcl = <$fh>;
close $fh;
unshift @tcl, "set arg1 str1\n", "set arg2 str2\n";
open $fh, '|-', 'vmd ... > output.file' or die 'msg...';
print $fh join('', @tcl);
close $fh or die 'msg...';

What you're doing is sending the contents of the program.tcl file to vmd, not the output of executing the program. If I understand you, you want to connect the Tcl program to vmd with a pipe:

system("program.tcl arg1 arg2 | vmd -... > output.file");

Edit:

So, if vmd reads Tcl code on stdin, you can still pass parameters without using a temp file:

system("( echo 'set arg1 str1; set arg2 str2'; cat program.tcl; ) | vmd ... > output_file");

or

open my $fh, '<', 'program.tcl';
my @tcl = <$fh>;
close $fh;
unshift @tcl, "set arg1 str1\n", "set arg2 str2\n";
open $fh, '|-', 'vmd ... > output.file' or die 'msg...';
print $fh join('', @tcl);
close $fh or die 'msg...';
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文