Awk array iteration for multi-dimensional arrays
AWK fakes multidimensional arrays by concatenating the indices with the character held in the SUBSEP variable (0x1c). You can iterate through a two-dimensional array using split
like this (based on an example in the info gawk
file):
awk 'BEGIN { OFS=","; array[1,2]=3; array[2,3]=5; array[3,4]=8; for (comb in array) {split(comb,sep,SUBSEP); print sep[1], sep[2], array[sep[1],sep[2]]}}'
Output:
2,3,53,4,81,2,3
You can, however, iterate over a numerically indexed array using nested for loops:
for (i = 1; i <= width; i++) for (j = 1; j < = height; j++) print array[i, j]
Another noteworthy bit of information from the GAWK manual:
To test whether a particular index sequence exists in a multidimensional array, use the same operator (in) that is used for single dimensional arrays. Write the whole sequence of indices in parentheses, separated by commas, as the left operand:
(subscript1, subscript2, ...) in array
Gawk 4 adds arrays of arrays. From that link:
for (i in array) { if (isarray(array[i])) { for (j in array[i]) { print array[i][j] } } else print array[i]}
Also see Traversing Arrays of Arrays for information about the following function which walks an arbitrarily dimensioned array of arrays, including jagged ones:
function walk_array(arr, name, i){ for (i in arr) { if (isarray(arr[i])) walk_array(arr[i], (name "[" i "]")) else printf("%s[%s] = %s\n", name, i, arr[i]) }}
No, the syntax
for(index1 in arr2) for(index2 in arr2) { print arr2[index1][index2];}
won't work. Awk doesn't truly support multi-dimensional arrays. What it does, if you do something like
x[1,2] = 5;
is to concatenate the two indexes (1 & 2) to make a string, separated by the value of the SUBSEP
variable. If this is equal to "*", then you'd have the same effect as
x["1*2"] = 5;
The default value of SUBSEP
is a non-printing character, corresponding to Ctrl+\. You can see this with the following script:
BEGIN { x[1,2]=5; x[2,4]=7; for (ix in x) { print ix; }}
Running this gives:
% awk -f scriptfile | cat -v1^\22^\4
So, in answer to your question - how to iterate a multi-dimensional array - just use a single for(a in b)
loop, but you may need some extra work to split up a
into its x
and y
parts.
The current versions of gawk (the gnu awk, default inlinux, and possible to install everywhere you want), has real multidimensional arrays.
for(b in a) for(c in a[b]) print a[b][c], c , b
See also function isarray()