#!/usr/bin/perl

###
###  Given two files, compare them line by line and print out lines in
###  file A not in file B, and lines in file B not in file A.
###
###  Note that this does not pay attention to the ORDER of the lines,
###  just the content; if ABC is on line 27 in file 1 and on line 56
###  in line 2, it will be counted as present in both files.  For the
###  same reason, duplicates are also ignored.
###
###  Probably not efficient for very large files since it sucks the
###  contents of both files into memory.
###
###  Anthony R. Thompson, written sometime in the mid 2000s
###  Contact: put @ between art and sigilservices.com
###
###  Copyright (C) 1998-2010 by the Free Software Foundation, Inc.
###
###  This program is free software; you can redistribute it and/or
###  modify it under the terms of the GNU General Public License
###  as published by the Free Software Foundation; either version 2
###  of the License, or (at your option) any later version.
###
###  This program is distributed in the hope that it will be useful,
###  but WITHOUT ANY WARRANTY; without even the implied warranty of
###  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
###  GNU General Public License for more details.
###
###  You should have received a copy of the GNU General Public License
###  along with this program; if not, write to the Free Software
###  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
###  02110-1301, USA. http://www.fsf.org/licensing/licenses/gpl.html
###

use strict;

my($file1) = shift;
my($file2) = shift;
die "Usage: $0 file1 file2\n" unless ($file1 and $file2);

my(%fileone);
open(FILEONE, $file1) or die "Unable to open file 1\n";
while(<FILEONE>) { $fileone{$_} = 1; }

my(%filetwo);
open(FILETWO, $file2) or die "Unable to open file 2\n";
while(<FILETWO>) { $filetwo{$_} = 1; }

my(%bothfiles);
my($onenottwo, $twonotone, $bothfiles) = 0;
print "Present in $file1 but not in $file2:\n";
foreach(keys(%fileone)) {
    if ($filetwo{$_}) { $bothfiles{$_} = 1; $bothfiles++; }
    else { print; $onenottwo++; }
}
print "(# present in $file1 but not in $file2: $onenottwo)\n\n";

print "Present in $file2 but not in $file1:\n";
foreach(keys(%filetwo)) {
    if ($fileone{$_}) { $bothfiles{$_} = 1; }
    else { print; $twonotone++; }
}
print "(# present in $file2 but not in $file1: $twonotone)\n\n";

print "Present in both files:\n";
foreach(keys(%bothfiles)) {
    print;
}
print "(# present in $file1 and $file2: $bothfiles)\n\n";
