Bash와 AWK를 사용하여 텍스트 파일 비교

Bash와 AWK를 사용하여 텍스트 파일 비교

두 개의 텍스트 파일이 있는데 행과 열에 따라 해당 값을 비교하고 싶습니다. 비교란 값이 같은지 확인하고 값이 같은지 아닌지 확인하는 것을 의미합니다. 파일은 다음과 같습니다.

file1.txt

Name  Col1  Col2  Col3  
-----------------------
row1  1     4     7        
row2  2     5     8         
row3  3     6     9   

file2.txt

Name  Col1  Col2  Col3  
-----------------------
row2  1     4     11        
row1  2     5     12

제약 조건은 다음과 같습니다.

  • 존재하는 행만 비교합니다. 즉, row3은 file1.txt에 있지만 file2.txt에는 없으므로 비교가 필요하지 않습니다.
  • 반드시 사용해야 함AWK
  • 파일의 행 순서가 잘못되었을 수 있습니다.
  • 내 AWK 버전이 이중 배열을 지원하지 않기 때문에 이중 배열이 없습니다.

나는 다음과 같은 것을 생각하고 있습니다 :

awk 'NR>2 {next}
{
    for (i=2;i<NR;i++)              #For each row of file1.txt
    {     
        for(j=1;i<NF;j++)           #For each column of file1.txt
        {
             // Check if row and column of file1.txt is equal to row and column of file2.txt.
        } 
    }
}
' file1.txt file2.txt

두 개의 서로 다른 텍스트 파일의 값을 어떻게 비교합니까? 더 많은 설명이 필요하면 알려주세요.

내가 요구하는 것은 AWK를 사용하는 일반적인 구조입니다. 나머지는 알아낼 수 있기를 바랍니다.

답변1

이것은 이름이 두 파일 모두에 있지만 값이 다른 file2의 행을 출력합니다.

awk 'NR==FNR {f1[$1]=$0; next} $1 in f1 && $0 != f1[$1]' file1.txt file2.txt 
row2  1     4     11        
row1  2     5     12

공백의 차이조차도 잘못된 결과를 낳는다는 것을 깨달았습니다. 우리는 라인을 "정규화"할 수 있습니다:

awk '
    NR==FNR  {$1=$1; f1[$1]=$0; next} 
    $1 in f1 {$1=$1; if ($0 != f1[$1]) print}
' file1.txt file2.txt 
row2 1 4 11
row1 2 5 12

답변2

이를 수행하는 방법은 다양하며 다음과 같은 솔루션이 있습니다 gawk 4.x.

$ awk '
    FNR < 2 { next }
    FNR == NR {
        for (i = 2; i <= NF; i++) {
            a[$1][i] = $i;
        }
        next;
    }
    ($1 in a) {
      for (i = 2; i <= NF; i++) {
          if (a[$1][i] == $i) {
              printf("%s->Col%d: Equal\n", $1, i-1);
          } else {
              printf("%s->Col%d: Not Equal\n", $1, i-1);
          }
       }
  }
' file1.txt file2.txt
row2->Col1: Not Equal
row2->Col2: Not Equal
row2->Col3: Not Equal
row1->Col1: Not Equal
row1->Col2: Not Equal
row1->Col3: Not Equal

설명

  • FNR < 2 { next }: 처음 두 줄 건너뛰기
  • FNR == NR: 첫 번째 파일을 처리할 때만 true입니다. a양식을 사용하여 각 열 값을 연관 배열에 저장합니다 a[ROW][COLUMN].
  • ($1 in a): file2의 행이 file1에 존재하는지 확인합니다. true인 경우 모든 열 값을 반복하여 file1의 값과 비교합니다.

이전 gawk버전에서는 다음을 시도해 볼 수 있습니다.

$ awk '
    FNR < 2 { next }
    FNR == NR {
        for (i = 2; i <= NF; i++) {
            a[i,$1] = $i;
            b[$1];
        }
        next;
    }
    ($1 in b) {
      for (i = 2; i <= NF; i++) {
          if (a[i,$1] == $i) {
              printf("%s->Col%d: Equal\n", $1, i-1);
          } else {
              printf("%s->Col%d: Not Equal\n", $1, i-1);
          }
       }
  }
' file1.txt file2.txt

답변3

내부 for 루프 내부에서 이것을 시도해 보세요:

awk ' {
      if(i == j)
           print "Same value";
      else
           print "Not the same";
       }'

이는 도움이 될 수 있는 간단한 조건문이지만 두 개의 서로 다른 텍스트 파일을 비교하여 추가 조정이 필요할 수 있습니다.

관련 정보