On Wed, Jun 26, 2024 at 11:50 PM Martin D Kealey <mar...@kurahaupo.gen.nz> wrote: > > > > On Thu, 27 Jun 2024 at 06:30, Chet Ramey <chet.ra...@case.edu> wrote: >> >> On 6/26/24 2:18 PM, Zachary Santer wrote: >> >> >> On Tue, Jun 11, 2024, 12:49 PM Zachary Santer <zsan...@gmail.com> wrote: >> >>> >> >>> $ array=( zero one two three four five six ) >> >>> $ printf '%s\n' "${array[@]( 1 5 )}" >> >>> one >> >>> five >> > >> > This is different functionality. >> >> Equivalent to printf '%s\n' "${array[1}" "${array[5]}". The innovation Zach >> wants is to have a single word expansion to do this. > > > Surely the point is to handle the case where we don't know in advance how > many elements will be wanted. > > In effect, it would mimic Perl's @array[@indeces] and @hash{@keys} > functionality, where we supply an arbitrary list of indices or subscripts, > and get back the corresponding values. > > Using the proposed syntax we would be able to write: > > array=( '' one two three four five six ) > indices=( 1 0 6 7 5 ) > printf '%s, ' "${array[@]( "${indices[@]}" )}" > printf end\\n > > to get > > one, , six, five, end > > (Note that there are only 4 words resulting from the expansion, since there > is no element '7' in 'array'. Unfortunately - and unlike Perl - Bash doesn't > have "undef", so we have to make do with getting back fewer values in the > resulting list if some requested array elements are unset, or if some indices > exceed the size of the array.)
This, though I would add the caveat that 'set -u'/'set -o nounset' should cause this expansion to fail and the script to error out if you supply an index without a matching value. > I agree that this syntax looks ugly, but since [@] and [*] don't function as > subscripts, it's tricky to improve on. > > My suggestion would be to generalise, turning [@] and [*] into fixed > syntactic tokens that can be combined with "ordinary" subscripting, or left > without subscripts to retain their current meanings: > > "${array[*][index]}" (a long-hand version of "${array[index]}") > "${array[@][index]}" (gives "${array[index]}" if it exists, but is > completely elided if it doesn't - similar to how "$@" can result in no words, > not an empty word) I'm not sure how interested people are in having multidimensional indexed arrays, but that's what this looks like. Like if you start with a two-dimensional array [ [ a b c d e ] [ f g h i j ] [ k l m n o ] [ p q r s t ] [ u v w x y ] ], expanding "${array[@][3]}" might give you "c" "h" "m" "r" "w". I am not asking for multidimensional array support here. And I guess my "${array[@]( index )}" would give the same behavior as your "${array[@][index]}".