Anagrams – Python
June 4, 2010 – 11:56 pmWrite a Python function to find all the anagrams for each of a supplied list of words. For the word dictionary to find the anagrams you could use the one found on Unix or OS X boxes at /usr/share/dict/words. So for example:
>>> for group in anagrams(['dog','cat','horse']): ... print group ... ['dog', 'god'] ['act', 'cat'] ['horse', 'shoer', 'shore']
When called without a parameter, make the function return a list of all the anagram groups in the word dictionary, ordered by the group of anagrams with the most words:
>>> for group in anagrams(): ... if len(group)>6: print len(group), group ... 9 ['ester', 'estre', 'reest', 'reset', 'steer', 'stere', 'stree', 'terse', 'tsere'] 9 ['angor', 'argon', 'goran', 'grano', 'groan', 'nagor', 'orang', 'organ', 'rogan'] 9 ['caret', 'carte', 'cater', 'crate', 'creat', 'creta', 'react', 'recta', 'trace'] 8 ['leapt', 'palet', 'patel', 'pelta', 'petal', 'plate', 'pleat', 'tepal'] 8 ['laster', 'lastre', 'rastle', 'relast', 'resalt', 'salter', 'slater', 'stelar'] 7 ['dater', 'derat', 'detar', 'drate', 'rated', 'trade', 'tread'] 7 ['easting', 'gainset', 'genista', 'ingesta', 'seating', 'signate', 'teasing'] 7 ['darter', 'dartre', 'redart', 'retard', 'retrad', 'tarred', 'trader'] 7 ['least', 'setal', 'slate', 'stale', 'steal', 'stela', 'tales'] 7 ['atle', 'laet', 'late', 'leat', 'tael', 'tale', 'teal'] 7 ['alem', 'alme', 'lame', 'leam', 'male', 'meal', 'mela'] 7 ['lapse', 'salep', 'saple', 'sepal', 'slape', 'spale', 'speal'] 7 ['armet', 'mater', 'metra', 'ramet', 'tamer', 'terma', 'trame'] 7 ['argel', 'ergal', 'garle', 'glare', 'lager', 'large', 'regal'] 7 ['aldern', 'darnel', 'enlard', 'lander', 'lenard', 'randle', 'reland'] 7 ['alert', 'alter', 'artel', 'later', 'ratel', 'taler', 'telar'] 7 ['arist', 'astir', 'sitar', 'stair', 'stria', 'tarsi', 'tisar'] 7 ['aril', 'lair', 'lari', 'liar', 'lira', 'rail', 'rial'] 7 ['asteer', 'easter', 'reseat', 'saeter', 'seater', 'staree', 'teaser'] 7 ['arpent', 'enrapt', 'entrap', 'panter', 'parent', 'pretan', 'trepan'] >>>
Can you think of an elegant (dare I say pythonic?) way to implement the anagrams function?
Here’s my attempt:
def anagrams(wordsin=None):
f=open('/usr/share/dict/words')
ana=dict()
for word in f.readlines():
ana.setdefault(''.join(sorted(word.rstrip())),[]).append(word.rstrip())
if wordsin!=None:
return [ana.get(''.join(sorted(wordin)),[]) for wordin in wordsin]
else:
return sorted(ana.values(), key=lambda(v): (len(v)),reverse=True)
2 Responses to “Anagrams – Python”
very elegant.
one tip, for memory efficiency and simplicity, you can do the following, which reads one line at a time directly from the file, rather than creating a whole list (as in readlines).
“for word in f:”
in profiling my words file, that saves about 30MB of RAM (about 20%).
one more thing, instead of “if wordsin!=None:”, you can do “if wordsin:”, which I think is more pythonic.
By Alex Benke on Jul 21, 2010
Word Maker Scrabble works good for this type of thing.
By Joe on Aug 14, 2011