搜索是電腦棋手AI的核心
view plaincopy to clipboardprint?
/*
* @(#)SearchEngine
* Author:
* Created on May
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version
* (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
* GNU Library General Public License for more details
*
* You should have received a copy of the GNU General Public License
* along with this program; if not
* Foundation
*/
package cn
import cn
import cn
import cn
import java
import java
/**
* This class descripts some search algorithms of game tree
* @author
* @version
*/
public class SearchEngine {
/**
* value while win a game
*/
public static final int WIN =
/**
* chessboard situation
*/
public Situation situation;
/**
* the best move
*/
public Motion bestMotion;
/**
* situation libaray
*/
private Book book = new Book();
/**
* default search depth
*/
public static int SEARCH_DEPTH =
/**
* For Performance Test
* @param args should be <code>null</code>
*/
public static void main(String[] args) {
SearchEngine instance;
instance = new SearchEngine(new Situation());
System
long startTime = System
//instance
//instance
//instance
//instance
//instance
instance
long estimatedTime = System
System
System
System
System
System
}
/**
* Finds the best move on the specified chessboard situation
* @param boardSituation the specified chessboard situation
* @return the evaluate value
*/
public int findTheBestMove(int[][] boardSituation) {
TranspositionTable
return negaScoutWithHHTTSearch(SEARCH_DEPTH
}
/**
* Search the FEN book for a good move
* @return if find a move in the book
* otherwise
*/
public boolean bookSearch() {
List<Motion> motions = situation
for (Motion motion : motions) {
situation
if (book
// this situation exists in book!
bestMotion = motion;
situation
return true;
}
situation
}
return false;
}
/**
* Basic Alpha
* @param depth depth of search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
final int basicAlphaBetaSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
for (Motion motion : motions) {
situation
int score =
situation
if (score > alpha) {
alpha = score;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
if (alpha >= beta) {
return beta;
}
}
}
return alpha;
}
/**
* Alpha
* @param depth depth of search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
@SuppressWarnings(
final int alphaBetaWithHistoryHeuristicSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
// History heuristic
if (depth < SEARCH_DEPTH) {
for (Motion motion : motions) {
motion
motion
motion
}
// XXX do sort algorithm by myself for performance?
Collections
}
for (Motion motion : motions) {
situation
int score =
situation
if (score > alpha) {
alpha = score;
HistoryHeuristicTable
motion
(HistoryHeuristicTable
motion
motion
motion
motion
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
if (alpha >= beta) {
return beta;
}
}
}
return alpha;
}
/**
* Principal Variation SearchEngine method
* <p>Probably the best of the alpha
* several names: <em><b>NegaScout</b></em>
* or <em>PVS</em> for short
* best if the first recursive search is likely to be the one
* with the best score
* or using a best move stored in the hash table make it especially
* likely that the first move is best
* the other moves more quickly by using the assumption that
* they are not likely to be as good
* search with a normal window
* zero
* move
* </p>
* <p>
* More detalis
* <a >
* ICS
* or Read this paper:<br>
* Alexander Reinefild
*
* </p>
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
final int principalVariationSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
situation
motions
int best =
situation
if (depth == SEARCH_DEPTH) {
bestMotion = motions
}
for (int i =
if (best < beta) {
if (best > alpha) {
alpha = best;
}
Motion motion = motions
situation
int score =
if (score > alpha && score < beta) {
// fail high
best =
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
} else if (score > best) {
best = score;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
}
situation
}
}
return best;
}
/**
* Principal Variation with History Heuristic SearchEngine method(fail
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
@SuppressWarnings(
final int principalVariationWithHHSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
// History heuristic
if (depth < SEARCH_DEPTH) {
for (Motion motion : motions) {
motion
motion
motion
}
Collections
}
Motion motion = motions
situation
motion
int best =
situation
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
int oldValue = HistoryHeuristicTable
motion
motion
motion
HistoryHeuristicTable
motions
motions
motions
(oldValue +
}
for (int i =
if (best < beta) {
if (best > alpha) {
alpha = best;
}
motion = motions
situation
int score =
if (score > alpha && score < beta) {
best =
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
} else if (score > best) {
int oldValue = HistoryHeuristicTable
motion
motion
motion
HistoryHeuristicTable
motion
motion
motion
(oldValue +
best = score;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
}
situation
}
}
return best;
}
/**
* Alpha
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
final int alphaBetaWithTranspositonSearch(int depth
if (situation
return
}
// lookup transposition table
int score = TranspositionTable
if (score !=
// hit the target!
return score;
}
if (depth <=
score = situation
// save the node
TranspositionTable
return score;
}
NodeType hashItemType = NodeType
List<Motion> motions = situation
for (Motion motion : motions) {
int toId = situation
motion
score =
situation
if (score > alpha) {
alpha = score;
hashItemType = NodeType
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
if (alpha >= beta) {
TranspositionTable
return beta;
}
}
}
if (hashItemType != NodeType
TranspositionTable
} else {
TranspositionTable
}
return alpha;
}
/**
* NegaScout with History Heuristic and Transposition Table search
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
@SuppressWarnings(
final int negaScoutWithHHTTSearch(int depth
if (situation
return
}
// lookup transpositiont table
int score = TranspositionTable
if (score !=
// hit the target!
return score;
}
if (depth <=
score = situation
TranspositionTable
return score;
}
List<Motion> motions = situation
// History heuristic
if (depth < SEARCH_DEPTH) {
for (Motion motion : motions) {
motion
motion
motion
}
Collections
}
int bestmove =
int a = alpha;
int b = beta;
int t;
int oldValue;
NodeType hashItemType = NodeType
for (int i =
Motion motion = motions
int toId = situation
motion
t =
if (t > a && t < beta && i >
a =
hashItemType = NodeType
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
bestmove = i;
}
situation
if (a < t) {
hashItemType = NodeType
a = t;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
}
if (a >= beta) {
TranspositionTable
oldValue = HistoryHeuristicTable
motion
motion
motion
HistoryHeuristicTable
motion
motion
motion
(oldValue +
return a;
}
b = a +
}
oldValue = HistoryHeuristicTable
motions
motions
motions
HistoryHeuristicTable
motions
motions
motions
(oldValue +
if (hashItemType != NodeType
TranspositionTable
} else {
TranspositionTable
}
return a;
}
/**
* Constructor with parameters
* @param situation the specified situation
*/
public SearchEngine(Situation situation) {
this
}
}
/*
* @(#)SearchEngine
* Author:
* Created on May
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version
* (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
* GNU Library General Public License for more details
*
* You should have received a copy of the GNU General Public License
* along with this program; if not
* Foundation
*/
package cn
import cn
import cn
import cn
import java
import java
/**
* This class descripts some search algorithms of game tree
* @author
* @version
*/
public class SearchEngine {
/**
* value while win a game
*/
public static final int WIN =
/**
* chessboard situation
*/
public Situation situation;
/**
* the best move
*/
public Motion bestMotion;
/**
* situation libaray
*/
private Book book = new Book();
/**
* default search depth
*/
public static int SEARCH_DEPTH =
/**
* For Performance Test
* @param args should be <code>null</code>
*/
public static void main(String[] args) {
SearchEngine instance;
instance = new SearchEngine(new Situation());
System
long startTime = System
//instance
//instance
//instance
//instance
//instance
instance
long estimatedTime = System
System
System
System
System
System
}
/**
* Finds the best move on the specified chessboard situation
* @param boardSituation the specified chessboard situation
* @return the evaluate value
*/
public int findTheBestMove(int[][] boardSituation) {
TranspositionTable
return negaScoutWithHHTTSearch(SEARCH_DEPTH
}
/**
* Search the FEN book for a good move
* @return if find a move in the book
* otherwise
*/
public boolean bookSearch() {
List<Motion> motions = situation
for (Motion motion : motions) {
situation
if (book
// this situation exists in book!
bestMotion = motion;
situation
return true;
}
situation
}
return false;
}
/**
* Basic Alpha
* @param depth depth of search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
final int basicAlphaBetaSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
for (Motion motion : motions) {
situation
int score =
situation
if (score > alpha) {
alpha = score;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
if (alpha >= beta) {
return beta;
}
}
}
return alpha;
}
/**
* Alpha
* @param depth depth of search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
@SuppressWarnings(
final int alphaBetaWithHistoryHeuristicSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
// History heuristic
if (depth < SEARCH_DEPTH) {
for (Motion motion : motions) {
motion
motion
motion
}
// XXX do sort algorithm by myself for performance?
Collections
}
for (Motion motion : motions) {
situation
int score =
situation
if (score > alpha) {
alpha = score;
HistoryHeuristicTable
motion
(HistoryHeuristicTable
motion
motion
motion
motion
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
if (alpha >= beta) {
return beta;
}
}
}
return alpha;
}
/**
* Principal Variation SearchEngine method
* <p>Probably the best of the alpha
* several names: <em><b>NegaScout</b></em>
* or <em>PVS</em> for short
* best if the first recursive search is likely to be the one
* with the best score
* or using a best move stored in the hash table make it especially
* likely that the first move is best
* the other moves more quickly by using the assumption that
* they are not likely to be as good
* search with a normal window
* zero
* move
* </p>
* <p>
* More detalis
* <a >
* ICS
* or Read this paper:<br>
* Alexander Reinefild
*
* </p>
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
final int principalVariationSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
situation
motions
int best =
situation
if (depth == SEARCH_DEPTH) {
bestMotion = motions
}
for (int i =
if (best < beta) {
if (best > alpha) {
alpha = best;
}
Motion motion = motions
situation
int score =
if (score > alpha && score < beta) {
// fail high
best =
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
} else if (score > best) {
best = score;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
}
situation
}
}
return best;
}
/**
* Principal Variation with History Heuristic SearchEngine method(fail
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
@SuppressWarnings(
final int principalVariationWithHHSearch(int depth
if (situation
return
}
if (depth <=
return situation
}
List<Motion> motions = situation
// History heuristic
if (depth < SEARCH_DEPTH) {
for (Motion motion : motions) {
motion
motion
motion
}
Collections
}
Motion motion = motions
situation
motion
int best =
situation
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
int oldValue = HistoryHeuristicTable
motion
motion
motion
HistoryHeuristicTable
motions
motions
motions
(oldValue +
}
for (int i =
if (best < beta) {
if (best > alpha) {
alpha = best;
}
motion = motions
situation
int score =
if (score > alpha && score < beta) {
best =
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
} else if (score > best) {
int oldValue = HistoryHeuristicTable
motion
motion
motion
HistoryHeuristicTable
motion
motion
motion
(oldValue +
best = score;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
}
situation
}
}
return best;
}
/**
* Alpha
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
final int alphaBetaWithTranspositonSearch(int depth
if (situation
return
}
// lookup transposition table
int score = TranspositionTable
if (score !=
// hit the target!
return score;
}
if (depth <=
score = situation
// save the node
TranspositionTable
return score;
}
NodeType hashItemType = NodeType
List<Motion> motions = situation
for (Motion motion : motions) {
int toId = situation
motion
score =
situation
if (score > alpha) {
alpha = score;
hashItemType = NodeType
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
if (alpha >= beta) {
TranspositionTable
return beta;
}
}
}
if (hashItemType != NodeType
TranspositionTable
} else {
TranspositionTable
}
return alpha;
}
/**
* NegaScout with History Heuristic and Transposition Table search
* @param depth depth search
* @param alpha min value to max value
* @param beta max value to min value
* @return if game is over
* returns evaluat value(leaf node value)
* determined by cut
*/
@SuppressWarnings(
final int negaScoutWithHHTTSearch(int depth
if (situation
return
}
// lookup transpositiont table
int score = TranspositionTable
if (score !=
// hit the target!
return score;
}
if (depth <=
score = situation
TranspositionTable
return score;
}
List<Motion> motions = situation
// History heuristic
if (depth < SEARCH_DEPTH) {
for (Motion motion : motions) {
motion
motion
motion
}
Collections
}
int bestmove =
int a = alpha;
int b = beta;
int t;
int oldValue;
NodeType hashItemType = NodeType
for (int i =
Motion motion = motions
int toId = situation
motion
t =
if (t > a && t < beta && i >
a =
hashItemType = NodeType
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
bestmove = i;
}
situation
if (a < t) {
hashItemType = NodeType
a = t;
if (depth == SEARCH_DEPTH) {
bestMotion = motion;
}
}
if (a >= beta) {
TranspositionTable
oldValue = HistoryHeuristicTable
motion
motion
motion
HistoryHeuristicTable
motion
motion
motion
(oldValue +
return a;
}
b = a +
}
oldValue = HistoryHeuristicTable
motions
motions
motions
HistoryHeuristicTable
motions
motions
motions
(oldValue +
if (hashItemType != NodeType
TranspositionTable
} else {
TranspositionTable
}
return a;
}
/**
* Constructor with parameters
* @param situation the specified situation
*/
public SearchEngine(Situation situation) {
this
}
}
view plaincopy to clipboardprint?
/*
* @(#)Book
* Author:
* Created on Jun
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version
* (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
* GNU Library General Public License for more details
*
* You should have received a copy of the GNU General Public License
* along with this program; if not
* Foundation
*/
package cn
import cn
import cn
import cn
import java
import java
import java
/**
* Opening book
* Currently
* @author
* @version
*/
final public class Book {
/**
* book situation hash map
*/
public Map<Integer
/**
* Packaged default constructor
*/
Book() {
List<FEN> fens = FENAccessor
Integer hashCode =
for (FEN fen : fens) {
hashCode = TranspositionTable
hashMap
}
}
/**
* This book exists the specified chessboard situation?
* @param chessboard the specified chessboard
* @return if exists
* returns <code>false</code>
*/
final public boolean exists(int[][] chessboard) {
FEN f = hashMap
if (f != null && f
return true;
}
return false;
}
}
/*
* @(#)Book
* Author:
* Created on Jun
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version
* (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
* GNU Library General Public License for more details
*
* You should have received a copy of the GNU General Public License
* along with this program; if not
* Foundation
*/
package cn
import cn
import cn
import cn
import java
import java
import java
/**
* Opening book
* Currently
* @author
* @version
*/
final public class Book {
/**
* book situation hash map
*/
public Map<Integer
/**
* Packaged default constructor
*/
Book() {
List<FEN> fens = FENAccessor
Integer hashCode =
for (FEN fen : fens) {
hashCode = TranspositionTable
hashMap
}
}
/**
* This book exists the specified chessboard situation?
* @param chessboard the specified chessboard
* @return if exists
* returns <code>false</code>
*/
final public boolean exists(int[][] chessboard) {
FEN f = hashMap
if (f != null && f
return true;
}
return false;
}
}
view plaincopy to clipboardprint?
/*
* @(#)HistoryHeuristicTable
* Author:
* Created on May
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version
* (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
* GNU Library General Public License for more details
*
* You should have received a copy of the GNU General Public License
* along with this program; if not
* Foundation
*/
package cn
/**
* A <em>History Heuristic Table</em> maintains all best motion in
* the past
* ({@link cn
* @author
* @version
*/
final class HistoryHeuristicTable {
/**
* hold all best moves
*/
static int[][][][] holds = new int[
/**
* singleton
*/
private static HistoryHeuristicTable instance = new HistoryHeuristicTable();
/**
* Gets the single instance of the class
* @return history heuristic instance
*/
final public static HistoryHeuristicTable getInstance() {
if (instance == null) {
instance = new HistoryHeuristicTable();
}
return instance;
}
/**
* Private default constructor
*/
private HistoryHeuristicTable() {
}
/**
* Returns the history motion
* @param fromX x coordinate of which chessman do this move
* @param fromY y coordinate of which chessman do this move
* @param toX x coordinate of which chessman
* @param toY y coordinate of which chessman
* @return this move
*/
final static int getValue(int fromX
return holds[fromX][fromY][toX][toY];
}
/**
* Sets the history motion
* @param fromX x coordinate of which chessman do this move
* @param fromY y coordinate of which chessman do this move
* @param toX x coordinate of which chessman
* @param toY y coordinate of which chessman
* @param newValue the new value
*/
final static void setValue(int fromX
holds[fromX][fromY][toX][toY] = newValue;
}
}
/*
* @(#)TranspositionTable
* Author:
* Created on Jun
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version
* (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
* GNU Library General Public License for more details
*
* You should have received a copy of the GNU General Public License
* along with this program; if not
* Foundation
*/
package cn
import java
/**
* A <em>Transpositon Table</em> maintains a mass of node had evaluated
* In the table
* @author
* @version
*/
final public class TranspositionTable {
// XXX currently
/**
* transposition table
*/
final static int SIZE =
/**
* holds the chessboard condition<br>
* <ul>
* <li>
* </li>
* </ul>
* @see cn
* @see cn
*/
static int[][][] hashCodes = new int[
/**
* the holds
*/
static HashNode[][] items = new HashNode[
/**
* a
*/
static int curHashCode;
/**
* Transposition table hit count
*/
public static int hashHitCount =
/**
* singleton
*/
private static TranspositionTable instance = new TranspositionTable();
/**
* Gets the single instance
* @return transposition table single instance
*/
public static TranspositionTable getInstance() {
if (instance == null) {
instance = new TranspositionTable();
}
return instance;
}
/**
* Initializes the hash code of the specified chessboard situation
* @param chessboard the specified chessboard situation
*/
final static void initHashCode(int[][] chessboard) {
curHashCode = calcCurHashCode(chessboard);
}
/**
* Private default constructor
*/
private TranspositionTable() {
Random random = new Random();
for (int i =
for (int j =
for (int k =
hashCodes[i][j][k] = Math
}
}
}
for (int i =
for (int j =
items[i][j] = new HashNode();
}
}
}
/**
* Calculates the hash code for the specified chessboard situation
* @param chessboard the specified chessboar situation
* @return
*/
final public static int calcCurHashCode(int[][] chessboard) {
int ret =
for (int i =
for (int j =
ret ^= hashCodes[chessboard[i][j]][i][j];
}
}
return ret;
}
/**
* Save a chessboard situation into transposition table
* @param type type of this hash item
* @param depth depth depth of search
* @param value value of this hash value
*/
final public static void save(NodeType type
// depth %
HashNode item = items[depth %
item
item
item
item
}
/**
* Lookup a chessboard situation in transposition table
* @param depth depth of search
* @param alpha min value to max value
* @param beta max value to min value
* @return if find the result
* returns <code>
*/
final public static int lookup(int depth
// depth %
HashNode item = items[depth %
if (item
hashHitCount++;
switch (item
case exact:
return item
case lowerBound:
if (item
return item
} else {
break;
}
case upperBound:
if (item
return item
} else {
break;
}
}
}
// doesn
return
}
/**
* Recovery the hash value of a motion had done
* @param fromX x coordinate of which chessman do this move
* @param fromY y coordinate of which chessman do this move
* @param toX x coordinate of which chessman
* @param toY y coordinate of which chessman
* @param chessmanId the target position
* @param chessboard current chessboard situation
*/
final public static void unMoveHash(int fromX
int chessmanId
int toId = chessboard[toX][toY];
// retrieves the random number before the motion done
curHashCode ^= hashCodes[toId][fromX][fromY];
// removes chessman which position is toId
curHashCode ^= hashCodes[toId][toX][toY];
if (chessmanId !=
// recovery hash value chessman be eaten
curHashCode ^= hashCodes[chessmanId][toX][toY];
}
}
/**
* Generates the hash value of a motion on the current situation
* @param fromX x coordinate of which chessman do this move
* @param fromY y coordinate of which chessman do this move
* @param toX x coordinate of which chessman
* @param toY y coordinate of which chessman
* @param chessboard current chessboard situation
*/
final public static void moveHash(int fromX
int[][] chessboard) {
int fromId
fromId = chessboard[fromX][fromY];
toId = chessboard[toX][toY];
// removes chessman which position is fromId
curHashCode ^= hashCodes[fromId][fromX][fromY];
if (toId !=
// if toId position has a chessman
curHashCode ^= hashCodes[toId][toX][toY];
}
// retrieves the random number at toId
curHashCode ^= hashCodes[fromId][toX][toY];
}
/**
* Hash item type description
*/
enum NodeType {
/**
* the hash item
*/
exact
/**
* the hash item
*/
lowerBound
/**
* the hash item
*/
upperBound
/**
* the hash item
*/
unknown
};
/**
* Hash item description
*/
final class HashNode {
/**
*
*/
int hashCode;
/**
* item
*/
NodeType type = NodeType
/**
* search depth
*/
int depth;
/**
* item
*/
int value;
}
}
轉載請保留作者信息
作者
Blog
MSN & Gmail & QQ
From:http://tw.wingwit.com/Article/program/Java/hx/201311/26849.html