---
和上一篇一样,这个也加上了中文注释。
# -*- coding: utf-8 -*-
# Copyright by XD
# 交流QQ:584927688 ^_^
#《learnpythonthehardway》ex41,学会说面向对象。
#oop_test.py
#
#此为learnpythonthehardway中作者为了帮助读者熟悉面向对面的编程\
#而设计的一个根据代码写描述或根据描述写代码的考试小程序。
#
#目的:一方面是督促我自己充分理解这段代码,另一方面也能帮助初学者理解。
import random
from urllib import urlopen
import sys
#作者随意准备的词汇。
WORD_URL = "http://learncodethehardway.org/words.txt"
WORDS = []
#代码及描述中的‘函数方法/属性’function/attribute,‘参数’parameters,‘类名’,‘实例名/对象’,
PHRASES = {
"class %%%(%%%):":
"Make a class named %%% that is-a %%%",
"class %%%(object):\n\tdef __init__(self,***)":
"class %%% has-a __init__ that takes self and *** parameters.",
"*** = %%%()":
"Set *** to an instance of class %%%.",
"***.***(@@@)":
"From *** get the *** function, and call it with parameters self,@@@.",
"***.*** = '***'":
"From *** get the *** attribute and set it to '***'."
}
# do they want to drill phrases first
#由答题者选择是要根据描述编码还是根据代码描述。
#sys.argv为从命令行接收的参数,第一个参数默认为文件名。
if len(sys.argv) == 2 and sys.argv[1] == "english":
PHRASE_FIRST = True
else:
PHRASE_FIRST = False
# load up the words from the website
#将词汇们载入到列表WORDS中。
for word in urlopen(WORD_URL).readlines():
WORDS.append(word.strip())
#定义覆盖描述及代码中预留位置的函数,参数为片段、描述。
#最后返回一个列表results
#先将预留放置词汇的位置分类
#参数为key或value,两个总是相对
def convert(snippet, phrase):
class_names = [w.capitalize() for w in random.sample(WORDS,snippet.count("%%%"))]
other_names = random.sample(WORDS, snippet.count('***'))
results = []
param_names = []
for i in range(0,snippet.count('@@@')):
#参数的个数为1-3个随机。
param_count = random.randint(1,3)
#随机到几个参数就从WORDS中获取几个词
param_names.append(', '.join(random.sample(WORDS, param_count)))
#准备好要进行替换的PHRASES
for sentence in snippet,phrase:
result = sentence[:]
#result = [snippet,phrase]
#扯句闲话,作者为了描述和代码对应,替换词汇的顺序是固定的。。
#用这种方法替换,描述与代码中词汇的顺序肯定是一样的。
#fake class names 类名
for word in class_names:
result = result.replace("%%%", word,1)#最后一位参数规定每次替换一个,保证%%%不重复。
#fake other names 对象、方法和其他
for word in other_names:
result = result.replace("***", word,1)
#fake parameter lists 参数名
for word in param_names:
result = result.replace("@@@",word,1)
results.append(result)
return results
# keep going until they hit CTRL-D
#这里才是重点,是作者的编程逻辑。
try:
while True:#循环抽题
snippets = PHRASES.keys()
random.shuffle(snippets)#随机打乱顺序
for snippet in snippets:#抽题
phrase = PHRASES[snippet]
question, answer = convert(snippet, phrase)
if PHRASE_FIRST:
question, answer =answer, question
print question
raw_input(" >")
print "ANSWER: %s\n\n" % answer
except EOFError:
print '\nBye!'