my $result = do_stuff_in_hash_without_autovivifying( sub { my $hash_to_work_on = shift; # do stuff here }, $coordinates, # initial hash $group, $id, $stage, 'coords' # list of keys to traverse ); sub do_stuff_in_hash_without_autovivifying { my($sub, $hash, @keys) = @_; if(@keys && exists($hash->{$keys[0]}) { return do_stuff_in_hash_without_autovivifying( $sub, $hash->{$keys[0]}, @keys[1 .. $#keys] ); } else { return $sub->($hash); } }