AWK를 통해 텍스트 파일의 배열을 검색하는 효율적인 방법

AWK를 통해 텍스트 파일의 배열을 검색하는 효율적인 방법

약 10,000개의 숫자를 포함하는 배열 SPLNO가 있습니다. 이제 MDN.TXT 파일(약 1.5lac 레코드 포함)에서 배열로 가입자 번호를 검색하고 싶습니다. 가입자 번호가 배열에서 발견되면 다음을 수행합니다. 내 문제는 숫자에 대해 10k 레코드의 전체 배열을 검색하기 때문에 시간이 더 걸린다는 것입니다. 따라서 1.5lac 레코드의 경우 반복됩니다(1.5lac*10K). 효율적인 방법을 제안해주세요.

SPLNO.TXT 예:

918542054921|30|1|2
918542144944|12|1|2
918542155955|12|1|2 918542166966|12 |1|2 918542355955|12|1|
2 9 1 8542455955|12|1|2 918542555955 |12|1| 2 918542955955|12|1|2




MDN.TXT 예:

8542166966
8542355955
8542555955

awk -F"|"  'FNR==1 { ++counter}
counter==1 {SPLNOPULSE[$1]=$4;SPLNOAMT[$1]=$3;SPLNOMAXLEN[$1]=$2;next}
{
for ( mdn in SPLNOMAXLEN)
        {
         if ( ($1 ~ "^"mdn && length($1) <=SPLNOMAXLEN[mdn]) || ("91"$1 ~ "^"mdn && length("91"$1) <=SPLNOMAXLEN[mdn]) )
              {                              
                print found
               }
         else
                print not found
        }                             
 } ' SPLNO.TXT MDN.TXT

답변1

이것은 사용하는 한 가지 방법입니다 perl.

#!/usr/bin/perl
# read the subscribers
open(A,"<","SPLNO.TXT");
while(<A>) {
 chomp;
 @a=split(/\|/,$_);
 $splnopulse{$a[0]}=$3;
 $splnoamt{$a[0]}=$2;
 $splnomaxlen{$a[0]}=$1;
}
close A;

# read the mdn, looking for matches
open(B,"<","MDN.TXT");
while(<B>) {
 chomp;
 @b=split(/\|/,$_);
 foreach $mdn (keys %splnomaxlen) {
  if($mdn eq $b[0] || "$mdn" eq "91" . $b[0]) {
   print "found\n";
  } else {
   print "not found\n";
  }
 }
}
close B;

답변2

파일 1의 각 라인에 대해 전체 파일 2를 검색하는 알고리즘의 시간 성능은 입니다 m * n. 여기서 m는 파일 2의 라인 수이고 는 n파일 1의 라인 수입니다. 이것은 매우 빠르지 않고 매우 느려집니다.
해결책은 먼저 각 파일을 정렬한 다음(예: *log(n) 시간) 다음과 같이 두 파일 간의 행을 비교하는 것입니다.

  1. i=1(파일 1의 줄 번호), j=1(파일 2의 줄 번호)로 둡니다.
  2. a=(file 1)[line i]그것과 비교해보세요 b=(file 2)[line j].
  3. if a<b;그런 다음 i를 증가시켜 2로 돌아갑니다(파일 1의 끝 확인).
  4. if a>b;그런 다음 j를 증가시켜 2로 돌아갑니다(파일 2의 끝을 확인하십시오).
  5. if a=b;이것은 일치합니다. 인쇄하고 i를 증가시키세요.

실행 시간은 다음과 같습니다( n + m모든 행을 읽는 데 걸리는 시간).

그러면 전체 프로세스의 실행 시간은 다음과 같습니다 n*log(n) + m*log(m) + n + m.
여기서 O(n)은 n * log(n)다음과 같습니다 n > m.

정렬은 쉽습니다. sort각 파일에 대해 다음 명령을 사용하면 됩니다.

sort -t '|' -k 1 file01.csv > file01-sorted.csv

그런 다음 awk에서 위 프로세스를 실행합니다.

편집: SPLNO의 10,000개 숫자가 모두 고유한 경우(중복 없음)라는 생각이 들었습니다. 그리고 MDN.TXT에도 고유한 레코드가 있습니다. 그런 다음 두 파일을 연결하고 중복된 값을 검색하면 해결 방법도 제공됩니다. 이는 단순한 평등에 적용됩니다. 대부분의 경우 정규식 일치는 이러한 개념을 깨뜨립니다.

관련 정보