【问题标题】:Awk not working inside a perl scipt?awk 不能在 perl 脚本中工作?
【发布时间】:2015-04-25 21:48:54
【问题描述】:

我试图在 perl 脚本中执行下面的 awk 命令,但它失败了。

#!/usr/bin/perl

print `awk -F, '{print $NF}' f1.txt > f2.txt`

这是错误:

syntax error at ./MO.pl line 3, near "print"
Execution of ./MO.pl aborted due to compilation errors.

谁能帮助我在这里做错了什么?

【问题讨论】:

  • 你可能需要转义$NF --> 说\$NF
  • 我建议在这种情况下 - 鉴于您对 awk 的操作不多,最好将其保留在 perl 中。
  • 为什么我们看到这么多问题询问如何从 perl(和 python)运行 awk 脚本?我认为 perl 至少可以做 awk 可以做的相同的文本操作操作,这是错误的吗?
  • @EdMorton,你说的很对。
  • 我会说是那些了解 shell 和 awk 并开始学习 perl 的人——他们坚持使用他们知道的习语,而不是双脚跳入新语言。

标签: perl awk


【解决方案1】:

这是一个 Perl 错误,与您的 awk 脚本本身无关。当 previous 语句末尾没有分号时,通常会出现该错误。

这是一个非常简单的程序(应该包括use strict;use warnings;,但我想模仿你所拥有的)。

#! /usr/bin/env perl
#

print "Hello, World\n"  # Line 4
print "Hello, Back\n";  # Line 5

错误信息是:

syntax error at test.pl line 5, near "print"
Execution of test.pl aborted due to compilation errors.

请注意,错误接近第 5 行中的 print,但错误实际上位于第 4 行的末尾,我缺少分号。

在我的系统上运行您的确切程序可以正常工作(尽管不能完全产生您想要的结果)。我假设这不是您的确切程序,而是您的程序的简化。之前有没有声明print

其他几件事:

  • 您正在重定向您的 awk 输出,因此 print 没有任何内容。
  • 使用 strictwarnings
  • 使用qx(....) 比使用反引号(重音)更好。它更具可读性,并允许您在引用的可执行文件中执行引用的可执行文件。
  • 注意代码中的 Perliss。 $NF 由 Perl 解释,没有 use strict;,不会给您错误。相反,您的 Awk 语句中的 print 是一个空打印,它打印整行。
  • 如果没有打印出来,为什么要使用print?你最好在这个位置使用system,它允许你在整个语句周围加上单引号:

    system q(awk -F, '{print $NF}' f1.txt > f2.txt);

    这样,$NF 就不必被引用了。

  • 你为什么在 Perl 程序中使用Awk? Perl 会做任何 awk 会做的事情,并且做得更好:

这是你的程序使用纯 ol' Perl 的版本:

#! /usr/bin/env perl

use strict;
use warnings;
use autodie;

while ( my $line = <> ) {
    my @array = split /\s*,\s*/, $line;
    print $array[-1];
}

要运行这个程序:

$ test.pl f1.txt > f2.txt

是的,它更长,但是程序的一半被所有 Perl 程序都应该使用的pragmas 占用。

我相信比我聪明的人可以把它变成 Perl 单行代码。

【讨论】:

    【解决方案2】:

    由于您正在重定向 awk 输出,因此 perl 没有可打印的内容。您不妨使用systemquoting operator q()

    system q(awk -F, '{print $NF}' f1.txt > f2.txt)
    

    或者,当然,在 perl 中执行,这样您就不必生成 shell,然后生成 awk:

    open my $in, '<', 'f1.txt';
    open my $out, '>', 'f1.txt';
    while (<$in>) {
        print $out (split " ")[-1], "\n";
    }
    close $in;
    close $out;
    

    【讨论】:

      【解决方案3】:

      如果脚本中有更多行,则需要在 print 语句的末尾加上分号。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2015-11-08
        • 2012-05-30
        • 1970-01-01
        • 2012-10-15
        • 2011-05-19
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多