동적으로 생성된 이름이 참조하는 배열의 요소 수 찾기

동적으로 생성된 이름이 참조하는 배열의 요소 수 찾기

비슷한 질문을 찾았습니다여기, 그러나 동일하지 않은 것 같고 답변 중 어느 것도 내가 원하는 결과를 제공하지 않습니다. 배열이 있고 동적으로 생성된 이름을 사용하여 배열에 액세스하여 포함된 요소 수를 확인하고 싶습니다.

declare -a array0=(2 4 2 5)  # contains 4 values
indx=0
Name="array$indx"            # create a name reference => array0

# I know how to obtain an indexed value by INDIRECT reference:
val0=${!Name[0]}
# I also know how to get array length using DIRECT name
len=${#array0[@]}

내가 필요한 것은 요소의 수를 찾는 것입니다배열 0변수를 사용하여 참조이름

len=${#!Name[@]}             # the syntax is incorrect

구현에 대한 제안 사항이 있습니까?

편집하다:
실수로 다음을 사용하여 배열 항목에 액세스했습니다.

val0=${!Name[0]}

indx=0에서만 작동하므로 배열에서 다른 항목을 가져오려면 빈 문자열만 반환합니다.

val4=${!Name[4]}          #does not work

또는

i=4
val4=${!Name[$i]}         # does not work

답변1

Pass bash-4.3이상에서는 nameref를 사용할 수 있습니다.

a0=(a b c)
i=0
typeset -n Name="a$i"
echo "${#Name[@]}"

아니면 언제든지 할 수 있어요사용eval. 어쨌든, bashnameref를 사용하는 것이 좋다고 생각하는 실수를 저지르지 마십시오.더 안전한비교하다 eval. for 와 마찬가지로 내용이 유효한 쉘 변수 이름인지 eval확인해야 합니다 . $Name유사한 값은 확장 시에도 x[`evil-command>&2`0]계속 실행됩니다 . evil-command에도 적용됩니다.$Name${#Name}${!var}

를 사용하면 ksh93다차원 배열을 대신 사용할 수 있습니다.

a[0]=(a b c)
i=0
echo "${#a[i][@]}"

zsh스프레드 연산자를 결합하는 보다 일관된 방법이 있습니다.

a0=(a b c)
i=0
name=a$i
echo ${(P)#name}

( P간접 매개변수 확장의 경우)

답변2

명시적으로 사용할 수 있지만 eval과도하게 사용하지 마세요.

eval "len=\${#$Name[@]}"

관련 정보