# Homework 3 Solutions # Software Design # Allen Downey import sys import string def is_palindrome(word): """return True if the given word is a palindrome; otherwise return False""" if len(word) < 2: return True if word[0] != word[-1]: return False middle = word[1:-1] return is_palindrome(middle) def is_palindrome2(word): """return True if the given word is a palindrome; otherwise return False""" t1 = list(word) t2 = list(word) t2.reverse() return t1 == t2 def has_e(word): """return True if the word has an e""" return 'e' in word def has_no_e(word): """return True if the word has no e""" return 'e' not in word def avoids(word, forbidden): """return True if none of the forbidden letters appears in the word""" for c in word: if c in forbidden: return False return True def uses_all(word, required): """return True if all the required letters appear in the word""" for c in required: if c not in word: return False return True def uses_only(word, available): """return True if the word only contains available letters""" for c in word: if c not in available: return False return True def is_tautonym(word): """return True if the word is a tautonym, like beriberi and tomtom""" if len(word)%2: return i = len(word)/2 return word[:i] == word[i:] def is_abecedarian(word): """return True if the letters of the word are in alphabetical order""" for i in range(len(word)-1): if word[i+1] <= word[i]: # strict version: no doubles return False return True def rotate_word(word, shift=1): """rotate the letters of a word by the given shift amount""" res = '' for c in word: res += rotate_letter(c, shift) return res def rotate_letter(c, shift=1): """rotate a letter by the given shift amount""" if c in string.lowercase: return rotate(c, shift, 'a') elif c in string.uppercase: return rotate(c, shift, 'A') else: return c def rotate(c, shift, base): """rotate a letter by the given shift amount, relative to the given base""" x = ord(c) - ord(base) y = (x + shift) % 26 + ord(base) return chr(y) def apply_filter(file, filter, *args): """read each line of the given file and apply the given filter. If the result is True, print the line.""" try: fp = open(file, 'r') except IOError: print "Couldn't find a file named", file sys.exit() for word in fp: word = string.rstrip(word) word = string.lower(word) if filter(word, *args): print word def main(name, filter='is_palindrome', *args): try: filter = eval(filter) except NameError: print 'There is no filter named', filter sys.exit() file='/usr/share/dict/words' apply_filter(file, filter, *args) if __name__ == '__main__': main(*sys.argv)