파이프로 연결된 여러 awk 명령을 단일 awk 명령으로 결합하는 방법

파이프로 연결된 여러 awk 명령을 단일 awk 명령으로 결합하는 방법

다음을 포함하는 파일을 필터링하는 스크립트를 작성 중입니다.

a:10
b:20
c:60
# comment
{{# random mustache templating}}
d=4
e=6

결과 출력은 다음과 같습니다.

a
b
c
d
e

이건 내 명령이야

cat filename.txt | awk '{$1=$1;print}' | awk -F'{{' '{print $1}' | awk -F'=' '{print $1}' | awk -F':' '{print $1}' | awk -F'#' '{print $1}' | awk /./

목적:

  • "=" 또는 ":" 문자가 나타나는 줄의 모든 항목을 삭제합니다.
  • 템플릿을 제거하려면 "{{"로 시작하는 줄을 삭제하세요.
  • 각 줄의 시작과 끝 부분에 있는 공백을 자릅니다.
  • 빈 줄을 모두 제거하세요.

저는 bash를 처음 사용하는데 어떻게 이 명령을 더 짧게 만들 수 있나요?

답변1

필드 구분 기호는 완전한 정규식일 수 있으므로

awk -F'[:#=]' '!/^{{/ && length($1) > 0 { split($1, a, " "); print a[1] }' filename.txt

충분합니다. ":", "#", "=" 중 하나가 구분 기호 역할을 합니다. "{{"로 시작하는 줄을 제외하고, $1비어 있지 않은 줄을 일치시키고, $1공백으로 분할하고, 첫 번째 결과 필드를 인쇄합니다.

답변2

작업을 단순하게 유지하세요.

$ awk 'NF && ($1 !~ /^(#|\{+)/) { sub(/[:=].*/,""); print $1 }' file
a
b
c
d
e

답변3

위의 결과를 얻기 위해 정규식을 필드 구분 기호로 사용하고 정규식을 사용하여 행을 선택하고 {print $1}첫 번째 열을 인쇄했습니다.

귀하의 예에는 선행 공백이나 빈 줄이 표시되지 않지만 이를 처리해야 하는 경우 아래에서 이 명령의 변형을 참조하세요.

awk -F'[:=]' '!/^[#{]/{print $1}' filename.txt

결과:

a
b
c
d
e

선행 또는 후행 공백이 있는 경우 다음이 작동할 수 있습니다. 하지만 예시를 보지 않고는 상상하기 어렵다는 점은 인정합니다.

awk -F'[:=]' '{gsub(/^\s+|\s+$/,"",$1)} !/^[#{]/{print $1}' filename.txt

가능한 모든 시나리오를 다루기 위해 귀하의 의견을 바탕으로 예제를 수정했습니다. 이제 선행 및 후행 공백과 빈 줄이 있습니다.

a:10
b :20
  c:60
# comment

 {{# random mustache templating}}
d=4
e =6   

이 문제를 처리하기 위해 약간 변경된 명령은 다음과 같습니다.

awk -F'[:=]' '{gsub(/^\s+|\s+$/,"",$1)} !/^[#{]/ && !/^$/{print $1}' filename.txt
  1. 필드 구분 정규식은 $1첫 번째 필드를 또는 뒤의 모든 필드에서 분리합니다 .:=
  2. gsub는 모든 선행 및 후행 공백을 제거합니다.
  3. 이전 정규식은 주석, "템플릿" 및 빈 줄을 제외하기 위해 또는로 시작하는 {print $1}모든 줄을 제거합니다 .#{

그러면 다음과 같은 결과가 생성됩니다.다음에서 수정된 예:

a
b
c
d
e

답변4

아마도 이것은 원하는 결과를 얻는 데 도움이 될 것입니다.

#!/bin/bash

dynamic_array=()

while read -r line 
do 
    var=$(echo "$line" | cut -c 1)    
    if ! { [ "$var" = '#' ] ||  [ "$var" = '{' ] || [ "$var" = '}' ]; }
    then
                 dynamic_array+=("$var")   
    fi 
done < A.txt

str_array_value="${dynamic_array[*]}" ; echo "$str_array_value" | tr ' ' '\n' | awk '!seen[$0]++'

산출:

a   
b   
c    
d
e

관련 정보