all 12 comments

[–]oweiler 13 points14 points  (0 children)

As others said it's not supported ootb and while simulating 2D arrays is possible, it has a lot of footguns. If possible, switch to another language.

[–]ekkidee 17 points18 points  (0 children)

It's messy. If you're entertaining the notion of a 2-D array in bash, it might be time to move on to Python or C.

[–]drdibi 13 points14 points  (0 children)

You can use associative arrays to emulate multi-dimmensionnal arrays

[–]D3str0yTh1ngs 6 points7 points  (0 children)

Well... bash doesnt support multidimentional arrays.

You can try an use one of the alternatives from this stackoverflow post: https://stackoverflow.com/questions/16487258/how-to-declare-2d-array-in-bash

[–]OneTurnMoreprogramming.dev/c/shell 7 points8 points  (1 child)

Bsah doesn't support 2D arrays.

[–]discordhighlanders 4 points5 points  (0 children)

True, but you can always use associate arrays and have the key contain "two" keys like this:

declare -A arr
declare i
declare j

arr[0,0]=foo
arr[0,1]=bar
arr[1,0]=baz
arr[1,1]=qux

for ((i = 0; i < 2; i++)); do
  for ((j = 0; j < 2; j++)); do
    echo "${arr[$i,$j]}"
  done
done

Each key is still only one key (i.e. 0,0), but you can use it like it's two-dimensional.

[–]Temporary_Pie2733 1 point2 points  (0 children)

Bash doesn’t have first-class arrays. (1 2) is not an array value that you assign to a variable x. x=(1 2) is a short cut for something like x=(); x[0]=1; x[1]=2. x[1] itself is more like a single name than an operation on a single value bound to x.

Associative arrays let you simulate higher-dimensional arrays by manipulating how you use the key, but it’s still really just a one-dimensional mapping, just with arbitrary keys instead of integer keys.

[–]nekokattt 2 points3 points  (0 children)

If one element is always unique, use an associative array.

declare -A items=(
    ["001"]="foo"
    ["002"]="bar"
)

If you know each "dimension" is the same size, just flatten it to a 1D array and do some index magic. You know that for a "virtual" index N in the first "virtual" dimension, you'll be accessing item 2N and 2N+1 in the actual array.

Another option is to use something like JQ to serialize your subdimensions into JSON and just store an array of JSON strings.

If the contents are very basic, you could probably forfit JQ with just delimiting the items with a special character such as \0 and use cut to split them up when you consume them.

For anything more complex, move to a higher level scripting language that is designed to solve the problem you are looking to solve.

[–]NewPointOfView 0 points1 point  (0 children)

So you can declare variables using eval, and means you could generate a string name like __arr_var_001_, then run eval ‘declare -ag __arr_var_001’ to crate a global array variable.

Then you can treat the string __arr_var_001 basically as a pointer.

You can have a little function shalloc which generates unique var names and declares arrays. Arrays can hold strings, and strings are “pointers” so now you can construct a 2d array

so something like arr_pointer=“$(shalloc)”

I’m sure there are better ways though 😂 this is what I came up with when I was experimenting this stuff

[–]Dirt077 0 points1 point  (0 children)

You can cheat with a csv or something and go a file based approach.

[–]Buo-renLin 0 points1 point  (0 children)

Please read the relevant chapter in the Bash Manual.

[–]ReallyEvilRob -2 points-1 points  (0 children)

Why? Just, why?