Principle of Computing (Python)学习笔记(7) DFS Search + Tic Tac Toe use MiniMax Stratedy
1. Trees
Tree is a recursive structure.
1.1 math nodes
https://class.coursera.org/principlescomputing-001/wiki/view?
page=trees
1.2 CODE无parent域的树
http://www.codeskulptor.org/#poc_tree.py
class Tree:
"""
Recursive definition for trees plus various tree methods
""" def __init__(self, value, children):
"""
Create a tree whose root has specific value (a string)
Children is a list of references to the roots of the subtrees.
""" self._value = value
self._children = children def __str__(self):
"""
Generate a string representation of the tree
Use an pre-order traversal of the tree
""" ans = "["
ans += str(self._value) for child in self._children:
ans += ", "
ans += str(child)
return ans + "]" def get_value(self):
"""
Getter for node's value
"""
return self._value def children(self):
"""
Generator to return children
"""
for child in self._children:
yield child def num_nodes(self):
"""
Compute number of nodes in the tree
"""
ans = 1
for child in self._children:
ans += child.num_nodes()
return ans def num_leaves(self):
"""
Count number of leaves in tree
"""
if len(self._children) == 0:
return 1 ans = 0
for child in self._children:
ans += child.num_leaves()
return ans def height(self):
"""
Compute height of a tree rooted by self
"""
height = 0
for child in self._children:
height = max(height, child.height() + 1)
return height def run_examples():
"""
Create some trees and apply various methods to these trees
"""
tree_a = Tree("a", [])
tree_b = Tree("b", [])
print "Tree consisting of single leaf node labelled 'a'", tree_a
print "Tree consisting of single leaf node labelled 'b'", tree_b tree_cab = Tree("c", [tree_a, tree_b])
print "Tree consisting of three node", tree_cab tree_dcabe = Tree("d", [tree_cab, Tree("e", [])])
print "Tree consisting of five nodes", tree_dcabe
print my_tree = Tree("a", [Tree("b", [Tree("c", []), Tree("d", [])]),
Tree("e", [Tree("f", [Tree("g", [])]), Tree("h", []), Tree("i", [])])])
print "Tree with nine nodes", my_tree print "The tree has", my_tree.num_nodes(), "nodes,",
print my_tree.num_leaves(), "leaves and height",
print my_tree.height() #import poc_draw_tree
#poc_draw_tree.TreeDisplay(my_tree) #run_examples()
1.3 CODE有parent域的树
http://www.codeskulptor.org/#user36_3SjNfYqJMV_4.py
import poc_tree class NavTree(poc_tree.Tree):
"""
Recursive definition for navigable trees plus extra tree methods
""" def __init__(self, value, children, parent = None):
"""
Create a tree whose root has specific value (a string)
children is a list of references to the roots of the children.
parent (if specified) is a reference to the tree's parent node
""" poc_tree.Tree.__init__(self, value, children)
self._parent = parent
for child in self._children:
child._parent = self def set_parent(self, parent):
"""
Update parent field
"""
self._parent = parent def get_root(self):
"""
Return the root of the tree
"""
if self._parent == None:
return self;
else:
return self._parent.get_root(); def depth(self):
"""
Return the depth of the self with respect to the root of the tree
"""
pass def run_examples():
"""
Create some trees and apply various methods to these trees
"""
tree_a = NavTree("a", [])
tree_b = NavTree("b", [])
tree_cab = NavTree("c", [tree_a, tree_b])
tree_e = NavTree("e", [])
tree_dcabe = NavTree("d", [tree_cab, tree_e]) print "This is the main tree -", tree_dcabe
print "This is tree that contains b -", tree_b.get_root() import poc_draw_tree
poc_draw_tree.TreeDisplay(tree_dcabe) print "The node b has depth", tree_b.depth()
print "The node e has depth", tree_e.depth() run_examples() # Expect output #This is the main tree - [d, [c, [a], [b]], [e]]]
#This is tree that contains b - [d, [c, [a], [b]], [e]]
#The node b has depth 2
#The node e has depth 1
1.4 CODE arithmetic expreesion由树来表达
Interior nodes in the tree are always arithmetic operators. The leaves of the tree are always numbers.
http://www.codeskulptor.org/#poc_arith_expression.py
# import Tree class definition
import poc_tree # Use dictionary of lambdas to abstract function definitions OPERATORS = {"+" : (lambda x, y : x + y),
"-" : (lambda x, y : x - y),
"*" : (lambda x, y : x * y),
"/" : (lambda x, y : x / y),
"//" : (lambda x, y : x // y),
"%" : (lambda x, y : x % y)} class ArithmeticExpression(poc_tree.Tree):
"""
Basic operations on arithmetic expressions
""" def __init__(self, value, children, parent = None):
"""
Create an arithmetic expression as a tree
"""
poc_tree.Tree.__init__(self, value, children) def __str__(self):
"""
Generate a string representation for an arithmetic expression
""" if len(self._children) == 0:
return str(self._value)
ans = "("
ans += str(self._children[0])
ans += str(self._value)
ans += str(self._children[1])
ans += ")"
return ans def evaluate(self):
"""
Evaluate the arithmetic expression
""" if len(self._children) == 0:
if "." in self._value:
return float(self._value)
else:
return int(self._value)
else:
function = OPERATORS[self._value]
left_value = self._children[0].evaluate()
right_value = self._children[1].evaluate()
return function(left_value, right_value) def run_example():
"""
Create and evaluate some examples of arithmetic expressions
""" one = ArithmeticExpression("1", [])
two = ArithmeticExpression("2", [])
three = ArithmeticExpression("3", [])
print one
print one.evaluate() one_plus_two = ArithmeticExpression("+", [one, two])
print one_plus_two
print one_plus_two.evaluate() one_plus_two_times_three = ArithmeticExpression("*", [one_plus_two, three])
print one_plus_two_times_three import poc_draw_tree
poc_draw_tree.TreeDisplay(one_plus_two_times_three)
print one_plus_two_times_three.evaluate() run_example()
2 List
In Python, lists are primarily iterative data structures that are processed using loops. However, in other languages such as Lisp and Scheme, lists are treated primarily as recursive data structures and processed
recursively.
2.1 a list example
class NodeList:
"""
Basic class definition for non-empty lists using recursion
""" def __init__(self, val):
"""
Create a list with one node
"""
self._value = val
self._next = None def append(self, val):
"""
Append a node to an existing list of nodes
"""
# print "---------called---append()--------\n"
if self._next == None:
# print "A:"+str(isinstance(val,int))+"\n";
# print "B:"+str(isinstance(val,type(self)))+"\n";
new_node = NodeList(val)
self._next = new_node
else:
self._next.append(val) def __str__(self):
"""
Build standard string representation for list
"""
if self._next == None:
return "[" + str(self._value) + "]"
else:
rest_str = str(self._next)
rest_str = rest_str[1 :]
return "[" + str(self._value) + ", " + rest_str def run_example():
"""
Create some examples
"""
node_list = NodeList(2) print node_list sub_list = NodeList(5)
# print "--------"
sub_list.append(6)
# print "--------"
sub_list2 = sub_list
node_list.append(sub_list)
node_list.append(sub_list2)
print node_list run_example()
3 Minimax
https://class.coursera.org/principlescomputing-001/wiki/minimax
X and O alternate back and forth between min and max.
In X’s term, try to maximize the score.
the O’s term, try to minimize the score.
4 Mini Project Tic Tac Toe with Minimax
"""
Mini-max Tic-Tac-Toe Player
""" import poc_ttt_gui
import poc_ttt_provided as provided # Set timeout, as mini-max can take a long time
import codeskulptor
codeskulptor.set_timeout(60) # SCORING VALUES - DO NOT MODIFY
SCORES = {provided.PLAYERX: 1,
provided.DRAW: 0,
provided.PLAYERO: -1} def minimax(board, player):
"""
Make a move through minimax method.
"""
check_res = board.check_win()
if check_res != None:
return SCORES[check_res] , (-1,-1)
else:
empty_list = board.get_empty_squares()
com_score = -2
max_score = -2
max_each = (-1,-1)
changed_player = provided.switch_player(player)
for each in empty_list:
cur_board = board.clone()
cur_board.move(each[0], each[1], player)
cur_score_tuple = minimax(cur_board, changed_player)
cur_score = cur_score_tuple[0]
if cur_score * SCORES[player] > com_score:
com_score = cur_score * SCORES[player] # used for compare
max_score = cur_score # used for return a value
max_each = each
if com_score == 1:
return max_score, max_each
return max_score, max_each def mm_move(board, player):
"""
Make a move on the board. Returns a tuple with two elements. The first element is the score
of the given board and the second element is the desired move as a
tuple, (row, col).
"""
# print "-----------------new_move--------------"
# print "B1:"+" player="+str(player)+"\n"
# print board
# print "----------------"
score_and_board = minimax(board, player)
# print "C1"
# print score_and_board
# print "-----------------new_move--------------"
return score_and_board def move_wrapper(board, player, trials):
"""
Wrapper to allow the use of the same infrastructure that was used
for Monte Carlo Tic-Tac-Toe.
"""
move = mm_move(board, player)
assert move[1] != (-1, -1), "returned illegal move (-1, -1)"
return move[1] # Test game with the console or the GUI.
# Uncomment whichever you prefer.
# Both should be commented out when you submit for
# testing to save time. #test1
#mm_move(provided.TTTBoard(3, False, [[provided.PLAYERX, provided.EMPTY, provided.EMPTY], [provided.PLAYERO, provided.PLAYERO, provided.PLAYERX], [provided.PLAYERO, provided.PLAYERX, provided.EMPTY]]), provided.PLAYERX)
#mm_move(provided.TTTBoard(3, False, [[provided.PLAYERX, provided.PLAYERO, provided.EMPTY], [provided.PLAYERO, provided.PLAYERO, provided.PLAYERX], [provided.PLAYERO, provided.PLAYERX, provided.PLAYERX]]), provided.PLAYERX)
#mm_move(provided.TTTBoard(3, False, [[provided.PLAYERX, provided.EMPTY, provided.PLAYERX], [provided.PLAYERO, provided.PLAYERO, provided.PLAYERX], [provided.PLAYERO, provided.PLAYERX, provided.EMPTY]]), provided.PLAYERO)
#mm_move(provided.TTTBoard(3, False, [[provided.PLAYERX, provided.EMPTY, provided.EMPTY], [provided.PLAYERO, provided.PLAYERO, provided.PLAYERX], [provided.PLAYERO, provided.PLAYERX, provided.PLAYERX]]), provided.PLAYERO)
#mm_move(provided.TTTBoard(3, False, [[provided.PLAYERX, provided.EMPTY, provided.EMPTY], [provided.PLAYERO, provided.PLAYERO, provided.PLAYERX], [provided.PLAYERO, provided.PLAYERX, provided.EMPTY]]), provided.PLAYERX)
#mm_move(provided.TTTBoard(3, False, [[provided.PLAYERX, provided.EMPTY, provided.EMPTY], [provided.PLAYERO, provided.PLAYERO, provided.EMPTY], [provided.EMPTY, provided.PLAYERX, provided.EMPTY]]), provided.PLAYERX)
#mm_move(provided.TTTBoard(2, False, [[provided.EMPTY, provided.EMPTY], [provided.EMPTY, provided.EMPTY]]), provided.PLAYERX)
#test1 #provided.play_game(move_wrapper, 1, False)
#poc_ttt_gui.run_gui(3, provided.PLAYERO, move_wrapper, 1, False)
注意上面的minimax()方法进行了一些简化处理:
In Minimax, you need to alternate between maximizing and minimizing. Given the SCORES that we have provided you with, player X is always the maximizing player and play O is always the minimizing player. You can use an if-else statement to decide when to
maximize and when to minimize. But, you can also be more clever by noticing that if you multiply the score by SCORES[player] then you can always maximize
假设要用if else的写法。是这种:
check_res = board.check_win()
if check_res != None:
return SCORES[check_res] , (-1,-1)
else:
empty_list = board.get_empty_squares()
if player == provided.PLAYERX:
max_score = -2;
max_each = (-1,-1)
changed_player = provided.switch_player(player)
for each in empty_list:
cur_board= board.clone()
cur_board.move(each[0], each[1], player)
cur_score_tuple = minimax(cur_board, changed_player)
cur_score = cur_score_tuple[0]
if cur_score > max_score:
max_score = cur_score
max_each = each
if max_score == SCORES[provided.PLAYERX]:
return max_score, max_each
return max_score, max_each
elif player == provided.PLAYERO:
min_score = 2;
min_each = (-1,-1)
changed_player = provided.switch_player(player)
for each in empty_list:
cur_board= board.clone()
cur_board.move(each[0], each[1], player)
cur_score_tuple = minimax(cur_board, changed_player)
cur_score = cur_score_tuple[0]
if cur_score < min_score:
min_score = cur_score
min_each = each
if min_score == SCORES[provided.PLAYERO]:
return min_score, min_each
return min_score, min_each
Principle of Computing (Python)学习笔记(7) DFS Search + Tic Tac Toe use MiniMax Stratedy的更多相关文章
- Principle of Computing (Python)学习笔记(5) BFS Searching + Zombie Apocalypse
1 Generators Generator和list comprehension非常类似 Generators are a kind of iterator that are defined l ...
- OpenCV之Python学习笔记
OpenCV之Python学习笔记 直都在用Python+OpenCV做一些算法的原型.本来想留下发布一些文章的,可是整理一下就有点无奈了,都是写零散不成系统的小片段.现在看 到一本国外的新书< ...
- python学习笔记整理——字典
python学习笔记整理 数据结构--字典 无序的 {键:值} 对集合 用于查询的方法 len(d) Return the number of items in the dictionary d. 返 ...
- VS2013中Python学习笔记[Django Web的第一个网页]
前言 前面我简单介绍了Python的Hello World.看到有人问我搞搞Python的Web,一时兴起,就来试试看. 第一篇 VS2013中Python学习笔记[环境搭建] 简单介绍Python环 ...
- python学习笔记之module && package
个人总结: import module,module就是文件名,导入那个python文件 import package,package就是一个文件夹,导入的文件夹下有一个__init__.py的文件, ...
- python学习笔记(六)文件夹遍历,异常处理
python学习笔记(六) 文件夹遍历 1.递归遍历 import os allfile = [] def dirList(path): filelist = os.listdir(path) for ...
- python学习笔记--Django入门四 管理站点--二
接上一节 python学习笔记--Django入门四 管理站点 设置字段可选 编辑Book模块在email字段上加上blank=True,指定email字段为可选,代码如下: class Autho ...
- python学习笔记--Django入门0 安装dangjo
经过这几天的折腾,经历了Django的各种报错,翻译的内容虽然不错,但是与实际的版本有差别,会出现各种奇葩的错误.现在终于找到了解决方法:查看英文原版内容:http://djangobook.com/ ...
- python学习笔记(一)元组,序列,字典
python学习笔记(一)元组,序列,字典
随机推荐
- Icon font font face
font-face自定义字体,iconfont就是把各种图片做成字体.iconfont优势: 字体文件小,一般20-50kb: 容易编辑和维护,尺寸和颜色可以用css来控制: 透明完全兼容IE6: ...
- 原生js实现简单移动端轮播图
最近项目不是很忙,自己就用原生js写了一个简单的移动端轮播图的小demo,可实现自动轮播和手势滑动轮播,然后就把它记录到个人博客里.还有很多不足的地方,希望多多指出,以便改进. 1.代码部分 分为四个 ...
- ios video标签部分mp4文件无法播放的问题
问题描述: 部分MP4文件在ios的微信浏览器中无法播放,点击播放后缓冲一下之后显示叉,而另外一些mp4文件正常,同时在安卓全部下正常. 分析: h264编码的压缩级别问题导致. 苹果官方文档中对 i ...
- Java线程面试题
1:什么是线程? 线程是操作系统能够进行运算调度的最小单位,它被包含在进程之中,是进程中的实际运作单位.程序员可以通过它进行多处理器编程,你可以使用多线程对运算密集型任务提速.比如,如果一个线 ...
- 史上最全的IntelliJIdea快捷键
Ctrl+Shift+方向键Up/Down 代码向上/下移动. Ctrl+X 删除行 Ctrl+Y 也是删除行,不知道有啥区别 Ctrl+D 复制行 Ctrl+Alt+L 格式化代码 Ctrl+N 查 ...
- php 例子 如何转换ISO8601为 utc时间
//firstpowertime "2017-01-02T13:22:22" 获取时间$firstpowertime=$list[$i]['firstpowertime'];//判 ...
- php 文档操作
ftp_mkdir() 函数在 FTP 服务器上建立新目录. 语法 ftp_mkdir(ftp_connection,dir) 参数 描述 ftp_connection 必需.规定要使用的 FTP 连 ...
- jenkins+docker 持续构建非docker in docker jenkins docker svn maven
工欲善其事必先利其器,为了解脱程序员的,我们程序员本身发明了很多好用的工具,通过各种工具的组合来达到我们想要的结果 本文采用jenkins docker svn maven作为相关工具,项目sprin ...
- linux kernel态下使用NEON对算法进行加速
ARM处理器从cortex系列开始集成NEON处理单元,该单元可以简单理解为协处理器,专门为矩阵运算等算法设计,特别适用于图像.视频.音频处理等场景,应用也很广泛. 本文先对NEON处理单元进行简要介 ...
- HtmlImageGenerator乱码问题解决、html2image放linux上乱码问题解决
使用html2image-0.9.jar生成图片. 在本地window系统正常,放到服务器linux系统时候中文乱码问题.英文可以,中文乱码应该就是字体问题了. 一.首先需要在linux安装字体,si ...