sub clean {
our $node; local *node = \$_[0]; # Alias
return if !defined($node);
my $reftype = ref($node);
return if !$reftype;
if ($reftype eq 'REF' || $reftype eq 'SCALAR') {
clean($$node);
$node = undef if !defined($$node);
} elsif ($reftype eq 'ARRAY') {
clean($_) for @$node;
@$node = grep defined, @$node;
$node = undef if !@$node;
} elsif ($reftype eq 'HASH') {
clean($_) for values(%$node);
delete @{$node}{ grep !defined($node->{$_}), keys(%$node) };
$node = undef if !keys(%$node);
}
}
####
use strict;
use warnings;
use Data::Dumper qw( Dumper );
sub dumper {
local $Data::Dumper::Useqq = 1;
local $Data::Dumper::Terse = 1;
local $Data::Dumper::Indent = 0;
return Dumper($_[0]);
}
for (
[ [1], [], {1 => 2, 2 =>{} } ],
[ undef, [ undef ], { x => undef }, \undef, \\\undef ],
) {
my $d = $_;
print(dumper($d), "\n");
clean($d);
print(dumper($d), "\n");
print("\n");
}
####
[[1],[],{1 => 2,2 => {}}]
[[1],{1 => 2}]
[undef,[undef],{"x" => undef},\undef,\\$VAR1->[3]]
undef