Find and replace string based on entries on another file

I have a file1 with different with multiple fields and records
File2 has 2 fields.
I want to find and replace strings in file1 based on file2 values (I Want an exact match i.e. for example: when searching for DT:3, Substr of DT:34 should not be matched)

File2:

DT:3 foo_err
DT:34 bar_frr
DT:47 foo_bar
TK:22 gree

file1:

he will come to DT:34 and stay there. I will meet her in DT:3 
gree will see me there

Desired Output:

he will come to bar_frr and stay there. I will meet her in foo_err
TK:22 will see me there

Question:
Can your entries for "DT:3" become "DT:03"?

If not, then searching for "DT:3 " {note, space after the '3'} might work. But, I fear it will be a problem when at end of a line.

Another approach would be to somehow make sure that you change all with two-digit numbers prior to single-digit numbers. Execute for "DT-34" before "DT-3".

Cannot change DT:3 to DT:03 because file1 is has many entries.

for given input this will work

$ awk 'FNR==NR{A[$1]=$2;next}{for(i in A){if($0~i){sub(i,A,$0)}else if($0~A){sub(A,i,$0)}}}1' file2 file1

he will come to bar_frr and stay there. I will meet her in foo_err 
TK:22 will see me there

Sorry for my Omission TK:22 should also be replaced (every occurrence should be replaced).

output:

he will come to bar_frr and stay there. I will meet her in foo_err 
gree will see me there

You shown desired output this right ?

Try this then

$ awk 'FNR==NR{A[$1]=$2;next}{for(i in A)if($0~i)sub(i,A,$0)}1' file2 file1

he will come to bar_frr and stay there. I will meet her in foo_err 
gree will see me there
1 Like

Pls I'm still having substring replaced i.e. DT:34 replaced to foo_err4, any ideas?

---------- Post updated 12-17-13 at 04:37 AM ---------- Previous update was 12-16-13 at 12:18 PM ----------

I have tried to sort file2 but still not working.

# cat f2
DT:3 foo_err
DT:34 bar_frr
DT:47 foo_bar
TK:22 gree
# cat f1
he will come to DT:34 and stay there. I will meet her in DT:3
gree will see me there
he will come to DT:34 and stay there. I will meet her in DT:3
TK:22 will see me there
# awk 'FNR==NR{A[$1]=$2;next}{for(i=0;++i<=NF;) if($i in A) sub($i,A[$i],$0); else { for(j in A) { if(A[j]==$i) sub($i,j,$0) }}}1' f2 f1
he will come to bar_frr and stay there. I will meet her in foo_err
TK:22 will see me there
he will come to bar_frr and stay there. I will meet her in foo_err
gree will see me there
#

Or :

# awk 'NR==FNR{A[$1]=$2;B[$2]=$1;next}{for(i=0;++i<=NF;) {x=($i in A)?A[$i]:($i in B)?B[$i]:z;if(x!=z) sub($i,x,$0)}}1' f2 f1
he will come to bar_frr and stay there. I will meet her in foo_err
TK:22 will see me there
he will come to bar_frr and stay there. I will meet her in foo_err
gree will see me there
1 Like

As joeyg pointed out, end-of-lines might be problematic. Try a modification of Akshay Hegde's proposal:

awk 'FNR==NR{A[$1]=$2;next}{for(i in A)if($0~i"[^0-9]|$")sub(i,A,$0)}1' file1 file2
1 Like