탭으로 구분된 파일의 첫 번째 및 다섯 번째 열을 검색하여 다섯 번째 열의 공백을 탭으로 변환합니다.

탭으로 구분된 파일의 첫 번째 및 다섯 번째 열을 검색하여 다섯 번째 열의 공백을 탭으로 변환합니다.

탭으로 구분된 열이 포함된 파일이 있습니다 tsv. 공백으로 구분된 값이 있는 다섯 번째 열을 가져오고 싶습니다. 구분된 공백을 탭 구분으로 변환하고 새 파일로 저장합니다.

시도:

cut -d"\t" -f"4" input.tsv
awk -v OFS="\t" '$1=$1' input.tsv > output.tsv

입력하다:

Composite_Element_REF   Gene_Symbol     Chromosome      Genomic_Coordinate      TCGA-KL-8323-01A-21D-2312-05 TCGA-KL-8324-01A-11D-2312-05 TCGA-KL-8325-01A-11D-2312-05 
cg00000027      RBL0    14      53468110        0.0545368833399913 0.635089208882213 0.0581022991274144
cg00000028      RBL1    15      53468111        0.0545366588241415 0.635089205024173 0.0581085373336217
cg00000029      RBL2    16      53468112        0.0545366588040571 0.635089205078394 0.0581085373332275

예상 출력:

Composite_Element_REF   TCGA-KL-8323-01A-21D-2312-05    TCGA-KL-8324-01A-11D-2312-05    TCGA-KL-8325-01A-11D-2312-05
cg00000027     0.0545368833399913    0.635089208882213    0.0581022991274144
cg00000028    0.0545366588241415    0.635089205024173    0.0581085373336217
cg00000029    0.0545366588040571    0.635089205078394    0.0581085373332275

답변1

원하는 것이 일부 입력 파일에서 첫 번째 및 다섯 번째 탭으로 구분된 필드를 가져온 input.tsv다음 해당 필드에 포함된 공백을 탭으로 변경하는 것이라면 아래와 같이 cut및를 사용하여 이 작업을 수행할 수 있습니다.tr

cut -f 1,5 input.tsv | tr ' ' '\t' >output.tsv

먼저 입력에서 첫 번째 및 다섯 번째 필드를 추출한 다음 모든 공백 문자를 탭 문자로 변경하고 출력을 파일에 씁니다. 첫 번째 필드가 변경되지 않은 상태로 유지되어야 하는 경우 필드에 공백이 포함되어 있지 않은 것으로 간주됩니다.

탭이 기본 구분 기호이므로 cut이 옵션을 사용할 필요가 없습니다 -d.

또는 다음을 사용하십시오 awk.

awk 'BEGIN { OFS=FS="\t" }
    {
        nf = split($5, a, " ")
        $0 = $1

        for (i = 1; i <= nf; ++i) $(NF+1) = a[i]

        print
    }' input.tsv >output.tsv

이렇게 하면 탭으로 구분된 다섯 번째 필드가 공백으로 분할된 다음 모든 원래 필드를 첫 번째 필드로 덮어쓰게 됩니다. 결과 레코드를 출력하기 전에 루프의 첫 번째 필드 뒤에 분할 필드를 추가합니다.

Miller( mlr)를 사용하면 입력을 헤드리스 TSV(헤더를 단순히 데이터로 처리하도록 헤드리스)로 읽고 관심 있는 필드를 잘라낸 다음 각 레코드를 우리가 하는 것처럼 다시 생성하도록 선택할 수 있지만 더 awk짧습니다.

mlr --tsv -N put '$* = {1:$1, 2:splita($5, " ")}' input.tsv >output.tsv

각 명령의 출력은 다음과 같습니다.

Composite_Element_REF   TCGA-KL-8323-01A-21D-2312-05    TCGA-KL-8324-01A-11D-2312-05    TCGA-KL-8325-01A-11D-2312-05
cg00000027      0.0545368833399913      0.635089208882213       0.0581022991274144
cg00000028      0.0545366588241415      0.635089205024173       0.0581085373336217
cg00000029      0.0545366588040571      0.635089205078394       0.0581085373332275

초기 필드에 헤더를 원한다고 가정하고 -05입력의 두 번째 줄에 있는 별도의 헤더는 오타이므로 헤더 줄의 최종 필드 끝에 추가해야 한다는 점에 유의하세요.

답변2

사용 awk:

$ awk -F '\t' '{gsub(OFS,FS,$5); print $1 FS $5}' file

답변3

FWIW 실제로 사용@PrapjhotSingh의 솔루션그러나 일반 작동 분야에 대한 유용한 정보를 제공할 수 있는 몇 가지 대안에 대해서는 계속 읽으십시오...

입력에서 표시된 출력을 얻으려면 표시해야 할 것은 다음과 같습니다.

$ awk -v OFS='\t' '{print $1, $5, $6, $7}' file
Composite_Element_REF   TCGA-KL-8323-01A-21D-2312-05    TCGA-KL-8324-01A-11D-2312-05    TCGA-KL-8325-01A-11D-2312-05
cg00000027      0.0545368833399913      0.635089208882213       0.0581022991274144
cg00000028      0.0545366588241415      0.635089205024173       0.0581085373336217
cg00000029      0.0545366588040571      0.635089205078394       0.0581085373332275

$1=$1또는 코드에서 사용하려고 하는 것을 보면 다음과 같이 할 수 있습니다.

$ awk -v OFS='\t' '{$2=$3=$4=""; $0=$0; $1=$1} 1' file
Composite_Element_REF   TCGA-KL-8323-01A-21D-2312-05    TCGA-KL-8324-01A-11D-2312-05    TCGA-KL-8325-01A-11D-2312-05
cg00000027      0.0545368833399913      0.635089208882213       0.0581022991274144
cg00000028      0.0545366588241415      0.635089205024173       0.0581085373336217
cg00000029      0.0545366588040571      0.635089205078394       0.0581085373332275

어디:

  • $2=$3=$4=""이 필드를 null로 설정하고 필드가 아직 비어 있지만 $0모든 공백과 탭 문자(사용 중인 기본값과 일치)를 단일 탭(사용 중인)으로 대체하여 원본의 공백을 탭으로 변경합니다. , 및 3개의 필드로 나뉩니다.FSOFS$5$5$6$7
  • $0=$0필드로 다시 분할해도 $0필드 사이의 공백은 변경되지 않으므로 이제 3개 필드는 사라졌지만 원래 필드 사이의 $1여러 탭 $5(Now $2및 ) $3$4여전히 ​​남아 있습니다.
  • $1=$1$1자체적으로 설정되어 $0해당 필드에서 다시 재구성되지만 이제 여러 개의 연속 탭(다시 FS우리가 사용하는 기본 옵션과 일치)이 단일 탭(우리가 사용 중인)으로 대체되어 OFS필드로 구분된 4개 탭의 최종 출력이 생성됩니다.

NF아래에서 이러한 다양한 단계를 볼 수 있습니다. 필드 사이의 간격 변경과 각 줄의 시작 부분에 인쇄된 값의 변경을 확인하세요.

$ awk -v OFS='\t' '{print NF ": " $0}' < <(printf 'a\tb\tc\td\te f g\n')
7: a    b       c       d       e f g

$ awk -v OFS='\t' '{$2=$3=$4=""; print NF ": " $0}' < <(printf 'a\tb\tc\td\te f g\n')
7: a                            e       f       g

$ awk -v OFS='\t' '{$2=$3=$4=""; $0=$0; print NF ": " $0}' < <(printf 'a\tb\tc\td\te f g\n')
4: a                            e       f       g

$ awk -v OFS='\t' '{$2=$3=$4=""; $0=$0; $1=$1; print NF ": " $0}' < <(printf 'a\tb\tc\td\te f g\n')
4: a    e       f       g

또는 GNU awk와 같은 일부 awk에서는 다음 중 하나를 수행할 수 있습니다.

awk -v OFS='\t' '{$2=$5; $3=$6; $4=$7; NF=4} 1' file
awk -v OFS='\t' '{for (i=2; i<=4; i++) $i=$(i+3); NF=i-1} 1' file

3개 필드 의 값을 위로 이동 한 다음 원래 필드 와 후속 필드를 제거하기 위해 4로 $5설정했지만 설정은 POSIX별로 정의되지 않은 동작이므로 다른 awks는 값을 존중하거나 무시하거나 다른 작업을 수행할 수 있습니다.NF$5NF

답변4

사용행복하다(이전 Perl_6)

~$ raku -ne 'put join "\t", .words.[0,4..*];'  file

위 내용은 Perl 계열의 프로그래밍 언어인 Raku로 작성된 답변입니다. 여기서는 (@Kusalananda와 동일) 가정합니다."두 번째 줄에 입력된 유일한 문자는 -05철자 오류이므로 헤더 줄의 마지막 필드 끝에 추가해야 합니다."(출처: @Kusalananda).

즉, 자동 인쇄가 아닌 한 줄씩 플래그를 사용하여 파일을 한 줄씩 읽습니다 -ne. Raku의 .words루틴은 주제(입력 라인)를 가져와 $_여백의 요소로 나눕니다. 대괄호는 [0,4..*]원하는 0 인덱스 요소를 선택합니다. 이들은 원하는 출력을 제공하는 탭 join에 다시 결합됩니다 .\t

입력 예:

Composite_Element_REF   Gene_Symbol     Chromosome      Genomic_Coordinate      TCGA-KL-8323-01A-21D-2312-05 TCGA-KL-8324-01A-11D-2312-05 TCGA-KL-8325-01A-11D-2312-05 
cg00000027      RBL0    14      53468110        0.0545368833399913 0.635089208882213 0.0581022991274144
cg00000028      RBL1    15      53468111        0.0545366588241415 0.635089205024173 0.0581085373336217
cg00000029      RBL2    16      53468112        0.0545366588040571 0.635089205078394 0.0581085373332275

예제 출력:

Composite_Element_REF   TCGA-KL-8323-01A-21D-2312-05    TCGA-KL-8324-01A-11D-2312-05    TCGA-KL-8325-01A-11D-2312-05
cg00000027  0.0545368833399913  0.635089208882213   0.0581022991274144
cg00000028  0.0545366588241415  0.635089205024173   0.0581085373336217
cg00000029  0.0545366588040571  0.635089205078394   0.0581085373332275

"짧은" 줄을 처리하는 것은 상당히 쉽습니다. 조건만 추가하면 됩니다.

~$ raku -ne 'put join "\t", .words.[0,4..*] if .words.elems == 7;'  file

마지막으로, 2개의 서로 다른 구분 기호가 있는 파일이 있는 경우 개별적으로/연속적으로 관리할 수 있습니다.

~$ raku -ne '.split("\t", 5).[0,4].split(" ").join("\t").put;'   file

마지막 두 솔루션은 위와 동일한 "예제 출력"을 제공합니다.

https://raku.org

관련 정보