最佳 Awk 命令

问题描述 投票:0回答:13

我发现 AWK 非常有用。 这是我用来操作数据的单行代码。

ls | awk '{ print "awk " "'"'"'"  " {print $1,$2,$3} " "'"'"'"  " " $1 ".old_ext > " $1    ".new_ext"  }' > file.csh

我使用此 AWK 制作了一个脚本文件,该文件将重命名一些文件并仅打印出选定的列。 有人知道更好的方法吗? 你最好的 AWK 单行或巧妙的操作是什么?

awk
13个回答
8
投票

AWK 书 充满了很棒的示例。它们过去是从 Kernighan 的网页 收集下载的(现在是 404)。


3
投票

您可以在这里找到几款漂亮的单衬。


2
投票

我用这个:

df -m | awk '{p+=$3}; END {print p}'

计算系统上跨文件系统使用的所有磁盘空间的总和。


2
投票

很多年前我用 awk 写了一个 tail 脚本:

#!/usr/bin/awk -f
BEGIN {
  lines=10
}

{
  high = NR % lines + 1
  a[high] = $0
}

END {
  for (i = 0; i < lines; i++) {
    n = (i + high) % lines + 1
    if (n in a) {
      print a[n]
    }
  }
}

我知道这很愚蠢,但这就是 awk 对你所做的。玩起来非常有趣。


1
投票

Henry Spencer 在 awk 上编写了一个相当好的 nroff 实现。 他称之为“awf”。 他还声称,如果 Larry Wall 知道 awk 有多强大,他就不需要发明 perl。


1
投票

这是我经常使用的几个 awks...请注意,您可以使用 $1、$2 等来获取您想要的列。 因此,为了操作一堆文件,例如,您可以使用一个愚蠢的命令来代替 mv ...

ls -1 *.mp3 | awk '{printf("mv %s newDir/%s\n",$1,$1)}' | /bin/sh

或者,如果您正在查看一组流程,也许......

ps -ef | grep -v username | awk '{printf("kill -9 %s\n",$2)}' | /bin/sh

非常微不足道,但你可以看到这会给你带来什么好处。 =) 我以前做的大部分事情都可以使用 xargs,但是嘿,谁需要它们新的命令?


1
投票

我经常使用这个脚本来编辑 PATH 和类似路径的环境变量。 用途:

export PATH=$(clnpath /new/bin:/other/bin:$PATH /old/bin:/other/old/bin)

此命令在 PATH 前面添加 /new/bin 和 /other/bin,从 PATH 中删除 /old/bin 和 /other/old/bin(如果存在 - 如果不存在则不会出现错误),并删除路径上的重复目录条目.

:   "@(#)$Id: clnpath.sh,v 1.6 1999/06/08 23:34:07 jleffler Exp $"
#
#   Print minimal version of $PATH, possibly removing some items

case $# in
0)  chop=""; path=${PATH:?};;
1)  chop=""; path=$1;;
2)  chop=$2; path=$1;;
*)  echo "Usage: `basename $0 .sh` [$PATH [remove:list]]" >&2
    exit 1;;
esac

# Beware of the quotes in the assignment to chop!
echo "$path" |
${AWK:-awk} -F: '#
BEGIN       {       # Sort out which path components to omit
                    chop="'"$chop"'";
                    if (chop != "") nr = split(chop, remove); else nr = 0;
                    for (i = 1; i <= nr; i++)
                            omit[remove[i]] = 1;
            }
{
    for (i = 1; i <= NF; i++)
    {
            x=$i;
            if (x == "") x = ".";
            if (omit[x] == 0 && path[x]++ == 0)
            {
                    output = output pad x;
                    pad = ":";
            }
    }
    print output;
}'

0
投票

统计httpd使用的内存

ps -ylC httpd | awk '/[0-9]/ {SUM += $8} END {print SUM/1024}'

或任何其他进程替换httpd。除以 1024 即可得到以 MB 为单位的输出。


0
投票

我设法为 UNIX 构建了一个 DOS 树命令模拟器(find + awk):

find . -type d -print 2>/dev/null|awk '{for (i=1;i< NF;i++)printf("%"length($i)"s","|");gsub(/[^\/]*\//,"--",$0);print $NF}'  FS='/'

0
投票

打印两个图案之间的线条:

awk '/END/{flag=0}flag;/START/{flag=1}' inputFile

详细解释:http://nixtip.wordpress.com/2010/10/12/print-lines- Between-two-patterns-the-awk-way/


0
投票

几个最喜欢的,本质上彼此无关。 读作 2 个不同的、互不相关的建议。

轻松识别列号

对于那些经常使用 awk 的人来说,就像我在工作中进行日志分析一样,我经常发现自己需要找出文件的列号。 因此,如果我正在分析 Apache 访问文件(可以在此处找到一些示例),我会针对该文件运行以下脚本:

NR == 1 {
        for (i = 1 ; i <= NF ; i++)
                {
                print i "\t" $i
                }
        }
NR > 1  {
        exit
        }

我通常将其称为“cn.awk”,表示“列数”。 有创意吧? 无论如何,输出看起来像:

1   64.242.88.10
2   -
3   -
4   [07/Mar/2004:16:05:49
5   -0800]
6   "GET
7   /twiki/bin/edit/Main/Double_bounce_sender?topicparent=Main.ConfigurationVariables
8   HTTP/1.1"
9   401
10  12846

很容易分辨什么是什么。 我通常在我的服务器上使用它的别名并将其放在各处。


按名称引用字段

现在,假设您的文件有标题行,并且您宁愿使用这些名称而不是字段编号。 这允许您这样做:

NR == 1 {
    for (i = 1 ; i <= NF ; i++)
        {
        field[$i] = i
        }
    }

现在,假设我有这个标题行...

metric,time,val,location,http_status,http_request

...我想对

val
列进行求和。 我可以通过名称来引用它,而不是引用 $3:

NR > 1  {
    SUM += $field["val"]
    }

主要好处是使脚本更具可读性。


0
投票

打印字段是大多数 AWK 教程中首先提到的事情之一。

awk '{print $1,$3}' file

鲜为人知但同样有用的是排除也是可能的字段:

awk '{$1=$3=""}1' file

0
投票

如果您只想打印奇数行而不进行任何除法或取模:

jot 20 | awk '_=!_'  

1
3
5
7
9
11
13
15
17
19
© www.soinside.com 2019 - 2024. All rights reserved.