시작 텍스트 문자열을 사용하여 줄 중간에서 새 줄을 제거합니다.

시작 텍스트 문자열을 사용하여 줄 중간에서 새 줄을 제거합니다.

파이프로 구분된 형식의 메시지 파일을 받았습니다. 메시지 줄 하나는 매우 길어서 6000에 가깝습니다. 그리고 총 파일 크기가 6GB를 초과합니다. 다음은 이 파일의 예제 형식입니다. 파일을 구문 분석하고 모든 것을 한 줄에 넣어야 합니다.

데이터 중간에서 개행 문자를 제거해야 합니다.

File: abc.txt
File_Name|abc.txt|date|04212019|this is one full line|Client_name|Whole
File_Name|abc.txt|date|04212019|half data is good
File_Name|abc.txt|date|04212019|Sample data
is split|Client_Name|Marshals
File_Name|abc.txt|date|04212019|this is good again|Processing_date|03282019
File_Name|abc.txt|date|04212019|line is not good 
again|Processing_date|04232019

나는 데이터가 다음과 같기를 원합니다.

File_Name|abc.txt|date|04212019|this is one full line|Client_name|Whole
File_Name|abc.txt|date|04212019|half data is good
File_Name|abc.txt|date|04212019|Sample data is split|Client_Name|Marshals
File_Name|abc.txt|date|04212019|this is good again|Processing_date|03282019
File_Name|abc.txt|date|04212019|line is not good again|Processing_date|04232019

저는 리눅스를 사용하고 있습니다.

메모리 부족 오류가 발생하는 perl -ef를 사용해 보았습니다.

답변1

File_Name그렇다면 ?로 시작하지 않는 줄을 이전 줄에 연결 하시겠습니까 ?

에서는 패턴을 sed사용하여 다음과 같은 작업을 수행할 수 있습니다 N;P;D.

sed 'N;/\nFile_Name/!s/\n/ /;P;D' abc.txt
  • N패턴 공간에 다음 줄 추가
  • /\nFile_Name/File_Name새 줄 뒤의 모든 줄을 지정합니다. !패턴 공간의 두 줄 중 두 번째 줄이 다음으로 시작하지 않는 경우에만 선택을 반전합니다.File_Name
  • s/\n/ /줄 사이의 개행을 공백으로 바꾸기
  • P패턴 공간의 첫 번째 줄을 인쇄합니다.
  • D줄 바꿈 앞의 모든 항목을 제거하고 두 번째 줄이 여전히 패턴 공간에 있는 상태에서 새 루프를 시작합니다(새 줄 쌍을 생성하려면 다음 줄에 추가됨).

이는 두 개의 와이어를 연결하는 경우에만 작동합니다. 행을 더 많은 행으로 분할할 수 있는 경우 루프를 추가하거나 다른 방식으로 수행해야 합니다.

답변2

다음은 perl텍스트에서 여러 줄의 새 줄을 제거하는 또 다른 버전입니다.

perl -pe 's/\n//' abc.txt | perl -pe 's/(.)File_Name/\1\nFile_Name/g'

먼저 텍스트에서 모든 줄바꿈을 제거한 다음 "File_Name"이 나타날 때마다("File_Name" 앞에 최소 한 문자가 올 때) 앞에 새 줄을 삽입합니다.

예를 들어 여러 공간을 청소해야 하는 경우 더 많은 파이프를 전달할 수 있습니다.

perl -pe 's/\n/ /' abc.txt \
| perl -pe 's/(.)File_Name/\1\nFile_Name/g' \
| perl -pe 's/ +/ /g'

답변3

어떤 이유로 -pe 버전이 충돌하는 경우 독립 실행형 perl프로그램은 다음과 같습니다. Stripper.pm 이는 이전 행의 내용을 기반으로 작업을 수행하는 표준 방법입니다. 다음을 실행하여 이 작업을 수행할 수 있습니다.

perl stripper.pm <abc.txt >new_abc.txt

#!/usr/bin/perl
my $previous = <STDIN>;

if( defined $previous ){
    chomp $previous;
};

while( $line = <STDIN> ){
    chomp $line;

    unless( $line =~ m/^File_Name/ ){
        $previous .= $line;

    } else { 
        print STDOUT "$previous\n";
        $previous = $line;
    }
}

print STDOUT "$previous\n";

관련 정보