下棋权限即是棋局状态State,由客户端与服务器通过 /rest/play/state 接口交互产生。
当State为1时即表示“轮到己方”,此时根据前设的模式决定不同的响应事件:“真人对战”——鼠标点击事件、“AI对战”——Agent走子事件,完成后再通过 /rest/board 接口将走子信息送达服务器记入数据库,并广播给其他客户端。
当State为0时即表示“轮到他方”,此时通过接口 /rest/play/state 获取其他客户端广播的走子信息,实现对战情况的实时更新。
5 项目实现前端业务代码不一一展示,主要列出后端数据处理的逻辑。只要运行本文实现的后端服务器,采取任意方式的前端页面访问接口都能实现相应功能,包括但不限于PyQt、C#、MFC、Vue等方案。
5.1 用户管理# 针对所有的用户的操作
class UserResource(Resource):
# get 请求的处理
# marshal 维持秩序,可以定制显示哪些数据(是有序的字典)
@marshal_with(user_fields)
def get(self):
users = User.query.all()
return users # 也可以users[0]
@marshal_with(user_fields)
def post(self):
# 获取数据
args = parser.parse_args() # 把验证通过的所有数据都放到一个字典里
username = args.get('username')
password = args.get('password')
# 创建user对象
user = User()
user.username = username
user.password = password
db.session.add(user)
db.session.commit()
return user # 返回创建成功的对象
# put
def put(self):
return {
'msg': '------>put'}
# delete
def delete(self):
return {
'msg': '------>delete'}
5.2 选子与游戏大厅玩家等待
# url:/rest/play
# 玩家在选完子之后向服务端不断发起提问,直至收到1
class RestPlayResource(Resource):
# get 请求的处理
def get(self):
result1 = Player.query.filter_by(ID=1).first()
if result1 is None:
playstate1 = 0 # 执黑棋的人
else:
playstate1 = 1
result2 = Player.query.filter_by(ID=2).first()
if result2 is None:
playstate2 = 0
else:
playstate2 = 1
result3 = Player.query.filter_by(ID=3).first()
if result3 is None:
playstate3 = 0
else:
playstate3 = 1
if playstate1 and playstate2 and playstate3:
playstate = 1
else:
playstate = 0
return {
"PlayState": playstate}
# url:/rest/player
# 判断玩家是否可以选择这个颜色的棋子,选子成功则注册玩家信息
class RestPlayerResource(Resource):
# post 请求的处理
def post(self):
# 获取数据
# global CountPlayers
args = parser.parse_args() # 把验证通过的所有数据都放到一个字典里
id = args.get('id')
color = args.get('color')
# 查询数据库中有没有重复的id
result = Player.query.filter_by(ID=id).first()
if result is None:
# 创建player对象,并加入数据库
player = Player()
player.ID = id
player.Player = color
player.Enable = 0
db.session.add(player)
db.session.commit()
if id == 1:
msg = "您当前执棋为黑棋"
config.add_value("CountPlayers", 1)
# CountPlayers = CountPlayers 1
elif id == 2:
msg = "您当前执棋为白棋"
config.add_value("CountPlayers", 1)
# CountPlayers = CountPlayers 1
else:
msg = "您当前执棋为黄棋"
config.add_value("CountPlayers", 1)
# CountPlayers = CountPlayers 1
if config.get_value("CountPlayers") == 3:
# if CountPlayers == 3: 如果三个人都到齐了 删掉上一次的走子信息表
Pieces.query.delete()
db.session.commit()
config.init_board() # 清全局变量
return {
"succ": 1, "msg": msg}
else:
msg = "该颜色已被选择!请重新选择。"
return {
"succ": 0, "msg": msg}
5.3 AI智能走子
def judge(JudgeId, x, y):
# global WinnerId, WinX1, WinX2, WinY1, WinY2, BoardSize
# 新建函数内变量 修改完成后提交全局变量
boardsizetemp = config.get_value("BoardSize")
checkerboardtemp = config.get_value("checkerboard")
winx1temp = config.get_value("WinX1")
winx2temp = config.get_value("WinX2")
winy1temp = config.get_value("WinY1")
winy2temp = config.get_value("WinY2")
winneridtemp = config.get_value("WinnerId")
# 判断算法
# 判断最后一子竖排
if y - 4 >= 0 and y <= boardsizetemp - 1:
if checkerboardtemp[x][y - 1] == JudgeId \
and checkerboardtemp[x][y - 2] == JudgeId \
and checkerboardtemp[x][y - 3] == JudgeId \
and checkerboardtemp[x][y - 4] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x
winy1temp = y
winy2temp = y - 4
if y - 3 >= 0 and y 1 <= boardsizetemp - 1:
if checkerboardtemp[x][y - 3] == JudgeId \
and checkerboardtemp[x][y - 2] == JudgeId \
and checkerboardtemp[x][y - 1] == JudgeId \
and checkerboardtemp[x][y 1] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x
winy1temp = y 1
winy2temp = y - 3
if y - 2 >= 0 and y 2 <= boardsizetemp - 1:
if checkerboardtemp[x][y - 2] == JudgeId \
and checkerboardtemp[x][y - 1] == JudgeId \
and checkerboardtemp[x][y 1] == JudgeId \
and checkerboardtemp[x][y 2] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x
winy1temp = y 2
winy2temp = y - 2
if y - 1 >= 0 and y 3 <= boardsizetemp - 1:
if checkerboardtemp[x][y - 1] == JudgeId \
and checkerboardtemp[x][y 1] == JudgeId \
and checkerboardtemp[x][y 2] == JudgeId \
and checkerboardtemp[x][y 3] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x
winy1temp = y 3
winy2temp = y - 1
if y >= 0 and y 4 <= boardsizetemp - 1:
if checkerboardtemp[x][y 1] == JudgeId \
and checkerboardtemp[x][y 2] == JudgeId \
and checkerboardtemp[x][y 3] == JudgeId \
and checkerboardtemp[x][y 4] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x
winy1temp = y 4
winy2temp = y
# 判断最后一子横排
if x - 4 >= 0 and x <= boardsizetemp - 1:
if checkerboardtemp[x - 1][y] == JudgeId \
and checkerboardtemp[x - 2][y] == JudgeId \
and checkerboardtemp[x - 3][y] == JudgeId \
and checkerboardtemp[x - 4][y] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x - 4
winy1temp = y
winy2temp = y
if x - 3 >= 0 and x 1 <= boardsizetemp - 1:
if checkerboardtemp[x - 3][y] == JudgeId \
and checkerboardtemp[x - 2][y] == JudgeId \
and checkerboardtemp[x - 1][y] == JudgeId \
and checkerboardtemp[x 1][y] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 1
winx2temp = x - 3
winy1temp = y
winy2temp = y
if x - 2 >= 0 and x 2 <= boardsizetemp - 1:
if checkerboardtemp[x - 2][y] == JudgeId \
and checkerboardtemp[x - 1][y] == JudgeId \
and checkerboardtemp[x 1][y] == JudgeId \
and checkerboardtemp[x 2][y] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 2
winx2temp = x - 2
winy1temp = y
winy2temp = y
if x - 1 >= 0 and x 3 <= boardsizetemp - 1:
if checkerboardtemp[x - 1][y] == JudgeId \
and checkerboardtemp[x 1][y] == JudgeId \
and checkerboardtemp[x 2][y] == JudgeId \
and checkerboardtemp[x 3][y] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 3
winx2temp = x - 1
winy1temp = y
winy2temp = y
if x >= 0 and x 4 <= boardsizetemp - 1:
if checkerboardtemp[x 1][y] == JudgeId \
and checkerboardtemp[x 2][y] == JudgeId \
and checkerboardtemp[x 3][y] == JudgeId \
and checkerboardtemp[x 4][y] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 4
winx2temp = x
winy1temp = y
winy2temp = y
# 判断最后一子45°
if x - 4 >= 0 and y - 4 >= 0 and x <= boardsizetemp - 1 and y <= boardsizetemp - 1:
if checkerboardtemp[x - 1][y - 1] == JudgeId \
and checkerboardtemp[x - 2][y - 2] == JudgeId \
and checkerboardtemp[x - 3][y - 3] == JudgeId \
and checkerboardtemp[x - 4][y - 4] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x - 4
winy1temp = y
winy2temp = y - 4
if x - 3 >= 0 and y - 3 >= 0 and x 1 <= boardsizetemp - 1 and y 1 <= boardsizetemp - 1:
if checkerboardtemp[x 1][y 1] == JudgeId \
and checkerboardtemp[x - 1][y - 1] == JudgeId \
and checkerboardtemp[x - 2][y - 2] == JudgeId \
and checkerboardtemp[x - 3][y - 3] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 1
winx2temp = x - 3
winy1temp = y 1
winy2temp = y - 3
if x - 2 >= 0 and y - 2 >= 0 and x 2 <= boardsizetemp - 1 and y 2 <= boardsizetemp - 1:
if checkerboardtemp[x 2][y 2] == JudgeId \
and checkerboardtemp[x 1][y 1] == JudgeId \
and checkerboardtemp[x - 1][y - 1] == JudgeId \
and checkerboardtemp[x - 2][y - 2] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 2
winx2temp = x - 2
winy1temp = y 2
winy2temp = y - 2
if x - 1 >= 0 and y - 1 >= 0 and x 3 <= boardsizetemp - 1 and y 3 <= boardsizetemp - 1:
if checkerboardtemp[x 3][y 3] == JudgeId \
and checkerboardtemp[x 2][y 2] == JudgeId \
and checkerboardtemp[x 1][y 1] == JudgeId \
and checkerboardtemp[x - 1][y - 1] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 3
winx2temp = x - 1
winy1temp = y 3
winy2temp = y - 1
if x >= 0 and y >= 0 and x 4 <= boardsizetemp - 1 and y 4 <= boardsizetemp - 1:
if checkerboardtemp[x 1][y 1] == JudgeId \
and checkerboardtemp[x 2][y 2] == JudgeId \
and checkerboardtemp[x 3][y 3] == JudgeId \
and checkerboardtemp[x 4][y 4] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 4
winx2temp = x
winy1temp = y 4
winy2temp = y
# 判断最后一子135°
if x - 4 >= 0 and y 4 <= boardsizetemp - 1 and x <= boardsizetemp - 1 and y >= 0:
if checkerboardtemp[x - 1][y 1] == JudgeId \
and checkerboardtemp[x - 2][y 2] == JudgeId \
and checkerboardtemp[x - 3][y 3] == JudgeId \
and checkerboardtemp[x - 4][y 4] == JudgeId:
winneridtemp = JudgeId
winx1temp = x
winx2temp = x - 4
winy1temp = y
winy2temp = y 4
if x - 3 >= 0 and y 3 <= boardsizetemp - 1 and x 1 <= boardsizetemp - 1 and y - 1 >= 0:
if checkerboardtemp[x - 1][y 1] == JudgeId \
and checkerboardtemp[x - 2][y 2] == JudgeId \
and checkerboardtemp[x - 3][y 3] == JudgeId \
and checkerboardtemp[x 1][y - 1] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 1
winx2temp = x - 3
winy1temp = y - 1
winy2temp = y 3
if x - 2 >= 0 and y 2 <= boardsizetemp - 1 and x 2 <= boardsizetemp - 1 and y - 2 >= 0:
if checkerboardtemp[x - 1][y 1] == JudgeId \
and checkerboardtemp[x - 2][y 2] == JudgeId \
and checkerboardtemp[x 1][y - 1] == JudgeId \
and checkerboardtemp[x 2][y - 2] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 2
winx2temp = x - 2
winy1temp = y - 2
winy2temp = y 2
if x - 1 >= 0 and y 1 <= boardsizetemp - 1 and x 3 <= boardsizetemp - 1 and y - 3 >= 0:
if checkerboardtemp[x - 1][y 1] == JudgeId \
and checkerboardtemp[x 1][y - 1] == JudgeId \
and checkerboardtemp[x 2][y - 2] == JudgeId \
and checkerboardtemp[x 3][y - 3] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 3
winx2temp = x - 1
winy1temp = y - 3
winy2temp = y 1
if x >= 0 and y <= boardsizetemp - 1 and x 4 <= boardsizetemp - 1 and y - 4 >= 0:
if checkerboardtemp[x 1][y - 1] == JudgeId \
and checkerboardtemp[x 2][y - 2] == JudgeId \
and checkerboardtemp[x 3][y - 3] == JudgeId \
and checkerboardtemp[x 4][y - 4] == JudgeId:
winneridtemp = JudgeId
winx1temp = x 4
winx2temp = x
winy1temp = y
winy2temp = y - 4
else:
pass
config.set_value("WinnerId", winneridtemp)
config.set_value("WinX1", winx1temp)
config.set_value("WinX2", winx2temp)
config.set_value("WinY1", winy1temp)
config.set_value("WinY2", winy2temp)
6 项目实际运行展示
结果表明:三个相同算法的AI分不出胜负,可以引入合作-竞争机制、增强学习算法等强化Agent算法,或是两个人类围堵一个AI。
原文链接:https://blog.csdn.net/FRIGIDWINTER/article/details/121341881
,