^를 쉘 메타 문자로 사용


19

나는 오늘 포함 된 작은 스크립트를 작성

grep -q ^local0 /etc/syslog.conf

검토 중에 동료 는 Bourne 쉘에서 "파이프"를 의미 ^local0하기 때문에 인용 할 것을 제안했습니다 ^. 이 주장에 놀라서, 나는 이것을 언급 한 모든 참조를 추적하려고했습니다. 인터넷에서 찾은 것이 이것이 문제라고 제안한 것은 없습니다.

그러나 bshAIX 7에서 (Bourne 쉘이라고 주장 하는) 구현에는 실제로 다음과 같은 동작이 있습니다.

> bsh
$ ls ^ wc
      23      23     183
$ ls | wc
      23      23     183

내가 시도한 다른 "Bourne shell"구현 중 어느 것도 이런 식으로 작동 ^하지 않습니다 (즉, 쉘 메타 문자로 간주되지 않습니다). 나는 shCentOS (실제 bash)와 shFreeBSD (bash가 아닌 )에서 시도했다 . 시도 할 다른 시스템이 많지 않습니다.

이 동작이 예상됩니까? 어떤 쉘 ^이 파이프 메타 문자로 간주 됩니까?


1
나는 그것이 ^zsh와 정규 표현식 공간에서 부정 문자 라는 것을 알고 있습니다. 별도의 의견으로, 일반적으로 쉘 간 이식성을 위해 grep 표현식에 작은 따옴표를 사용하는 것이 좋습니다.
mkc

bourne shell은 현대 쉘 코드에서 여전히 해결 방법이있는 이상한 행동을 많이했습니다 [ x"$foo" = x"bar" ].
jordanm

bshBourne Shell이 ​​아닙니다. 이 이름은 AIX의 Bourne Shell에서만 남용됩니다. bsh오히려 1984 년 UNOS (첫 번째 UNIX 복제본)의 H.Berhold AG에서 소개 한 쉘입니다. AIX는 1984
없었

답변:


21

^의 동의어로 문자 |날짜는에서 다시 톰슨 쉘 . 그것들은 유닉스 v4에서 동시에 소개되었고 매뉴얼 페이지 에서 함께 언급되었습니다 . 스벤 마스 체크 (Sven Mascheck)타이핑 이“약간 고통 스러웠던^ ”초기 대문자 전용 터미널의 편의상“아마도 소개되었다”고 언급했다 .|

톰슨 쉘은 오래 전에 사라졌지 만 그 후속 버전 인 Bourne 쉘 은 동일한 구문을 유지했습니다 (맨 페이지 만 언급하지만 |).

ash, bash 및 ksh와 같은 후속 쉘 |은 파이프 문자 로만 이해 합니다. 오랫동안 Bourne 셸의 오픈 소스 릴리스가 없었기 때문에 오픈 소스 유닉스 변형에서 실제 Bourne 셸을 찾지 못할 것입니다. (OpenSolaris에 하나가 포함 된 것으로 생각되지만, 그 당시에는 새로운 구현에 의해 오래 쓸모가 없었던 것처럼 다른 곳에서는 채택되지 않았습니다).

단일 유닉스 규격은 언급하지 않습니다 ^효과적으로 POSIX 껍질이 literally¹ 해석해야한다는 것을 의미 특수 문자로. Bourne 쉘의 완전한 POSIX 호환 변형이 있다고 생각하지 않습니다 (독립 구현 만).

^옵션 extendedglob이 활성화되어 있지만 sh 호환 모드가 아닌 zsh에서는 특별 합니다. 기본 모드에서는 여러 가지면에서 POSIX와 다릅니다.

^어쨌든 명확성을 위해 정규 표현식을 인용 하는 것이 좋습니다 . 어떤 문자가 나타나는지에 관계없이 스크립트에서 정규식을 인용하십시오.

¹ 와일드 카드 패턴에서 대괄호 식의 첫 문자를 제외하고 !표준 부정 문자는 어디에 있지만 구현 ^방식 도 같은 방식으로 해석 될 수 있습니다 .


고맙게도 2003 년부터의 전체 TUHS 스레드가 깨달았습니다.
Greg Hewgill

완성도를 들어, 당신은 언급 할 수 ^있는 특별한 fish그것은 리디렉션 연산자, 어디 rc/ es이 A의 연결 연산자 는 명령 행의 첫 번째 문자 때 역사 확장으로 csh / tcsh에서 / bash는 / zsh을, 또는.
Stéphane Chazelas


3

예, OpenSolaris에는 Bourne Shell 소스가 포함되어 있지만 해당 소스는 이식 가능하지 않습니다.

Bourne Shell 소스의 유지 관리가 용이 ​​한 버전은 여기 에서 확인할 수 있습니다 schily-*.tar.bz2.

소스의 관련 부분은 다음과 같습니다 cmd.c.

/* 
* ^ is a relic from the days of UPPER CASE ONLY tty model 33s 
*/ 
if ((t = item(TRUE)) != 0 && (wdval == '^' || wdval == '|')) 

알다시피, 이것은 특정 쉘 (예 : Thompson 쉘)과 관련이 없지만 1970 년대에는 여전히 터미널 주변에 대문자 만 존재했다는 사실과 관련이 있습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.