_iterative_copy( [ 'a' ] );
####
What's a ARRAY at script.pl line 12
main::_iterative_copy('ARRAY(0x15d5f18)') called at script.pl line 47
####
use strict;
use warnings;
use Data::Dumper qw( Dumper );
sub iterative_copy {
my $root;
my @src;
my @dst;
push @src, $_[0];
push @dst, \$root;
while (@src) {
my $src = shift(@src);
my $dst = shift(@dst);
if (not ref $src) {
$$dst = $src;
}
elsif (ref $src eq "HASH") {
$dst = ($$dst = {});
foreach my $key (keys %$src) {
push @src, $src->{$key};
push @dst, \($dst->{$key});
}
}
elsif (ref $src eq "ARRAY") {
$dst = ($$dst = []);
foreach my $i (0..$#$src) {
push @src, $src->[$i];
push @dst, \($dst->[$i]);
}
}
else {
Carp::croak "What's a " . ref $_ . "?"
}
}
return $root;
}
{
local $Data::Dumper::Indent = 0;
my $d1 = [ [ 'a', 'b' ], { k1=>'v1', k2=>'v2' } ];
my $d2 = iterative_copy($d1);
print(Dumper($d1), "\n");
print(Dumper($d2), "\n");
print($d1, " != ", $d2, "\n");
print($d1->[0], " != ", $d2->[0], "\n");
print($d1->[1], " != ", $d2->[1], "\n");
}
####
$VAR1 = [['a','b'],{'k2' => 'v2','k1' => 'v1'}];
$VAR1 = [['a','b'],{'k2' => 'v2','k1' => 'v1'}];
ARRAY(0x1ae0718) != ARRAY(0x1ae073c)
ARRAY(0x15d5fd8) != ARRAY(0x1ae076c)
HASH(0x15d6c98) != HASH(0x1ae0790)
####
sub iterative_copy {
my $root;
my @todo;
push @todo, [ $_[0], \$root ];
while (@todo) {
my ($src, $dst) = @{ shift(@todo) };
if (not ref $src) {
$$dst = $src;
}
elsif (ref $src eq "HASH") {
$dst = ($$dst = {});
push @todo, map { [ $src->{$_}, \($dst->{$_}) ] } keys %$src;
}
elsif (ref $src eq "ARRAY") {
$dst = ($$dst = []);
push @todo, map { [ $src->[$_], \($dst->[$_]) ] } 0..$#$src;
}
else {
Carp::croak "What's a " . ref $_ . "?"
}
}
return $root;
}