Take the 2-minute tour ×

There's not much guarantees about order of hash keys in Perl. Is there any mention in docs that I can't find that would say that as long as two hashes use exactly same keys, they will go in exactly same order?

Short test seems to confirm that. Even if I generate some additional keys for internal key table between assigning to two different hashes, their keys are returned in same order:

my %aaa;
my %bbb;
my %ccc;
my %ddd;

@aaa{qw(a b c d e f g h i j k l)}=();
# Let's see if generating more keys for internal table matters
@ccc{qw(m n o p q r s t u v w x)}=();
# Just to test if different insertion order matters
@ddd{qw(l k c d e f g h i j a)}=(); $ddd{b} = ();

print keys %aaa, "\n";
print keys %bbb, "\n";
print keys %ddd, "\n";

However I wouldn't rely on udocumented behavior and only fact that can be easily found in docs is that keys, values and each all will use same order as long as hash is not modified.

share|improve this question
add comment

5 Answers

up vote 6 down vote accepted

A longer test disproves.

So, different hashes with the same set of keys won't always have the same order. For me the program below demonstrates that two hashes with keys qw(a b c d e f) can differ in ordering:

%h1: ecabdf
%h2: eadcbf


#!/usr/bin/env perl

use strict;
use warnings;
use feature qw(say);

# http://stackoverflow.com/q/12724071/132382

use constant KEYS => qw(a b c d e f);

my %h1 = map { $_ => undef } KEYS;
my %h2 = map { $_ => undef } KEYS;

delete @h2{'b', 'd', 'f'};
@h2{'x', 'y', 'z'} = ();
@h2{'b', 'd', 'f'} = ();
delete @h2{'x', 'y', 'z'};

say $^V;
say '%h1: ', keys(%h1);
say '%h2: ', keys(%h2);


Here's a simpler demonstration that insertion order alone matters:

$ perl -MList::Util=shuffle -E \
> '@keys = ('a'..'z'); @h1{@keys} = @h2{shuffle @keys} = ();
> say keys(%$_) for (\%h1, \%h2)'
#^^             ^^  ^^
#||             ||  ||
share|improve this answer
This key reordering holds for me all the way back to 5.8.8 –  pilcrow Oct 4 '12 at 15:03
Well, that's what I kind of expected from beginning. And, additionally, it is hard to prove something does not exists in docs, but a practical demonstration is surely the best argument against this assumption. –  Oleg V. Volkov Oct 7 '12 at 19:17
add comment

From perlsec:



share|improve this answer
Yes, I understand that order itself is not guaranteed, but still it says nothing about if it will be same pseudo-random sequences in different hashes. I've added 3rd hash, with different insertion order: @ddd{qw(l k c d e f g h i j a)}=(); $ddd{b} = (); It still shows same order on print. –  Oleg V. Volkov Oct 4 '12 at 9:29
@OlegV.Volkov, Disco is pointing out that no order is guaranteed, and that does indeed answer your question. You asked whether a particular kind of order (identical order between two hashes with same keys) was guaranteed, and the answer is no. It may work for you now, but you can't rely on it working. –  dan1111 Oct 4 '12 at 10:11
@dan1111, no this single phrase doesn't mean that "no order is guaranteed" because there's another passage in perldoc -f keys: "but it is guaranteed to be the same order as either the values or each function produces." See, we have at least one guarantee and I'm looking if there's another that I need. –  Oleg V. Volkov Oct 4 '12 at 10:47
@OlegV.Volkov, ok, I see your point. –  dan1111 Oct 4 '12 at 11:26
That is about the ordering of keys on the same hash, not about the ordering of keys on different hashes. There exist no guarantees about the ordering of keys on different hashes. –  darch Oct 4 '12 at 16:58
add comment

It is specifically guaranteed that this is undependable.

See the Algorithmic Complexity Attacks section of perlsec in full. Despite its regrettable incoherency, it states that

  • in 5.8.1, the order is guaranteed to be random every time.
  • in 5.8.2 and later, the order will be the same unless Perl detects pathological behavior (specifically, a series of keys that would all hash to a small number of buckets, causing the hash performance to suffer). In those cases, "the function is perturbed by a pseudorandom seed".

The documentation does not guarantee that the ordering will always be the same; in fact, it specifically states that it will not be predictable in a pathological case. Should the hashing function be changed in a future release, it's possible that data which previously did not generate degenerate hashing would now do so, and then would be subject to the random perturbation.

So the takeaway is that if you're not using 5.8.1, maybe you'll get the same order, and maybe it won't change when you update your Perl, but it might. If you are using 5.8.1, then a random order is guaranteed.

If you want a dependable order, use one of the CPAN classes that provides a hash that has a guaranteed key order - Tie::Hash::Indexed, Tie::IxHash - or just sort your keys. If you have a hash that has less than a few thousand keys, you probably won't notice an appreciable difference. If it has more than that, maybe you should consider a heavier-weight solution such as a database anyway.

Edit: and just to make it more interesting, keys will be randomly ordered as of 5.18.

share|improve this answer
add comment

Here is a counter-example that is shorter than @pilcrow's (apparently I missed his answer when I first looked at this question):

#!/usr/bin/env perl

use strict; use warnings;

my @hashes = (
    { map { $_ => rand } 'a' .. 'z' },
    { map { $_ => rand } 'a' .. 'd', 'f' .. 'z' }

delete $hashes[0]{e};

print "@{[ keys %$_ ]}\n" for @hashes;


C:\temp> t
w r a x d j y u k h g f t i n v m s l c p q b z o
w r a x d j y u k h g f t i n v m s l c p b q z o
share|improve this answer
add comment

perldoc -f keys has some info on the ordering:


So the only guarantee is that no ordering is guaranteed.

share|improve this answer
That is not relevant. I compare order of different hashes, but in same run. –  Oleg V. Volkov Oct 4 '12 at 9:26
@Oleg V. Volkov, It's 100% relevant. You have two identical pieces of code, and the quoted paragraphs says that can lead to different orderings, so you can different orderings. –  ikegami Oct 4 '12 at 17:03
add comment

Your Answer


