특정 패턴 앞과 다른 패턴 뒤의 모든 단어를 제거합니다.

특정 패턴 앞과 다른 패턴 뒤의 모든 단어를 제거합니다.

줄이 많은 파일이 있습니다. 각 줄은 패턴으로 시작 gi_[0-9]하고 탭과 단어 목록이 차례로 따르며 모두 세미콜론으로 구분됩니다. 마지막 8단어만 유지하고 싶습니다(마지막 부분에 2단어가 있으므로 7부분).

이것은 예이다입력하다문서:

gi_1\tDog;Pink;Blue;Beige;Yellow;Orange;Red;Green irish

gi_2\tPork;Black;White;Beige;Brown;Cyan;Purple;Red pepper

이것해당 출력해야 한다:

gi_1\tPink;Blue;Beige;Yellow;Orange;Red;Green irish

gi_2\tBlack;White;Beige;Brown;Cyan;Purple;Red pepper

노트:탭 문자를 삽입하는 방법을 찾지 못해 대신 \t를 썼는데 파일에 탭 표시가 생겼습니다.

답변1

짧은sed방법:

sed 's/^\(.*\t\)[^;]*;/\1/' file

산출:

gi_1    Pink;Blue;Beige;Yellow;Orange;Red;Green irish
gi_2    Black;White;Beige;Brown;Cyan;Purple;Red pepper

  • \(.*\t\)- 첫 번째 부분에 필요한 부분을 캡처하세요.

답변2

그리고 awk:

awk -F '\t' -v OFS='\t' 'sub("^[^;]*;", "", $2)' file.txt
  • sub("^[^;]*;", "", $2);하위 문자열을 탭으로 구분된( -F '\t') 두 번째 필드에서 시작하고 첫 번째 필드에 대해 null로 끝나는 하위 문자열로 바꿉니다 . sub()교체품이 있는지 여부

  • -v OFS='\t'출력 필드 구분 기호를 탭으로 설정

  • 첫 번째 필드(및 기타 모든 필드)는 그대로 유지됩니다.


완전성을 위해 첫 번째 필드 gi_뒤에 숫자가 와야 합니다.

awk -F '\t' -v OFS='\t' '$1 ~ /^gi_[[:digit:]]$/ {sub("^[^;]*;", "", $2); print}' file.txt

예:

% cat file.txt 
gi_1    Dog;Pink;Blue;Beige;Yellow;Orange;Red;Green irish
gi_2    Pork;Black;White;Beige;Brown;Cyan;Purple;Red pepper

% awk -F '\t' -v OFS='\t' 'sub("^[^;]*;", "", $2)' file.txt
gi_1    Pink;Blue;Beige;Yellow;Orange;Red;Green irish
gi_2    Black;White;Beige;Brown;Cyan;Purple;Red pepper

% awk -F '\t' -v OFS='\t' '$1 ~ /^gi_[[:digit:]]$/ {sub("^[^;]*;", "", $2); print}' file.txt
gi_1    Pink;Blue;Beige;Yellow;Orange;Red;Green irish
gi_2    Black;White;Beige;Brown;Cyan;Purple;Red pepper

답변3

Perl 스타일 grep을 사용하는 일반적인 솔루션:

$ a="gi_1 \t Dog;Pink;Blue;Beige;Yellow;Orange;Red;Green irish"
[s@SS data]$ echo $a | grep -P -o "((^gi_. \\\t )|(?<=[; ])(?:.(?!(([; ].+)){8}))+$)" | sed ':a;N;$!ba;s/\n/ /g'
gi_1 \t  Pink;Blue;Beige;Yellow;Orange;Red;Green irish

이는 단어 수에 관계없이 작동합니다.

비캡처 그룹 및 부정 예측은 반복되는 시퀀스 [;를 따르지 않는 모든 문자를 제외합니다. ] 뒤에 임의의 문자가 옵니다.

시작 부분의 긍정적인 예측은 선행 [; \t] 문자를 제거합니다.

sed 부분은 중간에 있는 새 줄을 제거합니다.

답변4

GNU sed를 사용하면 do-until 루프 구조에서 6개의 세미콜론을 찾아서 이를 수행할 수 있습니다.

sed -e '
   :loop
      s/\t[^;]*;/\t/
      s/;/&/6
   Tloop
' yourfile

관련 정보