Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python - Speed up generation of permutations of a list (and process of checking if permuations in Dict)

I need a faster way to generate all permutations of a list, then check if each one is in a dictionary.

        for x in range (max_combo_len, 0, -1):
            possible_combos = []
            permutations = list(itertools.permutations(bag,x))
            for item in permutations:
                possible_combos.append(" ".join(item))
            #then check to see if each possible combo is in a specific Dict

If it helps, the lists are all going to be lists of strings. ['such as', 'this', 'one']

My solution works, but it's very slow. It could be that I need to stop using Python, but I thought I'd run it by you experts first!

Best, Gary

like image 774
Georgina Avatar asked Sep 22 '10 05:09

Georgina


3 Answers

A very basic optimization:

permutations = list(itertools.permutations(bag,x))
for item in permutations:

can become...

for item in itertools.permutations(bag,x):
like image 99
Amber Avatar answered Nov 15 '22 17:11

Amber


I can't test it very well without better input cases, but here are a few improvements:

for x in xrange(max_combo_len, 0, -1):
    possible_combos = (" ".join(item) for item in itertools.permutations(bag,x))
    #then check to see if each possible combo is in a specific Dict
    combos =  (c for c in possible_combos if c in specific_dict)

First, assuming you're using Python 2.x, xrange will help by not constructing an explicit list, but rather just yielding each x as you need it.

More importantly, you can throw the main effort into generator expressions and have it yield values on demand.

like image 44
perimosocordiae Avatar answered Nov 15 '22 19:11

perimosocordiae


    for x in xrange(max_combo_len, 0, -1):
        for item in itertools.permutations(bag,x):
            combo = " ".join(item)
            if combo in specificDict:
                yield combo

This way you don't have any large (and getting larger) lists, you just yield the passing comobs out of the function.

like image 33
eumiro Avatar answered Nov 15 '22 17:11

eumiro