for my $x ( $sub_x->() ) {
for my $y ( $sub_y->() ) {
return [ $x,$y ];
}
}
####
use 5.12.0;
use strict;
use warnings;
use Data::Dump qw/pp dd/;
my $DBG;
;;; # skipped
$DBG = 0;
my $i_cross = cross(
sub {"A".."B"},
sub {1..2},
sub {"a".."b"},
);
my $count = 4;
while ( my ($v) = $i_cross->() ) {
warn "*** First 5 RESULTs: ", pp $v;
last unless $count--;
}
warn "stopped";
while ( my ($v) = $i_cross->() ) {
warn "*** Remaining RESULT: ", pp $v;
}
sub cross {
my @stack = @_;
my $level = 0;
my @ranges = ();
my @res;
return sub {
while ( $level >= 0 ) {
my $ra_range = \ $ranges[$level];
# ENTER LOOP
unless (defined $$ra_range ) {
$$ra_range = [ $stack[$level]->() ];
warn "ENTER level=$level left \@ranges=" ,pp \@ranges if $DBG;
}
# LOOP OVER
if ( @$$ra_range ) {
$res[$level] = shift @$$ra_range ;
# deepest level?
if ( $level == $#stack ) {
return [@res];
}
# go deeper
else {
$level++;
}
}
#EXIT LOOP:
else {
$level--;
$$ra_range = undef;
}
}
return;
}
}
####
*** First 5 RESULTs: ["A", 1, "a"] at d:/exp/iter/cross.pl line 92.
*** First 5 RESULTs: ["A", 1, "b"] at d:/exp/iter/cross.pl line 92.
*** First 5 RESULTs: ["A", 2, "a"] at d:/exp/iter/cross.pl line 92.
*** First 5 RESULTs: ["A", 2, "b"] at d:/exp/iter/cross.pl line 92.
*** First 5 RESULTs: ["B", 1, "a"] at d:/exp/iter/cross.pl line 92.
stopped at d:/exp/iter/cross.pl line 96.
*** Remaining RESULT: ["B", 1, "b"] at d:/exp/iter/cross.pl line 99.
*** Remaining RESULT: ["B", 2, "a"] at d:/exp/iter/cross.pl line 99.
*** Remaining RESULT: ["B", 2, "b"] at d:/exp/iter/cross.pl line 99.