인용된 표현식에서 확장된 경로 이름 확장 패턴을 이스케이프 처리하는 방법은 무엇입니까?
-
22-08-2019 - |
문제
기본 외에 *
, ?
그리고 [...]
패턴과 관련하여 Bash 쉘은 다음과 같은 확장된 패턴 일치 연산자를 제공합니다. !(pattern-list)
("주어진 패턴 중 하나를 제외하고 모두 일치").그만큼 extglob
이를 사용하려면 쉘 옵션을 설정해야 합니다.예:
~$ mkdir test ; cd test ; touch file1 file2 file3
~/test$ echo *
file1 file2 file3
~/test$ shopt -s extglob # make sure extglob is set
~/test$ echo !(file2)
file1 file3
하위 쉘에서 이를 실행하는 프로그램에 쉘 표현식을 전달하면 연산자에서 오류가 발생합니다.다음은 하위 셸을 직접 실행하는 테스트입니다(여기서는 확장이 조기에 발생하지 않도록 다른 디렉터리에서 실행하고 있습니다).
~/test$ cd ..
~$ bash -c "cd test ; echo *"
file1 file2 file3
~$ bash -c "cd test ; echo !(file2)" # expected output: file1 file3
bash: -c: line 0: syntax error near unexpected token `('
bash: -c: line 0: `cd test ; echo !(file2)'
나는 온갖 종류의 탈출을 시도했지만, 내가 생각해낸 어떤 것도 제대로 작동하지 않았습니다.나도 의심했어 extglob
하위 쉘에 설정되어 있지 않지만 그렇지 않습니다.
~$ bash -c "shopt -s extglob ; cd test ; echo !(file2)"
bash: -c: line 0: syntax error near unexpected token `('
bash: -c: line 0: `cd test ; echo !(file2)'
어떤 솔루션이라도 감사하겠습니다!
해결책
$ bash -O extglob -c 'echo !(file2)' file1 file3
다른 팁
Bash가 Globbing Pattern Syntax를 검증 할 때 "Shopt -S Extglob"은 실행하기 전에 각 라인을 실행하기 전에 각 줄을 구문 분석합니다. 같은 줄에서 옵션을 활성화 할 수 없습니다. 그렇기 때문에 "Bash -o extglob -c 'xyz'"솔루션 (Randy Proctor)이 작동하고 필요합니다.
피하고 싶다면 다른 방법이 있습니다. eval
그리고 넌 방향을 바꿀 수 있어야 해 익스트글로브 서브쉘 내에서 켜고 끕니다.패턴을 변수에 넣으십시오.
bash -c 'shopt -s extglob; cd test; patt="!(file2)"; echo $patt; shopt -u extglob; echo $patt'
다음과 같은 출력을 제공합니다.
file1 file3
!(file2)
그것을 보여주는 익스트글로브 설정 및 해제되었습니다.첫 번째 경우 echo
주위에 인용문이 있었어요 $patt
, 그것은 두 번째와 같은 패턴을 뱉어 낼 것입니다 echo
(아마도 따옴표가 있어야 할 것입니다).
글쎄, 나는 진정한 경험이 없습니다 Extglob, 그러나 나는 그것을 감싸서 작동하게 할 수 있습니다. echo
에서 eval
:
$ bash -c 'shopt -s extglob ; cd test ; eval "echo !(file2)"'
file1 file3