ㅏ

내 문제의 원인은답은 이 링크에 있습니다, 그리고 추가 내용

고쳐 쓰다

즉, 첫 번째 명령은 이해 grep \\[[a-z\|1-9]*\\] file하지만 두 번째 명령의 출력은 이해하지 못합니다 grep \[[a-z\|1-9]*\] file.

이제 두 번째 명령의 출력이 어떻게 구성되는지, 특히 grep이 세 번째와 네 번째 줄 전체를 선택하지만 첫 번째 줄까지 두 번째와 세 번째 줄만 선택하는 이유를 이해하고 싶습니다.]

여기에 이미지 설명을 입력하세요.

답변1

귀하의 질문에 철저하게 답변하기에는 너무 많은 변수와 명시되지 않은 가정이 있습니다.

여기서 가장 큰 함정은 쉘(즉, 대부분의 Bourne 호환 쉘 - zsh 또는 csh 및 그 파생물에 대해 확실하지 않음)이 기본적으로 확장되지 않은 glob을 전달한다는 것입니다.아무것도 일치하지 않는 경우.따라서 먼저 이와 같은 표현식을 \\[[a-z0-9]*\\]와일드카드로 사용해 보십시오.만약에일치하지 않는 파일의 경우(예: 문자가 아닌 모든 단어는 리터럴임) 와일드카드가 그대로 전달 \fno[rd\]됩니다 .grep

(이것을 다시 확인해 보겠습니다. 이것은 이중 백슬래시입니다. 즉, 인용된 리터럴 백슬래시 뒤에 두 개의 왼쪽 대괄호가옵니다. 첫 번째 문자는 첫 번째 문자가 두 번째 문자인 문자 클래스를 만듭니다 [. 이를 정규식으로 구문 분석한 결과는 다음과 같습니다. 다르지만 똑같이 수수께끼입니다).

이에 대한 유일한 합리적인 해결책은 쉘에 의한 공백 토큰화 및 와일드카드 확장이 필요하지 않은 항목을 적절하게 인용하는 것입니다. 내 제안은 모든 정규식에 작은따옴표를 사용하는 것입니다. 그러면 별도의 노력을 하지 않고도 무엇을 어떻게 일치시킬지에 대한 합리적인 기대치를 형성할 수 있습니다.패턴(셸, 정규식)에 대한 전문적인 해석입니다.

정확한 일치를 원하는 경우 var[1]정규식은 [a-z]*\[[0-9]*\]비슷한 작업을 수행할 수 있습니다 . 대괄호를 문자 클래스의 일부로 사용하려면 [][a-z0-9]*첫 번째 ]와 두 번째가 [문자 클래스의 리터럴 멤버인지 시도해 보세요. 이를 grep쉘 에 전달하는 경우 주위에 있는 작은따옴표를 기억하십시오.

답변2

천천히 가자. 다음 내용이 포함된 파일이 있는 경우(표시하기 쉽도록 한 줄만 사용):

$ cat infile
list[1]; i[ab1]; var[1] [1]var  [1]var[2]

Simple은 grep --color a모든 a를 빨간색으로 표시합니다. (사이트에서 색상 제어를 허용하므로 굵은 글씨가 빨간색이라고 가정):

$ grep --color a infile  

list[1]; i[b1]; vr[1] [1]vr [1]vr[2]

a 가 (위와 같이) 인용되지 않거나 인용된 경우에도 똑같은 일이 발생합니다.

$ grep --color \a infile  

list[1]; i[b1]; vr[1] [1]vr [1]vr[2]

$ grep --color "a" infile  

list[1]; i[b1]; vr[1] [1]vr [1]vr[2]

$ grep --color 'a' infile  

list[1]; i[b1]; vr[1] [1]vr [1]vr[2]

왜? 왜냐하면 a는둘 다:

  1. 껍질에는 특별한 것이 없습니다.
  2. 쉘은 따옴표를 제거하고 grep은 a첫 번째 인수와 동일한 내용을 받습니다. 백슬래시 따옴표, 큰따옴표 또는 작은따옴표입니다.

]

중괄호를 선택하려면 ](닫는 중괄호부터 시작하겠습니다):

$ grep --color ] infile  

list[1]; i[ab1]; var[1][1]var [1]var[2]

]참조(모든 참조)가 있는 경우에도 동일한 일이 발생합니다.
이 경우에는 ]쉘에 특별하지만 일치하는 여는 중괄호가 없는 경우에는 그렇지 않습니다.

닫는 중괄호의 경우 상황이 더 복잡해집니다. 이러한 모든 오류는 다음과 같습니다.

grep --color  [  infile
grep --color '[' infile
grep --color "[" infile

왜? grep으로 받은 콘텐츠 때문에모두사건은 특이하다 [.
이 간단한 에코를 통해 쉘이 수행하는 작업을 확인할 수 있습니다.

 $ echo \[ "[" '['
 [ [ [

셸은 첫 번째 수준 참조를 제거하고 모든 값은 동일하게 보입니다.

[

그러나 grep이 얻고자 하는 것은 우리가 실제로 검색하는 문자가 [백슬래시로 묶인 대괄호( \[)라는 것을 이해하는 것입니다. 이 모든 일이 발생합니다.

$ echo \\[ "\[" '\['
\[ \[ \[

grep은 다음 중 하나와 함께 사용할 수 있습니다.

$ grep --color \\[ infile

list[1]; i[ab1]; var[1][1]var[1]var[2]

[[]

(단 하나의 문자만 포함하는 문자 목록)을 사용하면 [[]동일한 결과를 얻을 수 있습니다(따옴표가 있는 한).

$ grep --color '[[]' infile

list[1]; i[ab1]; var[1][1]var[1]var[2]

[[]Grep이 제대로 작동하려면 정확한 수신이 필요합니다 . 따옴표가 필요하지 않은 것 같습니다.

$ echo \[\[\] "[[]" '[[]' [[]
[[] [[] [[] [[]

그러나 다음과 같은 파일을 생성하면 [이 아이디어는 깨집니다 .

$ touch \[
$ echo \[\[\] "[[]" '[[]' [[]
[[] [[] [[] [

그것은 [껍질에 특별하기 때문입니다. 쉘의 경우 파일 이름 글로빙 모드를 활성화합니다. 하나 이상의 파일이 패턴과 일치하면 파일 목록이 대체됩니다.

따라서 다음은 올바르게 작동합니다.

$  grep --color '[[]' infile

list[1]; i[ab1]; var[1][1]var[1]var[2]

그리고 이것은: grep --color '[]]' infile닫는 중괄호와 일치합니다.

[][]

왼쪽 대괄호 일치그리고닫는 대괄호 안에는 특정 문자 시퀀스(물론 따옴표 포함)가 필요합니다.

이것을 시도하면:

$  grep --color '[[]]' infile

게임은 전혀 없을 것입니다. 작동하려면 다음이 필요합니다.

$ grep --color '[][]' infile

list[1]; i[ab1]; var[1][1]var[1]var[2]

이 특정 순서에서 닫는 중괄호는 문자 범위의 첫 번째 문자여야 합니다. 여는 중괄호는 문자 목록의 마지막 문자여야 합니다.

[]a-z0-9[]

그런 다음 추가 문자를 추가할 수 있습니다(그 이상은 추가할 수 없음 ;).

$ grep --color '[]a-z0-9[]' infile

목록[1];나[ab1];변수[1][1]변수[1]변수[2]

|그런 다음 범위에서 누락된 항목을 추가하고 게시한 링크와 일치하도록 만들 수 있습니다. 해당 링크의 정규식은 여기와 다르며 매우 다른 방식으로 작동합니다. one 과 다른 문자를 일치시키는 것으로 시작 [하고 종결자로 끝납니다 ]. 다음과 같은 것(탐욕스러운 성격이 *전체 라인을 차지합니다):

$  grep --color '\[.*\]' infile

list[1];i[ab1];변수[1][1]변수[1]변수[2]

아니면 다음과 같습니다:

$ grep --color '[[][a-c0-9]*[]]' infile

list[1]; i[ab1]; var[1][1]var[1]var[2]`

관련 정보