awk perl 새 줄의 첫 번째 열 복사

awk perl 새 줄의 첫 번째 열 복사

나는 bash를 사용하고 다음과 같은 테이블이 있습니다

001_1_174    [g/n                         474536         482492          
mo[g/n                    482492         504062          
'er/                      504062         517352          
ruze                      517352         529562                  
001_1_400    uz[`f                         960192        966656           
.ire                      966656         984416           
tuf/[                     984416         1006166

첫 번째 행(숫자와 밑줄만 포함)의 문자열을 다른 숫자까지 다른 행에 복사하고 다음 숫자에 대해 이 작업을 수행하고 싶습니다.

이와 같이

001_1_174    [g/n                    474536         482492           
001_1_174  mo[g/n                    482492         504062           
001_1_174  'er/                      504062         517352           
001_1_174  ruze                      517352       529562                  
001_1_400    uz[`f                   960192        966656           
001_1_400   .ire                      966656         984416           
001_1_400   tuf/[                     984416         1006166

답변1

단일 라이너를 선호하는 경우 Perl을 사용하십시오.

$ perl -pe 'if (/^\s*([\d_]+)/) {$x=$1} else {$_="$x $_"}' input.txt

그렇지 않으면 스크립트로 다음을 수행합니다.

use warnings;
use strict;

my $prefix;
while (<>) {
    if ( /^\s*([\d_]+)/ )
        { $prefix = $1 }
    else { $_ = "$prefix $_" }
    print;
}

둘 다 출력:

001_1_174    [g/n                         474536         482492          
001_1_174 mo[g/n                    482492         504062          
001_1_174 'er/                      504062         517352          
001_1_174 ruze                      517352         529562                  
001_1_400    uz[`f                         960192        966656           
001_1_400 .ire                      966656         984416           
001_1_400 tuf/[                     984416         1006166

정규식은 "숫자 및 밑줄만" 사양을 기반으로 하며 줄 시작 부분에 공백을 허용합니다( \s*원하지 않는 경우 제거). 추가적으로, 이는아니요읽은 첫 번째 줄이 숫자로 시작하지 않으면 제대로 작동합니다!

답변2

$ awk 'NF == 4 { col1 = $1; print; next } { print col1, $0 }' file
001_1_174    [g/n                         474536         482492
001_1_174 mo[g/n                    482492         504062
001_1_174 'er/                      504062         517352
001_1_174 ruze                      517352         529562
001_1_400    uz[`f                         960192        966656
001_1_400 .ire                      966656         984416
001_1_400 tuf/[                     984416         1006166

먼저 입력 줄에 4개의 열이 있는지 확인하세요. 있는 경우 col1변수는 첫 번째 열의 값으로 설정되고 행은 그대로 인쇄되며 스크립트는 다음 행에서 계속됩니다. 그렇지 않으면 행이 인쇄되지만 값은 col1원래 첫 번째 열 앞에 삽입됩니다.

이는 무작위로 보이는 횡설수설에 공백 문자가 포함되지 않은 경우에만 작동합니다. 그렇다면 열 사이에 사용되는 구분 기호(예: 탭) -F 'delimiter'를 사용해야 할 수도 있습니다 .delimiter'\t'

또한 첫 번째 행에 4개의 열이 있다고 가정합니다. 그렇지 않으면 col1해당 행의 변수가 설정되지 않은 상태로 유지됩니다.


구현하다댓글의 제안~에서사용자카스이는 입력 데이터의 열 수와 무관합니다(단지 첫 번째 행에 특수 첫 번째 열을 포함하는 모든 행에 대한 올바른 열 수가 포함되어 있다고 가정함).

$ awk 'NR == 1 { cols = NF } NF == cols { col1 = $1; print; next } { print col1, $0 }' file
001_1_174    [g/n                         474536         482492
001_1_174 mo[g/n                    482492         504062
001_1_174 'er/                      504062         517352
001_1_174 ruze                      517352         529562
001_1_400    uz[`f                         960192        966656
001_1_400 .ire                      966656         984416
001_1_400 tuf/[                     984416         1006166

답변3

가장 짧은 awk:

awk 'NF < 4{ $0=n OFS $0 }{ n=$1 }1' file

산출:

001_1_174    [g/n                         474536         482492          
001_1_174 mo[g/n                    482492         504062          
001_1_174 'er/                      504062         517352          
001_1_174 ruze                      517352         529562                  
001_1_400    uz[`f                         960192        966656           
001_1_400 .ire                      966656         984416           
001_1_400 tuf/[                     984416         1006166

특정 필드 형식을 사용하려면 다음을 사용하여 위의 내용을 변경할 수 있습니다.

awk 'NF<4{ $0=n OFS $0 }$1~/^[0-9_]+$/{ n=$1 }1' file

관련 정보