IT TIP

대소 문자를 구분하지 않는 검색 및 sed로 대체

itqueen 2020. 10. 23. 19:49
반응형

대소 문자를 구분하지 않는 검색 및 sed로 대체


SED를 사용하여 로그 파일에서 텍스트를 추출하려고합니다. 너무 많은 문제없이 검색 및 바꾸기를 수행 할 수 있습니다.

sed 's/foo/bar/' mylog.txt

그러나 검색시 대소 문자를 구분하지 않고 싶습니다. 내가 검색 한 내용 i에서 명령 끝에 추가 하면 작동 하는 것처럼 보입니다 .

sed 's/foo/bar/i' mylog.txt

그러나 이것은 나에게 오류 메시지를 제공합니다.

sed: 1: "s/foo/bar/i": bad flag in substitute command: 'i'

여기서 무엇이 잘못되었으며 어떻게 해결합니까?


명확하게 말하면 : macOS 에서-Mojave (10.14) sed현재 --BSD 구현-대소 문자를 구분하지 않는 일치를 지원하지 않음 -믿기 어렵지만 사실입니다. 이전 허용 대답 자체가 보여, GNU의 sed 명령 때문에 그 상태를 얻은 perl코멘트에 언급 기반 솔루션입니다.

확인하려면 펄 솔루션 과 함께 작업 외국 문자를 UTF-8을 통해,뿐만 아니라를 사용 뭔가 같은 :

perl -C -Mutf8 -pe 's/öœ/oo/i' <<< "FÖŒ" # -> "Foo"
  • -C 현재 로케일이 UTF-8 기반이라고 가정하고 스트림 및 파일에 대한 UTF-8 지원을 설정합니다.
  • -Mutf8Perl에게 소스 코드 를 UTF-8 (이 경우에 전달 된 문자열 -pe) 로 해석하도록 지시합니다. 이것은 더 자세한 감사, Mark Reed에 해당하는 짧은 값입니다.-e 'use utf8;'.

(참고 것을 사용하는 것이 awk중 하나를 선택할 수 없습니다 로, awk맥 OS (즉,에 대한 것은 BWK의 AWK , 일명 BSD AWK ) 모두 로케일 전혀 모르고 것으로 보인다 - 그 tolower()toupper()(함수 외국 문자를 무시하고 sub()/ gsub()에 케이스 - 무감각 플래그가 없습니다 로 시작).)


편집자 주 :이 솔루션은 GNU 에만 적용되는 sed반면 macOS는 BSD 와 함께 제공 되기 때문에 macOS (기본 제공)에서는 작동하지 않습니다 sed.

'I'를 대문자로하십시오.

sed 's/foo/bar/I' file

sedMac OS X에 대한 또 다른 해결 방법 gsed은 MacPorts 또는 HomeBrew에서 설치 한 다음 별칭을 만드는 것 sed='gsed'입니다.


의 Mac 버전은 sed약간 제한적인 것 같습니다. 이 문제를 해결하는 한 가지 방법은 사용 가능한 버전이있는 Linux 컨테이너 (Docker를 통해)를 사용하는 것입니다 sed.

cat your_file.txt | docker run -i busybox /bin/sed -r 's/[0-9]{4}/****/Ig'

나오지도 자주 묻는 질문 주소 밀접하게 관련 대소 문자를 구별하지 검색 . a) 많은 버전의 sed가 플래그를 지원하고 b) sed에서 수행하는 것이 어색합니다. awk 또는 Perl을 사용해야합니다.

그러나 POSIX sed에서 수행하기 위해 세 가지 옵션을 제안합니다 (여기에서 대체 용으로 조정 됨).

  1. 대문자로 변환하고 원래 줄을 보관 공간에 저장하십시오. 그러나 원본 콘텐츠는 인쇄 전에 복원되므로 대소 문자를 구분하지 않는 일치를 기반으로 행을 삽입하거나 추가하는 데만 유용합니다.

  2. 가능성은 FOO, Foo로 제한 될 수 있습니다 foo. 이것들은

    s/FOO/bar/;s/[Ff]oo/bar/
    
  3. 가능한 모든 일치 항목을 검색하려면 각 문자에 대괄호 표현식을 사용할 수 있습니다.

    s/[Ff][Oo][Oo]/bar/
    

나는 비슷한 필요가 있었고 이것을 생각해 냈습니다.

이 명령을 사용하면 모든 파일을 간단히 찾을 수 있습니다.

grep -i -l -r foo ./* 

이것은 this_shell.sh를 제외하고 (이 명령을 this_shell.sh 라는 스크립트에 넣은 경우 ) 콘솔에 출력을 입력하여 무슨 일이 일어 났는지 확인한 다음 찾은 각 파일 이름에 sed를 사용하여 텍스트 foo를 bar로 바꿉니다. :

grep -i -l -r --exclude "this_shell.sh" foo ./* | tee  /dev/fd/2 | while read -r x; do sed -b -i 's/foo/bar/gi' "$x"; done 

수정되지 않은 파일에 대해 모든 타임 스탬프가 변경되는 것을 좋아하지 않았기 때문에이 방법을 선택했습니다. grep 결과를 제공하면 대상 텍스트가있는 파일 만 볼 수 있습니다 (따라서 성능 / 속도도 향상 될 수 있음).

사용하기 전에 파일을 백업하고 테스트하십시오. 공백이 포함 된 파일의 일부 환경에서는 작동하지 않을 수 있습니다. (?)


패턴 매칭을 먼저하는 경우

/pattern/s/xx/yy/g

그런 다음 I패턴 뒤에 넣기를 원합니다 .

/pattern/Is/xx/yy/g

예:

echo Fred | sed '/fred/Is//willma/g'

반환 willma; 가 없으면 I손대지 않은 문자열 ( Fred)을 반환합니다 .


sed 's/string1/string2/Ig'

대문자 I는 대소 문자 구분에 관계없이 문자열을 검색하는 데 유용한 옵션입니다.

참고 URL : https://stackoverflow.com/questions/4412945/case-insensitive-search-and-replace-with-sed

반응형