열의 중복 항목을 제거하고 여러 행의 값을 단일 행으로 선형화합니다.

열의 중복 항목을 제거하고 여러 행의 값을 단일 행으로 선형화합니다.

다음과 같은 테이블이 있습니다.

DAPPUDRAFT_194440   Phosphorous     
DAPPUDRAFT_194440   Temperature     
DAPPUDRAFT_194472   Phosphorous Fishkairomones  
DAPPUDRAFT_194472   Temperature     
DAPPUDRAFT_194512   Fishkairomones      
DAPPUDRAFT_194512   Cadmium Zinc    Quantumdots
DAPPUDRAFT_195644   Salinity        
DAPPUDRAFT_195644   Phosphorous     
DAPPUDRAFT_196131   Salinity        
DAPPUDRAFT_196131   Phosphorous     
DAPPUDRAFT_196131   hypoxia     
DAPPUDRAFT_196694   Salinity        

보시다시피 다양한 수의 열(탭으로 구분)에 데이터가 포함될 수 있습니다.

"DAPPUDRAFT_"로 시작하는 첫 번째 열의 중복된 항목은 제거되어야 하며, 여러 행에 나타나는 다른 모든 값은 단일 행에 나타나야 합니다.

예를 들어, 내 입력 테이블에서 "DAPPUDRAFT_194440"은 테이블에 2번 표시되며, 여기 데이터 하위 집합에 표시된 것처럼 한 행에는 "Temperature", 두 번째 행에는 "Phosphorus"라는 두 개의 값이 있습니다.

 DAPPUDRAFT_194440   Phosphorous     
 DAPPUDRAFT_194440   Temperature  

내가 보고 싶은 것은 "DAPPUDRAFT_"가 한 번만 나타나야 하며 "Temperature"와 "Phosphorus" 두 항목이 다음과 같이 탭으로 구분되어 같은 줄에 나타나야 한다는 것입니다.

 DAPPUDRAFT_194440   Phosphorous   Temperature  

예상 출력:

DAPPUDRAFT_194440   Phosphorous Temperature     
DAPPUDRAFT_194472   Phosphorous Fishkairomones  Temperature 
DAPPUDRAFT_194512   Fishkairomones  Cadmium Zinc    Quantumdots
DAPPUDRAFT_195644   Salinity    Phosphorous     
DAPPUDRAFT_196694   Salinity            
DAPPUDRAFT_196131   Salinity    Phosphorous hypoxia 

R에서 "reshape2" 패키지와 dcast 기능을 사용해 보았습니다. 하지만 그것은 내가 원하는 것과는 완전히 다른 일을 합니다. 명령줄, R 또는 Perl에서 이 문제를 해결하는 데 도움이 될 수 있는 방법이 있나요?

답변1

간단하게:

awk '{ r=$0; sub($1,"",r); a[$1]=(a[$1])? a[$1]"\t"r : r }
     END{ for(i in a) { gsub(/[[:space:]]{2,}/," ",a[i]); print i,a[i] } }' file

  • r=$0- 기록 사본을 캡처하세요.

  • sub($1,"",r)- 복사본의 첫 번째 필드를 제거하여 나머지 필드를 r변수 에 저장합니다.

  • a[$1]=(a[$1])? a[$1]"\t"r : r- 같은 가치를 쌓아라그룹(세션 1에서 제안)

  • for(i in a)- 그룹화된 모든 항목을 반복합니다.

  • gsub(/[[:space:]]{2,}/," ",a[i])- 단어 사이에 불필요한 공백을 제거합니다.

  • print i,a[i]- 그룹 이름 및 값 인쇄


산출:

DAPPUDRAFT_194440  Phosphorous Temperature 
DAPPUDRAFT_196694  Salinity
DAPPUDRAFT_194512  Fishkairomones Cadmium Zinc Quantumdots
DAPPUDRAFT_194472  Phosphorous Fishkairomones Temperature 
DAPPUDRAFT_196131  Salinity Phosphorous hypoxia 
DAPPUDRAFT_195644  Salinity Phosphorous 

답변2

또는

$ perl -e 'while(<ARGV>){chomp;($x,$y)=split(/\s+/,$_,2);$hash{$x}.=$y;}for(keys %hash){print "$_ $hash{$_}\n";}' test1
DAPPUDRAFT_196694 Salinity
DAPPUDRAFT_194440 Phosphorous     Temperature
DAPPUDRAFT_195644 Salinity        Phosphorous
DAPPUDRAFT_194472 Phosphorous Fishkairomones  Temperature
DAPPUDRAFT_194512 Fishkairomones      Cadmium Zinc    Quantumdots
DAPPUDRAFT_196131 Salinity        Phosphorous     hypoxia

답변3

행과 요소가 정렬되는 방식에 관심이 없다면 다음을 수행하세요.

sed 'G;s/^\(.*\)\(\t.*\)\n\(.*\)\1/\3\1\2/;h;$!d;s/\n$//' file

GNU가 아닌 경우 문자 그대로 TAB으로 sed대체됩니다 .\t

관련 정보