使用参数(vars)调用具有awk shebang的脚本

时间:2009-09-13 17:06:58

标签: shell awk shebang

我有一个我已定义的awk脚本:

#!/usr/bin/env awk
BEGIN { if (!len) len = 1; end = start + len }
{ for (i = start; i < end; i++) { print $1 } }

我已将其保存为columnschmod +x。我想调用它,以便在遍历文件时定义startend。我以为这应该有效:

cat some_file | columns -v start=2

但事实并非如此。救命啊!

4 个答案:

答案 0 :(得分:43)

尝试使用:

#!/usr/bin/awk -f

作为翻译

答案 1 :(得分:5)

env是解决此问题的最简单方法:

#!/usr/bin/env -S awk -f

添加更多选项,并确保不干扰您的参数和awk的参数:

#!/usr/bin/env -S awk -F: -f ${_} --
BEGIN {
    # delete argv[1], which == ENVIRON[_]
    delete ARGV[1]
} # rest of my awk program

因为env有一个POSIX标准,所以这个shbang可以让你解决unixen上非标准shbang实现的困难。

修改

写完后,我意识到'-S'是一个非POSIX兼容的FreeBSD env扩展。所以shell包装器可能是要走的路,不幸就是这样。

答案 2 :(得分:0)

以下是此问题的答案 -

#!/bin/awk -f 

答案 3 :(得分:0)

不幸的是,这不容易以便携式方式解决。标准技术如下所示(用/usr/bin/awk替代awk路径):

#!/usr/bin/awk -f

BEGIN { if (!len) len = 1; end = start + len }
{ for (i = start; i < end; i++) { print $1 } }

硬编码的awk路径和非标准的-f标志使它不能在所有* nix上移植。如果您只打算在一台计算机上运行脚本,那么这可能会很好。但是,要制作可移植的awk脚本,您需要将其包装在Shell脚本中。您可以通过以下两种方法在一个文件中进行操作:

第一种方法是标准且易于阅读:

#!/bin/sh

awk '
BEGIN { if (!len) len = 1; end = start + len }
{ for (i = start; i < end; i++) { print $1 } }
' "$@"

不幸的是,这在两个关键方面没有实现:

  1. 如果awk脚本包含一个'字符,则需要这样输入:'"'"'以“转义”它。
  2. 如果您使用的是带有语法突出显示功能的文本编辑器,则不会正确突出显示awk脚本。

另一种解决方案是使用sed剥离sh包装器:

#!/bin/sh
exec awk "$(sed '1,2d' "$0")" "$@"

BEGIN { if (!len) len = 1; end = start + len }
{ for (i = start; i < end; i++) { print $1 } }

这有点像两行shabang标头。它使用第3行下方的文件作为脚本参数来调用awk。这使您可以突出显示漂亮的语法,并且仍然可以使用'字符来表达自己的兴趣。我看到的两个缺点是:

  1. 可以说这是不直观的。
  2. 如果您使用的是代码短毛绒,它可能不是这样。