저는 쉘 스크립팅을 처음 접 했지만 lftp 프로그램을 사용하는 스크립트를 거의 완성했습니다 . 문제가있는 스크립트 부분은 긴 문자열을 만들 때입니다 (로 구분 ;
).
for var in something
do
...
commands_to_run+="echo Result is `tail -n 1 $somefile`;"
done
내가 주목하는 것은 tail
for 루프가 반복 될 때 백틱으로 래핑 된 프로그램이 실행되고 있지만 나중에 스크립트에서 명령 문자열을 호출 할 때는 실행되지 않는다는 것입니다.
불행히도 $ somefile의 내용은이 단계에서 검사 할 준비가되지 않았습니다. 문자열을 만들 때가 아니라 필요할 때 명령을 실행하려면 어떻게해야합니까?
답변
이것은 조금 까다 롭습니다. Hauke가 제공 한 정보는 정확합니다. 사용 사례에 맞게 파싱하기 만하면됩니다.
가장 쉬운 방법은 변수 정의가 정의 할 때로 묶인 명령을 실행하지 않도록 $()
구문을 피하면서 구문 을 사용 하는 것입니다. 주의해야 할 점 은 중첩 된 명령을 실행하기 위해 실제 실행시 쉘에서 최종 결과를 (를 통해 ) 다시 평가해야한다는 것입니다 .$
$()
eval
예제를 보는 것이 훨씬 쉽기 때문에이 예제를 선택하면 올바른 길을 찾을 수 있습니다.
for((i=0;i<10;i++)); do
date +%s.%N # Print a timestamp (in format seconds.nanoseconds)
test="echo \$(date +%s.%N)" # Save a command to do the same
sleep 1 # Sleep for a second
eval "$test" # Evaluate the command saved in variable 'test'
echo # Print a new line before the next iteration
done
위 예제의 샘플 출력은 다음과 같습니다 (1 회 반복으로 트리밍).
1398832186.133661344
1398832187.139076728
각 루프의 두 번째 타임 스탬프는 첫 번째 루프 후 약 1 초입니다. 반대로, 정의 $
에서 이스케이프하지 않고 동일한 테스트를 수행 test
하고를 제거 eval
하면 두 타임 스탬프가 거의 일치합니다.
eval
대부분의 상황에서 사용하는 습관을 들이지 마십시오 . 그러나 이것을 피하는 좋은 방법을 모르는 사람들 중 하나입니다. 잘하면 이것이 도움이됩니다. 행운을 빕니다!
답변
인용에는 몇 가지 수준이 있습니다. 큰 따옴표 ( "..."
) 보호 공백 및 여러 특수 문자 ( ~
, &
, |
, ;
, …)하지만, 매개 변수 확장 및 명령 대체를 방지하지 않습니다.
'
“위험한”문자 앞에 작은 따옴표 ( ) 또는 백 슬래시 가 필요합니다 .
일반적으로 : $(tail ...)
백틱 대신에 사용을 고려해야 합니다. 백틱은 더 오래된 표준이지만 $()
대부분의 사람들에게 문제를 일으키지 않는 너무 오래된 것에 대해 이야기하고 있습니다. 새 버전은 읽기 쉽고 중첩 될 수 있습니다. sx의 형식 문제는 물론 …