issue with substituting using sed

have a fileA containing about 260 lines wherein i have to match 2 lines

fileA

blah blah 
OF 90 DAYS DOCS PERIOD 12/06/0"
Pairs_Id 52006
Amount1 -300000.0
Amount2 15091500.10
Codifiers_Id 0
OriginalId 0
EOT
--blah blah blah

TBL Tradt_IN
CardRate 0.0
hashAmount -15091500.0
FirstLegType ""

I have to substitute the Amount2 value with the hashAmount value ie (-)15091500.0 with 15091500.0 (without the negative symbol)

hashAmount and Amount2 occur only once in the file

I have tried the following

$STR=$(awk '/hash/ {print "Amount2" " " $2 * -1}' ins)

echo $STR shows the value

Amount2 15091500

I have to substitute this in place of the Amount2 line

sed -e "/$STR/" -e "/Amount2/d" fileA > fileB

i am getting the following error

sed: -e expression #1, char 19: missing command

further substitution to be done only

1) when hashAmount > 0
2) and when the difference between hashAmount and Amount2 is not more than 2 (i.e only when there is difference in decimal value
3) There are some 50 files on which i have to repeat this action

Regards

You probably mean:

STR=$(awk '/hash/ {print "Amount2" " " $2 * -1}' ins)

That's because you haven't told sed what to do when the patter "$STR" matches (missing command).
"/$STR/" matches the pattern, but you have to decide what to do after the match - print it ? delete it ? substitute it ?
"char 19" tells you that the command should've been at the 19th char position; check the characters in the expansion => /Amount2 15091500/

You probably wanted to do something like this -

$ 
$ # show the contents of the file
$ cat -n ins
     1  blah blah 
     2  OF 90 DAYS DOCS PERIOD 12/06/0"
     3  Pairs_Id 52006
     4  Amount1 -300000.0
     5  Amount2 15091500.10
     6  Codifiers_Id 0
     7  OriginalId 0
     8  EOT
     9  --blah blah blah
    10  TBL Tradt_IN
    11  CardRate 0.0
    12  hashAmount -15091500.0
    13  FirstLegType ""
$ 
$ # set the value of shell variable STR
$ STR=$(awk '/hash/ {print "Amount2" " " $2 * -1}' ins)
$ echo $STR
Amount2 15091500
$ 
$ # substitute using sed
$ sed -e "s/^Amount2.*$/$STR/" ins
blah blah 
OF 90 DAYS DOCS PERIOD 12/06/0"
Pairs_Id 52006
Amount1 -300000.0
Amount2 15091500
Codifiers_Id 0
OriginalId 0
EOT
--blah blah blah
TBL Tradt_IN
CardRate 0.0
hashAmount -15091500.0
FirstLegType ""
$ 
$ 

Here's a Perl solution to perform this processing.
I've assumed that the files of interest are the ones that end with ".txt" extension. It needn't be ".txt"; it can be any appropriate regular expression in the glob function.

$ 
$ # show how many txt files are here
$ ls -1 *.txt
f1.txt
f2.txt
f3.txt
$ 
$ # show the contents of each txt file
$ 
$ cat f1.txt
blah blah blah
Amount2 15091500.10
blah blah blah
hashAmount 15091500.0
blah blah blah
$ 
$ cat f2.txt
blah blah blah
Amount2 15
blah blah blah
hashAmount -15
blah blah blah
$ 
$ cat f3.txt
blah blah blah
Amount2 -34
blah blah blah
hashAmount 35
blah blah blah
$ 
$ 

So,

  • Amount2 in f1.txt should be substituted.

  • Amount2 in f2.txt should not be substituted because hashAmount < 0 (violation of Rule 1).

  • Amount2 in f3.txt should not be substituted because hashAmount - Amount2 = 35 - (-34) = 69 which is > 2 (violation of Rule 2).

Here's the Perl program to do that. The inline script comments should be self-explanatory.

$ 
$ cat -n swap.pl
     1  #!/usr/bin/perl -w
     2  # Assuming all "*.txt" files are to be scanned and updated
     3  while (defined($f = glob("*.txt"))) {
     4    print "NOW PROCESSING FILE : $f\n";
     5    open (FH, $f) or die "Can't open $f: $!";
     6    while (<FH>) {
     7      chomp;
     8      # Push current line to contents array
     9      push @contents, $_;
    10      # Check for the lines that start with Amount2 or hashAmount
    11      if (/^Amount2/) {
    12        $amtidx = $.-1;
    13        @amt = split;
    14      } elsif (/^hashAmount/) {
    15        $hshidx = $.-1;
    16        @hamt = split;
    17        # Swap only if line with "Amount2" exists, and
    18        # hashAmount > 0, and
    19        # difference between hashAmount and Amount2 is less than or equal to 2
    20        if (defined $amt[1] and $hamt[1] > 0 and $hamt[1] - $amt[1] <= 2) {
    21          $contents[$amtidx] = "$amt[0] $hamt[1]";
    22        } 
    23      }
    24    }
    25    close (FH) or die "Can't close $f: $!";
    26    # print array to temp file
    27    $tmpfile = "$f.tmp";
    28    open (TMP, ">$tmpfile") or die "Can't open $tmpfile: $!";
    29    foreach $item (@contents) {
    30      print TMP "$item\n" or die "Can't print: $!";
    31    }
    32    close (TMP) or die "Can't close $tmpfile: $!";
    33    # and move the temp file back to original
    34    rename $tmpfile, $f or die "File rename from $tmpfile to $f failed: $!";
    35    # now flush all variables before using them for the next file
    36    @contents = ();
    37    $amtidx = "";
    38    $hshidx = "";
    39  }
    40
$ 
$ 

Here's the execution -

$ 
$ # execute the Perl program
$ perl swap.pl
NOW PROCESSING FILE : f1.txt
NOW PROCESSING FILE : f2.txt
NOW PROCESSING FILE : f3.txt
$ 
$ # now check the files
$ 
$ cat f1.txt
blah blah blah
Amount2 15091500.0
blah blah blah
hashAmount 15091500.0
blah blah blah
$ 
$ cat f2.txt
blah blah blah
Amount2 15
blah blah blah
hashAmount -15
blah blah blah
$ 
$ cat f3.txt
blah blah blah
Amount2 -34
blah blah blah
hashAmount 35
blah blah blah
$ 
$ 

HTH,
tyler_durden

Thanks a lot that was great:b: