New FAMILUG

The PyMiers

Monday 3 March 2014

awk và cut

Các tiện ích UNIX (UNIX utilities) thường nhận đầu vào là text, và output ra cũng là text. Để các chương trình nối lại được với nhau, tức dùng output của chương trình này làm imput cho chương trình kia, người ta sử dụng pipeline (" | ").

Cũng vì điều nói trên, mà việc bóc tách dữ liệu từ output của 1 chương trình là cần thiết, bởi 1 chương trình có thể sinh ra nhiều dòng text, trong khi bạn chỉ cần 1 dữ liệu nào đó trong đống text đấy. Bạn có thể copy bằng tay, nhưng bạn sẽ không muốn làm như thế nếu phải làm 1000 lần, okay?

2 trong số nhiều công cụ phục vụ mục đích trên là "cut" và "awk", mục đích chính (được dùng nhiều nhất) là dùng để cắt theo cột. Các ví dụ sau sẽ minh họa tính năng của cut và awk

$ echo "one/two/three" | cut -d'/' -f1
one
$ echo "one/two/three" | cut -d'/' -f2
two
$ echo "one/two/three" | cut -d'/' -f3
three
$ echo "one/two/three" | cut -d'/' -f2-
two/three
$ echo "one:two:three" | cut -d':' -f2-
two:three
$echo "/one/two/three" | cut -d'/' -f2
one

Và awk

hvn@lappy: ~ () $ echo "one:two:three" | awk -F':' '{print $1}'
one
hvn@lappy: ~ () $ echo "one:two:three" | awk -F':' '{print $1}'
one
hvn@lappy: ~ () $ echo "one:two:three" | awk -F':' '{print $2}'
two
hvn@lappy: ~ () $ echo "one:two:three" | awk -F':' '{print $1 $2}'
onetwo

Từ các output nói trên, hãy nhớ rằng cut và awk đều coi vị trí số 1 là vị trí trước "separator" đầu tiên (separator được chỉ định bởi -d với cut và -F với awk)


awk có thể cho ra những output phức tạp hơn, bởi AWK là một ngôn ngữ lập trình. Thậm chí nó có thể làm phép tính:

$ echo '1/2/3/4' | awk -F'/' '{print $3 - $1}'
2
$ echo '1/2/3/4' | awk -F'/' '{print $3 * $2}'
6
Chỉ với 2 lệnh cơ bản trên, đã đủ để bạn có thể bóc tách những dữ liệu mình cần theo cột.

Hết.

1 comment:

  1. field separator với awk và cut đều không cần "quote", trừ khi nó là những ký tự đặc biệt đối với bash.

    Vì vậy ở các câu lệnh trên:
    cut -d':' có thể viết là cut -d:
    tương tự với awk.

    Một ví dụ khi cần phải quote:

    # echo "meo'meo" | cut -d' -f1 #không chạy được do với bash, dấu ' cần phải có một dấu ' tương ứng để đóng
    > ^C
    # echo "meo'meo" | cut -d"'" -f1
    meo

    ReplyDelete