加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
文件
克隆/下载
SingleGame.cpp 5.11 KB
一键复制 编辑 原始数据 按行查看 历史
Nemonameless 提交于 2017-02-28 10:31 . first commit
#include "SingleGame.h"
#include <QTimer>
void SingleGame::click(int id, int row, int col)
{
if(!this->_bRedTurn)//不是红走,就退出
return;
Board::click(id, row, col);//红走,重载Bored的click函数,只要直接调用
if(!this->_bRedTurn)//红走了,轮到黑走,就调用computerMove
{
/* 启动0.1秒定时器,在0.1秒后电脑再思考
* 否则clicked函数中轮到黑走时,先去计算下一步再下一步才相应主进程去重绘
*/
QTimer::singleShot(100, this, SLOT(computerMove()));
}
}
void SingleGame::computerMove()
{
Step* step = getBestMove();
moveStone(step->_moveid, step->_killid,
step->_rowTo, step->_colTo);
delete step;
update();
}
void SingleGame::getAllPossibleMove(QVector<Step *> &steps)
{
int min=16, max=32;
if(this->_bRedTurn)//假想红棋去走下一步
{
min = 0, max = 16;
}
for(int i=min; i<max; ++i)//死棋不应该再计算getAllPossibleMove
{
if(_s[i]._dead) continue;
for(int row=0; row<=9; ++row)
{
for(int col=0; col<=8; ++col)
{
int killid = this->getStoneId(row, col);
if(sameColor(killid, i))
continue;
if(canMove(i, killid, row, col))
{
saveStep(i, killid, row, col, steps);
}
}
}
}
}
void SingleGame::fakeMove(Step* step)
{
killStone(step->_killid);
moveStone(step->_moveid, step->_rowTo, step->_colTo);
}
void SingleGame::unfakeMove(Step* step)
{
reliveStone(step->_killid); //复活
moveStone(step->_moveid, step->_rowFrom, step->_colFrom);
}
/* 评价局面分 */
int SingleGame::calcScore()
{
int redTotalScore = 0;
int blackTotalScore = 0;
//enum TYPE{CHE, MA, PAO, BING, JIANG, SHI, XIANG};
static int chessScore[] = {100, 50, 50, 20, 1500, 10, 10};
// 黑棋分的总数 - 红旗分的总数
for(int i=0; i<16; ++i)
{
if(_s[i]._dead)
continue;
redTotalScore += chessScore[_s[i]._type];//_s[i]._type是下标
}
for(int i=16; i<32; ++i)
{
if(_s[i]._dead)
continue;
blackTotalScore += chessScore[_s[i]._type];
}
return blackTotalScore - redTotalScore;
}
int SingleGame::getMaxScore(int level, int curMinScore)
{
if(level == 0) return calcScore();
// 1.看看有那些步骤可以走
QVector<Step*> steps;
getAllPossibleMove(steps); // 是红棋的possiblemove
int maxScore = -100000;
while(steps.count())
{
Step* step = steps.back();
steps.removeLast();
fakeMove(step);
int score = getMinScore(level-1, maxScore);
unfakeMove(step);
delete step;
if(score >= curMinScore)
{
while(steps.count())
{
Step* step = steps.back();
steps.removeLast();
delete step;
}
return score;
}
if(score > maxScore)
{
maxScore = score;
}
}
return maxScore;
}
int SingleGame::getMinScore(int level, int curMaxScore)
{
if(level == 0) return calcScore();
// 1.看看有那些步骤可以走
QVector<Step*> steps;
getAllPossibleMove(steps); // 是红旗的possiblemove,即电脑假想人走红棋的下一步
int minScore = 100000;
while(steps.count())//for(QVector<Step*>::iterator it=steps.begin();it!=steps.end();++it){
{
Step* step = steps.back();
steps.removeLast(); //释放当前内存
fakeMove(step);
int score = getMaxScore(level-1, minScore);
unfakeMove(step);
delete step;
if(score <= curMaxScore)
{
while(steps.count())
{
Step* step = steps.back();
steps.removeLast();
delete step;
}
return score;
}
if(score < minScore)
{
minScore = score;
}
}
return minScore;
}
Step* SingleGame::getBestMove()
{
/*
2.试着走一下
3.评估走的结果
4.取最好的结果作为参考
*/
// 1.看看有那些步骤可以走
QVector<Step*> steps;
getAllPossibleMove(steps);
// 2.试着走一下
// 3.评估走的结果
int maxScore = -100000;
Step* ret = NULL;
while(steps.count())
{
Step* step = steps.back();
steps.removeLast();
fakeMove(step);
int score = getMinScore(_level-1, maxScore);
unfakeMove(step);
if(score > maxScore)
{
maxScore = score;
if(ret)
delete ret;
ret = step; //是的话就保存
}
else
{
delete step;
}
}
// 4.取最好的结果作为参考
return ret;
}
Loading...
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化