n列目まででdiff

はじめに

タブ区切りなどのファイルで、n列目までを考慮したdiffなどを取りたいけど、出力はその行のすべてを表示してほしい。
コマンドの組み合わせだけでやりたいけど、いい方法が思いつかない。。

コード

とりあえず1列目だけでdiff。

#!/usr/bin/perl
#
# column diff
#  Usage: $ cdiff.pl FILE1 FILE2
#
use strict;
use warnings;
use Text::Diff;

my @FILE_NAME = @ARGV;
my $delim = "\t";

my $file1 = $FILE_NAME[0];
my $file2 = $FILE_NAME[1];

my $FH1;
my $FH2;
my $linenum1 = 1;
my $linenum2 = 1;
open($FH1, "<", $file1) or die "cannot open $file1: $!";
open($FH2, "<", $file2) or die "cannot open $file2: $!";

sub seekLine1 {
    my ($start, $end) = @_;

    while($linenum1 < $start){ <$FH1>; $linenum1++; }
    for(my $i=$start; $i<=$end; $i++){
        my $tmp = <$FH1>; chomp $tmp;
        print "< ",$tmp,"\n";
        $linenum1++;
    }
}
sub seekLine2 {
    my ($start, $end) = @_;

    while($linenum2 < $start){ <$FH2>; $linenum2++; }
    for(my $i=$start; $i<=$end; $i++){
        my $tmp = <$FH2>; chomp $tmp;
        print "> ",$tmp,"\n";
        $linenum2++;
    }
}

# cut & diff
my $cut1 = `cut -f1 -d"$delim" $file1`;
my $cut2 = `cut -f1 -d"$delim" $file2`;

my $diff = diff(\$cut1, \$cut2, {STYLE => "OldStyle"});

# main loop
while($diff =~ m/(.*?)\n/gm){
    my $line = $1;
    if($line =~ m/^([\d,]+)(\w)([\d,]+)$/){
        print $line,"\n";

        my $range1 = $1;
        my $range2 = $3;
        my $type = $2;
        
        if($type eq 'c'){
            if($range1 =~ m/^(\d+),(\d+)$/){ seekLine1($1, $2); }
            elsif($range1 =~ m/^(\d+)$/){ seekLine1($1, $1); }
            print "---\n";
            if($range2 =~ m/^(\d+),(\d+)$/){ seekLine2($1, $2); }
            elsif($range2 =~ m/^(\d+)$/){ seekLine2($1, $1); }
        }
        elsif($type eq 'd'){
            if($range1 =~ m/^(\d+),(\d+)$/){ seekLine1($1, $2); }
            elsif($range1 =~ m/^(\d+)$/){ seekLine1($1, $1); }
        }
        elsif($type eq 'a'){
            if($range2 =~ m/^(\d+),(\d+)$/){ seekLine2($1, $2); }
            elsif($range2 =~ m/^(\d+)$/){ seekLine2($1, $1); }
        }
    }
}

結果

$ cat ma_a
東京特許許可局
東京	名詞,固有名詞,地域,一般,*,*,東京,トウキョウ,トーキョー
特許	名詞,サ変接続,*,*,*,*,特許,トッキョ,トッキョ
許可局	名詞,一般,*,*,*,*,許可局,キョカキョク,キョカキョク
EOS

$ cat ma_b
東京特許許可局
東京	名詞,名詞,地域,一般,*,*,東京,トウキョウ,トーキョー
特許	名詞,サ変接続,*,*,*,*,特許,トッキョ,トッキョ
許可	名詞,サ変接続,*,*,*,*,許可,キョカ,キョカ
局	名詞,接尾,一般,*,*,*,局,キョク,キョク
EOS

$ diff ma_a ma_b
2c2
< 東京	名詞,固有名詞,地域,一般,*,*,東京,トウキョウ,トーキョー
---
> 東京	名詞,名詞,地域,一般,*,*,東京,トウキョウ,トーキョー
4c4,5
< 許可局	名詞,一般,*,*,*,*,許可局,キョカキョク,キョカキョク
---
> 許可	名詞,サ変接続,*,*,*,*,許可,キョカ,キョカ
> 局	名詞,接尾,一般,*,*,*,局,キョク,キョク

$ cdiff.pl ma_a ma_b
4c4,5
< 許可局	名詞,一般,*,*,*,*,許可局,キョカキョク,キョカキョク
---
> 許可	名詞,サ変接続,*,*,*,*,許可,キョカ,キョカ
> 局	名詞,接尾,一般,*,*,*,局,キョク,キョク