Hi folks,

I'm going to make a script checking inconsistence on 2 documents, say doc_a and doc_b and have no idea how to start.

doc_b is reproduced from doc_a, (original document) not with 'copy and paste' command.

Making it simple first, as highlighted in following example, an one line document:-

1)
Original document "doc_a"

Check this link to sea what scannars are supported by SANE

Already having 2 typing mistakes
sea
scannars

2)
The reproduced document "doc_b" must maintain these 2 mistakes for consistence.

check thes link to sea what scannars are suppurted by SeNE

Unfortunately another 3 typing mistakes were further made;
thes
suppurted
SeNE

What I expect to have in the printout is;

Original    Mistake Line No. Word No.
this     thes     1         2
supported suppurted 1         9
SANE     SeNE     1         11

not just printing out their contents and saying "differ"

Kindly advise how to start. TIA

B.R.
satimis

Dani AI

Generated

For (and thanks to for the diff suggestion): the runtime messages you posted look like a classic parse problem — an unterminated string or a mis‑terminated Perl format — so start by fixing the syntax before worrying about logic.

Quick debug checklist

  • Run a syntax-only check: perl -c compare_s2 and fix the first reported error; later errors are usually cascading.
  • Look for an unclosed double quote or here-doc: an opening " (or <<) left unclosed will make later lines look like one long string (hence the “possible unintended interpolation” warnings).
  • If using Perl format blocks, the terminating line must be a single dot on its own line (no leading whitespace). Many people find format fragile — consider using printf/print instead.
  • Add use strict; use warnings; and three-arg open with lexical filehandles to catch simple mistakes early.

A simple, robust approach (avoid format)

  • Read both files line-by-line, chomp each line, split on whitespace (split /\s+/), then compare corresponding words. Print original-word, reproduced-word, line number and word position when they differ.
  • Handle different word counts by reporting missing/extra words.
  • Normalize punctuation and case if desired (strip trailing .,;: and compare lc()).

Example (small, self-contained script)

#!/usr/bin/perl
use strict;
use warnings;

my ($fa,$fb) = @ARGV ? @ARGV : ('doc_a','doc_b');
open my $A, '<', $fa or die $!;
open my $B, '<', $fb or die $!;

my $lineno = 0;
while (1) {
    my $la = <$A>;
    my $lb = <$B>;
    last unless defined $la || defined $lb;
    chomp($la //=''); chomp($lb //='');
    $lineno++;
    my @wa = grep length, split /\s+/, $la;
    my @wb = grep length, split /\s+/, $lb;
    my $n = @wa < @wb ? @wa : @wb;
    for my $i (0..$n-1) {
        if ($wa[$i] ne $wb[$i]) {
            printf "%-12s %-12s %4d %4d\n", $wa[$i], $wb[$i], $lineno, $i+1;
        }
    }
    for my $i ($n..$#wa) { printf "%-12s %-12s %4d %4d\n", $wa[$i], '<MISSING>', $lineno, $i+1 }
    for my $i ($n..$#wb) { printf "%-12s %-12s %4d %4d\n", '<EXTRA>', $wb[$i], $lineno, $i+1 }
}
close $A; close $B;

Notes

  • This approach is easier to debug than formats and good for learning Perl string/file handling.
  • For true “alignment” when words are inserted/deleted, consider Algorithm::Diff or external tools — but for a simple word-by-word consistency check the above will be sufficient.

Recommended Answers

All 2 Replies

Couldn't you just use the diff program under Linux/UNIX that already exists? It does that, and it does it well.

I mean, that'd be a very efficient way to go about it, unless you absolutely needed to write your own implementation.

Hi alc6379,

Tks for your advice.

I already tried "diff" before posting. It only told me that there is difference existing but not "what is the difference"

I'm learning programming starting on Bash about 10 days ago and now moving to Perl. The example is solely for learning purpose.

I tested following draft script
(Remark: compare_s2, doc_a and doc_b all under /home/satimis/PerlScript_testing)


1)
$ cat doc_a

Check this link to sea what scannars are supported by
SANE

$ cat doc_b

Check thes link to sea what scannars are suppurted by
SeNE

$ cat compare_s2

#!/usr/bin/perl -w


format   STDOUT_TOP=
       ORGINAL         MISTAKE      LINENO    WORDNO
.
format   STDOUT_MID=
       @<<<<<<<<<<     @<<<<<<<<<<  @##       @##
       $org,           $mis,        $lno1,    $wno
.

$orgfile='doc_a';
open(INFO,$orgfile)|| die 'cannot open $orgfile';
@basedoc=<INFO>;
close(INFO);
$typfile='doc_b';
open(INFO1,$typfile) || die 'cannot open $typfile';
@typedoc=<INFO1>;
close(INFO1);

#print  "       ORGINAL        MISTAKE      LINENO
WORDNO\n";

$~="STDOUT_TOP";
write();

$lno=0;
$wno=0;

foreach $i (@typedoc)
{
   $incr=0;
  @typedoc1=split(/ /,$i);

       @basedoc1=split(/ /,$basedoc[$lno]);

      foreach $k (@typedoc1)
      {
            $var=$basedoc1[$incr];

         if ( $var ne $k )
          {
             $org=$var;
             $mis=$k;
             $wno=$incr+1;
             $lno1=$lno+1;
             $~="STDOUT_MID";
              write();
          }
          $incr++;
      }
   $lno++;
}

2)
printout on xterm

$ ./compare_s1

Backslash found where operator expected at
./compare_s2 line 22, near "WORDN                 
   O\"
Unquoted string "n" may clash with future reserved
word at ./compare_s2 line                      22.
String found where operator expected at
./compare_s2 line 24, near "$~=""
  (Might be a runaway multi-line "" string starting on
line 22)
        (Missing semicolon on previous line?)
Bareword found where operator expected at
./compare_s2 line 24, near "$~="ST                
    DOUT_TOP"
        (Missing operator before STDOUT_TOP?)
String found where operator expected at
./compare_s2 line 47, near "$~=""
  (Might be a runaway multi-line "" string starting on
line 24)
        (Missing semicolon on previous line?)
Possible unintended interpolation of @typedoc1 in
string at ./compare_s2 lin                     e
24.
Possible unintended interpolation of @basedoc1 in
string at ./compare_s2 lin                     e
24.
Bareword found where operator expected at
./compare_s2 line 47, near "$~="ST                
    DOUT_MID"
        (Missing operator before STDOUT_MID?)
String found where operator expected at
./compare_s2 line 47, at end of line
        (Missing semicolon on previous line?)
syntax error at ./compare_s2 line 22, near
"WORDNO\"
Can't find string terminator '"' anywhere before EOF
at ./compare_s2 line 47

.


3)
line 22
#print " ORGINAL MISTAKE LINENO
WORDNO\n"; (line 22)

$~="STDOUT_TOP";


line 24
WORDNO\n";

$~="STDOUT_TOP"; (line 24)
write();


line 47
$lno1=$lno+1;
$~="STDOUT_MID"; (line 47)
write();


Could you please shed me some light on debugging. TIA

B.R.
satimis

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.