업데이트 날짜: 2019-05-17

업데이트 날짜: 2019-05-17

특정 접두사가 붙은 모든 변수를 나열하려고 하는데 접두사가 동적으로 결정됩니다. 예를 들어:

prefix=apple_
apple_one=a1
apple_two=a2

내가 간단히 이렇게 하면:

echo ${!apple_@}

apple_로 시작하는 변수 이름을 얻을 수 있습니다. 그러나 나는 어떤 방식으로든 변수 접두사를 사용하여 이 작업을 수행하고 싶습니다. 내가 시도한 모든 결과는 잘못된 대체 결과였습니다. 예를 들어 다음과 같은 작업은 할 수 없습니다.

echo ${!${prefix}@}

답변1

Bash는 중첩된 변수 확장을 구문 분석하지 않습니다. 원하는 대로 할 수 있습니다 eval. 즉, 쉘 조각을 작성한 ${!apple_@}다음 실행된 명령에서 이를 사용하십시오 eval.

prefix=apple_
eval 'vars=(${!'"$prefix"'@})'

유효한 식별자 문자만 포함 해야 합니다 prefix. 그렇지 않으면 조각에서 결과가 생성되지 않을 수 있습니다.

eval일반적으로 동적으로 계산된 이름을 가진 변수를 사용해야 하지만 이 특별한 경우에는 동일한 작업을 수행하는 완전히 다른 방법이 있습니다. 바로 완성 시스템을 사용하는 것입니다. Bash의 완성 시스템은 스크립트를 통해서도 실행할 수 있습니다. 내장 함수는 compgen한 줄에 하나의 완성을 나열합니다. 완성에 개행 문자가 포함될 수 있으면 모호하지만 여기서는 그렇지 않습니다. 와일드카드도 포함되지 않으므로 따옴표가 없는 간단한 확장 출력을 사용하여 분할할 수 있습니다. 접두사에 식별자에 유효하지 않은 문자가 포함되어 있으면 아무 것도 출력되지 않습니다.

vars=($(compgen -v "$prefix"))

답변2

당신이 사용할 수있는 env | grep '^prefix'.

예를 들어:

$ env | grep '^LESS'
LESSBINFMT=*u.
LESS=-MMqx4ij3
LESSOPEN=| /usr/bin/lesspipe %s
LESSCLOSE=/usr/bin/lesspipe %s %s

변수 이름이 아닌 값만 필요한 경우 awk를 사용하세요.

$ env | awk -F= '/^LESS/ {print $2}'
*u.
-MMqx4ij3
| /usr/bin/lesspipe %s
/usr/bin/lesspipe %s %s

(또는 $1을 변수 이름으로 인쇄)


업데이트 날짜: 2019-05-17

나는 찬성 투표를 통해 이 답변으로 돌아왔고 분명한 개선이 있음을 깨달았습니다.

typeset -p그보다 더 나은 점은 env내보내기 여부에 관계없이 모든 변수를 출력한다는 것입니다. 예를 들어:

typeset -p | awk '$3 ~ /^apple_/ { print $3 }'

고정 문자열 대신 변수를 사용하려면 다음을 수행하십시오.

prefix=apple_
typeset -p | awk '$3 ~ "^"pfx { print $3 }' pfx="$prefix" 

또는 awk의 ENVIRON 배열에서 사용할 수 있도록 $prefix를 내보내세요.

export prefix=apple_
typeset -p | awk '$3 ~ "^"ENVIRON["prefix"] { print $3 }'

노트:약간의 작업을 통해 다른 쉘(예: ksh 또는 zsh)과 작동하도록 만들 수 있지만 typeset -p다른 쉘에는 다른 출력 형식이 있으므로 이를 수용하도록 awk 스크립트를 수정해야 합니다.

답변3

preset(){
    eval "printf %b $(#"
          set -- "${1##[0-9]*}" _\[:alnum:]
          [ -z   "${1##*[!$2]*}"  ]|| set |
          sed -ne"s/^\($1[$2]*\)=.*/"'"${\1+\1\\n}" \\/p')
"; }; #"

apple_one="a single apple"
apple_two="an apple and an
apple_three='is not actually set at all'
"

preset apple_

apple_one
apple_two

관련 정보