A common first idea is to walk through the list and swap each element with a random other element. Like so:

import random def get_random(floor, ceiling): return random.randrange(floor, ceiling + 1) def naive_shuffle(the_list): # For each index in the list for first_index in xrange(0, len(the_list) - 1): # Grab a random other index second_index = get_random(0, len(the_list) - 1) # And swap the values if second_index != first_index: the_list[first_index], the_list[second_index] = \ the_list[second_index], the_list[first_index]

However, this does not give a uniform random distribution.

Why? We could calculate the exact probabilities of two outcomes to show they aren't the same. But the math gets a little messy. Instead, think of it this way:

Suppose our list had 3 elements: [a, b, c]. This means it'll make 3 calls to get_random(0, 2). That's 3 random choices, each with 3 possibilities. So our total number of possible sets of choices is 3*3*3=27. Each of these 27 sets of choices is equally probable.

But how many possible outcomes do we have? If you paid attention in stats class you might know the answer is 3!, which is 6. Or you can just list them by hand and count:

a, b, c a, c, b b, a, c b, c, a c, b, a c, a, b

But our function has 27 equally-probable sets of choices. 27 is not evenly divisible by 6. So some of our 6 possible outcomes will be achievable with more sets of choices than others.