
이 질문이 너무 일반적인 질문은 아니길 바랍니다. 저는 쉘 스크립팅을 처음 접했고 컴퓨터 아키텍처/비스크립팅 프로그래밍 경력을 갖고 있습니다. 나는 내 작업의 스크립트에서 전체 스크립트 주위에 하위 쉘을 만들어 스크립트를 작성하는 경우가 거의 없음을 확인했습니다. 내가 작성하고 있는 스크립트에서 하위 셸로 이를 포함할 수 있는 이유는 하위 셸이 내 것을 호출하는 다른 스크립트와 혼동되는 것을 방지하기 때문입니다(만일의 경우). 이 접근 방식과 관련된 일부 오버헤드 때문에 이는 일반적인 관행이 아닙니까? 나는 이것을 온라인에서 찾는 데 어려움을 겪고 있습니다.
예:
#!/bin/bash
( #Start of subshell
echo "Some stuff here"
) #End of subshell
답변1
서브쉘에는 오버헤드가 있습니다.
내 시스템에서 최소 포크 실행 비용(파일이 콜드되지 않은 상태에서 디스크에서 프로그램을 실행할 때)은 약 2ms
이고 최소 포크 비용은 약 입니다 1ms
.
서브쉘을 사용하면 파일을 편집할 필요가 없으므로 포크 비용만 이야기하는 것입니다 exec
. 서브쉘이 합리적으로 낮게 유지되면 1ms
인간을 대상으로 하는 프로그램에서는 매우 무시할 수 있습니다. 나는 인간이 더 빠르게 일어나는 일을 알아차릴 수 없다고 믿습니다 50ms
. (그리고 그것은 현대 스크립팅 언어 통역사가 최신 작업을 시작하는 데 (여기서는 python
루비라고 말하고 있습니다 rvm
)) 시작하는 데 걸리는 시간입니다 .nodejs
100ms
그러나 루프가 추가되고 예를 들어 함수에서 무언가를 $()
가져오는 다소 일반적인 백틱이나 패턴을 표준 출력으로 인쇄하여 상위 쉘이 bashism과 같은 것으로 캡처하도록 대체할 수 있습니다 (또는 빠른 외부 전체 배치를 처리하는 프로그램).return
printf -v
그만큼bash 완성패키지는 다음에 설명된 기술을 사용하여 전달된 변수 이름을 통해 반환함으로써 이 서브셸 비용을 특별히 방지합니다.http://fvue.nl/wiki/Bash:_Passing_variables_by_reference
비교
time for((i=0;i<10000;i++)); do echo "$(echo hello)"; done >/dev/null
~와 함께
time for((i=0;i<10000;i++)); do echo hello; done >/dev/null
fork
시스템 오버헤드가 무엇인지에 대한 좋은 추정치를 제공해야 합니다 .
답변2
내 시스템에서 PSkocik이 제공한 뛰어난 코드를 실행해도 무시할 만한 결과가 나타났습니다.
그러나 이 예제는 실제로 기본 명령과 하위 쉘 명령을 비교하여 적용됩니다.
MyPath="path/name.ext"
# this takes forever
time for((i=0;i<10000;i++)); do echo "$(basename ${MyPath} )"; done >/dev/null
#this is over 100x less time
time for((i=0;i<10000;i++)); do echo "${MyPath##*/}"; done >/dev/null