bash를 사용하여 함수의 출력을 변수에 어떻게 할당 할 수 있습니까?


답변:


146
VAR=$(scan)

프로그램과 똑같은 방식입니다.


3
나는 "echo $ VAR"를 할 때 줄 바꿈이 제거되는 것을 발견했습니다. 대신 $ VAR을 인용하면 개행 문자가 유지됩니다.
Brent

2
100 % 맞지 않습니다. 명령 대체는 항상 후행 줄 바꿈을 제거합니다.
TheBonsai

7
이것은 서브 쉘을 생성합니다; 같은 셸에서 할 수있는 방법이 있습니까?
제한 속죄

24

일반 프로그램을 사용하는 것처럼 명령 / 파이프 라인에서 bash 함수를 사용할 수 있습니다. 이 기능은 하위 셸 및 전 이적으로도 사용할 수 있습니다. 명령 대체 :

VAR=$(scan)

대부분의 경우 원하는 결과를 얻을 수있는 확실한 방법입니다. 아래에 특별한 경우를 설명하겠습니다.

후행 줄 바꿈 유지 :

Command Substitution의 (보통 유용한) 부작용 중 하나는 후행 줄 바꿈을 제거한다는 것입니다. 후행 줄 바꿈을 유지하려면 더미 문자를 서브 쉘의 출력에 추가 한 다음 매개 변수 확장으로 제거 할 수 있습니다.

function scan2 () {
    local nl=$'\x0a';  # that's just \n
    echo "output${nl}${nl}" # 2 in the string + 1 by echo
}

# append a character to the total output.
# and strip it with %% parameter expansion.
VAR=$(scan2; echo "x"); VAR="${VAR%%x}"

echo "${VAR}---"

인쇄 (3 개의 줄 바꿈 유지) :

output


---

출력 매개 변수 사용 : 서브 쉘 방지 (및 줄 바꿈 유지)

함수가 bash v4.3 이상을 사용하여 문자열을 변수로 "반환"하려는 경우 nameref. Namerefs는 함수가 하나 이상의 변수 출력 매개 변수의 이름을 가질 수 있도록합니다. nameref 변수에 사물을 할당 할 수 있으며 마치 '가리키는 / 참조하는'변수를 변경 한 것과 같습니다.

function scan3() {
    local -n outvar=$1    # -n makes it a nameref.
    local nl=$'\x0a'
    outvar="output${nl}${nl}"  # two total. quotes preserve newlines
}

VAR="some prior value which will get overwritten"

# you pass the name of the variable. VAR will be modified.
scan3 VAR

# newlines are also preserved.
echo "${VAR}==="

인쇄물:

output

===

이 양식에는 몇 가지 장점이 있습니다. 즉, 전역 변수를 사용하지 않고도 함수가 호출자의 환경을 수정할 수 있습니다.

참고 : 이름 참조를 사용하면 함수가 bash 내장 기능에 크게 의존하는 경우 프로그램의 성능이 크게 향상 될 수 있습니다. 바로 뒤에 버려지는 서브 쉘의 생성을 방지하기 때문입니다. 이것은 일반적으로 자주 재사용되는 작은 함수 (예 :echo "$returnstring"

이것은 관련이 있습니다. https://stackoverflow.com/a/38997681/5556676


0

나는 init_js가 local 대신 선언을 사용해야한다고 생각합니다!

function scan3() {
    declare -n outvar=$1    # -n makes it a nameref.
    local nl=$'\x0a'
    outvar="output${nl}${nl}"  # two total. quotes preserve newlines
}

local내장는 것을 어떤 옵션도 받아 들일 것이다 declare내장이 받아 들일 것입니다. 빠른 테스트 declare -n에서 함수 범위에서 변수 로컬 범위도 제공하는 것처럼 보입니다 . 여기에서 서로 교환 할 수있는 것 같습니다.
init_js
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.