Syntax:
delete arrayname[index];
The loop command below removes all elements from an array.
for (var in array)
delete array[var]
In GAWK, you can specify the following single command to delete all the elements from an array.
delete array
Also, as shown in the example below, item[103]="" does not delete the array element. It just stores null values in it.
$ cat array-delete.awk
BEGIN {
item[101]="HD Camcorder";
item[102]="Refrigerator";
item[103]="MP3 Player";
item[104]="Tennis Racket";
item[105]="Laser Printer";
item[1001]="Tennis Ball";
item[55]="Laptop";
item["na"]="Not Available";
delete item[102];
item[103]="";
delete item[104];
delete item[1001];
delete item["na"];
for (x in item)
print "Index",x,"contains",item[x];
}
$ awk -f array-delete.awk
Index 55 contains Laptop
Index 101 contains HD Camcorder
Index 103 contains
Index 105 contains Laser Printer
81. Multi Dimensional Array
Awk has only one dimensional array. But, the beauty of awk is that you can simulate a multi dimensional array using the single dimensional array itself.
Suppose you want to create the following 2 x 2 multi dimensional array.
10 20
30 40
In the above example, item at location "1,1" is 10, item at location "1,2" is 20, etc. Do the following to assign 10 to location "1,1".
item["1,1"]=10
Even though you've given "1,1" as index, it is not two indexes. It is just one index with the string "1,1". So, in the above example, you are really storing the value 10 at a single dimensional array with index "1,1".
$ cat array-multi.awk
BEGIN {
item["1,1"]=10;
item["1,2"]=20;
item["2,1"]=30;
item["2,2"]=40;
for (x in item)
print item[x];
}
$ awk -f array-multi.awk
10
20
30
40
Now, what happens when you don't enclose the indexes within quotes? i.e. item[1,1] (instead of item["1,1"]), as shown in the example below.
$ cat array-multi2.awk
BEGIN {
item[1,1]=10;
item[1,2]=20;
item[2,1]=30;
item[2,2]=40;
for (x in item)
print item[x];
}
$ awk -f array-multi2.awk
30
40
10
20
The above sample program will still work. But, there is a difference. In a multi-dimensional awk array, when you don't enclose the indexes within quotes, awk uses a subscript separator with default value of "\034".
When you specify item[1,2], it will be translated to item["1\0342"]. Awk will combine both the subscripts using \034 in between and convert them to string.
When you specify item["1,2"], it will not be translated, as it will be treated just as a one dimensional array with no subscripts.
This is demonstrated in the example below.
$ cat array-multi3.awk
BEGIN {
item["1,1"]=10;
item["1,2"]=20;
item[2,1]=30;
item[2,2]=40;
for (x in item)
print "Index",x,"contains",item[x];
}
$ awk -f array-multi3.awk
Index 1,1 contains 10
Index 1,2 contains 20
Index 2#1 contains 30
Index 2#2 contains 40
In the above example:
- Indexes "1,1" and "1,2" are enclosed in quotes. So, this is treated as a one dimensional array index, no subscript separator is used by awk. So, the index gets printed as is.
- Indexes 2,1 and 2,2 are not enclosed in quotes. So, this is treated as a multi-dimensional array index, and awk uses a subscript separator. So, the index is "2\0341" and "2\0342", which is printed with the non-printable character "\034" between the subscripts.
82. SUBSEP - Subscript Separator
You can change the default subscript separator to anything you like using the SUBSEP variable. In the following example, SUBSEP is set to colon.
$ cat array-multi4.awk
BEGIN {
SUBSEP=":";
item["1,1"]=10;
item["1,2"]=20;
item[2,1]=30;
item[2,2]=40;
for (x in item)
print "Index",x,"contains",item[x];
}
$ awk -f array-multi4.awk
Index 1,1 contains 10
Index 1,2 contains 20
Index 2:1 contains 30
Index 2:2 contains 40
In the above example, indexes "1,1" and "1,2" didn't use the SUBSEP because they were enclosed in quotes.
So, for a multi-dimensional awk array, the best practice is not to enclose any of the indexes within quotes, as shown below.
$ cat array-multi5.awk
BEGIN {
SUBSEP=":";
item[1,1]=10;
item[1,2]=20;
item[2,1]=30;
item[2,2]=40;
for (x in item)
print "Index",x,"contains",item[x];
}
$ awk -f array-multi5.awk
Index 1:1 contains 10
Index 1:2 contains 20
Index 2:1 contains 30
Index 2:2 contains 40
83. Sort Array Values using asort
The asort function sorts the array values and stores them in indexes from 1 through n. Where n is the total number of elements in the array.
Suppose you have two elements in the array: item["something"]="B - I'm big b" and item["notsure"]="A - I'm big a". After an asort function call, the array will be sorted based on the values to: item[1]="A - I'm big a" and item[2]="B - I'm big b".
In the following example, we have array indexes with various nonconsecutive numbers and strings. After the asort, the array values will be sorted and stored in the indexes 1,2,3,4,... Please note that asort returns the total number of items in the array.
$ cat asort.awk
BEGIN {
item[101]="HD Camcorder";
item[102]="Refrigerator";
item[103]="MP3 Player";
item[104]="Tennis Racket";
item[105]="Laser Printer";
item[1001]="Tennis Ball";
item[55]="Laptop";
item["na"]="Not Available";
print "------Before asort------"
for (x in item)
print "Index",x,"contains",item[x];
total = asort(item);
print "------After asort------"
for (x in item)
print "Index",x,"contains",item[x];
print "Return value from asort:", total;
}
$ awk -f asort.awk
------Before asort------
Index 55 contains Laptop
Index 101 contains HD Camcorder
Index 102 contains Refrigerator
Index 103 contains MP3 Player
Index 104 contains Tennis Racket
Index 105 contains Laser Printer
Index na contains Not Available
Index 1001 contains Tennis Ball
------After asort------
Index 4 contains MP3 Player
Index 5 contains Not Available
Index 6 contains Refrigerator
Index 7 contains Tennis Ball
Index 8 contains Tennis Racket
Index 1 contains HD Camcorder
Index 2 contains Laptop
Index 3 contains Laser Printer
Return value from asort: 8
In the above example, after the asort, the array elements are not printed from indexes 1 through 8. Instead, it is random. You can print them from 1 through 8 as shown in the example below.
$ cat asort1.awk
BEGIN {
item[101]="HD Camcorder";
item[102]="Refrigerator";
item[103]="MP3 Player";
item[104]="Tennis Racket";
item[105]="Laser Printer";
item[1001]="Tennis Ball";
item[55]="Laptop";
item["na"]="Not Available";
total = asort(item);
for (i=1; i<= total; i++)
print "Index",i,"contains",item[i];
}
$ awk -f asort1.awk
Index 1 contains HD Camcorder
Index 2 contains Laptop
Index 3 contains Laser Printer
Index 4 contains MP3 Player
Index 5 contains Not Available
Index 6 contains Refrigerator
Index 7 contains Tennis Ball
Index 8 contains Tennis Racket
As you may have noticed in the above examples, once asort is executed, you'll lose the original indexes forever. So, instead of overwriting the original array with the new indexes, you might want to create a new array with the new indexes.
In the following example, the original array "item" is not modified. Instead, the "itemnew" array will contain the new indexes. i.e. itemnew[1], itemnew[2], itemnew[3], etc.
total = asort(item, itemnew);
Again, remember that asort sorts the array values. But, instead of using the original indexes, it uses new indexes from 1 through n. Original indexes are lost.
84. Sort Array Indexes using asorti
Just like sorting array values, you can take all the array indexes, sort them, and store them in a new array using asorti.
The following example shows how asorti differs from asort. Keep the following in mind:
- asorti sorts the indexes (not the values) and stores them as values.
- If you specify asorti(state), you'll lose the original values. i.e. the indexes will now become the values. So, to be on safe side, always specify two parameters to the asorti function. i.e. asorti(state,stateabbr). This way, the original array (state), it not overwritten.
$ cat asorti.awk
BEGIN {
state["TX"]="Texas";
state["PA"]="Pennsylvania";
state["NV"]="Nevada";
state["CA"]="California";
state["AL"]="Alabama";
print "----- Function: asort -----"
total = asort(state,statedesc);
for (i=1; i<= total; i++)
print "Index",i,"contains",statedesc[i];
print "----- Function: asorti -----"
total = asorti(state,stateabbr);
for (i=1; i<= total; i++)
print "Index",i,"contains",stateabbr[i];
}
$ awk -f asorti.awk
----- Function: asort -----
Index 1 contains Alabama
Index 2 contains California
Index 3 contains Nevada
Index 4 contains Pennsylvania
Index 5 contains Texas
----- Function: asorti -----
Index 1 contains AL
Index 2 contains CA
Index 3 contains NV
Index 4 contains PA
Index 5 contains TX