내부에헤비히트 트랩"Greg's Wiki"에서 다음 인용문을 발견했습니다.
사실
echo
여기서 이 명령을 사용하는 것은 절대적으로 안전하지 않습니다.-n
예를 들어, 변수에 포함된 경우echo
인쇄할 데이터가 아닌 옵션으로 간주됩니다. 변수 값을 인쇄하는 절대적으로 신뢰할 수 있는 유일한 방법은 다음을 사용하는 것입니다printf
.printf "%s\n" "$foo"
하지만 내가 입력할 때:
var="-n Hello"
echo "$var"
잘 작동하고 옵션으로 설명되지 않는데 , 내가 인용한 출처에서 절대적으로 안전하려면 -n
이 기능을 사용해야 한다고 말하는 이유를 이해할 수 없습니다 .printf
답변1
귀하의 예에서는 "우연히" 잘 작동합니다. 그 이유는 이것이다
- 매개변수를 하나만 제공했습니다
echo
. - 제안된 대로 변수를 참조했습니다.
즉 , "단어" 사이의 공백을 포함하여 echo
문자열만 명령줄 인수로 간주됩니다 . -n Hello
이제 echo
(글쎄, 일부 s)는 옵션을 인식하지만 문자열은 echo
인식하지 않도록 프로그래밍되어 있으므로 옵션이라고 가정합니다.-n
-n<space>Hello
피연산자- 즉, "있는 그대로" 인쇄하려는 문자열입니다(아마도 \
시퀀스가 확장된 상태에서).
사용한 적이 있는 경우
echo $var
따옴표가 없고 기본값이 이면 $IFS
공백 $var
으로 분할되어 다음과 echo
같이 표시됩니다.둘논쟁: -n
-옵션으로 해석됩니다- 그리고 Hello
.
이것은 의미한다이 경우, 쉘 변수를 올바르게 인용하는 것은 echo
피연산자가 옵션으로 해석되는 상황이 부주의하게 발생하는 것을 방지하는 해결 방법입니다.
하지만:
링크된 소스의 예는 "전역 확장"( )을 통해 파일 목록을 인쇄하는 것입니다
*.zip
. 여기서 변수는~ 해야 하다따옴표 없이 사용되므로 이 보호 기능을 항상 사용할 수 있는 것은 아닙니다.참조 변수는 다음 상황에서만 유용합니다.분사
echo
옵션 매개변수가 표시 됩니다.. 인쇄하려는 매개변수가-n
처음부터 단일 매개변수인 경우 인용은 도움이 되지 않습니다.예를 들어, print 에 대한 문자열 배열을 수집했고
echo
문자열 중 하나가 다음에 대한 옵션 인수이기도 한 상황을 생각해 보세요echo
.arguments=( "-n" "Hello" )
그런 다음 변수를 올바르게 참조하더라도
echo "${arguments[@]}"
첫 번째 토큰은
echo
여전히-n
피연산자가 아닌 옵션으로 간주됩니다. 여러 변수를 인수로 전달echo
하고 첫 번째 변수가 or 인 경우에도 마찬가지입니다-n
. 여기서도 변수를 인용하는 것은 도움이 되지 않습니다.일반적으로 프로그램이 다음 형식의 매개변수를 허용하는 경우에는 인용조차 도움이 되지 않습니다.
-oValue
.가상의 상황에서
my_formula_renderer
수학 공식을 형식화하고 선택적 인수를 허용하는 프로그램을 사용하십시오. 그런 다음 다음과 같은 수식을 조판한다고 가정해 보겠습니다.-sfontsize
-sqrt(a^2 + b^2)
./my_formula_renderer "-sqrt(a^2+b^2)"
프로그램에 종료 옵션 구문 분석 지정자가 없으면 위 수식의 기본 글꼴 크기를 사용하는 대신
--
글꼴 크기 조판 "없음"을 사용하려고 한다고 가정합니다 .qrt(a^2+b^2)
;
-s
와 같은 다른 수식 요소 사이에 명시적인 공백이 있는 경우 에도 도움이 되지 않습니다. 선행 공백이 있는 "글꼴 크기""-s +2t +u^2"
로 잘못 해석했을 수도 있습니다 (참조+2t +u^2
예를 들어 이 질문이것이 문제가 됩니다.)프로그램이 단일 문자 옵션의 "클러스터링"을 허용하는 경우에도 마찬가지입니다.
예를 들어 @Stéphane Chazelas가 지적했듯이
echo
문자열은 options 및 의 연결로 해석될 수 있으므로 해당 문자열-neEenennne
을 인쇄하려고 하면 예기치 않은 방식으로 실패하거나 동작할 수 있습니다.-n
-e
-E
echo
옵션 처리 외에도
echo
( 일부 버전에서는 기본적으로 옵션이 활성화된 경우를echo
포함하여 일부 ) 등 이 개행, 백슬래시, 백스페이스 문자로 확장 됩니다.bash
xpg_echo
\n
\\
\b
백슬래시가 포함될 수 있는 축어적 문자열을 출력하는 데 사용할 수 없습니다..
TL/DR
핵심은 당신이 인용한 출처에 '절대'라는 단어가 있고, echo
그것이 구체적으로 가리키는 사실이다. 대부분의 경우 echo
괜찮을 것입니다. 그러나 맹목적으로 의존하기 시작하면 (조만간) 어떤 일이 일어나 echo
거나 실제로는 더 중요한 또 다른 프로그램이 될 것입니다."피연산자" 매개변수로 의도한 것을 실수로 "옵션" 매개변수로 잘못 해석함, 일반적으로 쉘 변수로 전달할 때.