AWK - Replacing Value Of Selected Column Destroys Output Format

62 views Asked by At

I have a .csv file with the following format. id|name|date

I am using the following Awk command to change a specific column in a row and it works. awk -F "|" '{$"'"$col"'"="'"$val"'";}1' filename.csv

I wanna save the output , however the format is destroyed.

What I want : 100|James|2015

What I get : 100 James 2015

How do I avoid the second one, and get the first one ?

2

There are 2 answers

1
Lars Fischer On BEST ANSWER

You could set the OFS, the Output Field Separator like in this example:

awk -F\| -v OFS=\| '{print $1, $2, $3 }'  test.psv 
  • The -v OFS=\| assigns the OFS variable the values |. It is an alternative to a BEGIN { OFS = "|" } block.
  • The | needs to be protected from the shell, since the meaning an shell level is piping of one commands output into the input of another command. Using "|" or \| are two ways to do so.
1
Ed Morton On

Never let shell variables expand to become part of the body of an awk script:

awk -F "|" '{$"'"$col"'"="'"$val"'";}1' filename.csv

as it opens you up to insidious errors given various values of those shell variables. Instead populate awk variables from the shell variables and use the awk variables within the script:

awk -F "|" -v col="$col" -v val="$val" '{$col=val}1' filename.csv

wrt your specific question, though, awk reconstructs the record when you assign a value to a field so you need the OFS to have the same value as the FS:

awk -v col="$col" -v val="$val" 'BEGIN{FS=OFS="|"} {$col=val}1' filename.csv