Home > Enterprise >  Replace the whole word with AWK
Replace the whole word with AWK

Time:03-30

In the following example:

echo "manoeuvre man track" | awk -v replace="man" '{ gsub(replace, ""); print }'

I get this result:

oeuvre  track

I would like it to replace text only when it finds the whole word, so as a result, I would get:

manoeuvre  track

(only the word man was removed)

--

  • I tried this with word boundaries (\b and \y), but I cannot understand how to apply them here.

  • I made it work with a for loop, but I thought maybe there is a more straightforward way using gsub?

  • I only have AWK and don't have gAWK.

CodePudding user response:

"Vanilla" awk is not a good fit for this task. I'd use perl:

$ echo "manoeuvre man track" |perl -pe 's/\bman\b//g'
manoeuvre  track

or if you want to pass "man" as a parameter:

$ echo "manoeuvre man track" |perl -spe 's/\b${word}\b//g' -- -word=man
manoeuvre  track

One last point: if you want the "word" treated as a literal string, use the \Q...\E regex markers:

$ echo "manoeuvre man m.n trackm.n" |perl -spe 's/\b${word}\b//g' -- -word=m.n
manoeuvre   trackm.n

$ echo "manoeuvre man m.n trackm.n" |perl -spe 's/\b\Q${word}\E\b//g' -- -word=m.n
manoeuvre man  trackm.n

CodePudding user response:

This may be what you're trying to do, using any awk, assuming you want the first full-field literal string match:

$ echo "manoeuvre man track" |
    awk -v replace="man" '
        s=index(" "$0" "," "replace" ") {
            $0 = substr($0,1,s-2) substr($0,s length(replace))
        }
        { print }
    '
manoeuvre track

or this if you want to do a full-field regexp match for all fields:

$ echo "manoeuvre man track" |
    awk -v replace="man" '
        {
            $0=" "$0" "
            gsub(" "replace" "," ")
            gsub(/^ | $/,"",$0)
            print
        }
    '
manoeuvre track

There are lots of other possibilities...

CodePudding user response:

You can use the following with GNU awk:

awk -v replace="man" '{gsub("\\<"replace"\\>", "")}1'

See the online demo:

#!/bin/bash
s="manoeuvre man track"
awk -v replace="man" '{gsub("\\<"replace"\\>", "")}1' <<< "$s"
# => manoeuvre  track

NOTE:

  • Word boundaries here are \< and \>, and to use a literal \ char in the awk command, it needs doubling
  • replace is a variable containing just word chars, so it is OK to use \< and \> word boundaries to wrap this value to match as a whole word (it would be more complicated if it contained non-word chars)
  • To create a pattern from a variable, you need to concatenate the values, here, it is done with "\\<"replace"\\>".
  • Note that print is replaced with 1 in the code above.
  • Related