여러 로그 파일의 모든 위치에서 이 패턴을 가져오려고 합니다(참고: 이러한 패턴의 크기(예: 어쩌고 저쩌고 하는 횟수)는 크게 다를 수 있습니다).
Found an txt File
Blah
Blah
10019874
Blah
Blah
Processed File
다음 명령줄을 사용하세요.
pcregrep -M 'Found an.*(\n|.)*10019874.*(\n|.)*Processed' log_*.txt
내 정규식으로 확인해 보세요.여기에 정규 표현식
나는 -M 여러 줄 플래그와 함께 pcregrep을 사용합니다. "log_"로 시작하고 ".txt"로 끝나는 모든 로그 파일에 나타납니다. 이 명령을 실행하면 "세그먼테이션 오류"가 반환됩니다.
이 작업을 수행하는 더 쉽고 더 좋은 방법이 있습니까?
답변1
댓글에서 말했듯이 게시한 명령은 내 LMDE(pcregrep 버전 8.31 2012-07-06)에서 제대로 작동합니다. 그러나 정규식은 찾고 있는 문자열의 일부만 지정하므로 일반을 사용하여 이 작업을 수행할 수도 있습니다 grep
.
grep -A 6 'Found an' log_*.txt | grep -C 3 10019874
-A 6
전달된 문자열과 다음 6줄과 일치하는 줄을 인쇄하고 3 -C 3
을 인쇄 합니다.약철사. 최종 결과는 pcregrep
사용한 방법과 정확히 동일합니다.
스키마의 행 수가 다를 수 있는 경우 이는 세그폴트를 설명할 수 있습니다. 아마도 일부 파일에서는 일치하는 부분이 너무 길어서 메모리 부족 오류가 발생하는 것 같습니다. 이 문제를 해결하는 한 가지 방법은 다음과 같은 스크립트를 작성하는 것입니다.
perl -ne '$c=1 if /Found an/; ## set $c to 1 if this line matches 'Found on'
if($c){ ## If $c is defined and non-0
push @F,$_; ## Add the current line to the @F array
$c++ if /10019874/; ## Increment $c if this line matches '10019874'
if(/Processed/){ ## If this line matches 'Processed'
print "@F" if $c>1; ## Print the contents of @F if $c is >1
@F=""; $c=0; ## Empty @F, set $c to 0.
}
}' log_*.txt
단일 라이너와 동일:
perl -ne '$c=1 if /Found an/; if($c){push @F,$_; $c++ if /10019874/; if(/Processed/){print "@F" if $c>1; @F=""; $c=0;}}' log_*txt