Daniel D.
Daniel D.

Reputation: 15

How can I replace lines from one file matched with lines from another file, based on matching pattern, with grep/sed/awk?

I have two files nmap.txt and hosts.txt. The first is, of course, the output from a nmap search, and it looks like this:

 ====================================
 192.168.2.1     (ComputerName1)
 Running: Microsoft Windows Vista/7/8
 ====================================
 192.168.2.2     (ComputerName2)
 Running: Running: Linux 3.X
 ====================================
 192.168.2.3     ()
 ====================================
 192.168.2.4     ()

It looks like this because the are no DNS entries for the 3rd and 4th computer, and nmap wasn't able to determine 100% their operating systems. But I have the computer names 3 and 4 in the hosts.txt file.

192.168.2.3     (ComputerName3)
192.168.2.4     (ComputerName4)

What's the easiest way to replace the missing computer names in nmap.txt (192.168.2.3 and 192.168.2.4) with their corresponding names in hosts.txt?

I tried grep -v -F -f nmap.txt hosts.txt > output.txt which will only output the missing computer names, like this:

192.168.2.3     (ComputerName3)
192.168.2.4     (ComputerName4)

But that's not what I want. The output should look like this:

====================================
192.168.2.1     (ComputerName1)
Running: Microsoft Windows Vista/7/8
====================================
192.168.2.2     (ComputerName2)
Running: Running: Linux 3.X
====================================
192.168.2.3     (ComputerName3)
====================================
192.168.2.4     (ComputerName4)

Maybe something with while read line, but I'm not an expert. Any help would be much appreciated!

Upvotes: 0

Views: 50

Answers (2)

James Brown
James Brown

Reputation: 37394

In awk:

$ awk 'NR==FNR{a[$1]=$0;next}{print ($1 in a?a[$1]:$0)}' hosts nmap

Output:

====================================
192.168.2.1     (ComputerName1)
Running: Microsoft Windows Vista/7/8
====================================
192.168.2.2     (ComputerName2)
Running: Running: Linux 3.X
====================================
192.168.2.3     (ComputerName3)
====================================
192.168.2.4     (ComputerName4)

Explained:

$ awk '
NR==FNR {                     # process the hosts file
    a[$1]=$0                  # hash records to a using ip as key
    next
}
{                             # process nmap file
    print ($1 in a?a[$1]:$0)  # print hashed record instead if it exists
}' hosts nmap

Upvotes: 0

Ed Morton
Ed Morton

Reputation: 203189

$ awk 'NR==FNR{map[$1]=$2;next} ($1 in map) && sub(/\(\)$/,""){$0=$0 map[$1]} 1' hosts.txt nmap.txt
====================================
192.168.2.1     (ComputerName1)
Running: Microsoft Windows Vista/7/8
====================================
192.168.2.2     (ComputerName2)
Running: Running: Linux 3.X
====================================
192.168.2.3     (ComputerName3)
====================================
192.168.2.4     (ComputerName4)

Upvotes: 1

Related Questions