2017-05-11 6 views
0

두 개의 파일이 겹쳐서 정확한 일치 및 부분 일치를 기반으로 결과를 검색 할 수 있습니다. 예를 들어 명확하게 알 수 있습니다.R, awk, sed : 빈을 병합하고 중앙 중첩을 출력 한 다음 중점 + 이웃 중첩을 출력합니다.

FILEA :

chr1 200  400  E1 
chr1 400  600  E2 
chr1 600  800  E3 
chr2 200  300  E4 

fileB :

chr1 100  250 TF1 G1 
chr1 250  650 TF2 G2 
chr1 450  850 TF3 G3 

출력 :이 단계 Uptil

chr1 100 250 TF1 G1 chr1 200  400  E1 
chr1 250 650 TF2 G2 chr1 200  400  E1 
chr1 250 650 TF2 G2 chr1 400  600  E2 
chr1 250 650 TF2 G2 chr1 600  800  E3 
chr1 450 850 TF3 G3 chr1 400  600  E2 
chr1 450 850 TF3 G3 chr1 600  800  E3 

내가 일을 할 수 있지만, 다음 단계는 당신의 도움을 필요로하는 것입니다. 여기

I는 두 경기 (예를 들면 5 행이 있다면 제 만 (예를 들어, 출력 파일의 1 행에 관계없이 오버랩 크기) 1 개 매치가있는 그 라인

  1. 서브 세트 할 및 6 출력) 다음 중첩이 가장 큰 '가운데 행'(행 6과 행 5가 겹침 인 행 5와 비교하여 200이 중복 됨)
  2. 3 개 이상의 일치가있는 경우 (예 : 행 3은 완전 중첩되지만 행 2와 4는 각각 부분 중첩, 150과 50을 갖는 이웃 행입니다. 그런 다음 반환 만하고 싶습니다. 중앙 행은이 경우 행 3이됩니다.

그 후, 나는 실제로 사용 데이터 세트에서이 파일 B의 한 빈 파일의 A.

5 개 또는 7 쓰레기통의 최대 겹칠 일이 발생할 수 있기 때문에, 그래서 첫 번째 이웃 한 후 2 neigbors 등을 검색 할

그래서 기본적으로 내가 원하는 것은 먼저 모든 중첩 된 중첩을 얻은 다음 중앙 + 1 번째 이웃을 선택한 다음 중앙 + 2 번째 이웃을 얻는 것입니다. 이 근거에 따라

, 내 첫 번째 결과는 다음과 같습니다

결과 1 (중앙 겹치) :

chr1 100 250 TF1 G1 chr1 200  400  E1 
chr1 250 650 TF2 G2 chr1 400  600  E2 
chr1 450 850 TF3 G3 chr1 600  800  E3 

Result2 (중앙 + 1 이웃) :

chr1 100 250 TF1 G1 chr1 200  400  E1 
chr1 250 650 TF2 G2 chr1 200  400  E1 
chr1 250 650 TF2 G2 chr1 400  600  E2 
chr1 250 650 TF2 G2 chr1 600  800  E3 
chr1 450 850 TF3 G3 chr1 400  600  E2 
chr1 450 850 TF3 G3 chr1 600  800  E3 

가능한 경우를, 나는 인접한 행만 검색하지만 중앙 행은 검색하지 않는 것이 좋습니다.

도움이 될 것입니다. 고맙습니다.

답변

1

시간 예산에 대한 추가 요구 사항을 이해할 수 없기 때문에 이것이 완전한 해결책은 아니지만, 아마도 이것이 시작될 것입니다. 파일을 가정

join fileB fileA | 
awk '{diff=($3<$7?$3:$7)-($2>$6?$2:$6)} diff>0{print $0, diff}' | 
sort -k1,1 -k9nr | 
awk '!a[$1,$2,$3]++' 

chr1 250 650 TF2 G2 400 600 E2 200 
chr1 450 850 TF3 G3 600 800 E3 200 
chr1 100 250 TF1 G1 200 400 E1 50 

마지막 열은 아마도뿐만 아니라 다음 단계에 유용 할 것이며, 오버랩 량을 도시 ... 제 키에 따라 정렬된다.마지막 awk의 약간의 수정과

UPDATE

당신이 chr1 250 650 목록에 세 번이뿐만 아니라 당신의 출력

$ join fileB fileA | ...| awk '!(a[$1,$2,$3]++-1)' 
chr1 250 650 TF2 G2 200 400 E1 150 
chr1 450 850 TF3 G3 400 600 E2 150 

$ join fileB fileA | ... | awk '!(a[$1,$2,$3]++-2)' 
chr1 250 650 TF2 G2 600 800 E3 50 

을 두 번째와 세 번째 이웃을 얻을 수있는, 아마도 그것은 오타가 나 여기에 당신이하려는 것을 오해하고 있습니다 ...

또는 레코드의 순서를 표시하고 ba 필터링을 할 수 있습니다 그것에 대해 sed. 0 중앙이다

$ join fileB fileA | ... | awk '{print a[$1,$2,$3]++, $0}' | sort -k1n 

0 chr1 100 250 TF1 G1 200 400 E1 50 
0 chr1 250 650 TF2 G2 400 600 E2 200 
0 chr1 450 850 TF3 G3 600 800 E3 200 
1 chr1 250 650 TF2 G2 200 400 E1 150 
1 chr1 450 850 TF3 G3 400 600 E2 150 
2 chr1 250 650 TF2 G2 600 800 E3 50 

여기에서 첫 번째 열은, 인접 번호를 나타낸다. 모두 함께 이겠지

, 당신은 파일

join fileB fileA       | 
awk ' {diff=($3<$7?$3:$7)-($2>$6?$2:$6)} 
    diff>0 {print $0,diff}'     | 
sort -k1,1 -k9nr       | 
awk '{print a[$1,$2,$3]++, $0}'    | 
sort -k1n         | 
awk '{file=($1==0)?"central":"neighbor"$1; 
     print $2,$3,$4,$5,$6,$7,$8,$9 > file}' 

이러한 파일을 생성을 분리 원하는 필드를 추출 할 수 있습니다. 이 양식 (필요한 경우 업데이트)이 모든 일 awk 스크립트에 결합 될 수있다,하지만 난 그게 이해하기 쉽게 생각

==> central <== 
chr1 100 250 TF1 G1 200 400 E1 
chr1 250 650 TF2 G2 400 600 E2 
chr1 450 850 TF3 G3 600 800 E3 

==> neighbor1 <== 
chr1 250 650 TF2 G2 200 400 E1 
chr1 450 850 TF3 G3 400 600 E2 

==> neighbor2 <== 
chr1 250 650 TF2 G2 600 800 E3 

참고.

+0

나를 도와 주실 시간을내어 주셔서 대단히 감사합니다. – Newbie

+0

여러분을 환영합니다. 앞으로 지불... – karakfa