culled a dead branch, Devel::Cover back to 100%, 0.07 released
[gitmo/Algorithm-C3.git] / lib / Algorithm / C3.pm
index 66c32ff..cc3b856 100644 (file)
@@ -6,13 +6,14 @@ use warnings;
 
 use Carp 'confess';
 
-our $VERSION = '0.06';
+our $VERSION = '0.07';
 
 sub merge {
     my ($root, $parent_fetcher, $cache) = @_;
 
     $cache ||= {};
-    my @STACK;  # stack for simulating recursion
+
+    my @STACK; # stack for simulating recursion
 
     my $pfetcher_is_coderef = ref($parent_fetcher) eq 'CODE';
 
@@ -32,13 +33,14 @@ sub merge {
             $new_root = $current_parents->[$i++];
 
             if($seen{$new_root}) {
-                my @isastack = (
-                    (map { $_->[0] } @STACK),
-                    $current_root,
-                    $new_root
-                );
-                shift @isastack while $isastack[0] ne $new_root;
-                my $isastack = join(q{ -> }, @isastack);
+                my @isastack;
+                my $reached;
+                for(my $i = 0; $i < $#STACK; $i += 4) {
+                    if($reached || ($reached = ($STACK[$i] eq $new_root))) {
+                        push(@isastack, $STACK[$i]);
+                    }
+                }
+                my $isastack = join(q{ -> }, @isastack, $current_root, $new_root);
                 die "Infinite loop detected in parents of '$root': $isastack";
             }
             $seen{$new_root} = 1;
@@ -47,12 +49,7 @@ sub merge {
                 confess "Could not find method $parent_fetcher in $new_root";
             }
 
-            push(@STACK, [
-                $current_root,
-                $current_parents,
-                $recurse_mergeout,
-                $i,
-            ]);
+            push(@STACK, $current_root, $current_parents, $recurse_mergeout, $i);
 
             $current_root = $new_root;
             $current_parents = $cache->{pfetch}->{$current_root} ||= [ $current_root->$parent_fetcher ];
@@ -119,10 +116,12 @@ sub merge {
 
         return @$mergeout if !@STACK;
 
-        ($current_root, $current_parents, $recurse_mergeout, $i)
-            = @{pop @STACK};
+        $i = pop(@STACK);
+        $recurse_mergeout = pop(@STACK);
+        $current_parents = pop(@STACK);
+        $current_root = pop(@STACK);
 
-        push(@$recurse_mergeout, $mergeout) if @$mergeout;
+        push(@$recurse_mergeout, $mergeout);
     }
 }