(gawk) Changing Fields
Info Catalog
(gawk) Non-Constant Fields
(gawk) Reading Files
(gawk) Field Separators
Changing the Contents of a Field
================================
You can change the contents of a field as seen by `awk' within an
`awk' program; this changes what `awk' perceives as the current input
record. (The actual input is untouched; `awk' _never_ modifies the
input file.)
Consider this example and its output:
$ awk '{ $3 = $2 - 10; print $2, $3 }' inventory-shipped
-| 13 3
-| 15 5
-| 15 5
...
The `-' sign represents subtraction, so this program reassigns field
three, `$3', to be the value of field two minus ten, `$2 - 10'. (
Arithmetic Operators Arithmetic Ops.) Then field two, and the new
value for field three, are printed.
In order for this to work, the text in field `$2' must make sense as
a number; the string of characters must be converted to a number in
order for the computer to do arithmetic on it. The number resulting
from the subtraction is converted back to a string of characters which
then becomes field three. Conversion of Strings and Numbers
Conversion.
When you change the value of a field (as perceived by `awk'), the
text of the input record is recalculated to contain the new field where
the old one was. Therefore, `$0' changes to reflect the altered field.
Thus, this program prints a copy of the input file, with 10 subtracted
from the second field of each line.
$ awk '{ $2 = $2 - 10; print $0 }' inventory-shipped
-| Jan 3 25 15 115
-| Feb 5 32 24 226
-| Mar 5 24 34 228
...
You can also assign contents to fields that are out of range. For
example:
$ awk '{ $6 = ($5 + $4 + $3 + $2)
> print $6 }' inventory-shipped
-| 168
-| 297
-| 301
...
We've just created `$6', whose value is the sum of fields `$2', `$3',
`$4', and `$5'. The `+' sign represents addition. For the file
`inventory-shipped', `$6' represents the total number of parcels
shipped for a particular month.
Creating a new field changes `awk''s internal copy of the current
input record--the value of `$0'. Thus, if you do `print $0' after
adding a field, the record printed includes the new field, with the
appropriate number of field separators between it and the previously
existing fields.
This recomputation affects and is affected by `NF' (the number of
fields; Examining Fields Fields.), and by a feature that has not
been discussed yet, the "output field separator", `OFS', which is used
to separate the fields ( Output Separators). For example, the
value of `NF' is set to the number of the highest field you create.
Note, however, that merely _referencing_ an out-of-range field does
_not_ change the value of either `$0' or `NF'. Referencing an
out-of-range field only produces an empty string. For example:
if ($(NF+1) != "")
print "can't happen"
else
print "everything is normal"
should print `everything is normal', because `NF+1' is certain to be
out of range. ( The `if'-`else' Statement If Statement, for more
information about `awk''s `if-else' statements. Variable Typing
and Comparison Expressions Typing and Comparison, for more information
about the `!=' operator.)
It is important to note that making an assignment to an existing
field will change the value of `$0', but will not change the value of
`NF', even when you assign the empty string to a field. For example:
$ echo a b c d | awk '{ OFS = ":"; $2 = ""
> print $0; print NF }'
-| a::c:d
-| 4
The field is still there; it just has an empty value. You can tell
because there are two colons in a row.
This example shows what happens if you create a new field.
$ echo a b c d | awk '{ OFS = ":"; $2 = ""; $6 = "new"
> print $0; print NF }'
-| a::c:d::new
-| 6
The intervening field, `$5' is created with an empty value (indicated
by the second pair of adjacent colons), and `NF' is updated with the
value six.
Finally, decrementing `NF' will lose the values of the fields after
the new value of `NF', and `$0' will be recomputed. Here is an example:
$ echo a b c d e f | ../gawk '{ print "NF =", NF;
> NF = 3; print $0 }'
-| NF = 6
-| a b c
Info Catalog
(gawk) Non-Constant Fields
(gawk) Reading Files
(gawk) Field Separators
automatically generated byinfo2html