IT박스

Bash에서 정규 표현식과 문자열을 어떻게 일치시킬 수 있습니까?

itboxs 2020. 6. 20. 10:40
반응형

Bash에서 정규 표현식과 문자열을 어떻게 일치시킬 수 있습니까?


나는 주어진 때 있도록 기능을 포함하는 bash는 스크립트를 작성하는 것을 시도하고있다 .tar, .tar.bz2, .tar.gz등의 파일을이 파일의 압축을 관련 스위치와 타르를 사용합니다.

if elif를 사용하여 파일 이름을 테스트하여 끝나는 것을 확인하고 정규식 메타 문자를 사용하여 일치시킬 수없는 문을 사용하고 있습니다.

명령 줄에서 'test'를 사용하는 스크립트를 지속적으로 다시 작성하지 않기 위해 아래 명령문이 작동해야한다고 생각했습니다. 가능한 모든 대괄호, 따옴표 및 메타 문자 조합을 시도했지만 여전히 실패합니다.

test sed-4.2.2.tar.bz2 = tar\.bz2$; echo $?
(this returns 1, false)

나는 문제가 단순한 문제라고 확신하며 어디에서나 보았지만 어떻게 해야할지 모릅니다. 누군가 내가 어떻게 할 수 있는지 알고 있습니까?


정규식을 일치 시키려면 =~연산자 를 사용해야합니다 .

이 시도:

[[ sed-4.2.2.tar.bz2 =~ tar.bz2$ ]] && echo matched

또는 ==연산자 와 함께 와일드 카드 (정규식 대신)를 사용할 수 있습니다 .

[[ sed-4.2.2.tar.bz2 == *tar.bz2 ]] && echo matched

이식성이 문제가되지 않는다면, [[대신에 [또는 test더 안전하고 강력하게 사용 하는 것이 좋습니다 . 테스트와 [와 [[의 차이점무엇입니까? 자세한 내용은.


이것을하는 기능

extract () {
  if [ -f $1 ] ; then
      case $1 in
          *.tar.bz2)   tar xvjf $1    ;;
          *.tar.gz)    tar xvzf $1    ;;
          *.bz2)       bunzip2 $1     ;;
          *.rar)       rar x $1       ;;
          *.gz)        gunzip $1      ;;
          *.tar)       tar xvf $1     ;;
          *.tbz2)      tar xvjf $1    ;;
          *.tgz)       tar xvzf $1    ;;
          *.zip)       unzip $1       ;;
          *.Z)         uncompress $1  ;;
          *.7z)        7z x $1        ;;
          *)           echo "don't know '$1'..." ;;
      esac
  else
      echo "'$1' is not a valid file!"
  fi
}

다른 주

위의 의견에서 Aquarius Power에 대한 답변으로, We need to store the regex on a var

변수 BASH_REMATCH는 표현과 일치하고, $ {BASH_REMATCH [n이]} 다음에 괄호 예에 싸여 n 번째 그룹을 일치합니다 후 설정 ${BASH_REMATCH[1]} = "compressed"${BASH_REMATCH[2]} = ".gz"

if [[ "compressed.gz" =~ ^(.*)(\.[a-z]{1,5})$ ]]; 
then 
  echo ${BASH_REMATCH[2]} ; 
else 
  echo "Not proper format"; 
fi

(위의 정규식은 파일 이름 지정 및 확장명에 유효한 것이 아니지만 예제에서 작동합니다.)


여기에 의견을 말할 충분한 담당자가 없으므로 dogbane의 답변을 개선하기 위해 새로운 답변을 제출하고 있습니다. 점. 정규 표현식에서

[[ sed-4.2.2.tar.bz2 =~ tar.bz2$ ]] && echo matched

실제로 'tar.bz2'사이의 리터럴 점뿐만 아니라 모든 문자와 일치합니다.

[[ sed-4.2.2.tar4bz2 =~ tar.bz2$ ]] && echo matched
[[ sed-4.2.2.tar§bz2 =~ tar.bz2$ ]] && echo matched

또는 '\'로 이스케이프 할 필요가없는 것 그러면 엄격한 구문은

[[ sed-4.2.2.tar.bz2 =~ tar\.bz2$ ]] && echo matched

또는 더 엄격하게 갈 수 있고 정규식에 이전 점을 포함시킬 수도 있습니다.

[[ sed-4.2.2.tar.bz2 =~ \.tar\.bz2$ ]] && echo matched

bash를 사용하고 있으므로이를 위해 자식 프로세스를 만들 필요가 없습니다. 다음은 bash 내에서 완전히 수행하는 솔루션입니다.

[[ $TEST =~ ^(.*):\ +(.*)$ ]] && TEST=${BASH_REMATCH[1]}:${BASH_REMATCH[2]}

설명 : 시퀀스 "콜론 및 하나 이상의 공백"전후의 그룹은 BASH_REMATCH 배열의 패턴 일치 연산자에 의해 저장됩니다.


shopt -s nocasematch

if [[ sed-4.2.2.$LINE =~ (yes|y)$ ]]
 then exit 0 
fi

if [[ $STR == *pattern* ]]
then
    echo "It is the string!"
else
    echo "It's not him!"
fi

나를 위해 작동합니다! GNU bash, version 4.3.11(1)-release (x86_64-pc-linux-gnu)

참고 URL : https://stackoverflow.com/questions/17420994/how-can-i-match-a-string-with-a-regex-in-bash

반응형