我一直在尝试添加一种存储和检索程序animal.py获得的知识的方法,这是一种通过二元决策树工作的“20问题”学习算法。 (请点击链接查看原始程序)
对于原始程序,我已将状态“up”添加到每个节点,以指向决策树中节点的父节点,以便更容易在树上下移动。我还使用正则表达式将所有非字母数字用户输入更改为空格,因此用户不会混淆我的两个新函数:
def know(know):
#Load preset knowledge
p=node("")
knowledge=p
for char in know:
if char not in "+-":p.question+=char
if char=="+":
p.right=node("")
p.right.up=p
p.left=node("")
p.left.up=p
p=p.right
if char=="-": p=p.up.left
return knowledge
def output(node,accum=""):
#Output all knowledge
accum=accum+node.question
if node.right!= None : accum=output(node.right,accum+"+")
if node.left!= None : accum=output(node.left,accum+"-")
return accum
函数“output”用于将传递给它的节点下面的完整树作为单个字符串返回,“+”和“ - ”字符表示字符串跟随的节点。函数“know”应该采用先前由“output”创建的字符串,创建二进制决策树并返回指向顶部节点的指针。这是我无法弄清楚的不完整的部分。 (目前,我正在将初始知识字符串直接输入到程序源中:加载和保存文件将在以后添加,这似乎是一项微不足道的任务)
例如:输出(知道('矿物+水晶+石英 - 黑曜石 - 无'))返回:'矿物+水晶+石英 - 黑曜石 - ' -
它应该返回原始字符串:'mineral + crystal + quartz-obsidian-nothing'
我确信这应该有效(理论上),但是我已经碰壁了,我真的迷失了为什么不是。
我的想法是错误的,还是仅仅是我尝试实施它?有没有更好的方法来存储原始程序中创建的决策树?
我是狂热的读者,但是第一次到stackoverflow的海报,我对这个网站上的人才感到敬畏,所以我非常期待你的想法。
答案 0 :(得分:0)
pickle module可以序列化和反序列化复杂的结构。这应该很简单:
with open('animal.dat', 'w') as outf:
pickle.dump(knowledge, outf)
和
with open('animal.dat', 'r') as inf:
knowledge = pickle.load(inf)
正如他们所说,"the batteries are included"所以学习标准库会让事情变得简单,even flying。
答案 1 :(得分:0)
根据请求,我无法找到“猜动物”的实现,但我找到了由它生成的存档的pickle文件。值得注意的是,我不需要原始应用程序来解释它:
>>> import pickle
>>> with open('animal.pickle') as inf:
... animals = pickle.load(inf)
...
>>> import pprint
>>> pprint.pprint(animals)
['is it fuzzy',
['does it have a tail',
['is it a pack hunter',
'dog',
['does it have thumbs',
'lemur',
['Does it have a bushy tail',
'chipmunk',
['Does it have a horn', 'rhinoceros', 'cat']]]],
'chimp'],
['can it breathe air',
['Does it have feathers',
'cockatoo',
['Does it have 8 legs', 'spider', 'iguana']],
'catfish']]
创建这个树作为嵌套列表的程序的实现留给读者练习。在我的回忆中,它与问题中链接的长度和一般方法大致相同,它会让你熟悉列表操作。