in reply to Re^3: What is the easiest way to merge two hashes?
in thread What is the easiest way to merge two hashes?

I realized after writing the comment that this example does not capture the whole complexity of the issue, so I added a more complex example to the question details for which the simple method would fail.
  • Comment on Re^4: What is the easiest way to merge two hashes?

Replies are listed 'Best First'.
Re^5: What is the easiest way to merge two hashes?
by hdb (Monsignor) on Feb 15, 2015 at 09:05 UTC

    If you want to write a recursive procedure, you might want the filter the common keys that point to hash refs, apply the procedure to them, and then use Corion's "simple" method.

    use Array::Utils qw( intersect ); my @refkeys1 = grep { ref $ref1->{$_} } keys %$ref1; my @refkeys2 = grep { ref $ref2->{$_} } keys %$ref2; my @common = intersect( @refkeys1, @refkeys2 );

    UPDATE: Here is a complete example which I only tested on your data provided. As with all recursive procedures more testing would be needed...

    use strict; use warnings; use Data::Dumper; use Array::Utils qw( intersect ); my $ref1={ ref1_specific_key => 'some value', common_key => { a => 1, common_subkey => 'foo' } }; my $ref2= { ref2_specific_key => 'some other value', common_key => { b => 2, common_subkey => 'bar' } }; sub mergehash { my ($ref1, $ref2) = @_; my @refkeys1 = grep { ref $ref1->{$_} } keys %$ref1; my @refkeys2 = grep { ref $ref2->{$_} } keys %$ref2; my @common = intersect( @refkeys1, @refkeys2 ); for my $c (@common) { $ref2->{$c} = mergehash( $ref1->{$c}, $ref2->{$c} ); } return { %$ref1, %$ref2 }; } my $output = mergehash($ref1,$ref2); print Dumper $output;
Re^5: What is the easiest way to merge two hashes?
by hdb (Monsignor) on Feb 15, 2015 at 08:50 UTC

    In the more complex case, you need to exactly specify what you want to happen. You might specify for two identical keys that both point to hash refs you want to recursively apply the procedure. But what will happen if in one hash the common key points to a scalar and in the other to a hash ref. Or if there are array refs containing hash refs, etc? Can these complexities be ruled out?

      They values are guaranteed to be of the same type, wherever a collision can happen ( namely scalar ). This is specific to my problem, so I need not worry about different types. Both hashes have the same structure, just here and there some values are missing from one or the other. If there is a collision the value to overwrite is always a scalar.