File Coverage

blib/lib/Algorithm/LCS/XS.pm
Criterion Covered Total %
statement 49 49 100.0
branch 4 8 50.0
condition 9 18 50.0
subroutine 11 11 100.0
pod 3 5 60.0
total 76 91 83.5


line stmt bran cond sub pod time code
1             package Algorithm::LCS::XS;
2              
3 1     1   63850 use 5.008;
  1         2  
4 1     1   4 use strict;
  1         2  
  1         15  
5 1     1   4 use warnings;
  1         1  
  1         28  
6 1     1   377 use version;
  1         1621  
  1         5  
7             our $VERSION = qv(2.0.2);
8 1     1   83 use base 'Exporter';
  1         2  
  1         570  
9             our @EXPORT_OK = qw/&ADLCS &LCSidx/;
10             require XSLoader;
11             XSLoader::load('Algorithm::LCS::XS', $VERSION);
12              
13             ##############################
14             # code adapted from Algorithm::Diff
15              
16             sub line_map {
17 200003     200003 1 245786 my $ctx = shift;
18 200003         210136 my %lines;
19 200003         393672 push @{ $lines{$_[$_]} }, $_ for 0..$#_; # values MUST be SvIOK
  11400174         16736485  
20 200003         323528 \%lines;
21             }
22              
23             sub callback {
24 1     1 1 9244 my ($ctx, @b) = @_;
25 1         4 my $h = $ctx->line_map(@b);
26 100001 50   100001   1694661 sub { @_ ? _core_loop($ctx, $_[0], 0, $#{$_[0]}, $h) : @b }
  100001         5246054  
27 1         5 }
28              
29             sub LCS {
30 200002     200002 1 280252 my ($ctx, $a, $b) = @_;
31 200002         332449 my ($amin, $amax, $bmin, $bmax) = (0, $#$a, 0, $#$b);
32              
33 200002   33     805268 while ($amin <= $amax and $bmin <= $bmax and $a->[$amin] eq $b->[$bmin]) {
      66        
34 200002         239348 $amin++;
35 200002         598455 $bmin++;
36             }
37 200002   33     593498 while ($amin <= $amax and $bmin <= $bmax and $a->[$amax] eq $b->[$bmax]) {
      66        
38 400004         401237 $amax--;
39 400004         1126261 $bmax--;
40             }
41              
42 200002         594599 my $h = $ctx->line_map(@$b[$bmin..$bmax]); # line numbers are off by $bmin
43              
44 200002 50       473664 return $amin + _core_loop($ctx, $a, $amin, $amax, $h) + ($#$a - $amax)
45             unless wantarray;
46              
47 200002         9163712 my @lcs = _core_loop($ctx,$a,$amin,$amax,$h);
48 200002 50       379611 if ($bmin > 0) {
49 200002         1204869 $_->[1] += $bmin for @lcs; # correct line numbers
50             }
51              
52 200002         1578731 map([$_ => $_], 0 .. ($amin-1)),
53             @lcs,
54             map([$_ => ++$bmax], ($amax+1) .. $#$a);
55             }
56              
57              
58             my $alg;
59              
60             sub LCSidx {
61 100001   66 100001 0 1793186 $alg //= Algorithm::LCS::XS->new;
62 100001         122265 my (@l, @r);
63 100001         170344 for my $arr ($alg->LCS(@_)) {
64 4000040         4353602 push @l, $$arr[0];
65 4000040         4513678 push @r, $$arr[1];
66             }
67 100001         1928238 return \@l, \@r;
68             }
69              
70             sub ADLCS {
71 100000   33 100000 0 2643214235 $alg //= Algorithm::LCS::XS->new;
72 100000         108453 my @rv;
73 100000         162301 for my $arr ($alg->LCS(@_)) {
74 4000000         5173659 $rv[$$arr[0]] = $_[0][$$arr[0]];
75             }
76 100000 50       1918882 return wantarray ? @rv : \@rv;
77             }
78              
79             1;
80              
81             __END__