Qt 改为需 C++17 支持并消除部分 clang 警告

This commit is contained in:
Calcitem Team 2019-08-11 14:26:36 +08:00
parent 560d0d4bbb
commit 118017173e
18 changed files with 1386 additions and 1382 deletions

View File

@ -68,9 +68,9 @@ DISTFILES += \
RC_FILE += NineChess.rc
# With C++14 support
# With C++17 support
greaterThan(QT_MAJOR_VERSION, 4) {
CONFIG += c++14
CONFIG += c++17
} else {
QMAKE_CXXFLAGS += -std=c++0x
}

View File

@ -25,6 +25,7 @@
#include <climits>
#include <cstddef>
#include <type_traits>
template <typename T, size_t BlockSize = 4096>
class MemoryPool

View File

@ -23,7 +23,7 @@
#ifndef MEMORY_BLOCK_TCC
#define MEMORY_BLOCK_TCC
#include <cstddef>
template <typename T, size_t BlockSize>
inline typename MemoryPool<T, BlockSize>::size_type

View File

@ -25,8 +25,8 @@
AiThread::AiThread(int id, QObject *parent) :
QThread(parent),
chess_(nullptr),
waiting_(false),
chess_(nullptr),
aiDepth(2),
aiTime(120)
{
@ -41,11 +41,11 @@ AiThread::AiThread(int id, QObject *parent) :
// 连接定时器处理函数
connect(&timer, &QTimer::timeout, this, &AiThread::act, Qt::QueuedConnection);
// 网络
// 网络
if (id == 1)
{
server = new Server(nullptr, 30001);
uint16_t clientPort = server->getPort() == 30001 ? 30002 : 30001;
server = new Server(nullptr, 30001);
uint16_t clientPort = server->getPort() == 30001 ? 30002 : 30001;
client = new Client(nullptr, clientPort);
}
}
@ -53,7 +53,7 @@ AiThread::AiThread(int id, QObject *parent) :
AiThread::~AiThread()
{
// 网络相关
//delete server;
//delete server;
//delete client;
stop();
@ -78,7 +78,7 @@ void AiThread::setAi(const NineChess &chess)
mutex.unlock();
}
void AiThread::setAi(const NineChess &chess, int depth, int time)
void AiThread::setAi(const NineChess &chess, NineChessAi_ab::depth_t depth, int time)
{
mutex.lock();
this->chess_ = &chess;

View File

@ -37,7 +37,7 @@ class AiThread : public QThread
public:
explicit AiThread(int id, QObject *parent = nullptr);
~AiThread();
~AiThread() override;
signals:
// 着法信号
@ -55,7 +55,7 @@ protected:
public:
// AI设置
void setAi(const NineChess &chess);
void setAi(const NineChess &chess, int depth, int time);
void setAi(const NineChess &chess, NineChessAi_ab::depth_t depth, int time);
Server *getServer()
{
@ -68,7 +68,7 @@ public:
}
// 深度和限时
void getDepthTime(int &depth, int &time)
void getDepthTime(NineChessAi_ab::depth_t &depth, int &time)
{
depth = aiDepth;
time = aiTime;
@ -113,7 +113,7 @@ private:
NineChessAi_ab ai_ab;
// AI的层数
int aiDepth;
NineChessAi_ab::depth_t aiDepth;
// AI的限时
int aiTime;

View File

@ -1,21 +1,21 @@
/*****************************************************************************
* Copyright (C) 2019 NineChess authors
*
* Authors: Calcitem <calcitem@outlook.com>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
/*****************************************************************************
* Copyright (C) 2019 NineChess authors
*
* Authors: Calcitem <calcitem@outlook.com>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
*****************************************************************************/
#include <QtWidgets>
@ -125,7 +125,7 @@ void Client::requestNewAction()
getActionButton->setEnabled(false);
tcpSocket->abort();
tcpSocket->connectToHost(hostCombo->currentText(),
portLineEdit->text().toInt());
portLineEdit->text().toUShort());
}
void Client::readAction()
@ -140,7 +140,6 @@ void Client::readAction()
currentAction = nextAction;
statusLabel->setText(currentAction);
// ·¢ÐźÅ
emit command(currentAction);
getActionButton->setEnabled(true);

View File

@ -21,6 +21,10 @@
#ifndef CONFIG_H
#define CONFIG_H
#if _MSC_VER >= 1600
#pragma execution_character_set("utf-8")
#endif
//#define DEBUG_MODE
//#define DEBUG_MODE_A

View File

@ -19,10 +19,6 @@
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
*****************************************************************************/
#if _MSC_VER >= 1600
#pragma execution_character_set("utf-8")
#endif
#include <QGraphicsView>
#include <QGraphicsSceneMouseEvent>
#include <QKeyEvent>
@ -42,6 +38,8 @@
GameController::GameController(GameScene & scene, QObject * parent) :
QObject(parent),
ai1(1),
ai2(2),
scene(scene),
currentPiece(nullptr),
currentRow(-1),
@ -56,8 +54,6 @@ GameController::GameController(GameScene & scene, QObject * parent) :
ruleNo_(-1),
timeLimit(0),
stepsLimit(50),
ai1(1),
ai2(2),
score1(-2),
score2(-2)
{
@ -316,7 +312,7 @@ void GameController::setEngine2(bool arg)
}
}
void GameController::setAiDepthTime(int depth1, int time1, int depth2, int time2)
void GameController::setAiDepthTime(NineChessAi_ab::depth_t depth1, int time1, NineChessAi_ab::depth_t depth2, int time2)
{
if (isEngine1) {
ai1.stop();
@ -338,7 +334,7 @@ void GameController::setAiDepthTime(int depth1, int time1, int depth2, int time2
}
}
void GameController::getAiDepthTime(int &depth1, int &time1, int &depth2, int &time2)
void GameController::getAiDepthTime(NineChessAi_ab::depth_t &depth1, int &time1, NineChessAi_ab::depth_t &depth2, int &time2)
{
ai1.getDepthTime(depth1, time1);
ai2.getDepthTime(depth2, time2);

View File

@ -90,8 +90,8 @@ public:
return &manualListModel;
}
void setAiDepthTime(int depth1, int time1, int depth2, int time2);
void getAiDepthTime(int &depth1, int &time1, int &depth2, int &time2);
void setAiDepthTime(NineChessAi_ab::depth_t depth1, int time1, NineChessAi_ab::depth_t depth2, int time2);
void getAiDepthTime(NineChessAi_ab::depth_t &depth1, int &time1, NineChessAi_ab::depth_t &depth2, int &time2);
signals:
@ -231,10 +231,10 @@ private:
int stepsLimit;
// 玩家1剩余时间毫秒
int remainingTime1;
long remainingTime1;
// 玩家2剩余时间毫秒
int remainingTime2;
long remainingTime2;
// 玩家1赢盘数
int score1;

View File

@ -32,11 +32,11 @@
GameScene::GameScene(QObject *parent) :
QGraphicsScene(parent),
board(nullptr),
pos_p1(LINE_INTERVAL * 4, LINE_INTERVAL * 6),
pos_p1_g(LINE_INTERVAL *(-4), LINE_INTERVAL * 6),
pos_p2(LINE_INTERVAL *(-4), LINE_INTERVAL *(-6)),
pos_p2_g(LINE_INTERVAL * 4, LINE_INTERVAL *(-6))
pos_p2_g(LINE_INTERVAL * 4, LINE_INTERVAL *(-6)),
board(nullptr)
{
// 添加棋盘
board = new BoardItem;

View File

@ -5,7 +5,7 @@
#include <iostream>
#include <functional>
#include <mutex>
#include <QFile>
#include <QFile>
#include <iostream>
#include "HashNode.h"
@ -91,10 +91,10 @@ namespace CTSL //Concurrent Thread Safe Library
//Function to remove an entry from the bucket, if found
void erase(const K &key)
{
size_t hashValue = hashFn(key) & (hashSize - 1);
#ifdef DISABLE_HASHBUCKET
// std::unique_lock<std::shared_timed_mutex> lock(mutex_);
#else
size_t hashValue = hashFn(key) & (hashSize - 1);
hashTable[hashValue].erase(key);
#endif
}
@ -117,9 +117,9 @@ namespace CTSL //Concurrent Thread Safe Library
void dump(const QString &filename)
{
#ifdef DISABLE_HASHBUCKET
QFile file(filename);
file.open(QIODevice::WriteOnly);
file.write((char *)hashTable, sizeof(HashNode<K, V>) * hashSize);
QFile file(filename);
file.open(QIODevice::WriteOnly);
file.write((char *)hashTable, sizeof(HashNode<K, V>) * hashSize);
file.close();
#endif
}
@ -128,9 +128,9 @@ namespace CTSL //Concurrent Thread Safe Library
void load(const QString &filename)
{
#ifdef DISABLE_HASHBUCKET
QFile file(filename);
file.open(QIODevice::ReadOnly);
file.read((char *)hashTable, sizeof(HashNode<K, V>) * hashSize);
QFile file(filename);
file.open(QIODevice::ReadOnly);
file.read((char *)hashTable, sizeof(HashNode<K, V>) * hashSize);
file.close();
#endif
}

View File

@ -19,10 +19,6 @@
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
*****************************************************************************/
#if _MSC_VER >= 1600
#pragma execution_character_set("utf-8")
#endif
#include <algorithm>
#include "ninechess.h"
#include "ninechessai_ab.h"
@ -129,10 +125,10 @@ const int NineChess::onBoard[(N_RINGS + 2) * N_SEATS] = {
};
// 着法表
int NineChess::moveTable[N_POINTS][N_MOVE_DIRECTIONS] = { 0 };
int NineChess::moveTable[N_POINTS][N_MOVE_DIRECTIONS] = {{0}};
// 成三表
int NineChess::millTable[N_POINTS][N_DIRECTIONS][N_RINGS - 1] = { 0 };
int NineChess::millTable[N_POINTS][N_DIRECTIONS][N_RINGS - 1] = {{{0}}};
NineChess::NineChess()
{
@ -667,373 +663,373 @@ int NineChess::cp2pos(int c, int p)
return c * N_SEATS + p - 1;
}
bool NineChess::place(int pos, long time_p, bool cp)
{
// 如果局面为“结局”返回false
if (context.stage == GAME_OVER)
return false;
// 如果局面为“未开局”,则开局
if (context.stage == GAME_NOTSTARTED)
start();
// 如非“落子”状态返回false
if (context.action != ACTION_PLACE)
return false;
// 如果落子位置在棋盘外、已有子点或禁点返回false
if (!onBoard[pos] || board_[pos])
return false;
// 格式转换
int c = 0;
int p = 0;
pos2cp(pos, c, p);
// 时间的临时变量
long player_ms = -1;
// 对于开局落子
int piece = '\x00';
int n = 0;
if (context.stage == GAME_PLACING) {
// 先手下
if (context.turn == PLAYER1) {
piece = '\x11' + currentRule.nTotalPiecesEachSide - context.nPiecesInHand_1;
context.nPiecesInHand_1--;
context.nPiecesOnBoard_1++;
}
// 后手下
else {
piece = '\x21' + currentRule.nTotalPiecesEachSide - context.nPiecesInHand_2;
context.nPiecesInHand_2--;
context.nPiecesOnBoard_2++;
}
board_[pos] = piece;
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
move_ = pos;
if (cp == true) {
player_ms = update(time_p);
sprintf(cmdline, "(%1u,%1u) %02u:%02u.%03u",
c, p, player_ms / 60000, (player_ms % 60000) / 1000, player_ms % 1000);
cmdlist.push_back(string(cmdline));
currentStep++;
}
currentPos = pos;
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
n = addMills(currentPos);
// 开局阶段未成三
if (n == 0) {
// 如果双方都无未放置的棋子
if (context.nPiecesInHand_1 == 0 && context.nPiecesInHand_2 == 0) {
// 进入中局阶段
context.stage = GAME_MOVING;
// 进入选子状态
context.action = ACTION_CHOOSE;
// 清除禁点
cleanForbiddenPoints();
// 设置轮到谁走
if (currentRule.isDefenderMoveFirst) {
context.turn = PLAYER2;
} else {
context.turn = PLAYER1;
}
// 再决胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
// 如果双方还有子
else {
// 设置轮到谁走
changeTurn();
}
}
// 如果成三
else {
// 设置去子数目
context.nPiecesNeedRemove = currentRule.allowRemoveMultiPieces ? n : 1;
// 进入去子状态
context.action = ACTION_CAPTURE;
}
if (cp == true) {
setTips();
}
return true;
}
// 对于中局落子
else if (context.stage == GAME_MOVING) {
// 如果落子不合法
if ((context.turn == PLAYER1 &&
(context.nPiecesOnBoard_1 > currentRule.nPiecesAtLeast || !currentRule.allowFlyWhenRemainThreePieces)) ||
(context.turn == PLAYER2 &&
(context.nPiecesOnBoard_2 > currentRule.nPiecesAtLeast || !currentRule.allowFlyWhenRemainThreePieces))) {
int i;
for (i = 0; i < 4; i++) {
if (pos == moveTable[currentPos][i])
break;
}
// 不在着法表中
if (i == 4)
return false;
}
// 移子
move_ = (currentPos << 8) + pos;
if (cp == true) {
player_ms = update(time_p);
sprintf(cmdline, "(%1u,%1u)->(%1u,%1u) %02u:%02u.%03u", currentPos / N_SEATS, currentPos % N_SEATS + 1,
c, p, player_ms / 60000, (player_ms % 60000) / 1000, player_ms % 1000);
cmdlist.push_back(string(cmdline));
currentStep++;
moveStep++;
}
board_[pos] = board_[currentPos];
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
board_[currentPos] = '\x00';
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
revertHash(currentPos);
#endif
currentPos = pos;
n = addMills(currentPos);
// 中局阶段未成三
if (n == 0) {
// 进入选子状态
context.action = ACTION_CHOOSE;
// 设置轮到谁走
changeTurn();
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
// 中局阶段成三
else {
// 设置去子数目
context.nPiecesNeedRemove = currentRule.allowRemoveMultiPieces ? n : 1;
// 进入去子状态
context.action = ACTION_CAPTURE;
if (cp == true) {
setTips();
}
}
if (cp == true) {
setTips();
}
return true;
}
return false;
bool NineChess::place(int pos, long time_p, bool cp)
{
// 如果局面为“结局”返回false
if (context.stage == GAME_OVER)
return false;
// 如果局面为“未开局”,则开局
if (context.stage == GAME_NOTSTARTED)
start();
// 如非“落子”状态返回false
if (context.action != ACTION_PLACE)
return false;
// 如果落子位置在棋盘外、已有子点或禁点返回false
if (!onBoard[pos] || board_[pos])
return false;
// 格式转换
int c = 0;
int p = 0;
pos2cp(pos, c, p);
// 时间的临时变量
long player_ms = -1;
// 对于开局落子
int piece = '\x00';
int n = 0;
if (context.stage == GAME_PLACING) {
// 先手下
if (context.turn == PLAYER1) {
piece = '\x11' + currentRule.nTotalPiecesEachSide - context.nPiecesInHand_1;
context.nPiecesInHand_1--;
context.nPiecesOnBoard_1++;
}
// 后手下
else {
piece = '\x21' + currentRule.nTotalPiecesEachSide - context.nPiecesInHand_2;
context.nPiecesInHand_2--;
context.nPiecesOnBoard_2++;
}
board_[pos] = piece;
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
move_ = pos;
if (cp == true) {
player_ms = update(time_p);
sprintf(cmdline, "(%1u,%1u) %02u:%02u.%03u",
c, p, player_ms / 60000, (player_ms % 60000) / 1000, player_ms % 1000);
cmdlist.push_back(string(cmdline));
currentStep++;
}
currentPos = pos;
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
n = addMills(currentPos);
// 开局阶段未成三
if (n == 0) {
// 如果双方都无未放置的棋子
if (context.nPiecesInHand_1 == 0 && context.nPiecesInHand_2 == 0) {
// 进入中局阶段
context.stage = GAME_MOVING;
// 进入选子状态
context.action = ACTION_CHOOSE;
// 清除禁点
cleanForbiddenPoints();
// 设置轮到谁走
if (currentRule.isDefenderMoveFirst) {
context.turn = PLAYER2;
} else {
context.turn = PLAYER1;
}
// 再决胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
// 如果双方还有子
else {
// 设置轮到谁走
changeTurn();
}
}
// 如果成三
else {
// 设置去子数目
context.nPiecesNeedRemove = currentRule.allowRemoveMultiPieces ? n : 1;
// 进入去子状态
context.action = ACTION_CAPTURE;
}
if (cp == true) {
setTips();
}
return true;
}
// 对于中局落子
else if (context.stage == GAME_MOVING) {
// 如果落子不合法
if ((context.turn == PLAYER1 &&
(context.nPiecesOnBoard_1 > currentRule.nPiecesAtLeast || !currentRule.allowFlyWhenRemainThreePieces)) ||
(context.turn == PLAYER2 &&
(context.nPiecesOnBoard_2 > currentRule.nPiecesAtLeast || !currentRule.allowFlyWhenRemainThreePieces))) {
int i;
for (i = 0; i < 4; i++) {
if (pos == moveTable[currentPos][i])
break;
}
// 不在着法表中
if (i == 4)
return false;
}
// 移子
move_ = (currentPos << 8) + pos;
if (cp == true) {
player_ms = update(time_p);
sprintf(cmdline, "(%1u,%1u)->(%1u,%1u) %02u:%02u.%03u", currentPos / N_SEATS, currentPos % N_SEATS + 1,
c, p, player_ms / 60000, (player_ms % 60000) / 1000, player_ms % 1000);
cmdlist.push_back(string(cmdline));
currentStep++;
moveStep++;
}
board_[pos] = board_[currentPos];
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
board_[currentPos] = '\x00';
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
revertHash(currentPos);
#endif
currentPos = pos;
n = addMills(currentPos);
// 中局阶段未成三
if (n == 0) {
// 进入选子状态
context.action = ACTION_CHOOSE;
// 设置轮到谁走
changeTurn();
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
// 中局阶段成三
else {
// 设置去子数目
context.nPiecesNeedRemove = currentRule.allowRemoveMultiPieces ? n : 1;
// 进入去子状态
context.action = ACTION_CAPTURE;
if (cp == true) {
setTips();
}
}
if (cp == true) {
setTips();
}
return true;
}
return false;
}
bool NineChess::place(int c, int p, long time_p)
{
// 转换为 pos
int pos = cp2pos(c, p);
return place(pos, time_p, true);
bool NineChess::place(int c, int p, long time_p)
{
// 转换为 pos
int pos = cp2pos(c, p);
return place(pos, time_p, true);
}
bool NineChess::capture(int c, int p, long time_p)
{
// 转换为 pos
int pos = cp2pos(c, p);
return capture(pos, time_p, true);
}
bool NineChess::capture(int pos, long time_p, bool cp)
{
// 如果局面为"未开局"或“结局”返回false
if (context.stage == GAME_NOTSTARTED || context.stage == GAME_OVER)
return false;
// 如非“去子”状态返回false
if (context.action != ACTION_CAPTURE)
return false;
// 如果去子完成返回false
if (context.nPiecesNeedRemove <= 0)
return false;
// 格式转换
int c = 0;
int p = 0;
pos2cp(pos, c, p);
// 时间的临时变量
long player_ms = -1;
// 对手
char opponent = context.turn == PLAYER1 ? 0x20 : 0x10;
// 判断去子是不是对手棋
if (!(opponent & board_[pos]))
return false;
// 如果当前子是否处于“三连”之中,且对方还未全部处于“三连”之中
if (currentRule.allowRemoveMill == false &&
isInMills(pos) && !isAllInMills(opponent)) {
return false;
}
// 去子(设置禁点)
if (currentRule.hasForbiddenPoint && context.stage == GAME_PLACING) {
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
revertHash(pos);
#endif
board_[pos] = '\x0f';
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
} else { // 去子
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
revertHash(pos);
#endif
board_[pos] = '\x00';
}
if (context.turn == PLAYER1)
context.nPiecesOnBoard_2--;
else if (context.turn == PLAYER2)
context.nPiecesOnBoard_1--;
move_ = -pos;
if (cp == true) {
player_ms = update(time_p);
sprintf(cmdline, "-(%1u,%1u) %02u:%02u.%03u", c, p, player_ms / 60000, (player_ms % 60000) / 1000, player_ms % 1000);
cmdlist.push_back(string(cmdline));
currentStep++;
moveStep = 0;
}
currentPos = 0;
context.nPiecesNeedRemove--;
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
// 去子完成
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
// 还有其余的子要去吗
if (context.nPiecesNeedRemove > 0) {
// 继续去子
return true;
}
// 所有去子都完成了
else {
// 开局阶段
if (context.stage == GAME_PLACING) {
// 如果双方都无未放置的棋子
if (context.nPiecesInHand_1 == 0 && context.nPiecesInHand_2 == 0) {
// 进入中局阶段
context.stage = GAME_MOVING;
// 进入选子状态
context.action = ACTION_CHOOSE;
// 清除禁点
cleanForbiddenPoints();
// 设置轮到谁走
if (currentRule.isDefenderMoveFirst) {
context.turn = PLAYER2;
} else {
context.turn = PLAYER1;
}
// 再决胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
// 如果双方还有子
else {
// 进入落子状态
context.action = ACTION_PLACE;
// 设置轮到谁走
changeTurn();
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
}
// 中局阶段
else {
// 进入选子状态
context.action = ACTION_CHOOSE;
// 设置轮到谁走
changeTurn();
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
}
if (cp == true) {
setTips();
}
return true;
bool NineChess::capture(int c, int p, long time_p)
{
// 转换为 pos
int pos = cp2pos(c, p);
return capture(pos, time_p, true);
}
bool NineChess::capture(int pos, long time_p, bool cp)
{
// 如果局面为"未开局"或“结局”返回false
if (context.stage == GAME_NOTSTARTED || context.stage == GAME_OVER)
return false;
// 如非“去子”状态返回false
if (context.action != ACTION_CAPTURE)
return false;
// 如果去子完成返回false
if (context.nPiecesNeedRemove <= 0)
return false;
// 格式转换
int c = 0;
int p = 0;
pos2cp(pos, c, p);
// 时间的临时变量
long player_ms = -1;
// 对手
char opponent = context.turn == PLAYER1 ? 0x20 : 0x10;
// 判断去子是不是对手棋
if (!(opponent & board_[pos]))
return false;
// 如果当前子是否处于“三连”之中,且对方还未全部处于“三连”之中
if (currentRule.allowRemoveMill == false &&
isInMills(pos) && !isAllInMills(opponent)) {
return false;
}
// 去子(设置禁点)
if (currentRule.hasForbiddenPoint && context.stage == GAME_PLACING) {
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
revertHash(pos);
#endif
board_[pos] = '\x0f';
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
} else { // 去子
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
revertHash(pos);
#endif
board_[pos] = '\x00';
}
if (context.turn == PLAYER1)
context.nPiecesOnBoard_2--;
else if (context.turn == PLAYER2)
context.nPiecesOnBoard_1--;
move_ = -pos;
if (cp == true) {
player_ms = update(time_p);
sprintf(cmdline, "-(%1u,%1u) %02u:%02u.%03u", c, p, player_ms / 60000, (player_ms % 60000) / 1000, player_ms % 1000);
cmdlist.push_back(string(cmdline));
currentStep++;
moveStep = 0;
}
currentPos = 0;
context.nPiecesNeedRemove--;
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
updateHash(pos);
#endif
// 去子完成
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
// 还有其余的子要去吗
if (context.nPiecesNeedRemove > 0) {
// 继续去子
return true;
}
// 所有去子都完成了
else {
// 开局阶段
if (context.stage == GAME_PLACING) {
// 如果双方都无未放置的棋子
if (context.nPiecesInHand_1 == 0 && context.nPiecesInHand_2 == 0) {
// 进入中局阶段
context.stage = GAME_MOVING;
// 进入选子状态
context.action = ACTION_CHOOSE;
// 清除禁点
cleanForbiddenPoints();
// 设置轮到谁走
if (currentRule.isDefenderMoveFirst) {
context.turn = PLAYER2;
} else {
context.turn = PLAYER1;
}
// 再决胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
// 如果双方还有子
else {
// 进入落子状态
context.action = ACTION_PLACE;
// 设置轮到谁走
changeTurn();
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
}
// 中局阶段
else {
// 进入选子状态
context.action = ACTION_CHOOSE;
// 设置轮到谁走
changeTurn();
// 如果决出胜负
if (win()) {
if (cp == true) {
setTips();
}
return true;
}
}
}
if (cp == true) {
setTips();
}
return true;
}
bool NineChess::choose(int pos)
@ -1364,7 +1360,7 @@ int NineChess::isInMills(int pos, bool test)
{
int n = 0;
int pos1, pos2;
char m = test? INT32_MAX : board_[pos] & '\x30';
int m = test? INT32_MAX : board_[pos] & '\x30';
for (int i = 0; i < 3; i++) {
pos1 = millTable[pos][i][0];
pos2 = millTable[pos][i][1];
@ -1633,7 +1629,7 @@ enum NineChess::Player NineChess::getWhosPiece(int c, int p)
return NOBODY;
}
void NineChess::getElapsedTimeMS(int &p1_ms, int &p2_ms)
void NineChess::getElapsedTimeMS(long &p1_ms, long &p2_ms)
{
update();
p1_ms = elapsedMS_1;

View File

@ -75,7 +75,6 @@ public:
// 定义类型
typedef int32_t move_t;
// 位置迭代器
// typedef typename std::vector<move_t>::iterator posIterator;
// typedef typename std::vector<move_t>::const_iterator constPosIterator;
@ -148,7 +147,7 @@ public:
};
uint64_t rand64(void) {
return rand() ^
return (uint64_t)rand() ^
((uint64_t)rand() << 15) ^
((uint64_t)rand() << 30) ^
((uint64_t)rand() << 45) ^
@ -379,7 +378,7 @@ public:
}
// 玩家1和玩家2的用时
void getElapsedTimeMS(int &p1_ms, int &p2_ms);
void getElapsedTimeMS(long &p1_ms, long &p2_ms);
// 获取棋局的字符提示
const string getTips() const

View File

@ -29,7 +29,7 @@
#include <algorithm>
#include "ninechessai_ab.h"
#include "HashMap.h"
#include "hashmap.h"
using namespace CTSL;
@ -103,7 +103,7 @@ struct NineChessAi_ab::Node *NineChessAi_ab::addNode(
newNode->pruned = false;
#endif
player = player; // Remove warning
//player = player; // Remove warning
#ifdef DEBUG_AB_TREE
#if ((defined HASH_MAP_ENABLE) || (defined BOOK_LEARNING) || (defined THREEFOLD_REPETITION))
@ -190,23 +190,23 @@ void NineChessAi_ab::shuffleMovePriorityTable()
std::shuffle(movePriorityTable3.begin(), movePriorityTable3.end(), std::default_random_engine(seed));
std::shuffle(movePriorityTable4.begin(), movePriorityTable4.end(), std::default_random_engine(seed));
for (int i = 0; i < 4; i++) {
for (size_t i = 0; i < 4; i++) {
movePriorityTable[i + 0] = movePriorityTable0[i];
}
for (int i = 0; i < 8; i++) {
for (size_t i = 0; i < 8; i++) {
movePriorityTable[i + 4] = movePriorityTable1[i];
}
for (int i = 0; i < 4; i++) {
for (size_t i = 0; i < 4; i++) {
movePriorityTable[i + 12] = movePriorityTable2[i];
}
for (int i = 0; i < 4; i++) {
for (size_t i = 0; i < 4; i++) {
movePriorityTable[i + 16] = movePriorityTable3[i];
}
for (int i = 0; i < 4; i++) {
for (size_t i = 0; i < 4; i++) {
movePriorityTable[i + 20] = movePriorityTable4[i];
}
}
@ -217,7 +217,7 @@ void NineChessAi_ab::generateLegalMoves(Node *node, move_t bestMove)
{
const int MOVE_PRIORITY_TABLE_SIZE = NineChess::N_RINGS * NineChess::N_SEATS;
int pos = 0;
size_t newCapacity = 24;
int newCapacity = 24;
// 留足余量空间避免多次重新分配,此动作本身也占用 CPU/内存 开销
switch (chessTemp.getStage()) {

View File

@ -32,11 +32,11 @@
//#endif
#include <mutex>
#include <string>
#include <Qdebug>
#include <QDebug>
#include <array>
#include "ninechess.h"
#include "hashMap.h"
#include "hashmap.h"
#ifdef MEMORY_POOL
#include "MemoryPool.h"
@ -62,13 +62,14 @@ public:
struct Node
{
public:
move_t move; // 着法的命令行指令,图上标示为节点前的连线
value_t value; // 节点的值
vector<struct Node*> children; // 子节点列表
struct Node* parent; // 父节点
move_t move; // 着法的命令行指令,图上标示为节点前的连线
value_t value; // 节点的值
#ifdef SORT_CONSIDER_PRUNED
bool pruned; // 是否在此处剪枝
#endif
#ifdef DEBUG_AB_TREE
size_t id; // 结点编号
string cmd;
@ -278,4 +279,12 @@ private:
char cmdline[32];
};
#ifdef HASH_MAP_ENABLE
extern HashMap<uint64_t, NineChessAi_ab::HashValue> hashmap;
#endif /* #ifdef HASH_MAP_ENABLE */
#ifdef THREEFOLD_REPETITION
extern vector<uint64_t> positions;
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@ -46,7 +46,7 @@ PieceItem::PieceItem(QGraphicsItem *parent) :
//setAcceptedMouseButtons(Qt::LeftButton);
// 不接受鼠标事件
setAcceptedMouseButtons(0);
setAcceptedMouseButtons(nullptr);
//setAcceptHoverEvents(true);
// 默认模型为没有棋子
@ -105,6 +105,8 @@ void PieceItem::paint(QPainter *painter,
painter->drawPixmap(-size / 2, -size / 2, size, size,
QPixmap(":/image/resources/image/white_piece.png"));
break;
default:
break;
}
// 如果模型要求显示序号

View File

@ -16,48 +16,48 @@
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
*****************************************************************************/
#ifndef SERVER_H
#define SERVER_H
#include <QDialog>
#include <QString>
#include <QVector>
QT_BEGIN_NAMESPACE
class QLabel;
class QTcpServer;
class QNetworkSession;
QT_END_NAMESPACE
class Server : public QDialog
{
Q_OBJECT
public:
explicit Server(QWidget *parent = nullptr, uint16_t port = 33333);
void setAction(const QString &action);
void setPort(uint16_t port)
{
this->port = port;
}
uint16_t getPort()
{
return port;
}
private slots:
void sessionOpened();
void sendAction();
private:
QLabel *statusLabel = nullptr;
QTcpServer *tcpServer = nullptr;
QVector<QString> actions;
QString action;
QNetworkSession *networkSession = nullptr;
uint16_t port;
};
#endif // SERVER_H
*****************************************************************************/
#ifndef SERVER_H
#define SERVER_H
#include <QDialog>
#include <QString>
#include <QVector>
QT_BEGIN_NAMESPACE
class QLabel;
class QTcpServer;
class QNetworkSession;
QT_END_NAMESPACE
class Server : public QDialog
{
Q_OBJECT
public:
explicit Server(QWidget *parent = nullptr, uint16_t port = 33333);
void setAction(const QString &action);
void setPort(uint16_t port)
{
this->port = port;
}
uint16_t getPort()
{
return port;
}
private slots:
void sessionOpened();
void sendAction();
private:
QLabel *statusLabel = nullptr;
QTcpServer *tcpServer = nullptr;
QNetworkSession *networkSession = nullptr;
uint16_t port;
QVector<QString> actions;
QString action;
};
#endif // SERVER_H