Lệnh awk toàn tập Image Lệnh awk toàn tập

Bài viết này giới thiệu các bạn cách dùng lệnh awk trên hệ điều hành Linux.

1. Lệnh awk

Ngôn ngữ awk là một ngôn ngữ lập trình giúp chúng ta thao tác dễ dàng với kiểu dữ liệu có cấu trúc và tạo ra những kết quả được định dạng. Nó được đặt tên bằng cách viết tắt các chữ cái đầu tiên của các tác giả: Aho, Weinberger và Kernighan.

Lệnh awk sử dụng để tìm kiếm và xử lý file text. Nó có thể tìm kiếm một hoặc nhiều file để xem các file có dòng nào bao gồm những pattern cần tìm kiếm và sau đó thực hiện những action. Cú pháp của lệnh awk như sau:

awk pattern actions file

Trong đó:

  • pattern: là những biểu thức chính quy
  • actions: là những câu lệnh cần thực hiện
  • file: file cần thực hiện lệnh awk

Cách lệnh awk hoạt động:

  • Lệnh awk đọc file đầu vào theo từng dòng.
  • Đối với mỗi dòng, nó sẽ khớp lần lượt với các pattern, nếu khớp thì sẽ thực hiện action tương ứng. Nếu không có pattern nào được so khớp thì sẽ không có action nào thực hiện.
  • Cú pháp cơ bản làm việc với lệnh awk thì pattern hoặc action phải có 1 trong 2 không thể thiếu cà 2.
  • Nếu không có pattern, awk sẽ thực hiện action đối với mỗi dòng của dữ liệu. Nếu không có action, awk sẽ mặc định in ra tất cả những dòng khớp với pattern đã cho.
  • Mỗi câu lệnh trong phần action được phân tách nhau bởi dấu chấm phẩy.

2. Dùng để in các dòng trong file

Mặc định, lệnh awk sẽ in ra từng dòng của file. Cú pháp như sau:

awk '{print}' file.txt 

Ví dụ: Dùng lệnh awk in các dòng trong file:

[root@test1 ~]# cat file.txt
fruit   qty
apple   42
banana  31
fig     90
guava   6
[root@test1 ~]# awk '{print}' file.txt
fruit   qty
apple   42
banana  31
fig     90
guava   6

3. Xử lý trường

3.1. Trách trường nhất định

  • $0: Chứa toàn bộ văn bản
  • $1: Chứa văn bản trường đầu tiên
  • $2: chứa văn bản trường thứ hai
  • $(2+3): Kết quả của các biểu thức được sử dụng, đưa ra trường thứ năm
  • NF: là một biến tích hợp có chứa số lượng các trường trong bản ghi hiện tại. Vì vậy $NF đưa ra trường cuối cùng và $(NF-1) sẽ đưa ra trường cuối cùng thứ hai.

Ví dụ:

[root@test1 ~]# cat file.txt
fruit   qty
apple   42
banana  31
fig     90
guava   6
[root@test1 ~]# awk '{print $1}' file.txt
fruit
apple
banana
fig
guava
[root@test1 ~]# awk '{print $2}' file.txt
qty
42
31
90
6

3.2. Chỉ định tách trường đầu vào

Sử dụng tùy chọn -F để chỉnh định tách trường đầu vào

[root@test1 ~]# echo 'foo:123:bar:456' | awk -F: '{print $2}'
123
[root@test1 ~]# echo 'foo:123:bar:456' | awk -F: '{print $NF}'
456
[root@test1 ~]# echo 'foo:123:bar:456' | awk -F: '{print $1, $NF}'
foo 456
[root@test1 ~]# echo 'foo:123:bar:456' | awk -F: '{print $(NF-1)}'
bar
[root@test1 ~]# echo 'one;two;three;four' | awk -F';' '{print $2}'
two

4. Phép so sánh

Ví dụ: Sử dụng lệnh awk thực hiện như sau awk '$1 > 200' file1.txt. Nếu $1 lớn hơn 200 thì chương trình sẽ thực hiện in nội dung của file1.txt.

[root@test1 ~]# cat file1.txt
500  Sanjay  Sysadmin   Technology  $7,000
300  Nisha   Manager    Marketing   $9,500
400  Randy   DBA        Technology  $6,000
[root@test1 ~]# awk '$1 > 200' file1.txt
500  Sanjay  Sysadmin   Technology  $7,000
300  Nisha   Manager    Marketing   $9,500
400  Randy   DBA        Technology  $6,000

5. Cú pháp điều kiện

Mỗi câu lệnh bên trong {} có thể được thêm bởi một điều kiện để các câu lệnh sẽ chỉ thực thi nếu điều kiện là đúng. Để kiểm tra điều kiện ta có thể thực hiện như sau:

[root@test1 ~]# cat file.txt
fruit   qty
apple   42
banana  31
fig     90
guava   6
[root@test1 ~]# awk '{
         if($1 == "apple"){
            print $2
         }
       }' file.txt
42
[root@test1 ~]# awk '{
         if(NR==1 || $2<35){
            print $0
         }
       }' file.txt
fruit   qty
banana  31
guava   6

6. Lọc các kí tự

Các kí tự cần lọc được đặt '//'.

Ví dụ:

[root@test1 ~]#cat file2.txt
Roses are red,
Violets are blue,
Sugar is sweet,
And so are you.
[root@test1 ~]# awk '/are/' file2.txt
Roses are red,
Violets are blue,
And so are you.
[root@test1 ~]# awk '!/are/' file2.txt
Sugar is sweet,
[root@test1 ~]# awk '/are/ && !/so/' poem.txt
Roses are red,
Violets are blue,
[root@test1 ~]# awk '/^[ab]/' file.txt
apple   42
banana  31
[root@test1 ~]# awk '/are/{print $NF}' file.txt
red,
blue,
you.

7. Lọc dựa trên số dòng

[root@test1 ~]# awk 'NR==2' file2.txt
Violets are blue,
[root@test1 ~]# awk 'NR==2 || NR==4' file2.txt
Violets are blue,
And so are you.
[root@test1 ~]# awk 'END{print}' file2.txt
And so are you.
[root@test1 ~]# awk 'NR==4{print $3}' file.txt
31

8. Thay thế

Sử dụng hàm sub chuỗi để thay thế lần xuất hiện đầu tiên

Sử dụng gsub để thay thế tất cả các lần xuất hiện

Ví dụ:

[root@test1 ~]# echo  ' 1-2-3-4-5 '  | awk ' {sub ("-", ":")} 1 '
 1:2-3-4-5
[root@test1 ~]# echo  ' 1-2-3-4-5 '  | awk ' {gsub ("-", ":")} 1 '
 1:2:3:4:5
[root@test1 ~]# echo '1-2-3-4-5' | awk '{n=gsub("-", ":"); print n} 1'
4
1:2:3:4:5
[root@test1 ~]# echo '1-2-3-4-5' | awk '{gsub(/[^-]+/, "abc")} 1'
abc-abc-abc-abc-abc
[root@test1 ~]# echo 'one;two;three;four' | awk -F';' '{gsub("e", "E", $3)} 1'
one two thrEE four

9. Tính tổng giá trị

9.1. Tính tổng giá trị của một cột

Lệnh awk thực hiện tính tổng dựa trên cú pháp sau:

awk '{s+=$(cột cần tính)} END {print s}' {{filename}}

Ví dụ:

[root@test1 ~]# cat file1.txt
500  Sanjay  Sysadmin   Technology  $7,000
300  Nisha   Manager    Marketing   $9,500
400  Randy   DBA        Technology  $6,000
[root@test1 ~]# awk '{s+=$1} END {print s}' file1.txt
1200

9.2. Tính tổng giá trị của một cột và in các giá trị của cột đó

Lệnh awk thực hiện tính tổng các giá trị trong cột và in các giá trị và sau đó là tổng cú pháp như sau:

awk '{s+=$1; print $(cột cần tính)} END {print "--------"; print s}' {{filename}}

Ví dụ:

[root@test1 ~]# cat file1.txt
500  Sanjay  Sysadmin   Technology  $7,000
300  Nisha   Manager    Marketing   $9,500
400  Randy   DBA        Technology  $6,000
[root@test1 ~]# awk '{s+=$1; print $1} END {print "--------"; print s}' file1.txt
500
300
400
--------
1200