libosl-0.8.0.orig/0000755000000000000000000000000013032206115012431 5ustar rootrootlibosl-0.8.0.orig/AUTHORS0000644000000000000000000000075311701005711013506 0ustar rootroot--------------- Authors: Team GPS TANAKA Tetsurou ÅÄÃæ ůϯ KANEKO Tomoyuki ¶â»Ò ÃÎŬ MORIWAKI Daigo ¿¹ÏÆ Âç¸ç SOEDA Shunsuke ÉûÅÄ ½Ó²ð HAYASHI Yoshiki ÎÓ Ë§¼ù TAKEUCHI Shougo ÃÝÆâ À»¸ç --------------- libosl-0.8.0.orig/CMakeLists.txt0000644000000000000000000000703212335610142015177 0ustar rootrootproject (osl CXX) # Tweak build mode if(NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Debug" CACHE STRING "" FORCE) endif() if(NOT CMAKE_BUILD_TYPE MATCHES "^[Dd][Ee][Bb][Uu][Gg]") add_definitions(-DQT_NO_DEBUG_OUTPUT) set(CMAKE_BUILD_RELEASE TRUE) else() set(CMAKE_BUILD_RELEASE FALSE) endif() # Installation directory if(APPLE AND CMAKE_INSTALL_PREFIX MATCHES "/usr/local") set(CMAKE_INSTALL_PREFIX "/Applications") endif() message(STATUS "Building ${PROJECT_NAME} in ${CMAKE_BUILD_TYPE} mode") cmake_minimum_required(VERSION 2.8.8) set (CMAKE_VERBOSE_MAKEFILE on) ENABLE_TESTING() # Common build options if(CMAKE_COMPILER_IS_GNUCXX OR MINGW OR APPLE) #if(CMAKE_BUILD_RELEASE) # add_definitions(-Werror) #endif() add_compile_options(-std=c++11) #CMake 2.8.12 or newer #add_definitions(-std=c++11) #older than CMake 2.8.11 set (CMAKE_CXX_FLAGS_DEBUG "-g -O0 -DDEBUG") set (CMAKE_CXX_FLAGS_RELEASE "-O3 -DNDEBUG") add_definitions(-Wall -D_REENTRANT -DOSL_SMP -DOSL_DFPN_SMP_SEARCH -DMORE_CHECKMATE_IF_CAPTURE_MAJOR) add_definitions(-DBOOST_FILESYSTEM_VERSION=3) endif() # Compiler specific build options if(MINGW) add_compile_options(-march=pentium4 -mthreads -mwin32 -msse2 -static-libgcc -static-libstdc++ -mstackrealign -fno-strict-aliasing) add_definitions(-D_MT -DWIN32_LEAN_AND_MEAN -D_WIN32_WINNT=0x0500) set (BOOST_ROOT "$ENV{HOME}/local/src/boost_1_54_0") set (Boost_NO_SYSTEM_PATHS ON) find_library(Winsock2_LIBRARY ws2_32) elseif (APPLE) add_compile_options(-march=core2) add_definitions(-Wall -D_REENTRANT) # -fno-common for shared library set (CMAKE_OSX_ARCHITECTURES x86_64) set (CMAKE_OSX_SYSROOT "/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.9.sdk") set (CMAKE_OSX_DEPLOYMENT_TARGET 10.6) set (BOOST_ROOT "/usr/local/Cellar/boost/1.54.0") elseif (UNIX) add_compile_options(-march=native) endif() if (APPLE) add_definitions(-DOSL_HOME="/Applications/gpsfish.app/Contents/Resources") else() add_definitions(-DOSL_HOME="${CMAKE_CURRENT_SOURCE_DIR}") endif() include_directories ("${PROJECT_SOURCE_DIR}/core") include_directories ("${PROJECT_SOURCE_DIR}/std") include_directories ("${PROJECT_SOURCE_DIR}/full") ## Pthreads #find_package (Threads) #if (Threads_FOUND) # message (STATUS "Threads: ${CMAKE_THREAD_LIBS_INIT}") #else() # message (FATAL_ERROR "Threads not found") #endif() ## Boost thing #set (BOOST_ROOT "$ENV{HOME}/local/boost_1_36_0_binaries/") set (Boost_USE_STATIC_LIBS ON) set (Boost_USE_MULTITHREADED ON) if (MINGW) find_package (Boost 1.54.0) else() find_package (Boost 1.54.0) endif() if (Boost_FOUND) include_directories (${Boost_INCLUDE_DIRS}) message (STATUS ${Boost_INCLUDE_DIRS}) else() message (FATAL_ERROR "Boost installation not found") endif() ## Program SampleCounter file(GLOB_RECURSE OSL_HEADERS core/osl/*.h core/osl/*.tcc std/osl/*.h std/osl/*.tcc full/osl/*.h full/osl/*.tcc) file(GLOB_RECURSE OSL_SRCS core/osl/*.cc std/osl/*.cc full/osl/*.cc) file(GLOB_RECURSE EXCLUDE_SRCS full/osl/ntesuki/*.cc) list(REMOVE_ITEM OSL_SRCS ${EXCLUDE_SRCS}) #message (STATUS "Headers: ${OSL_HEADERS}") #message (STATUS "Sources: ${OSL_SRCS}") #set (SampleAleriUDF_ALL_SRCS ${SampleAleriUDF_HEADERS} ${SampleAleriUDF_SRCS}) add_library (osl-static STATIC ${OSL_SRCS}) SET_TARGET_PROPERTIES(osl-static PROPERTIES OUTPUT_NAME "osl") SET_TARGET_PROPERTIES(osl-static PROPERTIES PREFIX "lib") if (${CMAKE_SYSTEM_NAME} MATCHES "Linux") add_library (osl SHARED ${OSL_SRCS}) target_link_libraries (osl ${CMAKE_THREAD_LIBS_INIT}) endif() libosl-0.8.0.orig/INSTALL.mingw0000644000000000000000000000404412335610142014610 0ustar rootrootHow to compile using Mingw ========================== This document depicts how to compile OSL and GPSShogi with Mingw cross compiler on Debian/Linux, targeting Windows. It is recommended to use Debian sid version for cross compiling (as GPSShogi developers do). Using virtual machines such as VirtualBox would be convenient to run Debian sid of an unstable flavor. Setup Mingw ----------- * Install mingw and cmake $ sudo apt-get install mingw-w64-dev cmake $ cp ./Toolchain-i686-mingw32.cmake.sample ~/Toolchain-i686-mingw32.cmake CMake is used as a build tool. Build dependencies ------------------ 1. Bzip - ~/local/src/bzip2-1.0.6 - http://www.bzip.org/ - vim Makefile CC=i686-w64-mingw32-gcc AR=i686-w64-mingw32-ar RANLIB=i686-w64-mingw32-ranlib LDFLAGS=-Wl,-s - % vim bzip2.c Replace with sys/stat.h % make CFLAGS="-O2 -march=pentium4 -pipe -fomit-frame-pointer -ffast-math -D_FILE_OFFSET_BITS=64" LDFALGS="-Wl,-s" % mkdir target % make install PREFIX=target % sudo cp target/include/bzlib.h /usr/i686-w64-mingw32/include % sudo cp target/lib/libbz2.a /usr/i686-w64-mingw32/lib 2. Boost 1.54.0 - ~/local/src/boost_1_46_1 % chmod 755 */.sh % cat ./user-config.jam using gcc : 4.6 : i686-w64-mingw32-g++ : /usr/bin/i686-w64-mingw32-windres /usr/bin/i686-w64-mingw32-ar ; % ./bootstrap.sh --without-icu % ./bjam -j4 toolset=gcc target-os=windows variant=release threading=multi threadapi=win32 --without-mpi --without-python -sNO_ZLIB=1 -sNO_BZIP2=0 --layout=tagged --user-config=user-config.jam 2>&1 | tee mingw.log % cd stage/lib % i686-w64-mingw32-ranlib *.a Build OSL --------- $ cd /path/to/osl $ mkdir mingw-release & cd mingw-release $ cmake -DCMAKE_TOOLCHAIN_FILE=$HOME/Toolchain-i686-mingw32.cmake -DCMAKE_BUILD_TYPE:STRING=Release .. $ make Build GPS --------- $ cd /path/to/gpsshogi/bin $ mkdir mingw-release & cd mingw-release $ cmake -DCMAKE_TOOLCHAIN_FILE=$HOME/Toolchain-i686-mingw32.cmake -DCMAKE_BUILD_TYPE:STRING=Release .. $ make $ make package --- 2014-05-17 Daigo Moriwaki libosl-0.8.0.orig/sample/0000755000000000000000000000000012457473631013735 5ustar rootrootlibosl-0.8.0.orig/sample/legal_moves.cc0000644000000000000000000000661512316770314016541 0ustar rootroot/* legal_moves.cc */ #include "osl/numEffectState.h" #include "osl/record/csaRecord.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/search/quiescenceGenerator.tcc" #include "osl/bits/king8Info.h" #include #include using namespace osl; /** * @file åˆæ³•手ã®è¡¨ç¤º */ int main(int argc, char **argv) { bool csa, generate_check, quiesce_check; boost::program_options::options_description command_line_options; command_line_options.add_options() ("csa", boost::program_options::value(&csa)->default_value(false), "Show legal moves in CSA format") ("input-file", boost::program_options::value< std::vector >(), "input files in kisen format") ("generate-check", boost::program_options::value(&generate_check)->default_value(false), "generate only check moves instead of all legal moves") ("generate-quiesce-check", boost::program_options::value(&quiesce_check)->default_value(false), "generate only check moves used in quiescence search") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] CSA_FILE1 CSA_FILE2 ..." << std::endl; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] CSA_FILE1 CSA_FILE2 ..." << std::endl; std::cerr << command_line_options << std::endl; return 1; } const std::vector files = vm["input-file"].as< std::vector >(); for (size_t i = 0; i < files.size(); ++i) { const auto record = CsaFileMinimal(files[i]).load(); NumEffectState state(record.initialState()); const auto moves=record.moves; for (auto p=moves.begin(); p!=moves.end(); ++p) { state.makeMove(*p); } MoveVector legal_moves; if (generate_check) { move_action::Store store(legal_moves); move_generator::GenerateAddEffectWithEffect::generate (state.turn(), state, state.kingPiece(alt(state.turn())).square(), store); } else if (quiesce_check) { const checkmate::King8Info info(state.Iking8Info(state.turn())); if (state.turn() == BLACK) search::QuiescenceGenerator::check(state, state.pin(WHITE), legal_moves, info.libertyCount()==0); else search::QuiescenceGenerator::check(state, state.pin(WHITE), legal_moves, info.libertyCount()==0); } else { state.generateLegal(legal_moves); } if (i > 0) { std::cout << std::endl; } if (csa) { for (size_t i = 0; i < legal_moves.size(); ++i) { std::cout << osl::csa::show(legal_moves[i]) << std::endl; } } else { std::cout << legal_moves; } } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/sample/progress/0000755000000000000000000000000012316770314015571 5ustar rootrootlibosl-0.8.0.orig/sample/progress/show-state.cc0000644000000000000000000000366312316770314020206 0ustar rootroot/* show-state.cc */ #include "osl/progress/effect5x3.h" #include "osl/progress.h" #include "osl/record/csaRecord.h" #include #include #include #include #include #include using namespace osl; using namespace osl::progress; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-a] csa-filename" << endl; exit(1); } void show(const char *filename); bool show_all_states = false; int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; // extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "at:f:vh")) != EOF) { switch(c) { case 'a': show_all_states = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); progress::ml::NewProgress::setUp(); for (int i=0; i #include namespace po = boost::program_options; int main(int argc, char **argv) { std::string kisen_filename; int kisen_index; po::options_description options("Options"); options.add_options() ("kisen,k", po::value(&kisen_filename), "kisen filename") ("index,i", po::value(&kisen_index)->default_value(0)) ("help", "produce help message") ; po::positional_options_description p; po::variables_map vm; try { po::store(po::command_line_parser(argc, argv). options(options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cout << options << std::endl; return 0; } } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; return 1; } osl::record::KisenFile kisen(kisen_filename); osl::NumEffectState state(kisen.initialState()); std::vector moves = kisen.moves(kisen_index); osl::progress::ml::NewProgress::setUp(); osl::progress::ml::NewProgress progress(state); for (size_t i = 0; i < moves.size() + 1; ++i) { if (!state.inCheck()) { // 16().value std::cout << i << " " << progress.progress() << std::endl; } if (i < moves.size()) { state.makeMove(moves[i]); progress.update(state, moves[i]); } } return 0; } libosl-0.8.0.orig/sample/annotate/0000755000000000000000000000000012316770314015536 5ustar rootrootlibosl-0.8.0.orig/sample/annotate/annotate.cc0000644000000000000000000000523012316770314017656 0ustar rootroot/* annotate.cc */ #include "osl/annotate/facade.h" #include "osl/record/kakinoki.h" #include "osl/record/record.h" #include "osl/record/ki2.h" #include "osl/usi.h" #include #include #include #include #include namespace po = boost::program_options; using namespace osl; void analyze_root(const NumEffectState& state, const std::vector& moves, int move_number); int main(int argc, char **argv) { po::options_description options; std::string filename; size_t start, end; options.add_options() ("filename,f", po::value(&filename), "specify .kif or .ki2 file to be analyzed") ("start,s", po::value(&start)->default_value(35), "skip first moves") ("end,e", po::value(&end)->default_value(350), "skip first moves") ("help,h", "Show help message"); po::variables_map vm; try { po::store(po::parse_command_line(argc, argv, options), vm); po::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] files" << std::endl; std::cout << options << std::endl; return 1; } } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; return 1; } if (filename.empty()) return 1; std::vector moves; NumEffectState state; try { if (filename.find(".kif") == filename.size()-4) { KakinokiFile file(filename); moves = file.moves(); state = file.initialState(); } else if (filename.find(".ki2") == filename.size()-4) { Ki2File file(filename); moves = file.moves(); state = file.initialState(); } } catch (KakinokiIOError&) { return 1; } for (size_t i=0; i= end) break; } } void analyze_root(const NumEffectState& src, const std::vector& moves, int move_number) { std::ostringstream ret; ret << "[(" << move_number << ") "; NumEffectState s; if (move_number) { for (int i=0; i #include #include #include using namespace osl; /** * @file ランダムプレイヤ */ void showState(const NumEffectState& state) { std::cout << state << std::endl; #if 0 KanjiPrint printer(std::cout); printer.print(state); #endif } /** * ランダムã«é¸ã¶ */ Move selectMove(const NumEffectState& state, const MoveVector& moves) { static std::mt19937 generator(random()); return moves[generator() % moves.size()]; #if 0 boost::uniform_int random(generator, 0, moves.size()); return moves[random()]; #endif } /** * 指ã—ãŸå¾Œï¼ŒçŽ‹ãŒå–られãŸã‚‰è² ã‘ */ bool isMated(const NumEffectState& state) { return state.inCheck(alt(state.turn())); } int main() { srandom(time(0)); NumEffectState state; std::string line; while (true) { // è‡ªåˆ†ã®æ‰‹ã‚’指㙠MoveVector moves; state.generateLegal(moves); if (moves.empty()) { std::cerr << "make masita\n"; break; } const Move my_move = selectMove(state, moves); assert(state.isValidMove(my_move)); state.makeMove(my_move); showState(state); std::cout << csa::show(my_move) << "\n"; if (isMated(state)) { std::cerr << "checkmate!"; break; } // ç›¸æ‰‹ã®æŒ‡æ‰‹ã‚’読ã¿ã“ã‚€ if (! std::getline(std::cin, line)) break; const Move op_move=csa::strToMove(line, state); if (! state.isValidMove(op_move)) break; state.makeMove(op_move); showState(state); std::cout << csa::show(op_move) << "\n"; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/show_repetition.cc0000644000000000000000000000342312316770314017460 0ustar rootroot/* show_repetition.cc */ #include "osl/repetitionCounter.h" #include "osl/record/csaRecord.h" #include "osl/csa.h" #include #include void usage(const char *program_name) { } using namespace osl; void processRecord(std::vector const& moves) { NumEffectState state; RepetitionCounter counter(state); for (size_t i=0; i 1) { std::cout << times << "-times, first appeared at " << counter.getFirstMove(HashKey(state)) << " check " << counter.checkCount(BLACK) << " " << counter.checkCount(WHITE) << "\n"; } std::cout << "\n"; } std::cout << state << std::endl; } int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; bool verbose = false; // extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "vh")) != EOF) { switch(c) { case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); nice(20); //次㫠CSAãƒ•ã‚¡ã‚¤ãƒ«ã‚’å‡¦ç† for (int i=0; i #include using namespace osl; /** * @file 一手読㿠*/ void showState(const NumEffectState& state) { std::cout << state << std::endl; #if 0 KanjiPrint printer(std::cout); printer.print(state); #endif } /** 先手有利ãªã»ã©æ­£ã«å¤§ããªæ•°ã‚’, 後手有利ãªã»ã©è² ã«å¤§ããªæ•°ã‚’返㙠*/ int evaluate(const NumEffectState& state) { OpenMidEndingEval e(state); return e.value(); } const bool use_book = true; Move selectMove(const NumEffectState& original, const MoveVector& moves) { if (use_book) { const BookInMemory& book = BookInMemory::instance(); osl::HashKey key(original); osl::MoveVector moves; book.find(key, moves); if(!moves.empty()) return moves[osl::time_seeded_random()%moves.size()]; } /** 先手+1, 後手-1 */ const int sgn = sign(original.turn()); int best_value = 0; Move best_move; for (auto move: moves) { NumEffectState state = original; state.makeMove(move); int value = evaluate(state); if (best_move == Move() || sgn*best_value < sgn*value) { best_move = move; best_value = value; } } return best_move; } /** * 指ã—ãŸå¾Œï¼ŒçŽ‹ãŒå–られãŸã‚‰è² ã‘ */ bool isMated(const NumEffectState& state) { return state.inCheck(alt(state.turn())); } int main() { OslConfig::setUp(); NumEffectState state; std::string line; while (true) { // è‡ªåˆ†ã®æ‰‹ã‚’指㙠MoveVector moves; state.generateLegal(moves); if (moves.empty()) { std::cerr << "make masita\n"; break; } const Move my_move = selectMove(state, moves); assert(state.isValidMove(my_move)); state.makeMove(my_move); showState(state); std::cout << csa::show(my_move) << "\n"; if (isMated(state)) { std::cerr << "checkmate!"; break; } // ç›¸æ‰‹ã®æŒ‡æ‰‹ã‚’読ã¿ã“ã‚€ if (! std::getline(std::cin, line)) break; const Move op_move=csa::strToMove(line, state); if (! state.isValidMove(op_move)) break; state.makeMove(op_move); showState(state); std::cout << csa::show(op_move) << "\n"; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/timer.cc0000644000000000000000000000040010044207676015350 0ustar rootroot#include "osl/real_time.h" #include int main () { osl::RealTime realTime (10); while (realTime.timeLeft ()) { long tlis = realTime.getTimeLeftApprox (); std::cout << tlis << std::endl; sleep (1); } return 0; } libosl-0.8.0.orig/sample/opening/0000755000000000000000000000000012443717205015365 5ustar rootrootlibosl-0.8.0.orig/sample/opening/showOpening.cc0000644000000000000000000000571212316770314020200 0ustar rootroot#include "osl/game_playing/winCountTracer.h" #include "osl/numEffectState.h" #include "osl/book/openingBook.h" #include "osl/usi.h" #include "osl/oslConfig.h" #include using namespace osl; using namespace osl::game_playing; using namespace osl::book; void printStats(WinCountBook& book, int index) { std::cout << "Win: " << book.winCount(index) << "\t" << "Lose: " << book.loseCount(index) << std::endl; } void printNextMoves(WinCountBook& book, WinCountTracer& tracer, NumEffectState* state) { std::cout << "" << std::endl; auto moves = book.moves(tracer.stateIndex()); if (moves.size() == 0) { std::cout << "No more moves in the book" << std::endl; } for (size_t i = 0; i < moves.size(); i++) { std::cout << "" << std::endl; std::cout << psn::show(moves[i].move) << std::endl; printStats(book, moves[i].stateIndex()); if (state != NULL) { NumEffectState newState(*state); newState.makeMove(moves[i].move); std::cout << "" << std::endl; std::cout << newState << std::endl; std::cout << "" << std::endl; } std::cout << "" << std::endl; } std::cout << "" << std::endl; } int main(int argc, char **argv) { std::string bookFilename = OslConfig::openingBook(); WinCountBook book(bookFilename.c_str()); WinCountTracer tracer(book); NumEffectState state; char *programName = argv[0]; bool showNextMoves = false; bool showBoards = false; bool trace = false; bool unknownOption = false; char c; while ((c = getopt(argc, argv, "nst")) != EOF) { switch(c) { case 'n': showNextMoves = true; break; case 's': showBoards = true; break; case 't': trace = true; break; default: unknownOption = true; } } argc -= optind; argv += optind; if (unknownOption) { std::cerr << "Usage: " << programName << " [-n] [-s] [-t]" << std::endl << "[-n show next moves] " << "[-s show boards] " << "[-t show next moves for every move]" << std::endl; return 1; } std::string line; // When in trace mode, show the candidates for the first move, too. if (trace) { printNextMoves(book, tracer, showBoards ? &state : NULL); } while (!std::getline(std::cin, line).eof()) { Move move = psn::strToMove(line, state); tracer.update(move); state.makeMove(move); if (trace) { printNextMoves(book, tracer, showBoards ? &state : NULL); } if (tracer.isOutOfBook()) { std::cout << "Out of Book" << std::endl; return 0; } } std::cout << "" << std::endl; printStats(book, tracer.stateIndex()); if (showBoards) { std::cout << "" << std::endl; std::cout << state << std::endl; std::cout << "" << std::endl; } std::cout << "" << std::endl; if (showNextMoves && !trace) { printNextMoves(book, tracer, showBoards ? &state : NULL); } return 0; } libosl-0.8.0.orig/sample/opening/openingBookConverter.cc0000644000000000000000000001024512316770314022037 0ustar rootroot#include "openingBookConverter.h" #include "osl/book/compactBoard.h" #include "osl/record/record.h" #include OpeningBookConverter::OpeningBookConverter(const char *filename) { std::ifstream ifs(filename); int nStates = osl::book::readInt(ifs); states.reserve(nStates); for (int i = 0 ; i < nStates; i++) { int blackWin = osl::book::readInt(ifs); int whiteWin = osl::book::readInt(ifs); int nMove = osl::book::readInt(ifs); int index = osl::book::readInt(ifs); states.push_back(OBState(index, nMove, blackWin, whiteWin)); } while (true) { osl::Move move=osl::Move::makeDirect(osl::book::readInt(ifs)); int stateIndex=osl::book::readInt(ifs); if (!ifs) break; moves.push_back({move,stateIndex}); } } void OpeningBookConverter::write(const char* filename) { std::ofstream ofs(filename); osl::book::writeInt(ofs, states.size()); for (auto it = states.begin(); it != states.end(); ++it) { osl::book::writeInt(ofs, it->getOBMoveIndex()); osl::book::writeInt(ofs, it->getNOBMove()); osl::book::writeInt(ofs, it->getBlackWinCount()); osl::book::writeInt(ofs, it->getWhiteWinCount()); } for (auto it = moves.begin(); it != moves.end(); ++it) { osl::book::writeInt(ofs, it->move.intValue()); osl::book::writeInt(ofs, it->stateIndex()); } } void OpeningBookConverter::writeInNewFormat(std::ofstream& ofs) { std::vector weights(moves.size()); osl::book::writeInt(ofs, 1); // version number osl::book::writeInt(ofs, states.size()); osl::book::writeInt(ofs, moves.size()); osl::book::writeInt(ofs, 0); // Start state index for (auto it = states.begin(); it != states.end(); ++it) { osl::book::writeInt(ofs, it->getOBMoveIndex()); osl::book::writeInt(ofs, it->getNOBMove()); int total_wins = 0; std::vector wins; wins.reserve(it->getNOBMove()); for (int i = 0; i < it->getNOBMove(); i++) { const osl::book::OBMove& move = moves.at(i + it->getOBMoveIndex()); const OBState& state = states.at(move.stateIndex()); if (move.move.player() == osl::BLACK) wins.push_back(state.getBlackWinCount()); else wins.push_back(state.getWhiteWinCount()); total_wins += wins.at(i); } for (int i = 0; i < it->getNOBMove(); i++) { if (total_wins != 0) weights.at(i + it->getOBMoveIndex()) = (wins.at(i) * 10000 / total_wins); else weights.at(i + it->getOBMoveIndex()) = 0; } osl::book::writeInt(ofs, it->getBlackWinCount()); osl::book::writeInt(ofs, it->getWhiteWinCount()); } int i = 0; for (std::vector::const_iterator it = moves.begin(); it != moves.end(); ++it, ++i) { osl::book::WMove wmove = {it->move, it->stateIndex(), weights.at(i)}; ofs << wmove; } } void OpeningBookConverter::writeInNewFormat(const char* filename) { std::ofstream ofs(filename); writeInNewFormat(ofs); } void OpeningBookConverter::writeInNewEditFormat(const char* filename) { std::ofstream ofs(filename); writeInNewFormat(ofs); std::vector simpleStates(states.size()); std::vector visited(states.size()); std::vector toTraceIndex; for (unsigned int i = 0; i < states.size(); i++) visited[i] = false; assert(states.size() >= 1); // First entry is assmed to be the start state. toTraceIndex.push_back(0); simpleStates[0] = osl::SimpleState(osl::HIRATE); visited[0] = true; while (!toTraceIndex.empty()) { const int index = toTraceIndex.back(); toTraceIndex.pop_back(); const OBState& s = states.at(index); const int moveIndex = s.getOBMoveIndex(); for (int i = 0; i < s.getNOBMove(); i++) { const osl::book::OBMove& m = moves.at(moveIndex + i); const int nextState = m.stateIndex(); if (!visited[nextState]) { toTraceIndex.push_back(nextState); osl::NumEffectState newState(simpleStates[index]); newState.makeMove(m.move); simpleStates[nextState] = newState; visited[nextState] = true; } } } for (unsigned int i = 0; i < states.size(); i++) { osl::book::CompactBoard board(simpleStates[i]); ofs << board; } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/opening/openingStatistics.cc0000644000000000000000000003105412316770314021410 0ustar rootroot#include "osl/book/openingBook.h" #include "osl/eval/pieceEval.h" #include "osl/hashKey.h" #include "osl/misc/math.h" #include "osl/record/csaRecord.h" #include "osl/record/kanjiPrint.h" #include "osl/search/fixedEval.h" #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceSearch2.tcc" #include "osl/search/simpleHashTable.h" #include #include #include #include #include #include namespace bp = boost::program_options; bp::variables_map vm; typedef std::vector WMoveContainer; osl::Player the_player = osl::BLACK; bool is_dump = false; int error_threshold = 500; int is_determinate = 0; // test only top n moves. 0 for all int max_depth, non_determinate_depth; double ratio; // use moves[n+1] when the weight[n+1] >= ratio*weight[n] bool is_quick = false; std::shared_ptr state_to_compare; size_t state_count = 0; /** * qsearch * * @param s state * @param lastMove * @return evaluation value */ int qsearch(const osl::SimpleState &s, const osl::Move& lastMove) { if (is_quick) return 0; typedef osl::search::QuiescenceSearch2 qsearch_t; osl::NumEffectState state(s); osl::search::SimpleHashTable table(100000, -1, false); osl::search::SearchState2Core::checkmate_t checkmate_searcher; osl::search::SearchState2Core core(state, checkmate_searcher); qsearch_t qs(core, table); osl::eval::PieceEval ev(state); return qs.search(state.turn(), ev, lastMove, 4); } void showStatistics(const std::deque& src) { double sum, mean, var, dev, skew, kurt; osl::misc::computeStats(src.begin(), src.end(), sum, mean, var, dev, skew, kurt); std::cout << boost::format(" total: %g\n") % src.size() << boost::format(" mean: %g\n") % mean << boost::format(" dev: %g\n") % dev; } void printUsage(std::ostream& out, char **argv, const boost::program_options::options_description& command_line_options) { out << "Usage: " << argv[0] << " [options] \n" << command_line_options << std::endl; } void showInfoOfState(osl::book::WeightedBook& book, const int state_index) { osl::record::KanjiPrint printer(std::cerr, std::shared_ptr( new osl::record::KIFCharacters()) ); std::cout << boost::format("state_index: %g\n") % state_index << boost::format("black win: %g\n") % book.blackWinCount(state_index) << boost::format("white win: %g\n") % book.whiteWinCount(state_index); std::cout << "\nTarget state:\n"; printer.print(book.board(state_index)); std::cout << "\n"; WMoveContainer moves = book.moves(state_index); std::cout << boost::format("found %g moves\n") % moves.size(); std::sort(moves.begin(), moves.end(), osl::book::WMoveSort()); for (WMoveContainer::const_iterator each = moves.begin(); each != moves.end(); ++each) { std::cout << boost::format("[%g] %g") % each->weight % each->move; const int next_index = each->stateIndex(); std::cout << "\n"; printer.print(book.board(next_index)); } } void doMain(const std::string& file_name) { osl::record::KanjiPrint printer(std::cerr, std::shared_ptr( new osl::record::KIFCharacters()) ); if (vm.count("verbose")) std::cout << boost::format("Opening... %s\n ") % file_name; osl::book::WeightedBook book(file_name.c_str()); if (vm.count("verbose")) std::cout << boost::format("Total states: %d\n") % book.totalState(); bool states[book.totalState()]; // mark states that have been visited. memset(states, 0, sizeof(bool) * book.totalState()); boost::progress_display progress(book.totalState()); int state_index_to_compare = -1; if (state_to_compare) state_index_to_compare = book.stateIndex(*state_to_compare); typedef std::pair state_depth_t; std::vector stateToVisit; if (vm.count("verbose")) std::cout << boost::format("Start index: %d\n)") % book.startState(); stateToVisit.push_back(state_depth_t(book.startState(), 1)); // root is 1 // depth-1手目ã‹ã‚‰depth手目ã®state。depth手目ã¯ã¾ã æŒ‡ã•れã¦ã„ãªã„(ã“れ㋠// らdepth手目) typedef std::pair eval_depth_t; std::deque evals; long finishing_games = 0; while (!stateToVisit.empty()) { const state_depth_t state_depth = stateToVisit.back(); if (vm.count("verbose")) std::cout << boost::format("Visiting... %d\n") % state_depth.first; const int stateIndex = state_depth.first; const int depth = state_depth.second; stateToVisit.pop_back(); states[stateIndex] = true; ++progress; // see if the state presents in the book if (state_to_compare && state_index_to_compare == stateIndex) ++state_count; WMoveContainer moves = book.moves(stateIndex); if (vm.count("verbose")) std::cout << boost::format(" #moves... %d\n") % moves.size(); // 自分(the_playerï¼‰ã®æ‰‹ç•ªã§ã¯ã€è‰¯ã„手ã®ã¿æŒ‡ã™ // 相手ã¯ã©ã‚“ãªæ‰‹ã‚’指ã—ã¦ãã‚‹ã‹åˆ†ã‹ã‚‰ãªã„ if ( !moves.empty() && ((the_player == osl::BLACK && depth % 2 == 1) || (the_player == osl::WHITE && depth % 2 == 0)) ) { std::sort(moves.begin(), moves.end(), osl::book::WMoveSort()); int min = 1; if (is_determinate) { min = moves.at(0).weight; if (depth <= non_determinate_depth) { for (int i=1; i<=std::min(is_determinate, (int)moves.size()-1); ++i) { const int weight = moves.at(i).weight; if ((double)weight < (double)moves.at(i-1).weight*ratio) break; min = weight; } } } // Do not play 0-weighted moves. if (min == 0) min = 1; WMoveContainer::iterator each = moves.begin(); for (; each != moves.end(); ++each) { if (each->weight < min) break; } moves.erase(each, moves.end()); } if (moves.empty() || depth > max_depth) // found leaves { const osl::NumEffectState state(book.board(stateIndex)); const int value = qsearch(state, osl::Move::PASS(alt(state.turn()))); if ( (the_player == osl::BLACK && value < -1 * error_threshold) || (the_player == osl::WHITE && value > error_threshold) ) { ++finishing_games; if (is_dump) { std::cerr << std::endl; std::cerr << "eval: " << value << std::endl; printer.print(state); std::cerr << "piece value:" << osl::PieceEval(state).value() << "\n" << state; } } else { evals.push_back(eval_depth_t(value, depth)); } continue; } // çµæžœã®å†ç¾æ€§ã‚’高ã‚ã‚‹ãŸã‚ã€visitã®é †ç•ªã‚’決ã‚ã‚‹ std::sort(moves.begin(), moves.end(), osl::book::WMoveMoveSort()); // recursively search the tree for (std::vector::const_iterator each = moves.begin(); each != moves.end(); ++each) { // consistancy check const osl::SimpleState state(book.board(stateIndex)); const osl::hash::HashKey hash(state); const int nextIndex = each->stateIndex(); const osl::SimpleState next_state(book.board(nextIndex)); const osl::hash::HashKey next_hash(next_state); const osl::hash::HashKey moved_hash = hash.newMakeMove(each->move); if (moved_hash != next_hash) throw std::string("Illegal move found."); if (! states[nextIndex]) stateToVisit.push_back(state_depth_t(nextIndex, depth+1)); } // each wmove } // while loop // Show the result std::cout << std::endl; std::cout << boost::format("Book: %s\n") % file_name; std::cout << boost::format("Player: %s\n") % the_player; std::cout << "FU=128 points\n"; std::cout << boost::format("#states: %d (+ %d finishing games over %d points; max %d)\n") % evals.size() % finishing_games % error_threshold % max_depth; { std::cout << "Eval\n"; std::deque tmp; for (std::deque::const_iterator each = evals.begin(); each != evals.end(); ++each) tmp.push_back(each->first); showStatistics(tmp); } { std::cout << "Depth\n"; std::deque tmp; for (std::deque::const_iterator each = evals.begin(); each != evals.end(); ++each) tmp.push_back(each->second); showStatistics(tmp); } if (state_to_compare) { std::cout << "\nthe state hits: " << state_count << std::endl; printer.print(*state_to_compare); const int stateIndex = book.stateIndex(*state_to_compare); const std::vector parents = book.parents(stateIndex); if (parents.empty()) { std::cout << "\nNo parent\n"; } else { int i = 0; for (std::vector::const_iterator each = parents.begin(); each != parents.end(); ++each, ++i) { std::cout << boost::format("\n--- Parent: %g ---\n ") % i; showInfoOfState(book, *each); } } } } int main(int argc, char **argv) { std::string player_str; std::string file_name; size_t csa_move_index; std::string csa_file_name; bp::options_description command_line_options; command_line_options.add_options() ("player,p", bp::value(&player_str)->default_value("black"), "specify a player, black or white, in whose point of view the book is validated. " "default black.") ("input-file,f", bp::value(&file_name)->default_value("./joseki.dat"), "a joseki file to validate.") ("dump", bp::value(&is_dump)->default_value(false), "dump finishing games' states") ("threshold", bp::value(&error_threshold)->default_value(500), "threshold of evaluatoin value to recognize a finishing game.") ("determinate", bp::value(&is_determinate)->default_value(0), "only search the top n moves. (0 for all, 1 for determinate).") ("non-determinate-depth", bp::value(&non_determinate_depth)->default_value(100), "use the best move where the depth is greater than this value") ("max-depth", bp::value(&max_depth)->default_value(100), "do not go beyond this depth from the root") ("ratio", bp::value(&ratio)->default_value(0.0), "skip move[i] (i >= n), if weight[n] < weight[n-1]*ratio") ("csa-move", bp::value(&csa_move_index)->default_value(1), "n-th-move state in the csa file") ("csa", bp::value(&csa_file_name)->default_value(""), "a csa file name. See if a state in the game exists in the book or not.") ("quick", bp::value(&is_quick)->default_value(false), "skip quiescence search.") ("verbose,v", "output verbose messages.") ("help,h", "show this help message."); bp::positional_options_description p; p.add("input-file", 1); try { bp::store( bp::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); bp::notify(vm); if (vm.count("help")) { printUsage(std::cout, argv, command_line_options); return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options\n" << e.what() << std::endl; printUsage(std::cerr, argv, command_line_options); return 1; } if (player_str == "black") the_player = osl::BLACK; else if (player_str == "white") the_player = osl::WHITE; else { printUsage(std::cerr, argv, command_line_options); return 1; } if (!csa_file_name.empty()) { is_quick = true; const osl::CsaFile csa(csa_file_name); const osl::Record record = csa.load(); const auto moves = record.moves(); const auto initial_state = record.initialState(); state_to_compare.reset(new osl::NumEffectState(initial_state)); if (csa_move_index < 1) csa_move_index = 1; if (csa_move_index > moves.size()) csa_move_index = moves.size(); if ( (the_player == osl::BLACK && csa_move_index%2 == 0) || (the_player == osl::WHITE && csa_move_index%2 == 1) ) { std::cout << "Invalid csa move index: " << csa_move_index << std::endl; return -1; } for (size_t i=0; i < csa_move_index; i++) { const osl::Move& move = moves[i]; state_to_compare->makeMove(move); } } doMain(file_name); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/opening/show-moves.cc0000644000000000000000000000403712443717205020007 0ustar rootroot#include "osl/book/openingBook.h" #include "osl/record/csaRecord.h" #include "osl/hashKey.h" #include "osl/oslConfig.h" #include #include using namespace osl; using namespace osl::record; using namespace osl::book; typedef std::unordered_map> state_map; void show(const std::string& filename, const state_map& states, const SimpleState& state) { state_map::const_iterator it = states.find(HashKey(state)); if (it == states.end()) { std::cout << filename << "\t" << "Not found" << std::endl; } else { std::cout << filename; const WeightedBook::WMoveContainer &moves = it->second; for (size_t j = 0; j < moves.size(); ++j) { std::cout << "\t" << osl::csa::show(moves[j].move) << "\t" << moves[j].weight; } std::cout << std::endl; } } int main(int argc, char **argv) { std::string book_filename = OslConfig::openingBook(); WeightedBook book(book_filename.c_str()); state_map states; { std::vector state_stack; state_stack.push_back(book.startState()); while (!state_stack.empty()) { const int index = state_stack.back(); state_stack.pop_back(); const SimpleState state = book.board(index); const HashKey key = HashKey(state); if (states.find(key) == states.end()) { WeightedBook::WMoveContainer moves = book.moves(index); for (size_t i = 0; i < moves.size(); ++i) { state_stack.push_back(moves[i].stateIndex()); } states[key] = moves; } } } for (int i = 1; i < argc; ++i) { const std::string filename(argv[i]); osl::CsaFileMinimal csa(filename); NumEffectState state = csa.initialState(); auto record_moves = csa.moves(); if (record_moves.empty() || !(state == SimpleState(HIRATE))) show(filename, states, state); for (Move move: record_moves) { state.makeMove(move); show(filename, states, state); } } return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/opening/convert.cc0000644000000000000000000000044110205271544017346 0ustar rootroot#include "openingBookConverter.h" int main(int argc, char **argv) { if (argc != 3) { fprintf(stderr, "Usage: %s old-file new-file\n", argv[0]); return 1; } OpeningBookConverter rw(argv[1]); // rw.write(argv[2]); rw.writeInNewEditFormat(argv[2]); return 0; } libosl-0.8.0.orig/sample/opening/opening-validator.cc0000644000000000000000000000434212316770314021320 0ustar rootroot#include "osl/book/openingBook.h" #include "osl/csa.h" #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceSearch2.tcc" #include "osl/eval/pieceEval.h" #include #include using namespace osl::book; static int qsearch(osl::SimpleState &s, osl::Move lastMove) { typedef osl::search::QuiescenceSearch2 qsearch_t; osl::NumEffectState state(s); osl::search::SimpleHashTable table(100000, -16, false); osl::search::SearchState2Core::checkmate_t checkmate_searcher; osl::search::SearchState2Core core(state, checkmate_searcher); qsearch_t qs(core, table); osl::eval::PieceEval ev(state); return qs.search(state.turn(), ev, lastMove); } int main(int argc, char **argv) { if (argc != 2) { std::cerr << "Usage: " << argv[0] << " FILENAME" << std::endl; return 1; } WeightedBook book(argv[1]); bool states[book.totalState()]; memset(states, 0, sizeof(bool) * book.totalState()); std::vector stateToVisit; stateToVisit.push_back(book.startState()); const int threshold = osl::eval::Ptype_Eval_Table.value(osl::SILVER); while (!stateToVisit.empty()) { const int stateIndex = stateToVisit.back(); stateToVisit.pop_back(); states[stateIndex] = true; osl::SimpleState state = book.board(stateIndex); int value = qsearch(state, osl::Move::PASS(alt(state.turn()))); const auto moves = book.moves(stateIndex); for (size_t i = 0; i < moves.size(); i++) { const int nextIndex = moves[i].stateIndex(); osl::SimpleState newState = book.board(nextIndex); osl::Move move = moves[i].move; int newValue = qsearch(newState, move); int diff = newValue - value; // the loss too big if ((state.turn() == osl::BLACK && diff < -threshold) || (state.turn() == osl::WHITE && diff > threshold)) std::cout << "----" << std::endl << state << osl::csa::show(move) << std::endl; // the gain too big if ((state.turn() == osl::BLACK && diff > threshold) || (state.turn() == osl::WHITE && diff < -threshold)) std::cout << "++++" << std::endl << state << osl::csa::show(move) << std::endl; if (! states[nextIndex]) { stateToVisit.push_back(nextIndex); } } } } libosl-0.8.0.orig/sample/opening/openingBookConverter.h0000644000000000000000000000210312316770314021673 0ustar rootroot#ifndef _OPENING_BOOK_CONVERTER_H #define _OPENING_BOOK_CONVERTER_H #include "osl/book/openingBook.h" class OBState { int OBMoveIndex; int nOBMove; int blackWinCount; int whiteWinCount; public: OBState(int startIndex, int nMove, int blackWin, int whiteWin) : OBMoveIndex(startIndex), nOBMove(nMove), blackWinCount(blackWin), whiteWinCount(whiteWin) {} int getOBMoveIndex() const { return OBMoveIndex; } int getNOBMove() const { return nOBMove; } int getBlackWinCount() const { return blackWinCount; } int getWhiteWinCount() const { return whiteWinCount; } }; class OpeningBookConverter { std::vector states; std::vector moves; public: OpeningBookConverter(const char* filename); ~OpeningBookConverter() {}; void write(const char* filename); void writeInNewFormat(const char* filename); void writeInNewEditFormat(const char* filename); private: int readInt(std::ifstream& ifs); void writeInt(std::ofstream& ofs, int n); void writeInNewFormat(std::ofstream& ofs); }; #endif // _OPENING_BOOK_CONVERTER_H libosl-0.8.0.orig/sample/opening/compare-book.cc0000644000000000000000000002643612443717205020265 0ustar rootroot// compare-book.cc #include "osl/book/openingBook.h" #include "osl/csa.h" #include "osl/record/kanjiPrint.h" #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceSearch2.tcc" #include "osl/search/simpleHashTable.h" #include "osl/eval/pieceEval.h" //#include "osl/misc/math.h" #include "osl/search/fixedEval.h" #include #include #include #include #include #include typedef std::vector WMoveContainer; osl::Player the_player = osl::BLACK; std::string dump_mode = "none"; int is_determinate = 0; // test only top n moves. 0 for all int max_depth, non_determinate_depth; double ratio; // use moves[n+1] when the weight[n+1] >= ratio*weight[n] size_t state_count = 0; void printUsage(std::ostream& out, char **argv, const boost::program_options::options_description& command_line_options) { out << "Usage: " << argv[0] << " [options] \n" << command_line_options << std::endl; } typedef std::unordered_map> table_t; void store(osl::book::WeightedBook& book, table_t& table, std::vector& parents) { WMoveContainer moves = book.moves(book.startState()); parents.resize(book.totalState()); std::fill(parents.begin(), parents.end(), -1); boost::progress_display progress(book.totalState()); typedef std::pair state_depth_t; std::deque stateToVisit; stateToVisit.push_back(state_depth_t(book.startState(), 1)); // root is 1 // depth-1手目ã‹ã‚‰depth手目ã®state。depth手目ã¯ã¾ã æŒ‡ã•れã¦ã„ãªã„(ã“れ㋠// らdepth手目) typedef std::pair eval_depth_t; long leaves = 0; int depth_found = 0; while (!stateToVisit.empty()) { const state_depth_t state_depth = stateToVisit.front(); const int stateIndex = state_depth.first; const int depth = state_depth.second; stateToVisit.pop_front(); ++progress; assert(parents[stateIndex] >= 0 || stateIndex == book.startState()); depth_found = std::max(depth_found, depth); WMoveContainer moves = book.moves(stateIndex); // 自分(the_playerï¼‰ã®æ‰‹ç•ªã§ã¯ã€è‰¯ã„手ã®ã¿æŒ‡ã™ // 相手ã¯ã©ã‚“ãªæ‰‹ã‚’指ã—ã¦ãã‚‹ã‹åˆ†ã‹ã‚‰ãªã„ std::sort(moves.begin(), moves.end(), osl::book::WMoveWeightMoveSort()); if ( !moves.empty() && ((the_player == osl::BLACK && depth % 2 == 1) || (the_player == osl::WHITE && depth % 2 == 0)) ) { int min = 1; if (is_determinate) { min = moves.at(0).weight; if (depth <= non_determinate_depth) { for (int i=1; i<=std::min(is_determinate, (int)moves.size()-1); ++i) { const int weight = moves.at(i).weight; if ((double)weight < (double)moves.at(i-1).weight*ratio) break; min = weight; } } } // Do not play 0-weighted moves. if (min == 0) min = 1; WMoveContainer::iterator each = moves.begin(); for (; each != moves.end(); ++each) { if (each->weight < min) break; } moves.erase(each, moves.end()); } if (moves.empty() || depth > max_depth) // found leaves { ++leaves; continue; } if (moves[0].weight) { // not leaf const osl::NumEffectState state(book.board(stateIndex)); const osl::HashKey key(state); table[key] = stateIndex; } // recursively search the tree for (std::vector::const_iterator each = moves.begin(); each != moves.end(); ++each) { const int nextIndex = each->stateIndex(); if (parents[nextIndex] < 0) { parents[nextIndex] = stateIndex; stateToVisit.push_back(state_depth_t(nextIndex, depth+1)); } } // each wmove } // while loop // Show the result std::cout << std::endl; std::cout << boost::format("Player: %s\n") % the_player; std::cout << boost::format("#leaves: %d, max_depth %d\n") % leaves % depth_found; } void show_moves(const char *name, osl::book::WeightedBook& book, int node) { WMoveContainer moves = book.moves(node); std::sort(moves.begin(), moves.end(), osl::book::WMoveWeightMoveSort()); if (! moves.empty() && moves[0].weight) { std::cout << name; for (size_t i=0; i& parents, int node) { std::vector history; history.push_back(node); while (parents[node] >= 0) { node = parents[node]; history.push_back(node); } std::reverse(history.begin(), history.end()); assert(book.startState() == history[0]); osl::MoveVector result; for (size_t i=0; istateIndex() != history[i+1]) continue; result.push_back(p->move); break; } } return result; } void dump(osl::book::WeightedBook& book_a, const std::vector& parents_a, int node_a, osl::book::WeightedBook& book_b, const std::vector& parents_b, int node_b) { const osl::NumEffectState state(book_a.board(node_a)); osl::record::KanjiPrint printer(std::cout, std::shared_ptr( new osl::record::KIFCharacters()) ); printer.print(state); const osl::MoveVector history_a = make_history(book_a, parents_a, node_a); const osl::MoveVector history_b = make_history(book_b, parents_b, node_b); show_history(history_a); if (! (history_a == history_b)) show_history(history_b); show_moves("a", book_a, node_a); show_moves("b", book_b, node_b); } void dump(const char *name, osl::book::WeightedBook& book, const std::vector& parents, int node) { const osl::NumEffectState state(book.board(node)); osl::record::KanjiPrint printer(std::cout, std::shared_ptr( new osl::record::KIFCharacters()) ); printer.print(state); show_history(make_history(book, parents, node)); show_moves(name, book, node); } bool is_same_node(osl::book::WeightedBook& book_a, int node_a, osl::book::WeightedBook& book_b, int node_b) { WMoveContainer moves_a = book_a.moves(node_a); WMoveContainer moves_b = book_b.moves(node_b); std::sort(moves_a.begin(), moves_a.end(), osl::book::WMoveWeightMoveSort()); std::sort(moves_b.begin(), moves_b.end(), osl::book::WMoveWeightMoveSort()); size_t i=0; for (; i& parents_a, osl::book::WeightedBook& book_b, const table_t& table_b, const std::vector& parents_b) { long only_a = 0, only_b = 0, same = 0, diff = 0; for (table_t::const_iterator p=table_a.begin(); p!=table_a.end(); ++p) { table_t::const_iterator q=table_b.find(p->first); if (q == table_b.end()) { ++only_a; if (dump_mode == "a") dump("a", book_a, parents_a, p->second); continue; } if (is_same_node(book_a, p->second, book_b, q->second)) ++same; else { ++diff; if (dump_mode == "common") dump(book_a, parents_a, p->second, book_b, parents_b, q->second); } } for (table_t::const_iterator p=table_b.begin(); p!=table_b.end(); ++p) { table_t::const_iterator q=table_a.find(p->first); if (q == table_a.end()) { ++only_b; if (dump_mode == "b") dump("b", book_b, parents_b, p->second); continue; } } std::cout << "same " << same << " diff " << diff << " only-in-a " << only_a << " only-in-b " << only_b << std::endl; } int main(int argc, char **argv) { std::string player_str; namespace bp = boost::program_options; bp::variables_map vm; bp::options_description command_line_options; command_line_options.add_options() ("player,p", bp::value(&player_str)->default_value("black"), "specify a player, black or white, in whose point of view the book is validated. " "default black.") ("input-file,f", bp::value >(), "a joseki file to validate.") ("dump", bp::value(&dump_mode)->default_value(dump_mode), "common: dump positions where two books have different moves\n" "(a|b): dump positions registered to only book_[ab]\n") ("determinate", bp::value(&is_determinate)->default_value(0), "only search the top n moves. (0 for all, 1 for determinate).") ("non-determinate-depth", bp::value(&non_determinate_depth)->default_value(100), "use the best move where the depth is greater than this value") ("max-depth", bp::value(&max_depth)->default_value(100), "do not go beyond this depth from the root") ("ratio", bp::value(&ratio)->default_value(0.0), "skip move[i] (i >= n), if weight[n] < weight[n-1]*ratio") ("help,h", "show this help message."); bp::positional_options_description p; p.add("input-file", -1); std::vector filenames; try { bp::store( bp::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); bp::notify(vm); filenames = vm["input-file"].as >(); if (vm.count("help") || filenames.size() != 2 || (dump_mode != "none" && dump_mode != "a" && dump_mode != "b" && dump_mode != "common")) { printUsage(std::cout, argv, command_line_options); return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options\n" << e.what() << std::endl; printUsage(std::cerr, argv, command_line_options); return 1; } if (player_str == "black") the_player = osl::BLACK; else if (player_str == "white") the_player = osl::WHITE; else { printUsage(std::cerr, argv, command_line_options); return 1; } osl::book::WeightedBook book_a(filenames[0].c_str()), book_b(filenames[1].c_str()); osl::CArray,2> parents; osl::CArray tables; std::cout << boost::format("Book: %s\n") % filenames[0]; store(book_a, tables[0], parents[0]); std::cout << boost::format("Book: %s\n") % filenames[1]; store(book_b, tables[1], parents[1]); compare(book_a, tables[0], parents[0], book_b, tables[1], parents[1]); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/rating/0000755000000000000000000000000012316770314015211 5ustar rootrootlibosl-0.8.0.orig/sample/rating/probability.cc0000644000000000000000000000560612316770314020047 0ustar rootroot/* probability.cc */ #include "osl/rating/featureSet.h" #include "osl/rating/ratingEnv.h" #include "osl/effect_util/effectUtil.h" #include "osl/numEffectState.h" #include "osl/csa.h" #include "osl/record/kisen.h" #include "osl/progress/effect5x3.h" #include "osl/stat/average.h" #include "osl/stat/histogram.h" #include #include using namespace osl; using namespace osl::rating; int verbose = 0; const char *kisen_filename="0.kif"; size_t num_kisen = 4096; double verbose_limit = 0; void show(const NumEffectState&, Move, const progress::Effect5x3& progress); void show_statistics(); int main() { KisenFile kisen_file(kisen_filename); for (size_t i=0; i moves = kisen_file.moves(i); RatingEnv env; env.make(state); progress::Effect5x3 progress(state); for (size_t i=0; i rating_to_probability(const RatedMoveVector& moves) { double sum = 0; for (size_t i=0; i result(moves.size()); for (size_t i=0; i probability = rating_to_probability(moves); const RatedMove *rm = moves.find(next); top_rated[progress.progress16().value()].add(rm && rm == &moves[0]); if (rm) histogram.add(-log10(probability[rm - &moves[0]])); if (verbose || (rm && probability[rm - &moves[0]] < verbose_limit)) { std::cout << state; if (verbose > 1) { for (size_t i=0; i #include #include using namespace osl; using namespace osl::rating; namespace po = boost::program_options; size_t num_kisen, opening_skip, target_limit; void run(NumEffectState& state, const std::vector& moves); void show_statistics(); int main(int argc, char **argv) { std::string kisen_filename; std::vector filenames; po::options_description options("Options"); options.add_options() ("csa-file", po::value >(), "csa filename") ("kisen,k", po::value(&kisen_filename), "kisen filename") ("num-kisen", po::value(&num_kisen)->default_value(0), "number of records in kisen to be processed") ("target-limit", po::value(&target_limit)->default_value(1000), "ignore moves whose log-probability is greater than this threshold") ("opening-skip", po::value(&opening_skip)->default_value(20), "number of opening moves ignored in analysis"); po::variables_map vm; po::positional_options_description p; p.add("csa-file", -1); try { po::store(po::command_line_parser(argc, argv). options(options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cout << options << std::endl; return 0; } if (vm.count("csa-file")) filenames = vm["csa-file"].as >(); } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; throw; } if (kisen_filename != "") { std::cerr << "kisen " << kisen_filename << "\n"; KisenFile kisen_file(kisen_filename.c_str()); if (num_kisen == 0) num_kisen = kisen_file.size(); for (size_t i=0; i moves = kisen_file.moves(i); run(state, moves); } } for (size_t i=0; i moves = file.moves(); run(state, moves); } std::cerr << "\n"; show_statistics(); } CArray top_rated, active; void show(const NumEffectState& state, Move next) { static const StandardFeatureSet& feature_set = StandardFeatureSet::instance(); MoveLogProbVector moves; RatingEnv env; env.make(state); feature_set.generateLogProb(state, env, 2000, moves); const MoveLogProb *rm = moves.find(next); if (! rm) return; int index = rm - &*moves.begin(); for (size_t i=0; i= moves.size()) break; bool a = moves[i].logProb() <= (int)target_limit; active[i].add(a); if (! a) continue; bool found = index == (int)i; top_rated[i].add(found); } } void run(NumEffectState& state, const std::vector& moves) { for (size_t i=0; i= opening_skip) show(state, move); state.makeMove(move); } } void show_statistics() { for (size_t i=0; i #include #include #include #include using namespace osl; using namespace osl::rating; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-v] [-f skip] csafiles or -k kisen-filename -n num\n" << endl; exit(1); } size_t first_skip = 3; int verbose = 0; const char *kisen_filename=0; size_t num_kisen = 4000; size_t kisen_start = 200000; size_t min_rating = 1500; struct KeepMin { int min; explicit KeepMin(int initial = 10000) : min(initial) { } void add(int value) { min = std::min(value, min); } int value() const { return min; } }; struct KeepMax { int max; explicit KeepMax(int initial = -10000) : max(initial) { } void add(int value) { max = std::max(value, max); } int value() const { return max; } }; struct Histogram8 { CArray histograms; const stat::Histogram& operator[](size_t i) const { return *histograms[i]; } Histogram8(int width, int length, int start=0) { for (int i=0; i<8; ++i) histograms[i] = new stat::Histogram(width, length, start); } void add(Progress16 progress, int data, double weight = 1.0) { const int min = histograms[0]->start(); const int max = histograms[0]->start() + histograms[0]->width()*histograms[0]->length(); if (data < min || data >= max) { return; } histograms[progress.value()/2]->add(data, weight); } }; stat::Average moves, probs, order, top_score, selected_score; const int width = 4, length = 20; Histogram8 moves_histogram(width, length), selected_histogram(width, length); Histogram8 all_moves_histogram(width, length); const int sc_width = 100, sc_length = 16, sc_start = -400; stat::Histogram takeback_histogram(sc_width, sc_length, sc_start), selected_takeback(sc_width, sc_length, sc_start); stat::Histogram takeback_order(1, 10), takeback_order_all(1, 10), takeback_order_selected(1, 10); stat::Histogram seeplus_histogram(sc_width, sc_length, sc_start), selected_seeplus(sc_width, sc_length, sc_start); stat::Histogram seeplus_order(1, 10), seeplus_order_all(1, 10), seeplus_order_selected(1, 10); stat::Histogram king_escape_histogram(sc_width, sc_length, sc_start), selected_king_escape(sc_width, sc_length, sc_start); stat::Histogram kingescape_order(1, 10), kingescape_order_all(1, 10), kingescape_order_selected(1, 10); Histogram8 score_histogram(sc_width, sc_length+4, sc_start), selected_score_histogram(sc_width, sc_length+4, sc_start); Histogram8 all_score_histogram(sc_width, sc_length+4, sc_start); Histogram8 rscore_histogram(sc_width, sc_length), rselected_score_histogram(sc_width, sc_length); Histogram8 rall_score_histogram(sc_width, sc_length); KeepMin min_selected, min_top; KeepMax max_notakeback, max_nocapture; const int sc_length_2d = sc_length+2; const int sc_start_2d = -100; namespace osl { void showLogProb(const stat::Histogram& numerator, const stat::Histogram& denominator) { assert(numerator.width() == denominator.width()); assert(numerator.length() == denominator.length()); assert(numerator.start() == denominator.start()); stat::Histogram logprob(numerator.width(), numerator.length(), numerator.start()); for (size_t i=0; i= 15 ? static_cast(-100.0*log(prob)/log(2.0)) : 0; } logprob.show(std::cout); } void showLogProb(const stat::Histogram& numerator, const stat::Histogram& denom1, const stat::Histogram& denom2) { assert(numerator.width() == denom1.width()); assert(numerator.length() == denom1.length()); assert(numerator.start() == denom1.start()); assert(denom1.width() == denom2.width() && denom1.length() == denom2.length() && denom1.start() == denom2.start()); stat::Histogram l1(numerator.width(), numerator.length(), numerator.start()), l2(numerator.width(), numerator.length(), numerator.start()); for (size_t i=0; i 20 ? static_cast(-100.0*log(p1)/log(2.0)) : 0; l2.frequency(i) = d2 > 20 ? static_cast(-100.0*log(p2)/log(2.0)) : 0; } int value=l1.start(); for (size_t i=0; i 20 ? static_cast(-100.0*log(p1)/log(2.0)) : 0; const double f2 = n > 20 ? static_cast(-100.0*log(p2)/log(2.0)) : 0; std::cout << " " << std::setw(5) << f1 << " " << std::setw(4) << f2; } std::cout << "\n"; } // depth std::cout << "static const osl::CArray2d xxx_to_depth = {{\n"; for (int p=0; p<8; ++p) { std::cout << " { "; for (size_t i=0; i 20 ? static_cast(-100.0*log(p)/log(2.0)) : 0; std::cout << std::setw(4) << f << ","; if (i % 5 == 4) std::cout << " "; } std::cout << "},\n"; } std::cout << "}};\n"; // width std::cout << "static const osl::CArray2d xxx_to_width = {{\n"; for (int p=0; p<8; ++p) { std::cout << " { "; for (size_t i=0; i 20 ? static_cast(-100.0*log(p)/log(2.0)) : 0; std::cout << std::setw(4) << f << ","; if (i % 5 == 4) std::cout << " "; } std::cout << "},\n"; } std::cout << "}};\n"; } enum Property { All, /** 一手目ã®å–り返㗠*/ TakeBack, /** 2手目ã®å–り返㗠*/ TakeBack2, /** å–り返ã—ã§ãªã„先頭 */ NoTakeBack, /** å–り返ã—以外ã®é§’å¾—ã®å…ˆé ­ */ SeePlus, SeePlus2, /** 3手目ã®é§’å¾—ã¾ãŸã¯é§’得以外ã®å…ˆé ­ */ SeePlusX, /** å–り返ã—ã§ã‚‚é§’å¾—ã§ã‚‚ãªã„先頭 */ NoSeePlus }; size_t find(Property property, const NumEffectState& state, const RatingEnv& e, const RatedMoveVector& moves, Move selected) { if (moves.empty()) return 1; size_t i = 0; if (property == TakeBack || property == TakeBack2) { if (! e.history.lastMove().isNormal()) return moves.size(); for (; i 0) break; } } if (property == SeePlus2) { ++i; for (; i 0) break; } } if (property == SeePlusX) { int num_seeplus=0; for (; i 0) { if (++num_seeplus <= 1) // use 2 for 3rd see+ continue; } break; } } if (property == NoSeePlus) { for (; i 0) continue; break; } } return i; } /** カテゴリ内ã§ãƒˆãƒƒãƒ—ã®æ‰‹ãŒæŒ‡ã•れãŸç¢ºçއ */ struct TopProb { stat::Histogram selected; stat::Histogram generated, generated_all; Property property; TopProb(Property p) : selected(sc_width,sc_length+1,200), generated(sc_width,sc_length+1,200), generated_all(sc_width,sc_length+1,200), property(p) { } void add(const NumEffectState& state, const RatingEnv& e, const RatedMoveVector& moves, Move selected) { const size_t i = find(property, state, e, moves, selected); if (i >= moves.size()) return; generated_all.add(moves[i].rating()); const RatedMove *found = moves.find(selected); if (found && (found - &*moves.begin()) <= (int)i) { if (moves[i].move() == selected) this->selected.add(moves[i].rating()); generated.add(moves[i].rating()); } } void show() { showLogProb(selected, generated, generated_all); } }; /** rating ã¨ãã®å±€é¢ã®ratingã®æœ€å¤§å€¤ã¨ã®å·®ã«åŸºã¥ã 2次元ã®å®Ÿç¾ç¢ºçއ */ struct RatingDiffRange { stat::Histogram selected; stat::Histogram generated; stat::Histogram all_generated; CArray variance; size_t first, last; RatingDiffRange(size_t f, size_t l) : selected(1,sc_length_2d*sc_length_2d), generated(1,sc_length_2d*sc_length_2d), all_generated(1,sc_length_2d*sc_length_2d), first(f), last(l) { } static int index(int score, int diff) { const int score_index = std::max(0, std::min((score - sc_start_2d) / sc_width, sc_length_2d-1)); const int diff_index = std::min(diff / sc_width, sc_length_2d-1); assert(diff_index >= 0); return score_index*sc_length_2d + diff_index; } void add(const NumEffectState& state, const RatedMoveVector& moves, Move selected) { if (moves.empty() || state.inCheck()) return; const int highest = moves[0].rating(); const RatedMove *found = moves.find(selected); if (! found) return; // records may contain illegal move const size_t selected_order = found - &*moves.begin(); if (first <= selected_order && selected_order < last) { const int selected_index = index(found->rating(), highest - found->rating()); this->selected.add(selected_index); } for (size_t i=first; iindex(moves[i].rating(), highest - moves[i].rating()); all_generated.add(index); if (i <= selected_order) generated.add(index); variance[index].add(i); } } void show(std::ostream& os) { os << "depth\n"; for (int i=0; i 20 ? s/g : 0.0); os << std::setw(5) << (std::min(s,g) > 20 ? static_cast(-100.0*log(s/g)/log(2.0)) : 0); } os << "\n"; } os << "width\n"; for (int i=0; i 20 ? s/a : 0.0); os << std::setw(5) << (std::min(s,a) > 20 ? static_cast(-100.0*log(s/a)/log(2.0)) : 0); } os << "\n"; } os << "order\n"; for (int i=0; i(variance[i*sc_length_2d+j].average()); } os << "\n"; } } }; struct RatingDiff { RatingDiffRange r0, r1, r_all; RatingDiff() : r0(1,25), r1(25,800), r_all(1,800) { } void add(const NumEffectState& state, const RatedMoveVector& moves, Move selected) { #ifdef SHOW_SPLIT_RATING r0.add(state, moves, selected); r1.add(state, moves, selected); #endif r_all.add(state, moves, selected); } void show(std::ostream& os) { #if SHOW_SPLIT_RATING r0.show(os); r1.show(os); #endif r_all.show(os); } }; } RatingDiff rating_diff; TopProb top_prob(All), takeback_topprob(TakeBack), takeback2_topprob(TakeBack2), no_takeback_topprob(NoTakeBack), seeplus_topprob(SeePlus), seeplus2_topprob(SeePlus2), seeplusx_topprob(SeePlusX); CArray top_rating_progress; void test_file(const FeatureSet&, const char *filename); void test_record(const FeatureSet& f, const SimpleState& initial, const std::vector& moves); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "f:k:n:vh")) != EOF) { switch(c) { case 'f': first_skip = atoi(optarg); break; case 'k': kisen_filename = optarg; break; case 'n': num_kisen = atoi(optarg); break; case 'v': ++verbose; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (!kisen_filename && argc < 1)) usage(program_name); eval::ProgressEval::setUp(); StandardFeatureSet f; if (kisen_filename) { KisenFile kisen_file(kisen_filename); KisenIpxFile ipx(kisen_file.ipxFileName()); size_t skip = 0; for (size_t i=0; i 1) { std::cout << "top move (no takeback)\n"; no_takeback_topprob.show(); } std::cout << "top move (see+)\n"; seeplus_topprob.show(); std::cout << "top move (2nd see+)\n"; seeplus2_topprob.show(); std::cout << "top move (2nd see+ or no see+)\n"; seeplusx_topprob.show(); } std::cout << "top rating for each progress8\n"; for (size_t i=0; irating()); min_selected.add(p->rating()); if (p->rating() < -2000) { std::cerr << state << "selected " << *p << "\n" << moves; } for (int i=0; i& moves) { NumEffectState state(initial); RatingEnv env; env.make(state); eval::ProgressEval eval(state); for (size_t i=0; i= first_skip) { test_position(f, moves[i], (i>0 ? moves[i-1] : Move::PASS(alt(moves[i].player()))), env, state, eval); } state.makeMove(move); eval.update(state, move); env.update(state, move); } } void test_file(const FeatureSet& f, const char *filename) { RecordMinimal record; try { record = CsaFileMinimal(filename).load(); } catch (CsaIOError& e) { std::cerr << "skip " << filename <<"\n"; std::cerr << e.what() << "\n"; return; } catch (...) { throw; } test_record(f, record.initialState(), record.moves); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/checkmate/0000755000000000000000000000000012320177344015650 5ustar rootrootlibosl-0.8.0.orig/sample/checkmate/fixed-checkmate.cc0000644000000000000000000000432312316770314021203 0ustar rootroot#include "osl/checkmate/fixedDepthSearcher.h" #include "osl/csa.h" #include "osl/misc/perfmon.h" #include #include #include #include #include using namespace osl; using namespace osl::checkmate; using namespace osl::misc; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-d depth] csa-filenames " << endl << endl; exit(1); } bool verbose=false; int num_checkmate=0, num_escape=0, num_unkown=0; void search(int depth, const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; int depth=2; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "d:vh")) != EOF) { switch(c) { case 'd': depth = atoi(optarg); break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); std::cerr << "depth " << depth << "\n"; try { for (int i=0; i #include #include #include #include #include namespace po = boost::program_options; size_t max_nodes, min_nodes, filenumber; bool search_proof; void run(const std::string& filename); int main(int argc, char **argv) { po::options_description options("options"); options.add_options() ("help", "produce help message") ("maximum-nodes,M", po::value(&max_nodes)->default_value(80000), "search proof/disproof positions within this limit") ("min-nodes,m", po::value(&min_nodes)->default_value(8000), "ignore positions proven/disproven by search with less than this limit") ("proof,p", po::value(&search_proof)->default_value(1), "search proof/disproof problems") ("file-number,n", po::value(&filenumber)->default_value(1), "start number of filenames for generated problems") ; po::options_description hidden("Hidden options"); hidden.add_options() ("target-file", po::value >()); po::options_description command_line_options; command_line_options.add(options).add(hidden); po::options_description visible_options("All options"); visible_options.add(options); po::positional_options_description p; p.add("target-file", -1); po::variables_map vm; std::vector filenames; try { po::store(po::command_line_parser(argc, argv). options(command_line_options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] files" << std::endl; std::cout << visible_options << std::endl; return 0; } filenames = vm["target-file"].as >(); } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] files" << std::endl; std::cerr << visible_options << std::endl; return 1; } boost::progress_display progress(filenames.size()); for (const std::string& filename: filenames) { run(filename); ++progress; } } using namespace osl; std::string write_file(const NumEffectState& state, Move move, size_t count) { std::ostringstream ss; ss << std::setw(4) << std::setfill('0') << filenumber++ << ".csa"; std::ofstream os(ss.str().c_str()); os << state; if (search_proof) os << csa::show(move) << "\n"; os << "' " << count << " nodes\n"; return ss.str(); } bool find_problem(DualDfpn& dfpn, NumEffectState& state) { HashKey key(state); PathEncoding path(state.turn()); Move win_move; const size_t before = dfpn.totalNodeCount(); ProofDisproof pdp = dfpn.findProof(max_nodes, state, key, path, win_move); const size_t after = dfpn.totalNodeCount(); if ((search_proof && !pdp.isCheckmateSuccess()) || (!search_proof && !pdp.isCheckmateFail()) || after-before < min_nodes) return false; write_file(state, win_move, after-before); return true; } void run(const std::string& filename) { CsaFileMinimal file(filename); const auto moves=file.moves(); NumEffectState state; DualDfpn dfpn; size_t moved = 0; for (Move move: moves) { state.makeMove(move); if (++moved < 50 || state.inCheck()) continue; if (search_proof) { MoveVector legal_moves; state.generateLegal(legal_moves); std::random_shuffle(legal_moves.begin(), legal_moves.end()); for (Move a: legal_moves) { NumEffectState copy(state); copy.makeMove(a); if (copy.inCheck()) continue; copy.makeMove(Move::PASS(copy.turn())); if (find_problem(dfpn, copy)) return; } } else { DualDfpn dfpn; if (find_problem(dfpn, state)) return; } } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/checkmate/dfpnstat.cc0000644000000000000000000002014112320177344020000 0ustar rootroot#include "osl/checkmate/dfpn.h" #include "osl/checkmate/dfpnParallel.h" #include "osl/csa.h" #include "osl/misc/perfmon.h" #include "osl/misc/milliSeconds.h" #include "osl/checkmate/dfpnRecord.h" #include "osl/hash/hashRandomPair.h" #include "osl/oslConfig.h" #include #include #include #include #include #include #include using namespace osl; using namespace osl::checkmate; using namespace osl::misc; unsigned int dovetailing_seed = 0; unsigned int dovetailing_prob = 0; bool verbose=false; unsigned long long total_cycles=0; bool show_escape_filename = false; bool force_attack = false; int num_checkmate=0, num_nocheckmate=0, num_escape=0, num_unkown=0; double total_nodes=0, total_tables=0; int limit = 100000; bool blocking_verify = true; size_t table_growth_limit = 8000000; bool debug = false; int forward_moves = 0; template void search(DfpnSearch&, const char *filename); void usage(const char *program_name) { std::cerr << "usage: " << program_name << " [-d] [-v] [-f] [-l limit] [-N] csa-files\n"; } int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; int parallel = 0; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "dfl:N:F:s:p:t:vh")) != EOF) { switch(c) { case 's': dovetailing_seed = static_cast(atoi(optarg)); break; case 'p': dovetailing_prob = static_cast(atoi(optarg)); break; case 'd': debug = true; break; case 'f': force_attack = true; break; case 'F': forward_moves = atoi(optarg); break; case 'l': limit = atoi(optarg); break; case 'N': parallel = atoi(optarg); break; case 't': table_growth_limit = atoi(optarg); break; #if 0 case 'V': blocking_verify = false; break; #endif case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) { usage(program_name); return 1; } osl::OslConfig::setUp(); OslConfig::setDfpnMaxDepth(1600); // sufficient for microcosmos if (dovetailing_prob > 0) HashRandomPair::setUp(dovetailing_seed, dovetailing_prob); try { for (int i=0; i void analyzeCheckmate(DfpnSearch& searcher, const NumEffectState& state, Move checkmate_move) { NumEffectState new_state = state; std::cerr << state << " " << checkmate_move << "\n"; new_state.makeMove(checkmate_move); HashKey key(new_state); const DfpnTable& table = searcher.currentTable(); DfpnRecordBase record = table.probe(key, PieceStand(WHITE, new_state)); std::cerr << record.proof_disproof << " " << std::bitset<64>(record.solved) << "\n"; MoveVector moves; new_state.generateLegal(moves); for (size_t i=0; i(new_state, false, Square(), moves); else Dfpn::generateEscape(new_state, false, Square(), moves); std::cerr << "Escape " << moves.size()<< "\n"; moves.clear(); if (state.turn() == BLACK) Dfpn::generateEscape(new_state, true, Square(), moves); else Dfpn::generateEscape(new_state, true, Square(), moves); std::cerr << "Escape full " << moves.size() << "\n"; } } template void testWinOrLose(const char *filename, DfpnSearch& searcher, const SimpleState& sstate, int limit, ProofDisproof& result, Move& best_move, const std::vector& moves) { const Player P = sstate.turn(); NumEffectState state(sstate); const PathEncoding path(state.turn()); const Square my_king = state.kingSquare(P); if ((! force_attack) && ! my_king.isPieceStand() && state.inCheck(P)) { // 相手ã‹ã‚‰çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ã‚‹ time_point timer = clock::now(); misc::PerfMon clock; result = searcher.hasEscapeMove(state, HashKey(state), path, limit, Move::PASS(alt(P))); total_cycles += clock.stop(); real_seconds = elapsedSeconds(timer); if (verbose) std::cerr << result << "\n"; if (result.isCheckmateSuccess()) { ++num_checkmate; } else { if (result.isCheckmateFail()) ++num_escape; else { assert(! result.isFinal()); ++num_unkown; } } return; } Move checkmate_move; std::vector pv; time_point timer = clock::now(); PerfMon clock; result = searcher. hasCheckmateMove(state, HashKey(state), path, limit, checkmate_move, Move(), &pv); total_cycles += clock.stop(); real_seconds = elapsedSeconds(timer); if (verbose) std::cerr << result << "\n"; if (result.isCheckmateSuccess()) { ++num_checkmate; best_move = checkmate_move; if (verbose) { std::cerr << checkmate_move << "\n"; for (size_t i=0; i void search(DfpnSearch& searcher, const char *filename) { NumEffectState state; std::vector moves; try { CsaFileMinimal file(filename); state = file.initialState(); moves = file.moves(); int forward_here = std::min(forward_moves, (int)moves.size()); for (int i=0; i #include #include #include #include using namespace osl; using namespace osl::checkmate; using namespace osl::misc; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-d depth] csa-filenames " << endl << endl; exit(1); } bool verbose=false; int num_checkmate=0, num_escape=0, num_unkown=0; void search(int depth, const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; int depth=2; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "d:vh")) != EOF) { switch(c) { case 'd': depth = atoi(optarg); break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); std::cerr << "depth " << depth << "\n"; try { for (int i=0; i #include using namespace osl; Square target(5,8); int main(int argc, char **argv) { // const char *program_name = argv[0]; bool error_flag = false; bool verbose = false; // extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "vh")) != EOF) { switch(c) { case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) return 1; nice(20); //次㫠CSAãƒ•ã‚¡ã‚¤ãƒ«ã‚’å‡¦ç† for (int i=0; i void * * Set up the OSL library. This should be called once in a program. */ extern "C" VALUE osl4r_setup(VALUE self) { osl::eval::ml::OpenMidEndingEval::setUp(); osl::progress::ml::NewProgress::setUp(); osl::rating::StandardFeatureSet::instance(); return self; } /** * call-seq: * OSL::checkmate_attack(state = :str, limit = :int) => [win = :bool, limit = :int, move = :str] * * Check if an attacking player can checkmate an opponent. * Returns [true, limit, best_move] if an attacking player is in winning; [false, nil, nil] otherwise. */ extern "C" VALUE osl4r_checkmate_attack(VALUE self, VALUE v_state, VALUE v_limit) { const char *state = StringValuePtr(v_state); int limit = NUM2INT(v_limit); char move[32]; // output memset(&move, 0, sizeof(move)); const int win = checkmate_attack(state, limit, move); if (win) { VALUE best_move = rb_str_new2(move); return rb_ary_new3(3, Qtrue, INT2NUM(limit), best_move); } else { return rb_ary_new3(3, Qfalse, Qnil, Qnil); } } /** * call-seq: * OSL::checkmate_escape(state = :str, limit = :int) => bool * * Check if an escaping player is checkmated. * Returns true if checkmated; false otherwise. */ extern "C" VALUE osl4r_checkmate_escape(VALUE self, VALUE v_state, VALUE v_limit) { const char *state = StringValuePtr(v_state); const int limit = NUM2INT(v_limit); const int escape = checkmate_escape(state, limit); return (escape ? Qtrue : Qfalse); } /** * call-seq: * OSL::search(state = :str, seconds = :int, verbose = :bool) => [eval = :int, move = :str] * * Search a state within seconds, then return an array of an evaluation * value and best move. */ extern "C" VALUE osl4r_search(VALUE self, VALUE v_state, VALUE v_seconds, VALUE v_verbose) { const char *state = StringValuePtr(v_state); const int seconds = NUM2INT(v_seconds); const bool verbose = (Qtrue == v_verbose); char move[32]; // output memset(&move, 0, sizeof(move)); const int eval = search(state, seconds, verbose, move); VALUE best_move = rb_str_new2(move); return rb_ary_new3(2, INT2NUM(eval), best_move); } extern "C" void Init_osl4r (void) { /* ------ module OSL ------ */ rb_cOSL4R = rb_define_class("OSL", rb_cObject); rb_define_module_function(rb_cOSL4R, "setup", reinterpret_cast(osl4r_setup), 0); rb_define_module_function(rb_cOSL4R, "search", reinterpret_cast(osl4r_search), 3); rb_define_module_function(rb_cOSL4R, "checkmate_is_winning", reinterpret_cast(osl4r_checkmate_attack), 2); rb_define_module_function(rb_cOSL4R, "checkmate_is_losing", reinterpret_cast(osl4r_checkmate_escape), 2); #if 0 /* utilities */ rb_define_module_function(rb_cUUID4R, "uuid_v1", uuid4r_uuid_v1, -1); rb_define_module_function(rb_cUUID4R, "uuid_v3", uuid4r_uuid_v3, -1); rb_define_module_function(rb_cUUID4R, "uuid_v4", uuid4r_uuid_v4, -1); rb_define_module_function(rb_cUUID4R, "uuid_v5", uuid4r_uuid_v5, -1); rb_define_module_function(rb_cUUID4R, "import", uuid4r_import, 2); /* ------ UUID4RCommon ------ */ rb_cUUID4RCommon = rb_define_class_under(rb_cUUID4R, "UUID4RCommon", rb_cObject); rb_define_alloc_func(rb_cUUID4RCommon, uuid4r_alloc); rb_define_method(rb_cUUID4RCommon, "export", uuid4r_export, -1); rb_define_method(rb_cUUID4RCommon, "compare", uuid4r_compare, 1); rb_define_alias(rb_cUUID4RCommon, "<=>", "compare"); /* ------ UUID4Rv1 ------ */ rb_cUUID4Rv1 = rb_define_class_under(rb_cUUID4R, "UUID4Rv1", rb_cUUID4RCommon); rb_define_alloc_func(rb_cUUID4Rv1, uuid4r_alloc); rb_define_method(rb_cUUID4Rv1, "initialize", uuid4rv1_initialize, 0); /* ------ UUID4Rv3 ------ */ rb_cUUID4Rv3 = rb_define_class_under(rb_cUUID4R, "UUID4Rv3", rb_cUUID4RCommon); rb_define_alloc_func(rb_cUUID4Rv3, uuid4r_alloc); rb_define_method(rb_cUUID4Rv3, "initialize", uuid4rv3_initialize, 2); /* ------ UUID4Rv4 ------ */ rb_cUUID4Rv4 = rb_define_class_under(rb_cUUID4R, "UUID4Rv4", rb_cUUID4RCommon); rb_define_alloc_func(rb_cUUID4Rv4, uuid4r_alloc); rb_define_method(rb_cUUID4Rv4, "initialize", uuid4rv4_initialize, 0); /* ------ UUID4Rv5 ------ */ rb_cUUID4Rv5 = rb_define_class_under(rb_cUUID4R, "UUID4Rv5", rb_cUUID4RCommon); rb_define_alloc_func(rb_cUUID4Rv5, uuid4r_alloc); rb_define_method(rb_cUUID4Rv5, "initialize", uuid4rv5_initialize, 2); #endif } libosl-0.8.0.orig/sample/osl4r/test/0000755000000000000000000000000011355550661015752 5ustar rootrootlibosl-0.8.0.orig/sample/osl4r/test/tc_all.rb0000644000000000000000000000021611355550661017534 0ustar rootroot$:.unshift File.dirname(__FILE__) $osl_test_long = (!ENV['OSL_TEST_LONG'].nil?) require 'tc_osl' require 'tc_benchmark' if $osl_test_long libosl-0.8.0.orig/sample/osl4r/test/tc_benchmark.rb0000644000000000000000000000120411355550661020714 0ustar rootroot$:.unshift File.join(File.dirname(__FILE__), "..", "ext") require 'test/unit' require 'osl4r.so' class OSLTest < Test::Unit::TestCase def initialize(a) super OSL::setup end def test_osl_search_benchmark val, move = OSL::search(<<-EOF, 30, true); P1-KY-KE * * * * * -KE-OU P2 * * * +UM-KY-GI * -GI-KY P3 * * * * * -FU * * * P4 * * -FU-FU-FU * * * -FU P5-FU+KE * +FU * * * * * P6 * * * * * +FU+FU * +FU P7+FU+FU * * +KI * +KE+FU * P8 * * * * +FU * +GI+OU * P9-RY-HI * * * +KI * * +KY P+00KA00KI00KI00FU00FU P-00GI00FU00FU + EOF assert(val > 0) assert_equal(move, "+0039KI") end end libosl-0.8.0.orig/sample/osl4r/test/tc_osl.rb0000644000000000000000000000333211355550661017563 0ustar rootroot$:.unshift File.join(File.dirname(__FILE__), "..", "ext") require 'test/unit' require 'osl4r.so' HIRATE = <<-EOF P1-KY-KE-GI-KI-OU-KI-GI-KE-KY P2 * -HI * * * * * -KA * P3-FU-FU-FU-FU-FU-FU-FU-FU-FU P4 * * * * * * * * * P5 * * * * * * * * * P6 * * * * * * * * * P7+FU+FU+FU+FU+FU+FU+FU+FU+FU P8 * +KA * * * * * +HI * P9+KY+KE+GI+KI+OU+KI+GI+KE+KY P+ P- EOF class OSLTest < Test::Unit::TestCase def initialize(a) super OSL::setup end def setup end def test_osl_search val, move = OSL::search(HIRATE, 1, false); assert(val > 0) assert(/\+\d\d\d\dFU/ =~ move) end def test_checkmate_is_losing_true ret = OSL::checkmate_is_losing(<<-EOF, 1); P1 * * * * * * -OU * * P2 * -HI * * * * +GI * * P3 * * * * * +TO+TO * * P4 * * * * * * * * * P5 * * * * * * * * * P6 * * * * * * * * * P7 * * * * * * * * * P8 * * * * * * * * * P9 * * * * * +OU * * * P+ P-00AL - EOF assert(ret) end def test_checkmate_is_losing_false ret = OSL::checkmate_is_losing(HIRATE, 1); assert(!ret) end def test_checkmate_is_winning_true ret, val, move = OSL::checkmate_is_winning(<<-EOF, 1); P1 * * * * * * -OU * * P2 * -HI * * * * * * * P3 * * * * * +TO+TO * * P4 * * * * * * * * * P5 * * * * * * * * * P6 * * * * * * * * * P7 * * * * * * * * * P8 * * * * * * * * * P9 * * * * * +OU * * * P+00GI P-00AL + EOF assert(ret) assert_equal(move, "+0032GI") end def test_checkmate_is_winning_false ret, val, move = OSL::checkmate_is_winning(HIRATE, 1); assert(!ret) assert_equal(val, nil) assert_equal(move, nil) end end libosl-0.8.0.orig/sample/osl4r/README0000644000000000000000000000024311355550661015652 0ustar rootrootOSL4R ===== This is a Ruby extention library for OSL How To Build ============ % cd ext % ruby extconf.rb % make % make check % make check-all % make install libosl-0.8.0.orig/sample/learn/0000755000000000000000000000000012316770314015026 5ustar rootrootlibosl-0.8.0.orig/sample/learn/learn-piece.cc0000644000000000000000000001165512316770314017531 0ustar rootroot/* learn-piece.cc */ #include "osl/numEffectState.h" #include "osl/record/csaRecord.h" #include "osl/record/ki2.h" #include "osl/record/kakinoki.h" #include "osl/record/kisen.h" #include "osl/eval/see.h" #include #include using namespace osl; using namespace std; CArray weight, gradient; void show() { for (size_t i=0; i copy; for (int i=0; i > gradient_ptype; for (size_t i=0; i& out) { out.fill(0); for (int i=0; i c0, c1, diff; count(selected, c0); count(not_selected, c1); int evaldiff = 0; for (int i=0; i 0) return; for (int i=0; i& moves) { NumEffectState state; for (size_t i=0; i #include using namespace osl; using namespace std; void run(const std::vector& moves) { NumEffectState state; for (size_t i=0; i using namespace osl; int main(int argc, char **argv) { std::string filename(argv[1]); NumEffectState state=CsaFile(filename).getInitialState(); HashKey key(state); key.dumpContents(std::cerr); std::cerr << std::endl; } libosl-0.8.0.orig/sample/debug/printPtypeO.cc0000644000000000000000000000061212316770314017616 0ustar rootroot/* printPtypeO.cc */ #include "osl/basic_type.h" #include using namespace osl; int main() { long ptypeo; while (std::cin >> ptypeo) { PtypeO p = static_cast(ptypeo); std::cout << p << std::endl; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/debug/printPdp.cc0000644000000000000000000000200710153342653017117 0ustar rootroot/* printPdp.cc */ #include "osl/checkmate/proofDisproof.h" #include using namespace osl; using namespace osl::checkmate; int main() { std::cout << "Checkmate " << ProofDisproof::Checkmate() .ulonglongValue() << "\n"; std::cout << "NoEscape " << ProofDisproof::NoEscape() .ulonglongValue() << "\n"; std::cout << "NoCheckmate " << ProofDisproof::NoCheckmate() .ulonglongValue() << "\n"; std::cout << "LoopDetection " << ProofDisproof::LoopDetection().ulonglongValue() << "\n"; std::cout << "PawnCheckmate " << ProofDisproof::PawnCheckmate().ulonglongValue() << "\n"; std::cout << "ProofLimit " << ProofDisproof::PROOF_LIMIT << "\n"; std::cout << "DisproofLimit " << ProofDisproof::DISPROOF_LIMIT << "\n"; unsigned long long pdp; while (std::cin >> pdp) { std::cout << ProofDisproof::makeDirect(pdp) << "\n"; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/debug/printPosition.cc0000644000000000000000000000072512316770314020207 0ustar rootroot/* printPiece.cc */ #include "osl/basic_type.h" #include using namespace osl; int main() { unsigned long position; while (std::cin >> position) { Square p = Square::makeDirect(position); std::cout << p.x() << " " << p.y() << " " << std::boolalpha << p.isOnBoard() << std::endl; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/debug/printPiece.cc0000644000000000000000000000060212316770314017422 0ustar rootroot/* printPiece.cc */ #include "osl/basic_type.h" #include using namespace osl; int main() { int piece; while (std::cin >> piece) { Piece p = Piece::makeDirect(piece); std::cout << p << std::endl; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/debug/printMove.cc0000644000000000000000000000120512316770314017303 0ustar rootroot/* printMove.cc */ #include "osl/basic_type.h" #include "osl/csa.h" #include bool csa_mode = false; using namespace osl; void show(int move) { Move m = Move::makeDirect(move); if (csa_mode) std::cout << csa::show(m) << std::endl; else std::cout << m << std::endl; } int main() { long long move; while (std::cin >> move) { int imove = move; if (imove == move) { show(imove); } else { std::cerr << (int)imove << "\n"; show(imove); std::cerr << (int)(move>>32) << "\n"; show(move >> 32); } } } /* ------------------------------------------------------------------------- */ libosl-0.8.0.orig/sample/sort.cc0000644000000000000000000000247112316770314015227 0ustar rootroot/* * */ #include "osl/search/sortCaptureMoves.h" #include "osl/numEffectState.h" #include "osl/move_generator/allMoves.h" #include "osl/effect_util/effectUtil.h" #include "osl/record/csaRecord.h" #include #include #include #include using namespace osl; int main(int argc, char **argv) { // const char *program_name = argv[0]; bool error_flag = false; bool verbose = false; // const char *kisenFilename = 0; // extern char *optarg; extern int optind; char c; // size_t num_records = 1; while ((c = getopt(argc, argv, "vh")) != EOF) { switch(c) { case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) return 1; try { nice(20); // size_t record_processed = 0; for (int i=0; i #include #include namespace po = boost::program_options; using namespace osl; void run(const NumEffectState& initial, const std::vector& moves) { game_playing::GameState state(initial); for (size_t i=0; i(&kisen_filename), "kisen filename") ("csa-file", po::value >()) ("help", "produce help message") ; po::positional_options_description p; p.add("csa-file", -1); po::variables_map vm; std::vector filenames; try { po::store(po::command_line_parser(argc, argv). options(options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cout << options << std::endl; return 0; } if (vm.count("csa-file")) filenames = vm["csa-file"].as >(); } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; return 1; } if (kisen_filename != "") { KisenFile kisen(kisen_filename); for (size_t i=0; i #include #include namespace po = boost::program_options; using namespace osl; int count = 0; bool run(const NumEffectState& initial, const std::vector& moves) { NumEffectState state(initial); for (size_t i=0; i(&kisen_filename), "kisen filename") ("csa-file", po::value >()) ("help", "produce help message") ; po::positional_options_description p; p.add("csa-file", -1); po::variables_map vm; std::vector filenames; try { po::store(po::command_line_parser(argc, argv). options(options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cout << options << std::endl; return 0; } if (vm.count("csa-file")) filenames = vm["csa-file"].as >(); } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; return 1; } if (kisen_filename != "") { KisenFile kisen(kisen_filename); for (size_t i=0; i #include #include #include #include bool real_value = false, binary_to_text = false; template void to_binary() { std::vector data; T value; while (std::cin >> value) { data.push_back(value); assert(value == data.back()); } osl::misc::BinaryWriter::write(std::cout, data); } template void write_line(T value) { std::cout << value << std::endl; } void write_line(double value) { printf("%.8f\n", value); } template void to_text() { std::vector data; osl::misc::BinaryReader reader(std::cin); while (reader.read(data)) { for (T value: data) { write_line(value); } if (data.size() < reader.blockSize()) break; } } int main(int argc, char **argv) { extern int optind; bool error_flag = false; char c; while ((c = getopt(argc, argv, "rth")) != EOF) { switch(c) { case 'r': real_value = true; break; case 't': binary_to_text = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) { std::cerr << "unknown option\n"; return 1; } if (binary_to_text) { if (real_value) to_text(); else to_text(); } else { if (real_value) to_binary(); else to_binary(); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/misc/showMemory.cc0000644000000000000000000000127711216661055017346 0ustar rootroot#include "osl/oslConfig.h" #include int main(int /*argc*/, char ** /*argv*/) { osl::OslConfig oslConfig; std::cout << "Memory Use Limit: " << oslConfig.memoryUseLimit() << "\n"; std::cout << "Resident Memory Use: " << oslConfig.residentMemoryUse() << "\n"; const int MAX = 10000000; // 10M std::cout << "new int[" << MAX << "]\n"; int *large_space = new int[MAX]; std::cout << "Resident Memory Use: " << oslConfig.residentMemoryUse() << "\n"; std::cout << "Delete it\n"; delete[] large_space; std::cout << "Resident Memory Use: " << oslConfig.residentMemoryUse() << "\n"; return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/misc/showCores.cc0000644000000000000000000000037412316770314017147 0ustar rootroot#include #include int main(int /*argc*/, char ** /*argv*/) { std::cout << "Cores: " << std::thread::hardware_concurrency() << std::endl; return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/Makefile0000644000000000000000000000644012443721750015372 0ustar rootrootOSL_HOME = .. -include makefile.local -include $(OSL_HOME)/makefile.local include $(OSL_HOME)/makefile.conf LDFLAGS += -L../full/osl -L../std/osl -L../core/osl LOADLIBES += -losl_full -losl_std -losl_core $(BOOST_LIBS) -lboost_regex -lboost_program_options $(LDLIBS) INCLUDES += -I$(OSL_HOME)/full -I$(OSL_HOME)/std -I$(OSL_HOME)/core PERFORMANCE_SRCS = isCheckPerf.cc \ pin_perf.cc \ progress_perf.cc rating-perf.cc see-perf.cc simpleMovePerf.cc # commented out because their compilation take very long time: checkMovePerf.cc fixedDepthSearchPerf.cc EVAL_SRCS = show-state.cc show-progresseval.cc show-eval.cc \ openmidending-stat.cc PPAIR_SRCS = pairdiff.cc pairedit.cc pairstat.cc DEBUG_SRCS = printPdp.cc printPosition.cc printMove.cc printPiece.cc \ printPtypeO.cc OPENING_SRCS = convert.cc showOpening.cc opening-validator.cc openingStatistics.cc \ compare-book.cc show-moves.cc RATING_SRCS = ratingstat.cc probability.cc topn.cc CHECKMATE_SRCS = dfpnstat.cc fixed-checkmate.cc make-problems.cc RECORD_SRCS = check-kisen.cc show-ipx.cc all-states.cc bad-moves.cc \ show-ki2.cc show-ipx-result.cc csa-to-kisen.cc kisen-to-csa.cc \ count-win-loss.cc win-rate-openingbook-weight-level.cc \ all-states2.cc find-states.cc check-ki2.cc showRecord.cc \ kakinoki-to-csa.cc csa-to-kifu.cc kifu-to-myshogi.cc showRecord.cc \ last-position.cc unique-csa.cc first-search-eval.cc \ csajapanize.cc MISC_SRCS = showCores.cc showMemory.cc convert.cc LEARN_SRCS = show-sibling.cc learn-piece.cc BOARD_SRCS = random_play.cc search1_play.cc legal_moves.cc \ show_repetition.cc show-effect.cc \ progress/show-state.cc progress/progress.cc\ $(patsubst %.cc,eval/%.cc,$(EVAL_SRCS)) \ $(patsubst %.cc,eval/ppair/%.cc,$(PPAIR_SRCS)) \ $(patsubst %.cc,record/%.cc,$(RECORD_SRCS)) \ $(patsubst %.cc,misc/%.cc,$(MISC_SRCS)) SEARCH_SRCS = sort.cc pass.cc \ find-losing-moves.cc find-uplevel-king.cc find-almost-entering.cc \ quiescence/quiescencestat.cc quiescence/range-vs-nodes.cc \ quiescence/quiescence2stat.cc \ $(patsubst %.cc,checkmate/%.cc,$(CHECKMATE_SRCS)) \ $(patsubst %.cc,debug/%.cc,$(DEBUG_SRCS)) \ $(patsubst %.cc,opening/%.cc,$(OPENING_SRCS)) \ $(patsubst %.cc,rating/%.cc,$(RATING_SRCS)) \ annotate/annotate.cc \ $(patsubst %.cc,performance/%.cc,$(PERFORMANCE_SRCS)) \ $(patsubst %.cc,learn/%.cc,$(LEARN_SRCS)) \ record/checkmate-kisen.cc BOARD_PROGRAMS = $(BOARD_SRCS:.cc=) SEARCH_PROGRAMS = $(SEARCH_SRCS:.cc=) PROGRAMS = $(BOARD_PROGRAMS) $(SEARCH_PROGRAMS) CC = $(CXX) all: $(BOARD_PROGRAMS) $(SEARCH_PROGRAMS) $(PROGRAMS): $(FILE_OSL_ALL) # CC, LDFLAGS, LOADLIBES を定義ã—ã¦ãŠã㨠# %.o ã‹ã‚‰ % ã‚’å‹æ‰‹ã«ä½œã£ã¦ãれるã®ã§ # 特別ãªã‚‚ã®ä»¥å¤–ã¯æ›¸ãå¿…è¦ãŒãªã„ opening/convert: opening/convert.o opening/openingBookConverter.o opening/openingBookConverter.o: opening/openingBookConverter.cc opening/openingBookConverter.h checkmate/dfpnstatone-static: checkmate/dfpnstatone.cc checkmate/dfpnstat.cc $(CXX) -o $@ $(CXXFLAGS) $(OSL_HOME_FLAGS) $(LDFLAGS) $< $(LDLIBS) $(FILE_TCMALLOC) $(LOADLIBES) clean: rm -f core *.o */*.o $(PROGRAMS) nohup.out *~ distclean: clean rm -f *~ -include $(patsubst %.cc,.deps/%.cc.d,$(BOARD_SRCS)) -include $(patsubst %.cc,.deps/%.cc.d,$(SEARCH_SRCS)) # hash-dump.cc # fixed-checkmate2.cclibosl-0.8.0.orig/sample/performance/0000755000000000000000000000000012316770314016226 5ustar rootrootlibosl-0.8.0.orig/sample/performance/pin_perf.cc0000644000000000000000000000603712316770314020345 0ustar rootroot/* pin_perf.cc */ #include "osl/effect_util/pin.h" #include "osl/csa.h" #include "osl/record/csaRecord.h" #include "osl/misc/perfmon.h" #include #include using namespace osl; using namespace osl::effect_util; void usage(const char *program_name) { std::cerr << program_name << " csafiles\n"; exit(1); } size_t skip_first = 0; void run(const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "s:vh")) != EOF) { switch(c) { case 's': skip_first = atoi(optarg); break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); try { for (int i=0; i= skip_first) { misc::PerfMon clock; const PieceMask black_pins = Pin::make(state, BLACK); const PieceMask white_pins = Pin::make(state, WHITE); total_cycles += clock.stop(); clock.restart(); const PieceMask black_pins_naive = Pin::makeNaive(state, BLACK); const PieceMask white_pins_naive = Pin::makeNaive(state, WHITE); total_cycles_naive += clock.stop(); clock.restart(); const PieceMask black_pins_step = Pin::makeStep(state, state.kingSquare(),BLACK); const PieceMask white_pins_step = Pin::makeStep(state, state.kingSquare(),WHITE); total_cycles_step += clock.stop(); clock.restart(); const PieceMask black_pins_step1 = Pin::makeStep1(state, state.kingSquare(),BLACK); const PieceMask white_pins_step1 = Pin::makeStep1(state, state.kingSquare(),WHITE); total_cycles_step1 += clock.stop(); ++positions; } if (i >= moves.size()) break; const Move move = moves[i++]; state.makeMove(move); } std::cerr << "p " << total_cycles << " / " << positions << " = " << total_cycles/(double)positions << "\n"; std::cerr << "n " << total_cycles_naive << " / " << positions << " = " << total_cycles_naive/(double)positions << "\n"; std::cerr << "n " << total_cycles_step << " / " << positions << " = " << total_cycles_step/(double)positions << "\n"; std::cerr << "n " << total_cycles_step1 << " / " << positions << " = " << total_cycles_step1/(double)positions << "\n"; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/performance/checkMovePerf.cc0000644000000000000000000001527112316770314021264 0ustar rootroot/** * è©°å°†æ£‹ã®æŒ‡æ‰‹ç”Ÿæˆã®é€Ÿã•を見る */ #include "osl/csa.h" #define NO_SAFE_MOVE_ACTION_IN_LIBOSL #define SIMPLE_STATE_ONLY #include "osl/move_generator/addEffect_.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/move_generator/escape_.h" #ifdef NO_SAFE_MOVE_ACTION_IN_LIBOSL # include "osl/move_generator/open.tcc" # include "osl/move_generator/allMoves.tcc" # include "osl/move_generator/escape_.tcc" # include "osl/move_generator/capture_.tcc" # include "osl/move_generator/addEffect_.tcc" # include "osl/move_generator/addEffectWithEffect.tcc" #endif #ifndef SIMPLE_STATE_ONLY # include "osl/boardBitEffect.h" # include "osl/evalHashEffectState.h" # include "osl/numEffectState.h" #endif #include "osl/applyMove.h" #include "osl/move_action/store.h" #include "osl/move_action/safeFilter.h" #include "osl/perfmon.h" #include #include using namespace osl; using namespace osl::move_generator; using namespace osl::move_action; int moveCount; int maxLevel; template void nextMoves(State& state,int level,Move lastMove); template struct DoUndoHelper { State& state; int level; Move move; DoUndoHelper(State& s, int level) : state(s), level(level), move(MOVE_INVALID){} void operator()(Square p) { assert(move!=MOVE_INVALID); nextMoves(state,level,move); } }; template void nextMoves(State& state,int level,Move lastMove) { typedef typename State::effect_state_t effect_t; if (level>maxLevel) return; MoveVector moves; typedef DoUndoHelper::opponent,!isAttack,withEffect> helper_t; helper_t helper(state, level+1); { Store store(moves); if (isAttack) { typedef SafeFilter action_t; action_t safeAction(state,store); const Square opKingSquare =state.template kingSquare::opponent>(); #if 1 if (state.hasEffectAt(P,opKingSquare)) // 逃ã’る手ã«ãªã£ã¦ã„ãªã„ return; // è©° #else assert(!state.hasEffectAt(P,opKingSquare)); #endif if(withEffect) AddEffectWithEffect:: generateMoves(P,(effect_t)state,opKingSquare,safeAction); #if 1 else AddEffect:: generateMoves(P,state,opKingSquare,safeAction); #endif } else { assert(!state.hasEffectAt(P,state.template kingSquare::opponent>())); Escape:: generateKingEscape((effect_t)state, lastMove,store); } } size_t size=moves.size(); for(size_t i=0;i::doUndoMove(state,moves[i],helper); } } int main(int argc,char **argv){ bool effectMode=false; bool hashMode=false; bool evalMode=false; bool nullMode=false; bool withEffectMode=false; bool simpleMode=false; bool boardBitMode=false; int level=3; extern char *optarg; char c; while ((c = getopt(argc, argv, "l:dehEnwsb")) != EOF) { switch(c) { case 'l': level=atoi(optarg); break; case 'e': effectMode=true; break; case 'h': hashMode=true; break; case 'E': evalMode=true; break; case 'n': nullMode=true; break; case 'w': withEffectMode=true; break; case 's': simpleMode=true; break; case 'b': boardBitMode=true; break; default: std::cerr << "unknown option\n"; return 1; } } SimpleState state=CsaString( "P1-KY * * * -KY * -FU-KE * \n" "P2 * * * * -OU * * * * \n" "P3 * * * -FU-FU+RY * * -KY\n" "P4-FU * * -GI * * * * * \n" "P5 * * * * * * * * * \n" "P6+FU * * +RY * * +FU * * \n" "P7 * +FU * +FU+FU+FU * * * \n" "P8 * * +OU * -TO * * * * \n" "P9+KY * * * * * * +KE * \n" "P+00KI00GI00GI00GI00KE00KE00FU00FU00FU00KI\n" "P-00KA00KA00KI00FU00FU00FU00FU00KI\n" "-\n").getInitialState(); maxLevel=level; moveCount=0; clock_start(); #ifndef SIMPLE_STATE_ONLY if(evalMode) { std::cerr << "evalMode" << std::endl; NumEffectState neState(state); HashEffectState hState(neState); EvalHashEffectState eState(hState); Move lastMove=newMove(newSquare(4,4),newSquare(4,3),PROOK, PTYPE_EMPTY,false,BLACK); if(withEffectMode) nextMoves(eState,0,lastMove); else nextMoves(eState,0,lastMove); } else if(hashMode) { std::cerr << "hashMode" << std::endl; NumEffectState neState(state); HashEffectState hState(neState); Move lastMove=newMove(newSquare(4,4),newSquare(4,3),PROOK, PTYPE_EMPTY,false,BLACK); if(withEffectMode) nextMoves(hState,0,lastMove); else nextMoves(hState,0,lastMove); } else if(effectMode); { assert(effectMode); std::cerr << "effectMode" << std::endl; NumEffectState neState(state); Move lastMove=newMove(newSquare(4,4),newSquare(4,3),PROOK, PTYPE_EMPTY,false,BLACK); if(withEffectMode) nextMoves(neState,0,lastMove); else nextMoves(neState,0,lastMove); } #if 0 else if(boardBitMode){ std::cerr << "boardBitEffectMode" << std::endl; typedef BoardBitEffect effect_state_t; effect_state_t neState(state); Move lastMove=newMove(newSquare(4,4),newSquare(4,3),PROOK, PTYPE_EMPTY,false,BLACK); nextMoves(neState,0,lastMove); } #endif #if 0 else if(nullMode){ std::cerr << "nullBoardEffectMode" << std::endl; typedef NullBoardEffect effect_state_t; effect_state_t neState(state); Move lastMove=newMove(newSquare(4,4),newSquare(4,3),PROOK, PTYPE_EMPTY,false,BLACK); nextMoves(neState,0,lastMove); } #endif else #else /* SIMPLE_STATE_ONLY */ if(simpleMode){ std::cerr << "nullBoardEffectMode" << std::endl; typedef SimpleState effect_state_t; effect_state_t neState(state); Move lastMove=newMove(newSquare(4,4),newSquare(4,3),PROOK, PTYPE_EMPTY,false,BLACK); nextMoves(neState,0,lastMove); } #endif clock_stop("total", moveCount+1); std::cerr << "maxLevel=" << maxLevel << ",moveCount=" << moveCount << std::endl; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/performance/fixedDepthSearchPerf.cc0000644000000000000000000000206612316770314022570 0ustar rootroot#include "osl/csa.h" #include "osl/checkmate/fixedDepthSearcher.tcc" #include "osl/state/numEffectState.h" #include "osl/misc/perfmon.h" #include #include #include using namespace osl; using namespace osl::checkmate; int main() { SimpleState state=CsaString( "P1-KY * * * -KY * -FU-KE * \n" "P2 * * * * -OU * * * * \n" "P3 * * * -FU-FU * * * -KY\n" "P4-FU * * -GI * * * * * \n" "P5 * * * * * * * * * \n" "P6+FU * * +RY * +HI+FU * * \n" "P7 * +FU * +FU+FU+FU * * * \n" "P8 * * +OU * -TO * * * * \n" "P9+KY * * * * * * +KE * \n" "P+00KI00GI00GI00GI00KE00KE00FU00FU00FU00KI\n" "P-00KA00KA00KI00FU00FU00FU00FU00KI\n" "+\n").getInitialState(); NumEffectState eState(state); ProofDisproof pdp; osl::misc::PerfMon perfmon; FixedDepthSearcher searcher(eState); perfmon.restart(); searcher.setCount(0); for(int i=0;i<1000;i++) { Move dummy; pdp=searcher.hasCheckmateMove(1,dummy); } perfmon.stop("total", searcher.getCount()); std::cerr << pdp << std::endl; return 0; } libosl-0.8.0.orig/sample/performance/progress_perf.cc0000644000000000000000000000357112316770314021423 0ustar rootroot/* progress_perf.cc */ #include "osl/progress/effect5x3.h" #include "osl/progress/effect5x3d.h" #include "osl/csa.h" #include "osl/record/csaRecord.h" #include "osl/misc/perfmon.h" #include #include using namespace osl; void usage(const char *program_name) { std::cerr << program_name << " csafiles\n"; exit(1); } size_t skip_first = 0; void run(const char *filename); void finish(); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "s:vh")) != EOF) { switch(c) { case 's': skip_first = atoi(optarg); break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); try { for (int i=0; i= moves.size()) break; const Move move = moves[i++]; state.makeMove(move); if (i >= skip_first) { misc::PerfMon clock; progress.update(state, move); total_cycles += clock.stop(); ++positions; } } } void finish() { std::cerr << "p " << total_cycles << " / " << positions << " = " << total_cycles/(double)positions << "\n"; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/performance/simpleMovePerf.cc0000644000000000000000000001625312316770314021501 0ustar rootroot/** * 以å‰ï¼Œã‚²ãƒ¼ãƒ æƒ…報学研究会ã§ç™ºè¡¨ã—ãŸä¾‹é¡Œã‚’高速ã«å®Ÿè¡Œã§ãã‚‹ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯ * ãªãŠï¼Œä»¥å‰ã¯ * maxLevel=3,moveCount=444378267,dropCount=357602901,sec=11.630000,count/s=38209653.224420 * ã¨ã„ã†çµæžœã ã£ãŸï¼Ž */ #include "osl/csa.h" #include "osl/numEffectState.h" #ifdef MORE_STATE # include "osl/boardBitEffect.h" # include "osl/signatureEffect.h" #endif #ifdef PPAIR_PERF # include "osl/piecePairEval.h" # include "osl/pieceEval.h" #endif #include "osl/move_generator/allMoves.h" #include "osl/move_generator/allMoves.tcc" #include "osl/move_generator/move_action.h" #include "osl/misc/perfmon.h" #include #include #include #include using namespace osl; int moveCount; int dropCount; int maxLevel; int maxVal=0; #ifdef PPAIR_PERF bool noPair = false; bool piecePair = false; int value; #endif template void nextMoves(State& state,int level); template struct DoUndoHelper{ State& state; int level; DoUndoHelper(State& s, int level) : state(s), level(level){} void operator()(Square p){ nextMoves(state,level); } }; template void callValWithMove(State& state,Move move,Int2Type){ } template void callValWithMove(State& state,Move move,Int2Type){ typename State::eval_t ev = state.getEval(); const int ret = ev.template computeValWithMove(state, move); if(ret>maxVal){maxVal=ret;} } template void nextMoves(State& state,int level){ if(level>maxLevel) return; MoveVector moves; DoUndoHelper helper(state, level+1); GenerateAllMoves::generate(P,state,moves); size_t size=moves.size(); for(size_t i=0;i(state,moves[i],Int2Type()); moveCount++; #ifdef PPAIR_PERF const int prevValue = value; if (noPair) value += PieceEval::diffWithMove(state, moves[i]); else if (piecePair) value += PiecePairEval::diffWithMove(state, moves[i]); #endif state.makeUnmakeMove(Player2Type

(),moves[i],helper); #ifdef PPAIR_PERF value = prevValue; #endif } } #ifdef ENABLE_DIRECT_MODE template void nextMovesDirect(State& state,int level); template struct CallNextMoves{ State& state; int level; CallNextMoves(State& s, int level) : state(s), level(level){} void operator()(Square p){ nextMovesDirect(state,level); } }; template struct DirectCallAction{ State& state; int level; DirectCallAction(State& s, int level) : state(s), level(level){} typedef CallNextMoves::opponent,isMoveEval> next_t; void receiveSimpleMove(Square from,Square to,Ptype ptype, bool isPromote,Player p){ moveCount++; next_t caller(state,level); ApplyDoUndoSimpleMove::template doUndoSimpleMove (state,from,to,promoteMask(isPromote),caller); } void receiveUnknownMove(Square from,Square to,Piece p1,Ptype ptype,bool isPromote,Player p){ next_t caller(state,level); moveCount++; if(p1==PIECE_EMPTY) ApplyDoUndoSimpleMove::template doUndoSimpleMove (state,from,to,promoteMask(isPromote),caller); else ApplyDoUndoCaptureMove::template doUndoCaptureMove (state,from,to,p1,promoteMask(isPromote),caller); } void receiveDropMove(Square to,Ptype ptype,Player p){ moveCount++; next_t caller(state, level); ApplyDoUndoDropMove::template doUndoDropMove(state,to,ptype,caller); } }; template void nextMovesDirect(State& state,int level){ if(level>maxLevel) return; DirectCallAction action(state, level+1); typedef move_generator::AllMoves > generate_t; generate_t::template generateMoves

(state,action); } #endif /* ENABLE_DIRECT_MODE */ int main(int argc,char **argv){ bool directMode=false; bool effectMode=false; bool hashMode=false; bool boardBitMode=false; bool signatureMode=false; int level=3; extern char *optarg; char c; while ((c = getopt(argc, argv, "l:dehpPbS")) != EOF) { switch(c) { case 'l': level=atoi(optarg); break; case 'd': directMode=true; break; case 'e': effectMode=true; break; case 'h': hashMode=true; break; case 'b': boardBitMode=true; break; case 'S': signatureMode=true; break; #ifdef PPAIR_PERF case 'p': noPair=true; break; case 'P': piecePair=true; break; #endif default: std::cerr << "unknown option\n"; return 1; } } SimpleState state=CsaString( "P1+RY * * * * * * -KE-KY\n" "P2 * * * +GI * -KI-KI-OU *\n" "P3 * * +TO * * * -GI-FU-FU\n" "P4-FU * -UM * -FU * -FU * *\n" "P5 * * +GI * * -FU * +FU+FU\n" "P6+FU+OU+GI+FU+FU * +FU * *\n" "P7 * +FU * +KE * * * * *\n" "P8 * * * * * * * * * \n" "P9-RY * * * * * * * +KY\n" "P+00KA00KY00FU00FU00FU00FU\n" "P-00KI00KI00KE00KE00KY\n" "+\n").initialState(); maxLevel=level; moveCount=0; dropCount=0; misc::PerfMon timer; if(effectMode){ std::cerr << "effectMode" << std::endl; NumEffectState neState(state); if(directMode){ std::cerr << "directMode" << std::endl; #ifdef ENABLE_DIRECT_MODE nextMovesDirect(neState,0); #endif } else{ nextMoves(neState,0); } } else #ifdef MORE_STATE #ifndef PPAIR_PERF if(signatureMode){ std::cerr << "signatureMode" << std::endl; SimpleState sState(state); typedef SignatureEffect > state_t; state_t bState(sState); if(directMode){ std::cerr << "directMode" << std::endl; #ifdef ENABLE_DIRECT_MODE nextMovesDirect(bState,0); #endif } else{ nextMoves(bState,0); } } else if(boardBitMode){ std::cerr << "boardBitMode" << std::endl; SimpleState sState(state); typedef BoardBitEffect state_t; state_t bState(sState); if(directMode){ std::cerr << "directMode" << std::endl; #ifdef ENABLE_DIRECT_MODE nextMovesDirect(bState,0); #endif } else{ nextMoves(bState,0); } } else #endif /* ifndef PPAIR_PERF */ if(simpleMode){ std::cerr << "simpleMode" << std::endl; SimpleState sState(state); if(directMode){ std::cerr << "directMode" << std::endl; #ifdef ENABLE_DIRECT_MODE nextMovesDirect(sState,0); #endif } else{ nextMoves(sState,0); } } else #endif /* MORE_STATE */ { } timer.stop("total", moveCount+1); std::cerr << "maxLevel=" << maxLevel << ",moveCount=" << moveCount << ",dropCount=" << dropCount << std::endl; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/performance/see-perf.cc0000644000000000000000000000545212316770314020251 0ustar rootroot#include "osl/eval/see.h" #include "osl/eval/pieceEval.h" #include "osl/effect_util/pin.h" #include "osl/record/csaRecord.h" #include "osl/stat/average.h" #include "osl/misc/perfmon.h" #include #include #include #include #include #include using namespace osl; /** * @file * see付加ã®é€Ÿåº¦ã‚’測る */ void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-v] [-f skip] [-o] csafiles\n" << endl; exit(1); } size_t first_skip = 0; bool verbose = false; bool old = false; stat::Average moves, cycles, cycles_per_move; void test_file(const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "f:ovh")) != EOF) { switch(c) { case 'f': first_skip = atoi(optarg); break; case 'v': verbose = true; break; case 'o': old = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); for (int i=0; i= first_skip) { test_position(state); } state.makeMove(move); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/performance/rating-perf.cc0000644000000000000000000000732212316770314020757 0ustar rootroot#include "osl/rating/featureSet.h" #include "osl/rating/ratingEnv.h" #include "osl/eval/progressEval.h" #include "osl/effect_util/sendOffSquare.h" #include "osl/effect_util/effectUtil.h" #include "osl/record/csaRecord.h" #include "osl/stat/average.h" #include "osl/misc/perfmon.h" #include #include #include #include #include #include using namespace osl; using namespace osl::rating; /** * @file * rating付加ã®é€Ÿåº¦ã‚’測る */ void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-v] [-f skip] csafiles\n" << endl; exit(1); } size_t first_skip = 0; bool verbose = false; stat::Average moves, cycles, cycles_per_move, probs, order, top_score, selected_score; int min_selected = 1000; void test_file(const FeatureSet&, const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "f:vh")) != EOF) { switch(c) { case 'f': first_skip = atoi(optarg); break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); eval::ProgressEval::setUp(); StandardFeatureSet f; for (int i=0; irating() < min_selected) min_selected = p->rating(); if (p->rating() < -2000) { std::cerr << state << "selected " << *p << "\n" << my_moves; } } else { ::order.add(count); } moves.add(count); cycles.add(consumed); cycles_per_move.add(consumed/count); ++num_positions; } void test_file(const FeatureSet& f, const char *filename) { RecordMinimal record; try { record = CsaFileMinimal(filename).load(); } catch (CsaIOError& e) { std::cerr << "skip " << filename <<"\n"; std::cerr << e.what() << "\n"; return; } catch (...) { throw; } NumEffectState state(record.initialState()); const auto& moves=record.moves; RatingEnv env; env.make(state); for (size_t i=0; i= first_skip) { test_position(f, moves[i], (i>0 ? moves[i-1] : Move::PASS(alt(moves[i].player()))), env, state); } state.makeMove(move); env.update(state, move); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/performance/isCheckPerf.cc0000644000000000000000000000301312316770314020720 0ustar rootroot/** * 王手判定ã®é€Ÿã•を見る */ #include "osl/numEffectState.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/move_action.h" #include "osl/move_classifier/check_.h" #include "osl/csa.h" #include "osl/misc/perfmon.h" #include #include using namespace osl; int main(int argc,char **argv) { // extern char *optarg; char c; while ((c = getopt(argc, argv, "vh")) != EOF) { switch(c) { default: std::cerr << "unknown option\n"; return 1; } } NumEffectState state((CsaString( "P1-KY * * * -KY * -FU-KE * \n" "P2 * * * * -OU * * * * \n" "P3 * * * -FU-FU+RY * * -KY\n" "P4-FU * * -GI * * * * * \n" "P5 * * * * * * * * * \n" "P6+FU * * +RY * * +FU * * \n" "P7 * +FU * +FU+FU+FU * * * \n" "P8 * * +OU * -TO * * * * \n" "P9+KY * * * * * * +KE * \n" "P+00KI00GI00GI00GI00KE00KE00FU00FU00FU00KI\n" "P-00KA00KA00KI00FU00FU00FU00FU00KI\n" "-\n").initialState())); MoveVector moves; GenerateAllMoves::generate(state.turn(),state,moves); int count = 0; misc::PerfMon clock; for (size_t i=0; i::isMember (state, moves[i].ptype(), moves[i].from(), moves[i].to())) ++count; } clock.stop("total", moves.size()); std::cerr << "checks " << count << " / " << moves.size() << "\n"; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/sample/eval/0000755000000000000000000000000012316770314014654 5ustar rootrootlibosl-0.8.0.orig/sample/eval/show-state.cc0000644000000000000000000000615112316770314017264 0ustar rootroot/* show-state.cc */ #include "osl/eval/ppair/piecePairPieceEval.h" #include "osl/eval/ppair/piecePairRawEval.h" #include "osl/eval/endgame/attackDefense.h" #include "osl/eval/endgame/attackKing.h" #include "osl/eval/endgame/defenseKing.h" #include "osl/eval/endgame/kingPieceValues.h" #include "osl/eval/progressEval.h" #include "osl/container/pieceValues.h" #include "osl/record/csaRecord.h" #include "osl/oslConfig.h" #include #include #include #include #include #include using namespace osl; using namespace osl::eval; using namespace osl::eval::endgame; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-a] [-t raw|piece|attack|defense|endgame|progress] [-f pair-file-name] csa-filename" << endl; exit(1); } void show(const char *filename, const std::string&); bool show_all_states = false; int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; std::string table_filename = OslConfig::home() + "/data/sibling-attack.pair"; std::string eval_type = "piece"; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "at:f:vh")) != EOF) { switch(c) { case 'a': show_all_states = true; break; case 'f': table_filename = optarg; break; case 't': eval_type = optarg; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); PiecePairPieceTable::Table.setUp(table_filename.c_str()); for (int i=0; i::setValues(state, values); else if (eval_type == "defense") KingPieceValues::setValues(state, values); else if (eval_type == "piece") PiecePairPieceEval::setValues(state, values); else if (eval_type == "raw") PiecePairRawEval::setValues(state, values); else throw std::runtime_error("unknown function type "+eval_type); values.showValues(std::cout, state); } void show(const char *filename, const std::string& eval_type) { CsaFile file(filename); const auto moves = file.load().moves(); NumEffectState state(file.initialState()); for (unsigned int i=0; i #include #include #include #include using namespace osl; using namespace osl::eval; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-f pair-file-name] [-P player(0 for black, 1 for white)] [-p position(e.g. 11)] [-t ptype(e.g. 7 for PROOK)]" << endl << "if any of -Ppt options are specified, relation of [,] will be shown \n" << "otherwise, relation of [,] will be shown \n" << endl; exit(1); } void showPieceStat(Player, Ptype); void showPairStat(Player, Square, Ptype); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; const char *pairFileName = 0; int ptype = PROOK; Square pos(1,1); Player player = BLACK; int singleStateMode = true; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "f:p:P:t:vh")) != EOF) { switch(c) { case 'f': pairFileName = optarg; break; case 'p': pos = Square(atoi(optarg)/10, atoi(optarg)%10); singleStateMode = false; break; case 'P': player = (atoi(optarg) ? WHITE : BLACK); singleStateMode = false; break; case 't': ptype = atoi(optarg); singleStateMode = false; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (! pairFileName)) usage(program_name); PiecePairRawEval::setUp(pairFileName); if (singleStateMode) { for (int i=PPAWN; i<=PTYPE_MAX; ++i) { showPieceStat(BLACK,static_cast(i)); showPieceStat(WHITE,static_cast(i)); } } else showPairStat(player,pos,static_cast(ptype)); } void showPieceStat(Player player, Ptype ptype) { const PtypeO ptypeo = newPtypeO(player, ptype); // single [piece,position] std::cout << player << ", " << ptype << "\n"; for (int y=1; y<=9; ++y) { for (int x=9; x>=1; --x) { const Square pos1(x,y); const unsigned int index1 = PiecePairIndex::indexOf(pos1,ptypeo); std::cout << std::setw(4) << PiecePairRawTable::Table.valueOf(index1,index1); } std::cout << "\n"; } const Square pos1 = Square::STAND(); const unsigned int index1 = PiecePairIndex::indexOf(pos1,ptypeo); std::cout << pos1 << " " << std::setw(4) << PiecePairRawTable::Table.valueOf(index1,index1); std::cout << "\n"; } void showPairStatAgainst(Player player2, Ptype ptype2, unsigned int index1) { const PtypeO ptypeo2 = newPtypeO(player2, ptype2); for (int y=1; y<=9; ++y) { for (int x=9; x>=1; --x) { const Square pos2(x,y); const unsigned int index2 = PiecePairIndex::indexOf(pos2,ptypeo2); std::cout << std::setw(4) << PiecePairRawTable::Table.valueOf(index1,index2); } std::cout << "\n"; } const Square pos2 = Square::STAND(); const unsigned int index2 = PiecePairIndex::indexOf(pos2,ptypeo2); std::cout << pos2 << " " << std::setw(4) << PiecePairRawTable::Table.valueOf(index1,index2); std::cout << "\n"; } void showPairStat(Player player, Square pos1, Ptype ptype1) { const PtypeO ptypeo1 = newPtypeO(player, ptype1); std::cout << player << ", " << pos1 << ", " << ptype1 << "\n"; const unsigned int index1 = PiecePairIndex::indexOf(pos1,ptypeo1); for (int p2=PPAWN; p2<=PTYPE_MAX; ++p2) { Ptype ptype2 = static_cast(p2); std::cout << player << ptype2 << " (<=> " << player << ptype1 << ", " << pos1 << ")\n"; showPairStatAgainst(player, ptype2, index1); std::cout << alt(player) << ptype2 << " (<=> " << player << ptype1 << ", " << pos1 << ")\n"; showPairStatAgainst(alt(player), ptype2, index1); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/eval/ppair/pairdiff.cc0000644000000000000000000000371212316770314020065 0ustar rootroot/* pairdiff.cc */ #include "osl/eval/ppair/piecePairRawEval.h" #include "osl/csa.h" #include #include #include #include // 二ã¤ã®ãƒ†ãƒ¼ãƒ–ルã®å·®ã‚’表示 using namespace osl; using namespace osl::eval; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " table1 table2" << endl; exit(1); } void show(std::ostream& os, Square pos, PtypeO ptypeo) { os << csa::show(pos) << " "; os << getOwner(ptypeo); os << csa::show(getPtype(ptypeo)); } int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; const char *filename1 = 0; const char *filename2 = 0; // extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "vh")) != EOF) { switch(c) { default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 2)) usage(program_name); filename1 = argv[0]; filename2 = argv[1]; std::unique_ptr table1(new PiecePairRawTable()); table1->loadFromBinaryFile(filename1); std::unique_ptr table2(new PiecePairRawTable()); table2->loadFromBinaryFile(filename2); for (unsigned int i=0; ivalue(i); const int val2 = table2->value(i); if (val1 != val2) { size_t i1, i2; PiecePairRawTable::meltIndex(i, i1, i2); Square pos1, pos2; PtypeO ptypeo1, ptypeo2; PiecePairRawTable::meltIndex(i1, pos1, ptypeo1); PiecePairRawTable::meltIndex(i2, pos2, ptypeo2); show(std::cout, pos1, ptypeo1); std::cout << " "; show(std::cout, pos2, ptypeo2); std::cout << " : " << val1 << " != " << val2 << "\n"; } } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/sample/eval/ppair/pairedit.cc0000644000000000000000000005352212316770314020106 0ustar rootroot/* pairedit.cc */ #include "osl/eval/ppair/piecePairRawEval.h" #include #include #include #include #include /** * @file * PiecePairEvalTable ã«äººç‚ºçš„ã«æ‰‹ã‚’加ãˆã‚‹ * * 試ã—ã«ï¼Œçމã®å‘¨ã‚Š5x5 端ã§ã¯4x4 ã«ã„る敵ã®é§’ã‚’+100ã—ã¦ã¿ã‚‹ * 歩桂香ã¯çŽ‰ã‚ˆã‚Šä¸‹ã§ã¯åŠ ç‚¹ã—ãªã„,代ã‚りã«ä¸Šã‚’å»¶ã°ã™ * 下ã«ã„る金ã¯åŠåˆ†? * 頂点ã¯åŠåˆ†? * * å‚考 * http://www32.ocn.ne.jp/~yss/book.html#SEC3 * æ¡‚ã€é¦™ã®é§’ã¯çމãŒå®Ÿéš›ã®ä½ç½®ã‚ˆã‚Šã‚‚ã‚‚ã†ï¼‘段上ã«ã„ã‚‹ã¨ã—ã¦è¨ˆç®—ã—ã¦ã„る(桂香ã§ã¯æ•µçމã‹ã‚‰ï¼“æ®µä¸ŠãŒæœ€å¤§ã¨ãªã‚‹ï¼‰ */ using namespace osl; using namespace osl::eval; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-f read-pair-file-name] [-o write-pair-file-name] " << endl; exit(1); } bool verbose = false; void adjust(PiecePairRawTable& table, Square pos1, PtypeO ptypeo1, Square pos2, PtypeO ptypeo2, int value) { assert(pos1.isOnBoard()); assert(pos2.isOnBoard()); const unsigned int index1 = table.indexOf(pos1, ptypeo1); const unsigned int index2 = table.indexOf(pos2, ptypeo2); int val = table.valueOf(index1, index2); assert(val == table.valueOf(index2, index1)); if (verbose) std::cerr << pos1 << ptypeo1 << " " << pos2 << ptypeo2 << " " << val << " => "; val += value; val = std::min(127, val); val = std::max(-127, val); if (verbose) std::cerr << val << "\n"; table.valueOf(index1, index2) = val; table.valueOf(index2, index1) = val; } void adjustKingBonus(PiecePairRawTable& table, Square pos1, PtypeO ptypeo1, // king Square pos2, PtypeO ptypeo2, // attacker int bonus) { assert(getPtype(ptypeo1) == KING); assert(getPtype(ptypeo2) != KING); assert(getOwner(ptypeo1) != getOwner(ptypeo2)); assert((bonus > 0) ^ (getOwner(ptypeo1) == BLACK)); adjust(table, pos1, ptypeo1, pos2, ptypeo2, bonus); } /** king: white, attacker: black*/ void adjustDual(PiecePairRawTable& table, Square king, Square attacker, Ptype attackerType, int blackAttackBonus, int whiteAttackBonus) { adjustKingBonus(table, king.rotate180(), newPtypeO(BLACK, KING), attacker.rotate180(), newPtypeO(WHITE, attackerType), whiteAttackBonus); adjustKingBonus(table, king, newPtypeO(WHITE, KING), attacker, newPtypeO(BLACK, attackerType), blackAttackBonus); } void adjustDual(PiecePairRawTable& table, Square black, Ptype black_ptype, Square white, Ptype white_ptype, int value) { adjust(table, black, newPtypeO(BLACK, black_ptype), white, newPtypeO(WHITE, white_ptype), value); adjust(table, black.rotate180(), newPtypeO(WHITE, black_ptype), white.rotate180(), newPtypeO(BLACK, white_ptype), -value); } void addValue(Player player, PiecePairRawTable& table, Square pos1, Ptype ptype1, Square pos2, Ptype ptype2, int bonus) { const PtypeO ptypeo1 = newPtypeO(player, ptype1); const PtypeO ptypeo2 = newPtypeO(player, ptype2); adjust(table, pos1, ptypeo1, pos2, ptypeo2, bonus); } void addPenalty(Player player, PiecePairRawTable& table, Square pos1, Ptype ptype1, Square pos2, Ptype ptype2, int bonus) { assert(eval::betterThan(player, 0, bonus)); addValue(player, table, pos1, ptype1, pos2, ptype2, bonus); } void addBonus(Player player, PiecePairRawTable& table, Square pos1, Ptype ptype1, Square pos2, Ptype ptype2, int bonus) { assert(eval::betterThan(player, bonus, 0)); addValue(player, table, pos1, ptype1, pos2, ptype2, bonus); } void addPenaltyDual(PiecePairRawTable& table, Square pos1, Ptype ptype1, Square pos2, Ptype ptype2, int black_bonus) { assert(black_bonus < 0); addPenalty(BLACK, table, pos1, ptype1, pos2, ptype2, black_bonus); addPenalty(WHITE, table, pos1, ptype1, pos2, ptype2, -black_bonus); } void addSelfPenaltyDual(PiecePairRawTable& table, Square pos, Ptype ptype, int black_bonus) { addPenaltyDual(table, pos, ptype, pos, ptype, black_bonus); } int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; const char *read_pairfilename = 0; const char *write_pairfilename = 0; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "f:o:vh")) != EOF) { switch(c) { case 'f': read_pairfilename = optarg; break; case 'o': write_pairfilename = optarg; break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (! read_pairfilename) || (! write_pairfilename)) usage(program_name); std::unique_ptr table(new PiecePairRawTable); table->loadFromBinaryFile(read_pairfilename); // 通常ã®5x5ã®ç¯„囲 CArray2d adjusted; adjusted.fill(false); for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king(king_x,king_y); for (int attacker_x = ((king_x==9) ? king_x-3 : king_x-2); attacker_x <= ((king_x==1) ? king_x+3 : king_x+2); ++attacker_x) { if ((attacker_x < 1) || (attacker_x > 9)) continue; for (int attacker_y = ((king_y==9) ? king_y-3 : king_y-2); attacker_y <= ((king_y==1) ? king_y+3 : king_y+2); ++attacker_y) { if ((attacker_y < 1) || (attacker_y > 9)) continue; const Square attacker(attacker_x,attacker_y); if (king == attacker) continue; adjusted[king.index()][attacker.index()] = true; adjustDual(*table, king, attacker, PPAWN, 100, -100); adjustDual(*table, king, attacker, PLANCE, 100, -100); adjustDual(*table, king, attacker, PKNIGHT, 100, -100); adjustDual(*table, king, attacker, PBISHOP, 100, -100); adjustDual(*table, king, attacker, PROOK, 100, -100); adjustDual(*table, king, attacker, SILVER, 100, -100); adjustDual(*table, king, attacker, BISHOP, 100, -100); adjustDual(*table, king, attacker, ROOK, 100, -100); // é‡‘ã¨æˆéŠ€ã¯1段目以外 if (attacker_y != 1) { const int bonus = (attacker_y >= king_y) ? 100 : 50; adjustKingBonus(*table, king, newPtypeO(WHITE, KING), attacker, newPtypeO(BLACK, PSILVER), bonus); adjustKingBonus(*table, king, newPtypeO(WHITE, KING), attacker, newPtypeO(BLACK, GOLD), bonus); } if (attacker_y != 9) { const int bonus = (attacker_y <= king_y) ? -100 : -50; adjustKingBonus(*table, king, newPtypeO(BLACK, KING), attacker, newPtypeO(WHITE, PSILVER), bonus); adjustKingBonus(*table, king, newPtypeO(BLACK, KING), attacker, newPtypeO(WHITE, GOLD), bonus); } // æ­©ã¯çŽ‹ã¨åŒåˆ—ã‹ã‚ˆã‚Šæ‰‹å‰ if (attacker_y >= king_y) { adjustKingBonus(*table, king, newPtypeO(WHITE, KING), attacker, newPtypeO(BLACK, PAWN), 100); } if (attacker_y <= king_y) { adjustKingBonus(*table, king, newPtypeO(BLACK, KING), attacker, newPtypeO(WHITE, PAWN), -100); } } // attacker_y // 桂香ã¯é•·ç›®ã«ã¨ã‚‹ for (int attacker_y = ((king_y==9) ? king_y-4 : king_y-3); attacker_y <= ((king_y==1) ? king_y+4 : king_y+3); ++attacker_y) { if ((attacker_y < 1) || (attacker_y > 9)) continue; const Square attacker(attacker_x,attacker_y); if (king == attacker) continue; // 王より手å‰, 25,45,65,85 ã¯å¼Šå®³ãŒå¤§ãã„ã®ã§é™¤ã if (! ((attacker_y == 5) && ((attacker_x == 2) || (attacker_x == 4) || (attacker_x == 6) || (attacker_x == 8)))) { if ((attacker_y > king_y) && (attacker_y > 2)) { adjustKingBonus(*table, king, newPtypeO(WHITE, KING), attacker, newPtypeO(BLACK, LANCE), 100); adjustKingBonus(*table, king, newPtypeO(WHITE, KING), attacker, newPtypeO(BLACK, KNIGHT), 100); } if ((attacker_y < king_y) && (attacker_y < 8)) { adjustKingBonus(*table, king, newPtypeO(BLACK, KING), attacker, newPtypeO(WHITE, LANCE), -100); adjustKingBonus(*table, king, newPtypeO(BLACK, KING), attacker, newPtypeO(WHITE, KNIGHT), -100); } } } // attacker_y, knight, lance } // attacker_x } // king_y } // king_x // 5x5ã®ç¯„囲外ã®è£œæ­£ x+1 for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=3; ++king_y) { const Square king(king_x,king_y); for (int rook_x=1; rook_x<=9; ++rook_x) { for (int rook_y=king_y-1; rook_y<=king_y+1; ++rook_y) { if ((rook_y < 1) || (rook_y > 9)) continue; const Square rook(rook_x, rook_y); if (king == rook) continue; if (! adjusted[king.index()][rook.index()]) { adjustDual(*table, king, rook, ROOK, 30, -30); adjustDual(*table, king, rook, PROOK, 30, -30); } } } for (int attacker_x = ((king_x==9) ? king_x-4 : king_x-3); attacker_x <= ((king_x==1) ? king_x+4 : king_x+3); ++attacker_x) { if ((attacker_x < 1) || (attacker_x > 9)) continue; for (int attacker_y = king_y; attacker_y <= ((king_y==1) ? king_y+3 : king_y+2); ++attacker_y) { if ((attacker_y < 1) || (attacker_y > 9)) continue; const Square attacker(attacker_x,attacker_y); if (king == attacker) continue; if (adjusted[king.index()][attacker.index()]) continue; adjusted[king.index()][attacker.index()] = true; adjustDual(*table, king, attacker, PPAWN, 40, -40); adjustDual(*table, king, attacker, PLANCE, 40, -40); adjustDual(*table, king, attacker, PKNIGHT, 40, -40); adjustDual(*table, king, attacker, SILVER, 40, -40); } } } } // x+2 for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=3; ++king_y) { const Square king(king_x,king_y); for (int attacker_x = ((king_x==9) ? king_x-5 : king_x-4); attacker_x <= ((king_x==1) ? king_x+5 : king_x+4); ++attacker_x) { if ((attacker_x < 1) || (attacker_x > 9)) continue; for (int attacker_y = king_y+1; attacker_y <= ((king_y==1) ? king_y+3 : king_y+2); ++attacker_y) { if ((attacker_y < 1) || (attacker_y > 9)) continue; const Square attacker(attacker_x,attacker_y); if (king == attacker) continue; if (adjusted[king.index()][attacker.index()]) continue; adjustDual(*table, king, attacker, PPAWN, 10, -10); adjustDual(*table, king, attacker, PLANCE, 10, -10); adjustDual(*table, king, attacker, PKNIGHT, 10, -10); adjustDual(*table, king, attacker, SILVER, 10, -10); } } } } for (int attacker_x=1; attacker_x<=9; ++attacker_x) { for (int attacker_y=1; attacker_y<=9; ++attacker_y) { const Square attacker(attacker_x,attacker_y); // 端ã®é§’ã¯è‰²ã€…減点 if ((attacker_x == 1) || (attacker_x == 9)) { addSelfPenaltyDual(*table, attacker, KNIGHT, -100); addSelfPenaltyDual(*table, attacker, SILVER, -100); addSelfPenaltyDual(*table, attacker, GOLD , -100); addSelfPenaltyDual(*table, attacker, PPAWN , -100); addSelfPenaltyDual(*table, attacker, PLANCE, -100); addSelfPenaltyDual(*table, attacker, PKNIGHT, -100); addSelfPenaltyDual(*table, attacker, PSILVER, -100); } } } // æŒãã«ãã„銀 addPenalty(BLACK, *table, Square(2,6), SILVER, Square(3,7), KNIGHT, -80); addPenalty(WHITE, *table, Square(8,4), SILVER, Square(7,3), KNIGHT, +80); addPenalty(BLACK, *table, Square(2,6), SILVER, Square(1,5), PAWN, -80); addPenalty(WHITE, *table, Square(8,4), SILVER, Square(9,5), PAWN, +80); addPenalty(BLACK, *table, Square(9,7), SILVER, Square(8,8), BISHOP, -80); addPenalty(BLACK, *table, Square(1,7), SILVER, Square(2,8), BISHOP, -80); addPenalty(WHITE, *table, Square(9,3), SILVER, Square(8,2), BISHOP, +80); addPenalty(WHITE, *table, Square(1,3), SILVER, Square(2,2), BISHOP, +80); // 穴熊関係 addPenalty(BLACK, *table, Square(9,9), KING, Square(7,7), KNIGHT, -120); addPenalty(BLACK, *table, Square(9,9), KING, Square(9,7), KNIGHT, -120); addPenalty(BLACK, *table, Square(1,9), KING, Square(3,7), KNIGHT, -120); addPenalty(BLACK, *table, Square(1,9), KING, Square(1,7), KNIGHT, -120); addPenalty(WHITE, *table, Square(9,1), KING, Square(7,3), KNIGHT, +120); addPenalty(WHITE, *table, Square(9,1), KING, Square(9,3), KNIGHT, +120); addPenalty(WHITE, *table, Square(1,1), KING, Square(3,3), KNIGHT, +120); addPenalty(WHITE, *table, Square(1,1), KING, Square(1,3), KNIGHT, +120); // 玉ã®ç‚¹æ•°ã‚’引ã„ã¦ãŠã,桂香ãŒã‚れã°å¾©æ´»ã•ã›ã‚‹ addPenalty(BLACK, *table, Square(9,9), KING, Square(9,9), KING, -120); addBonus(BLACK, *table, Square(9,9), KING, Square(9,8), LANCE, 40); addBonus(BLACK, *table, Square(9,9), KING, Square(8,9), KNIGHT, 80); addPenalty(BLACK, *table, Square(1,9), KING, Square(1,9), KING, -120); addBonus(BLACK, *table, Square(1,9), KING, Square(1,8), LANCE, 40); addBonus(BLACK, *table, Square(1,9), KING, Square(2,9), KNIGHT, 80); addPenalty(WHITE, *table, Square(9,1), KING, Square(9,1), KING, +120); addBonus(WHITE, *table, Square(9,1), KING, Square(9,2), LANCE, -40); addBonus(WHITE, *table, Square(9,1), KING, Square(8,1), KNIGHT, -80); addPenalty(WHITE, *table, Square(1,1), KING, Square(1,1), KING, +120); addBonus(WHITE, *table, Square(1,1), KING, Square(1,2), LANCE, -40); addBonus(WHITE, *table, Square(1,1), KING, Square(2,1), KNIGHT, -80); // 5æ®µç›®ã®æ¡‚馬 (å–られãã†) for (int x=2; x<=8; ++x) // 1,9ã¯ãƒšãƒŠãƒ«ãƒ†ã‚£æ¸ˆ { // const Square attacker(x,5); addSelfPenaltyDual(*table, attacker, KNIGHT, -100); // ç›¸æ‰‹ã®æ­©ãŒé ã‘れã°å¤§ä¸ˆå¤«ã‹ã‚‚. adjust(*table, Square(x,1), newPtypeO(WHITE,PAWN), attacker, newPtypeO(BLACK,KNIGHT), 100); adjust(*table, Square(x,2), newPtypeO(WHITE,PAWN), attacker, newPtypeO(BLACK,KNIGHT), 100); adjust(*table, Square(x,9), newPtypeO(BLACK,PAWN), attacker, newPtypeO(WHITE,KNIGHT), -100); adjust(*table, Square(x,8), newPtypeO(BLACK,PAWN), attacker, newPtypeO(WHITE,KNIGHT), -100); } // 敵ã®å¤§é§’ã®æˆé§’ã¨è‡ªé™£ã®ç”Ÿã®é§’ for (int promoted_x=1; promoted_x<=9; ++promoted_x) { for (int x=1; x<=9; ++x) { for (int promoted_y=1; promoted_y<=3; ++promoted_y) { const Square promoted(promoted_x, promoted_y); for (int y=1; y<=3; ++y) { const Square unpromoted(x, y); if (promoted == unpromoted) continue; adjust(*table, promoted, newPtypeO(BLACK,PROOK), unpromoted, newPtypeO(WHITE,ROOK), 100); adjust(*table, promoted, newPtypeO(BLACK,PROOK), unpromoted, newPtypeO(WHITE,BISHOP), 100); adjust(*table, promoted, newPtypeO(BLACK,PBISHOP), unpromoted, newPtypeO(WHITE,ROOK), 100); adjust(*table, promoted, newPtypeO(BLACK,PBISHOP), unpromoted, newPtypeO(WHITE,BISHOP), 100); } } for (int promoted_y=7; promoted_y<=9; ++promoted_y) { const Square promoted(promoted_x, promoted_y); for (int y=7; y<=9; ++y) { const Square unpromoted(x, y); if (promoted == unpromoted) continue; adjust(*table, promoted, newPtypeO(WHITE,PROOK), unpromoted, newPtypeO(BLACK,ROOK), -100); adjust(*table, promoted, newPtypeO(WHITE,PROOK), unpromoted, newPtypeO(BLACK,BISHOP), -100); adjust(*table, promoted, newPtypeO(WHITE,PBISHOP), unpromoted, newPtypeO(BLACK,ROOK), -100); adjust(*table, promoted, newPtypeO(WHITE,PBISHOP), unpromoted, newPtypeO(BLACK,BISHOP), -100); } } } // x } // 4,6æ®µç›®ã®æ­©ã«æŠ‘ãˆè¾¼ã¿ãƒœãƒ¼ãƒŠã‚¹ for (int x=1; x<=9; ++x) { // const Square black_position(x,4); const Square white_position(x,6); addBonus(BLACK, *table, black_position, PAWN, black_position, PAWN, 100); addBonus(WHITE, *table, white_position, PAWN, white_position, PAWN,-100); } for (int x=1; x<=9; ++x) { // å±ãªã„飛車 addPenalty(BLACK, *table, Square(x,6), ROOK, Square(x,7), PAWN, -95); addPenalty(WHITE, *table, Square(x,4), ROOK, Square(x,3), PAWN, +95); // æŒãã«ãã„銀 if (x == 1 || x == 3 || x == 7 || x == 9) { addPenalty(BLACK, *table, Square(x,6), SILVER, Square(x,7), PAWN, -80); addPenalty(WHITE, *table, Square(x,4), SILVER, Square(x,3), PAWN, +80); } // æ»ã‚Šé£›è»Šå¤±æ•—? for (int i=x-1; i<=x+1; ++i) { if (i<1 || i > 9) continue; addPenalty(BLACK, *table, Square(x,6), ROOK, Square(i,8), KING, -100); addPenalty(BLACK, *table, Square(x,6), ROOK, Square(i,9), KING, -90); addPenalty(WHITE, *table, Square(x,4), ROOK, Square(i,2), KING, +100); addPenalty(WHITE, *table, Square(x,4), ROOK, Square(i,1), KING, +90); } // 玉飛接近 for (int y=7; y<=9; ++y) { const int wy = 10-y; addPenalty(BLACK, *table, Square(x,y), KING, Square(x,y-1), ROOK, -70); addPenalty(BLACK, *table, Square(x,y-1), KING, Square(x,y), ROOK, -70); addPenalty(WHITE, *table, Square(x,wy), KING, Square(x,wy+1), ROOK, +70); addPenalty(WHITE, *table, Square(x,wy+1), KING, Square(x,wy), ROOK, +70); if (x > 1) { addPenalty(BLACK, *table, Square(x,y), KING, Square(x-1,y), ROOK, -70); addPenalty(WHITE, *table, Square(x,wy), KING, Square(x-1,wy), ROOK, +70); } if (x > 2) { addPenalty(BLACK, *table, Square(x,y), KING, Square(x-2,y), ROOK, -50); addPenalty(WHITE, *table, Square(x,wy), KING, Square(x-2,wy), ROOK, +50); } if (x < 9) { addPenalty(BLACK, *table, Square(x,y), KING, Square(x+1,y), ROOK, -70); addPenalty(WHITE, *table, Square(x,wy), KING, Square(x+1,wy), ROOK, +70); } if (x < 8) { addPenalty(BLACK, *table, Square(x,y), KING, Square(x+2,y), ROOK, -50); addPenalty(WHITE, *table, Square(x,wy), KING, Square(x+2,wy), ROOK, +50); } } // for y } // for x // 桂馬ã¨é£›è»Š addPenalty(BLACK, *table, Square(1,7), ROOK, Square(2,9), KNIGHT, -70); addPenalty(BLACK, *table, Square(3,7), ROOK, Square(2,9), KNIGHT, -70); addPenalty(BLACK, *table, Square(7,7), ROOK, Square(8,9), KNIGHT, -70); addPenalty(BLACK, *table, Square(9,7), ROOK, Square(8,9), KNIGHT, -70); addPenalty(WHITE, *table, Square(1,3), ROOK, Square(2,1), KNIGHT, +70); addPenalty(WHITE, *table, Square(3,3), ROOK, Square(2,1), KNIGHT, +70); addPenalty(WHITE, *table, Square(7,3), ROOK, Square(8,1), KNIGHT, +70); addPenalty(WHITE, *table, Square(9,3), ROOK, Square(8,1), KNIGHT, +70); // è§’é“を防ã金 for (int x=1; x<=9; ++x) { for (int y=8; y<=9; ++y) { const Square bishop(x, y); if (x < 9) { const Square ul(x+1, y-1); addPenalty(BLACK, *table, bishop, BISHOP, ul, GOLD, -65); addPenalty(WHITE, *table, bishop.rotate180(), BISHOP, ul.rotate180(), GOLD, 65); } if (x > 1) { const Square ur(x-1, y-1); addPenalty(BLACK, *table, bishop, BISHOP, ur, GOLD, -65); addPenalty(WHITE, *table, bishop.rotate180(), BISHOP, ur.rotate180(), GOLD, 65); } } } // 隣接ã™ã‚‹æˆé§’ const CArray types = {{ LANCE, KNIGHT, PPAWN, PLANCE, PKNIGHT, PSILVER }}; for (int x1=1; x1<=9; ++x1) { for (int x2=x1; x2<=9; ++x2) { const int xdiff = abs(x1 - x2); if (xdiff > 2) continue; for (int y1=1; y1<=3; ++y1) { const Square p1(x1,y1); for (int y2=y1; y2<=3; ++y2) { if (x1 == x2 && y1 == y2) continue; const Square p2(x2,y2); const int py = (3-std::min(y1, y2))*10; // 3段目ã®ã»ã†ãŒãƒžã‚·ã« const int center = std::min(abs(5-x1), abs(5-x2)); // 端を減点 const int p = 0-py-center*15; // y=1:0,-80 if (p == 0) continue; for (int t1=0; t1<(int)types.size(); ++t1) { assert(isPiece(types[t1])); if (y1 < 3 && types[t1] == KNIGHT) continue; if (y1 == 1 && (types[t1] == LANCE || types[t1] == PAWN)) continue; for (int t2=0; t2<(int)types.size(); ++t2) { if (y2 < 3 && types[t2] == KNIGHT) continue; if (y2 == 1 && (types[t2] == LANCE || types[t2] == PAWN)) continue; addPenalty(BLACK, *table, p1, types[t1], p2, types[t2], p); addPenalty(WHITE, *table, p1.rotate180(), types[t1], p2.rotate180(), types[t2], -p); } } } } } } // é£›è»Šå…ˆã®æ­©ã‚’切る for (int x=1; x<=9; ++x) { for (int y=5; y<=7; ++y) { const Square pawn(x,y); for (int ry=6; ry<=9; ++ry) { if (y == ry) continue; const Square rook(x,ry); const int p = -y*10-25; addPenalty(BLACK, *table, rook, ROOK, pawn, PAWN, p); addPenalty(WHITE, *table, rook.rotate180(), ROOK, pawn.rotate180(), PAWN, -p); } } } // 相手ã®é£›è»Š/香車をå—ã‘ã‚‹ for (int x=1; x<=9; ++x) { for (int y=3; y<=7; ++y) { const Square pawn(x,y); for (int ry=1; rywriteInBinaryFile(write_pairfilename); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/eval/show-eval.cc0000644000000000000000000001100212316770314017062 0ustar rootroot/* show-eval.cc */ #include "osl/eval/openMidEndingEval.h" #include "osl/progress.h" #include "osl/record/csaRecord.h" #include "osl/container/pieceValues.h" #include "osl/oslConfig.h" #include "osl/record/kanjiPrint.h" #include #include #include #include #include using namespace osl; using namespace osl::eval; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " csa-filename" << endl; exit(1); } void show(const char *filename); int verbose = 0; int piece_estimate_level = 2; int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "e:vh")) != EOF) { switch(c) { case 'e': if (atoi(optarg) > 0) piece_estimate_level = atoi(optarg); break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); eval::ml::OpenMidEndingEval::setUp(); progress::ml::NewProgress::setUp(); for (int i=0; i count = {{ 0 }}; for (int i=0; i characters(new osl::record::KIFCharacters()); static osl::record::KanjiPrint printer(std::cout, characters); static const double scale = 200.0 / eval::ml::OpenMidEndingEval::captureValue(newPtypeO(WHITE,PAWN)); const eval::ml::OpenMidEndingEval eval(state); PieceValues values; if (piece_estimate_level == 1) make1(state, eval, values); else make2(state, eval, values); printer.print(state); for (int z=0; z<2; ++z) { for (size_t t=0; t #include #include #include #include using namespace osl; using namespace osl::eval; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " csa-filename" << endl; exit(1); } void show(const char *filename); void finish(); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern int optind; char c; while ((c = getopt(argc, argv, "e:vh")) != EOF) { switch(c) { default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); eval::ml::OpenMidEndingEval::setUp(); progress::ml::NewProgress::setUp(); for (int i=0; i, OpenMidEndingEvalDebugInfo::STAGE_FEATURE_LIMIT> stage_features; CArray progress_independent_features; void show(const NumEffectState& state) { OpenMidEndingEval eval(state); const OpenMidEndingEvalDebugInfo info = eval.debugInfo(state); for (int i=0; i #include #include #include #include using namespace osl; using namespace osl::eval; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " csa-filename" << endl; exit(1); } void show(const char *filename); int verbose = 0; int max_progress = 8; int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; // extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "vh")) != EOF) { switch(c) { default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); eval::ProgressEval::setUp(); eval::PiecePairPieceEval::setUp(); for (int i=0; i max_progress) return; if (verbose) std::cout << state; const eval::ProgressEval eval(state); const PieceEval piece(state); const eval::PiecePairPieceEval ppair(state); if (verbose) std::cout << "progress piece ppair endgame safety pieceadjust total\n"; std::cout << progress.progress16().value() << " " << piece.value() << " " << ppair.value() << " " << eval.endgameValue() << " " << eval.attackDefenseBonus() << " " << eval.minorPieceValue() << " " << eval.value() << "\n"; } void show(const char *filename) { CsaFile file(filename); const auto moves = file.load().moves(); NumEffectState state(file.initialState()); for (unsigned int i=0; i #include using namespace osl; using namespace osl::search; using namespace osl::misc; void qsearch(const char *filename); void usage(const char *program_name) { std::cerr << program_name << " [-C] [-P] [-d depth] [-s skip] [-v] csafiles\n"; std::cerr << "-C comparison w,w/o table\n"; exit(1); } int depth = -6; bool verbose = false; size_t skip_first = 0; bool comparison = false; bool use_progress_eval = false; template void qsearch(const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "C:Pd:s:vh")) != EOF) { switch(c) { case 'C': comparison = true; break; case 'd': depth = atoi(optarg); break; case 'P': use_progress_eval = true; break; case 's': skip_first = atoi(optarg); break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); std::cerr << "using table record depth " << depth << "\n"; try { for (int i=0; i(argv[i]); else qsearch(argv[i]); } } catch (std::exception& e) { std::cerr << e.what() << "\n"; return 1; } catch (...) { throw; } } template void qsearch(const char *filename) { unsigned long long total_cycles=0; unsigned long long positions = 0; Record record=CsaFile(filename).load(); NumEffectState state(record.initialState()); const auto moves=record.moves(); typedef QuiescenceSearch2 qsearch_t; SimpleHashTable table(1000000,depth,verbose); SimpleHashTable nulltable(0,0,false); SearchState2Core::checkmate_t checkmate_searcher; Eval ev(state); size_t i=0; while (true) { if (i >= skip_first) { SearchState2Core core(state, checkmate_searcher); qsearch_t qs(core, table); qsearch_t qsnull(core, nulltable); const Move last_move = (i > 0) ? moves[i-1] : Move::PASS(alt(moves[0].player())); if (verbose) std::cerr << i << " " << last_move << "\n"; if (verbose) { const char *logfile = "/tmp/q-w-table.log"; unlink(logfile); QuiescenceLog::init(logfile); } PerfMon clock; const int val = qs.search(state.turn(), ev, last_move); total_cycles += clock.stop(); if (comparison) { if (verbose) { const char *logfile = "/tmp/q-wo-table.log"; unlink(logfile); QuiescenceLog::init(logfile); } const int valnull = qsnull.search(state.turn(), ev, last_move); if (verbose || (valnull != val)) { std::cerr << state << "\n"; std::cerr << ev.value() << " " ; if (! state.inCheck()) std::cerr << ((state.turn() == BLACK) ? qs.template staticValueWithThreat(ev) : qs.template staticValueWithThreat(ev)) << " "; std::cerr << val << " " << valnull << "\n"; // break; } } positions += qs.nodeCount(); } if (i >= moves.size()) break; const Move move = moves[i++]; state.makeMove(move); ev.update(state, move); } const size_t checkmate_count = checkmate_searcher.totalNodeCount(); std::cerr << total_cycles << " / ( " << positions << " + " << checkmate_count << " ) = " << total_cycles/(double)(positions + checkmate_count) << "\n"; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/quiescence/range-vs-nodes.cc0000644000000000000000000003413512316770314021216 0ustar rootroot/** * @file range-vs-nodes.cc * mtdf ã‹ã‚‰ QuiescenceSearch ã‚’å‘¼ã¶æ™‚ã«è‰¯ã„rangeを求ã‚ã‚‹. * root ã®é™çš„評価値ã«è¿‘付ã‘ã‚‹ã¨ï¼ŒãƒŽãƒ¼ãƒ‰æ•°ã¯å¢—ãˆã‚‹ãŒå€¤ã¯æ­£ç¢ºã« * - range-vs-nodes -s 30 ../data/kifdat/01haru*.csa * records 51 * full width 19999994.000 457.325 61726.239 0.055 * acc_center2 4094.000 300.855 0.000 1.000 * acc_center4 2046.000 279.150 0.000 1.000 * root_center2 4094.000 176.201 21992.548 0.576 * root_center4 2046.000 147.995 22273.435 0.517 * fixed_center0/2 4094.000 74.885 33217.950 0.477 * fixed_center0/4 2046.000 58.941 33452.582 0.446 * extend2c46 6581.951 71.833 33004.644 0.458 * extend2cm46 6179.796 67.668 33085.086 0.451 * fixed_center0/8 1022.000 50.712 33568.813 0.432 * extend2c84 7760.072 79.849 30521.245 0.459 * extend2cm84 7586.770 78.229 30568.973 0.455 * - */ #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceSearch2.tcc" #include "osl/search/simpleHashTable.h" #include "osl/checkmate/dualDfpn.h" #include "osl/numEffectState.h" #include "osl/record/csaRecord.h" #include "osl/eval/progressEval.h" #include "osl/stat/average.h" #include #include #include #include #include using namespace osl; using namespace osl::search; using namespace osl::misc; void qsearch(const char *filename); void usage(const char *program_name) { std::cerr << program_name << " [-d depth] [-s skip] [-v] csafiles\n"; exit(1); } int record_depth = -6; bool verbose = false; size_t skip_first = 0; int center = 0; int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "c:d:s:vh")) != EOF) { switch(c) { case 'c': center = atoi(optarg); break; case 'd': record_depth = atoi(optarg); break; case 's': skip_first = atoi(optarg); break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); std::cerr << "using table record depth " << record_depth << "\n"; try { for (int i=0; i qsearch_t; typedef qsearch_t::eval_t eval_t; class Searcher { protected: stat::Average width, nodes, diff, accuracy; qsearch_t **searcher; eval_t& eval; public: Searcher(qsearch_t **q, eval_t& e) : searcher(q), eval(e) { } virtual ~Searcher() { } virtual const std::string name() const=0; virtual const std::pair alphaBeta(Player turn, int pawn_value, int real_value) const=0; /** * @return search result */ virtual int search(Player turn, int pawn_value, int real_value, Move last_move)=0; protected: const std::pair count(Player turn, int alpha, int beta, Move last_move) { width.add(abs(alpha-beta)); alpha = eval::max(turn, alpha, FixedEval::winThreshold(alt(turn))); beta = eval::max(alt(turn), beta, FixedEval::winThreshold(turn)); const int before = (*searcher)->nodeCount(); int result; if (turn == BLACK) result = (*searcher)->search(alpha, beta, eval, last_move); else result = (*searcher)->search(alpha, beta, eval, last_move); const int after = (*searcher)->nodeCount(); return std::make_pair(after - before, result); } public: void report() const { const std::string n = name(); fprintf(stderr, "%s\t%8.3f\t%8.3f\t%10.3f\t%8.3f\n", n.c_str(), width.average(), nodes.average(), diff.average(), accuracy.average()); }; }; class NormalSearcher : public Searcher { public: NormalSearcher(qsearch_t **q, eval_t& e) : Searcher(q,e) { } /** * @return search result */ int search(Player turn, int pawn_value, int real_value, Move last_move) { const std::pair alpha_beta = alphaBeta(turn, pawn_value, real_value); const std::pair node_result = count(turn, alpha_beta.first, alpha_beta.second, last_move); nodes.add(node_result.first); diff.add(abs(real_value - node_result.second)); accuracy.add(real_value == node_result.second); return node_result.second; } }; class FullWidth : public NormalSearcher { public: FullWidth(qsearch_t **q, eval_t& e) : NormalSearcher(q, e) { } const std::string name() const { return "full width"; } const std::pair alphaBeta(Player turn, int /*pawn_value*/, int /*real_value*/) const { const int alpha = FixedEval::winThreshold(alt(turn)); const int beta = FixedEval::winThreshold(turn); return std::make_pair(alpha, beta); } }; /** * [center-half_range, center+half_range] ã§æŽ¢ç´¢ */ class FixedRange : public NormalSearcher { protected: int divider; public: FixedRange(qsearch_t **q, eval_t& e, int d) : NormalSearcher(q,e), divider(d) { } virtual int center(int real_value) const=0; int halfRange(int pawn_value) const { return pawn_value/divider; } const std::pair alphaBeta(Player turn, int pawn_value, int real_value) const { const int center=this->center(real_value); const int half_range=halfRange(pawn_value); const int alpha = center - half_range + eval::delta(turn); const int beta = center + half_range - eval::delta(turn); return std::make_pair(alpha, beta); } }; const std::string tos(int val) { assert(val < 100); assert(val >= 0); std::string result = "00"; sprintf(&result[0], "%d", val); return result; } class FixedCenter : public FixedRange { protected: const int center_value; public: FixedCenter(qsearch_t **q, eval_t& e, int d, int c) : FixedRange(q, e, d), center_value(c) { } int center(int /*real_value*/) const { return center_value; } const std::string name() const { return "fixedcenter" + tos(center_value) +"/"+ tos(divider); } }; class AccurateCenter : public FixedRange { public: AccurateCenter(qsearch_t **q, eval_t& e, int d) : FixedRange(q, e, d) { } int center(int real_value) const { return real_value; } const std::string name() const { return "acc_center" + tos(divider); } }; class RootCenter : public FixedRange { public: RootCenter(qsearch_t **q, eval_t& e, int d) : FixedRange(q, e, d) { } int center(int /*real_value*/) const { return eval.value(); } const std::string name() const { return "root_center" + tos(divider); } }; /** * [0-min_range, max(0+min_range, ev.value()-frontier_range] ã§æŽ¢ç´¢. */ class ExtendToCenter : public FixedCenter { const int extend_multiplier; public: ExtendToCenter(qsearch_t **q, eval_t& e, int range_d, int c, int extend_m) : FixedCenter(q, e, range_d, c), extend_multiplier(extend_m) { } const std::string name() const { return "extend2c" + tos(divider) + tos(extend_multiplier); } const std::pair alphaBeta(Player turn, int pawn_value, int real_value) const { const int root_value = eval.value(); const int extend_range = pawn_value * extend_multiplier; const std::pair alpha_beta = FixedCenter::alphaBeta(turn, pawn_value, real_value); const int delta = eval::delta(turn); int alpha = alpha_beta.first; int beta = alpha_beta.second; if (eval::betterThan(turn, center(real_value), root_value)) { alpha = eval::min(turn, root_value+extend_range-delta, alpha); } else { beta = eval::max(turn, root_value-extend_range+delta, beta); } return std::make_pair(alpha, beta); } }; /** * [0-min_range, max(0+min_range/2, ev.value()-frontier_range] ã§æŽ¢ç´¢. * (root ã«ã¯ã‚ã¾ã‚Šè¿‘付ã‹ãªã„) */ class ExtendToCenterModest : public FixedCenter { const int extend_multiplier; public: ExtendToCenterModest(qsearch_t **q, eval_t& e, int range_d, int c, int extend_m) : FixedCenter(q, e, range_d, c), extend_multiplier(extend_m) { } const std::string name() const { return "extend2cm" + tos(divider) + tos(extend_multiplier); } const std::pair alphaBeta(Player turn, int pawn_value, int real_value) const { const int root_value = eval.value(); const int extend_range = pawn_value * extend_multiplier; const int center=this->center(real_value); const int half_range=halfRange(pawn_value); const int delta = eval::delta(turn); int alpha = center - half_range - delta; int beta = center + half_range + delta; if (eval::betterThan(turn, center, root_value)) { alpha = eval::min(turn, root_value+extend_range-delta, center - half_range/2 - delta); } else { beta = eval::max(turn, root_value-extend_range+delta, center + half_range/2 + delta); } return std::make_pair(alpha, beta); } }; /** * [0-min_range*2, 0+min_range] */ class ExtendToOther : public FixedCenter { static const int extend_multiplier=2; public: ExtendToOther(qsearch_t **q, eval_t& e, int range_d, int c) : FixedCenter(q, e, range_d, c) { } const std::string name() const { return "extend2o" + tos(divider) + tos(extend_multiplier); } const std::pair alphaBeta(Player turn, int pawn_value, int real_value) const { const int root_value = eval.value(); const int center=this->center(real_value); const int half_range=halfRange(pawn_value); int alpha = center - half_range - eval::delta(turn); int beta = center + half_range + eval::delta(turn); if (eval::betterThan(turn, center, root_value)) { beta = center + half_range*extend_multiplier + eval::delta(turn); } else { alpha = center - half_range*extend_multiplier - eval::delta(turn); } return std::make_pair(alpha, beta); } }; class Analyzer { size_t records; NumEffectState state; eval_t ev; checkmate_t checkmate; SimpleHashTable table; qsearch_t *qs; FullWidth full_searcher; typedef std::forward_list list_t; list_t searchers; public: Analyzer() : records(0), state(SimpleState(HIRATE)), ev(state), table(100000,record_depth,verbose), full_searcher(&qs, ev) { searchers.push_front(new AccurateCenter(&qs, ev, 2)); searchers.push_front(new AccurateCenter(&qs, ev, 4)); searchers.push_front(new RootCenter(&qs, ev, 2)); searchers.push_front(new RootCenter(&qs, ev, 4)); searchers.push_front(new RootCenter(&qs, ev, 8)); searchers.push_front(new RootCenter(&qs, ev, 16)); searchers.push_front(new FixedCenter(&qs, ev, 2, center)); #if 0 searchers.push_front(new ExtendToCenter(&qs, ev, 2, center, 4)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 2, center, 4)); searchers.push_front(new ExtendToCenter(&qs, ev, 2, center, 8)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 2, center, 8)); searchers.push_front(new ExtendToOther(&qs, ev, 2, center)); #endif searchers.push_front(new FixedCenter(&qs, ev, 4, center)); #if 0 searchers.push_front(new ExtendToCenter(&qs, ev, 4, center, 4)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 4, center, 4)); #endif searchers.push_front(new ExtendToCenter(&qs, ev, 4, center, 6)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 4, center, 6)); #if 0 searchers.push_front(new ExtendToCenter(&qs, ev, 4, center, 8)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 4, center, 8)); searchers.push_front(new ExtendToOther(&qs, ev, 4, center)); #endif searchers.push_front(new FixedCenter(&qs, ev, 8, center)); searchers.push_front(new ExtendToCenter(&qs, ev, 8, center, 4)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 8, center, 4)); #if 0 searchers.push_front(new ExtendToCenter(&qs, ev, 8, center, 6)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 8, center, 6)); searchers.push_front(new ExtendToCenter(&qs, ev, 8, center, 8)); searchers.push_front(new ExtendToCenterModest(&qs, ev, 8, center, 8)); searchers.push_front(new ExtendToOther(&qs, ev, 8, center)); #endif searchers.reverse(); } void report() const { std::cerr << "\nrecords " << records << "\n"; full_searcher.report(); for (list_t::const_iterator p=searchers.begin(); p!=searchers.end(); ++p) { (*p)->report(); } } void search(size_t i, Move last_move) { SearchState2Core core(state, checkmate); qsearch_t searcher(core, table); qs = &searcher; const Player turn = state.turn(); const int pawn_value = qsearch_t::eval_t::captureValue(newPtypeO(alt(turn),PAWN)); if (verbose) std::cerr << i << " " << csa::show(last_move) << "\n"; table.clear(); const int real_value_dummy = 0; const int real_value = full_searcher.search(turn, pawn_value, real_value_dummy, last_move); for (list_t::iterator p=searchers.begin(); p!=searchers.end(); ++p) { table.clear(); (*p)->search(turn, pawn_value, real_value, last_move); } } void search(const char *filename) { Record record=CsaFile(filename).load(); state = NumEffectState(record.initialState()); ev = eval_t(state); const auto moves=record.moves(); size_t i=0; while (true) { if (i >= skip_first) { const Move last_move = (i > 0) ? moves[i-1] : Move::PASS(alt(moves[0].player())); search(i, last_move); } if (i >= moves.size()) break; const Move move = moves[i++]; state.makeMove(move); ev.update(state, move); } ++records; report(); } }; Analyzer analyzer; void qsearch(const char *filename) { analyzer.search(filename); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/quiescence/quiescence2stat.cc0000644000000000000000000000700412316770314021463 0ustar rootroot/* quiescencestat.cc */ #include "osl/search/quiescenceSearch2.h" #include "osl/search/simpleHashTable.h" #include "osl/search/searchState2.h" #include "osl/effect_util/effectUtil.h" #include "osl/record/csaRecord.h" #include "osl/eval/openMidEndingEval.h" #include "osl/misc/perfmon.h" #include #include #include using namespace osl; using namespace osl::search; using namespace osl::misc; void qsearch(const char *filename); void usage(const char *program_name) { std::cerr << program_name << " [-d depth] [-s skip] [-v] [-p] csafiles\n"; exit(1); } int depth = -2; bool verbose = false, problem_solving = false; size_t skip_first = 0; void qsearch(const char *filename); int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; extern char *optarg; extern int optind; char c; while ((c = getopt(argc, argv, "d:s:pvh")) != EOF) { switch(c) { case 'd': depth = atoi(optarg); break; case 's': skip_first = atoi(optarg); break; case 'p': problem_solving = true; break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag || (argc < 1)) usage(program_name); std::cerr << "using table record depth " << depth << "\n"; eval::ml::OpenMidEndingEval::setUp(); progress::ml::NewProgress::setUp(); try { for (int i=0; i qsearch_t; SimpleHashTable table(1000000,depth,verbose); SearchState2Core::checkmate_t checkmate_searcher; eval::ml::OpenMidEndingEval ev(state); size_t i=0; Player initial_turn = state.turn(); while (true) { if (i >= skip_first) { SearchState2Core core(state, checkmate_searcher); qsearch_t qs(core, table); const Move last_move = (i > 0) ? moves[i-1] : Move::PASS(alt(initial_turn)); if (verbose) std::cerr << i << " " << last_move << "\n"; if (problem_solving) { std::cout << state; table.allocate(HashKey(state), 1000); } PerfMon clock; const int val = qs.search(state.turn(), ev, last_move, 4); total_cycles += clock.stop(); positions += qs.nodeCount(); if (verbose || problem_solving) { const SimpleHashRecord *record = table.find(HashKey(state)); std::cout << "result "; if (record) std::cout << csa::show(record->qrecord.bestMove()) << " "; std::cout << val << "\n"; if (i < moves.size()) std::cout << "recorded " << csa::show(moves[i]) << "\n"; } } if (i >= moves.size() || problem_solving) break; const Move move = moves[i++]; state.makeMove(move); ev.update(state, move); } const size_t checkmate_count = checkmate_searcher.totalNodeCount(); std::cerr << total_cycles << " / ( " << positions << " + " << checkmate_count << " ) = " << total_cycles/(double)(positions + checkmate_count) << "\n"; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/find-uplevel-king.cc0000644000000000000000000000440312316770314017555 0ustar rootroot/* find-uplevel-king.cc */ #include "osl/game_playing/gameState.h" #include "osl/record/kisen.h" #include "osl/record/csaRecord.h" #include "osl/sennichite.h" #include #include #include namespace po = boost::program_options; using namespace osl; int count = 0; bool run(const NumEffectState& initial, const std::vector& moves) { NumEffectState state(initial); for (size_t i=0; i(&kisen_filename), "kisen filename") ("csa-file", po::value >()) ("help", "produce help message") ; po::positional_options_description p; p.add("csa-file", -1); po::variables_map vm; std::vector filenames; try { po::store(po::command_line_parser(argc, argv). options(options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cout << options << std::endl; return 0; } if (vm.count("csa-file")) filenames = vm["csa-file"].as >(); } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; return 1; } if (kisen_filename != "") { KisenFile kisen(kisen_filename); for (size_t i=0; i moves = kisen.moves(i); if (run(state, moves)) std::cout << i << "\n"; } } for (size_t i=0; i #include #include #include #include #include #include #include // #include #include #include #include #include std::vector good_tournaments; bool accept_tournament(const std::string& name) { for (const std::string& tournament: good_tournaments) { if (tournament.find(name) == 0) return true; else if (tournament.find(name) != tournament.npos) std::cerr << tournament << " != " << name << "\n"; } return good_tournaments.empty(); } std::string heuristic_find_title(osl::Record& record, osl::Player player) { static const osl::CArray titles = {{ K_K1 K_DAN, K_K2 K_DAN, K_K3 K_DAN, K_K4 K_DAN, K_K5 K_DAN, K_K6 K_DAN, K_K7 K_DAN, K_K8 K_DAN, K_K9 K_DAN, K_MEIJIN, K_PROOK2 K_KING2, K_KING2 K_KURAI, K_KING2 K_SHOU, K_KING2 K_ZA, K_KI K_KING2, K_KI K_SEI, K_K2 K_KANMURI, K_K3 K_KANMURI, K_K4 K_KANMURI, K_K5 K_KANMURI, K_K6 K_KANMURI, K_K7 K_KANMURI, K_K8 K_KANMURI, K_K9 K_KANMURI, K_JORYUU, }}; std::string name = record.player[player]; std::string title_found = ""; for (const char *title: titles) { if (boost::algorithm::iends_with(name, title)) { title_found = title + title_found; name.resize(name.size() - strlen(title)); } } record.player[player] = name; return title_found; } void run(osl::record::Record& record, osl::KisenWriter& ks, std::unique_ptr& ipx_writer, osl::record::CheckDuplicate& check_duplicates, int default_rating, int min_year, int max_year) { boost::gregorian::date date = record.start_date; if (min_year > 0 && (date.is_special() || date.year() < min_year)) return; if (max_year > 0 && (date.is_special() || date.year() > max_year)) return; // é‡è¤‡ãƒã‚§ãƒƒã‚¯ const std::vector& moves = record.moves(); if (check_duplicates.regist(moves)) return; std::string black_title = heuristic_find_title(record, osl::BLACK); std::string white_title = heuristic_find_title(record, osl::WHITE); ks.save(record.record); if (ipx_writer) { ipx_writer->save(record, default_rating, default_rating, black_title, white_title); } } static void convert(const std::string &kisen_filename, const std::vector &files, bool output_ipx, osl::record::CheckDuplicate& check_duplicates, int default_rating, int min_year, int max_year) { std::ofstream ofs(kisen_filename.c_str()); osl::KisenWriter ks(ofs); std::unique_ptr ipx_writer; std::unique_ptr ipx_ofs; if (output_ipx) { const boost::filesystem::path ipx_path = boost::filesystem::change_extension(boost::filesystem::path(kisen_filename), ".ipx"); const std::string ipx = osl::misc::file_string(ipx_path); ipx_ofs.reset(new std::ofstream(ipx.c_str())); ipx_writer.reset(new osl::record::KisenIpxWriter(*ipx_ofs)); } boost::progress_display progress(files.size()); boost::regex date_time_regex("/(20[0-9][0-9]/[0-9][0-9]/[0-9][0-9])/"); for (size_t i = 0; i < files.size(); ++i, ++progress) { const std::string& filename = files[i]; try { osl::record::Record record; if (boost::algorithm::iends_with(filename, ".kif")) { if (osl::KakinokiFile::isKakinokiFile(filename)) { const osl::KakinokiFile kif(filename); record = kif.load(); } else { osl::KisenFile kisen(filename); osl::KisenIpxFile ipx(kisen.ipxFileName()); for (size_t j=0; j 0) continue; // it was actually kisen file, going to next file } // fall through } else if (boost::algorithm::iends_with(filename, ".csa")) { const osl::CsaFile csa(filename); record = csa.load(); } else if (boost::algorithm::iends_with(filename, ".ki2")) { const osl::Ki2File ki2(filename); record = ki2.load(); // std::cerr << osl::misc::eucToLang(record.tounamentName()) << "\n"; if (! accept_tournament(record.tournament_name)) continue; } else { std::cerr << "Unknown file type: " << filename << "\n"; continue; } if (record.start_date.is_special()) { boost::smatch match; if (boost::regex_search(filename, match, date_time_regex)) { std::string s(match[1].first, match[1].second); record.start_date = boost::gregorian::from_string(s); } } run(record, ks, ipx_writer, check_duplicates, default_rating, min_year, max_year); } catch(std::exception& e) { std::cerr << "ERROR: reading " << files[i] << "; " << e.what() << std::endl; continue; } } } int main(int argc, char **argv) { bool output_ipx; std::string kisen_filename, tournament_filename; int default_rating, year, min_year, max_year; boost::program_options::options_description command_line_options; command_line_options.add_options() ("output-ipx", boost::program_options::value(&output_ipx)->default_value(true), "Whether output IPX file in addition to KIF file") ("tournament-file", boost::program_options::value(&tournament_filename) ->default_value(""), "ignore records unless the name of their tournament is listed in the file in EUC-JP") ("year", boost::program_options::value(&year)->default_value(0), "year to select (0 for all)") ("min-year", boost::program_options::value(&min_year)->default_value(0), "min year to select (0 for all)") ("max-year", boost::program_options::value(&max_year)->default_value(0), "max year to select (0 for all)") ("kisen-filename,o", boost::program_options::value(&kisen_filename)-> default_value("test.kif"), "Output filename of Kisen file") ("input-file", boost::program_options::value< std::vector >(), "input files in kisen format") ("default-rating", boost::program_options::value(&default_rating)-> default_value(0), "default rating") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] csa-files | ki2-files \n"; std::cerr << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] csa-files | ki2-files\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } if (tournament_filename != "") { std::ifstream is(tournament_filename.c_str()); std::string name; while(std::getline(is, name)) { boost::algorithm::trim(name); good_tournaments.push_back(name); } if (good_tournaments.empty()) throw std::runtime_error("read failed "+tournament_filename); } if (year) min_year = max_year = year; std::vector files; if (vm.count("input-file")) { const std::vector temp = vm["input-file"].as >(); files.insert(files.end(), temp.begin(), temp.end()); } else { std::string line; while(std::getline(std::cin , line)) { boost::algorithm::trim(line); files.push_back(line); } } osl::OslConfig::setUp(); osl::record::CheckDuplicate check_duplicate; convert(kisen_filename, files, output_ipx, check_duplicate, default_rating, min_year, max_year); std::locale::global(std::locale("")); check_duplicate.print(std::cout); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/sample/record/kifu-to-myshogi.cc0000644000000000000000000000131312316770314020543 0ustar rootroot/* kifu-to-myshogi.cc */ #include "osl/record/myshogi.h" #include "osl/record/kakinoki.h" #include using namespace std; int main(int argc, char **argv) { if (! argv[1] || ! osl::KakinokiFile::isKakinokiFile(argv[1])) return 1; std::string filename = argv[1]; const osl::KakinokiFile file(filename); const auto record = file.load(); auto moves = record.moves(); auto state = record.initialState(); for (size_t i=0; i #include #include #include #include #include #include // ---------------------------------------------- // Global variables // ---------------------------------------------- boost::program_options::variables_map vm; osl::record::CheckDuplicate check_duplicate; void process( const std::string& file_name) { try { bool verbose = false; if (vm.count("verbose")) verbose = true; bool show_each_move = vm.count("show-moves"); if (verbose) std::cerr << "Processing... " << file_name << std::endl; const osl::Ki2File ki2(file_name, verbose); const osl::Record& record = ki2.load(); const auto& moves = record.moves(); if (check_duplicate.regist(moves)) { std::cerr << "Found a duplicated play: " << file_name << "\n"; return; } osl::NumEffectState state; for (const osl::Move move: moves) { if (!state.isValidMove(move, false)) { std::cout << file_name << "\n"; continue; } if (show_each_move) std::cout << move.from().x() << move.from().y() << ' ' << move.to().x() << move.to().y() << ' ' << osl::csa::show(move.oldPtype()) << ' ' << osl::csa::show(move.ptype()) << ' ' << osl::csa::show(move.capturePtype()) << std::endl; state.makeMove(move); } } catch (osl::Ki2IOError& err) { std::cerr << err.what() << "\n"; std::cerr << "Found an error: " << file_name << "\n"; return; } } int main(int argc, char **argv) { boost::program_options::options_description command_line_options; command_line_options.add_options() ("input-file", boost::program_options::value< std::vector >(), "input files in ki2 format (.ki2)") ("show-moves", "show each move") ("verbose,v", "Verbose mode") ("help,h", "Show this help message"); boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cout << "Usage: " << argv[0] << " [options] ki2-file [ki2-file...]\n"; std::cout << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] ki2-file [ki2-file...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) { const std::vector temp = vm["input-file"].as >(); files.insert(files.end(), temp.begin(), temp.end()); } else { std::string line; while(std::getline(std::cin , line)) { boost::algorithm::trim(line); files.push_back(line); } } // main std::for_each(files.begin(), files.end(), [](std::string f){ process(f); }); check_duplicate.print(std::cout); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/record/last-position.cc0000644000000000000000000000173312316770314020323 0ustar rootroot/* * */ #include "osl/record/csaRecord.h" #include "osl/numEffectState.h" #include "osl/effect_util/effectUtil.h" #include #include #include #include #include using namespace osl; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " csa-filenames " << endl; // kisenファイル 㨠csaファイル ã‚’å†ç”Ÿ exit(1); } int main(int argc, char **argv) { try { nice(20); //次㫠CSAãƒ•ã‚¡ã‚¤ãƒ«ã‚’å‡¦ç† for (int i=1; i #include using namespace osl; int main(int argc, char **argv) { for (int i=1; i #include #include "osl/record/csaRecord.h" #include "osl/record/record.h" #include "osl/record/searchInfo.h" static int eval_threshold = 128; static int critical_drop = 64; struct MoveData { MoveData() : index(0), value(0), next_value(0) { } MoveData(size_t i, int v, int next_v) : index(i), value(v), next_value(next_v) { } size_t index; int value; int next_value; }; void find_bad_moves(bool sente, const std::string &filename) { osl::CsaFile file(filename); std::vector moves; std::vector dummy1; std::vector time; std::vector info; file.load().load(moves, time, dummy1, info); int prev_value = 0; std::vector bad_indices; for (size_t i = sente ? 0 : 1; i < info.size(); i += 2) { // skip joseki if (time[i] == 1 && info[i].value == 0 && prev_value == 0) { } else { if ((sente && info[i].value > -eval_threshold && info[i].value - prev_value < -critical_drop) || (!sente && info[i].value < eval_threshold && info[i].value - prev_value > critical_drop)) { bad_indices.push_back(MoveData(i - 2, prev_value, info[i].value)); } } prev_value = info[i].value; } osl::NumEffectState state(file.initialState()); for (size_t i = 0, j = 0; i < moves.size() && j < bad_indices.size(); i++) { if (bad_indices[j].index == i) { std::cout << state << "' " << i << ": " << info[i].value << " -> " << info[i+2].value<< std::endl << osl::csa::show(moves[i]) << std::endl << osl::csa::show(moves[i+1]) << std::endl << osl::csa::show(moves[i+2]) << std::endl; std::vector &pv_moves = info[i+2].moves; bool found_pass = false; for (size_t k = 0; k < pv_moves.size(); k++) { if (found_pass) std::cout << "' "; if (pv_moves[k].isPass()) { if (!found_pass) std::cout << "' "; else found_pass = true; std::cout << "%PASS" << std::endl; } else { std::cout << osl::csa::show(pv_moves[k]) << std::endl; } } j++; } state.makeMove(moves[i]); } } int main(int argc, char **argv) { bool sente; boost::program_options::options_description command_line_options; command_line_options.add_options() ("sente", boost::program_options::value(&sente)->default_value(true), "Whether you want to check sente or gote moves") ("input-file", boost::program_options::value< std::vector >(), "input files in CSA format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] csa-file" << std::endl; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] csa-file" << std::endl; std::cerr << command_line_options << std::endl; return 1; } const std::vector files = vm["input-file"].as< std::vector >(); for (size_t i = 0; i < files.size(); i++) { find_bad_moves(sente, files[i]); } return 0; } libosl-0.8.0.orig/sample/record/all-states.cc0000644000000000000000000001010412316770314017557 0ustar rootroot#include "osl/numEffectState.h" #include "osl/hashKey.h" #include "osl/record/kisen.h" #include "osl/csa.h" #include #include #include #include #include struct hash { unsigned long operator() (const osl::SimpleState &state) const { return osl::HashKey(state).signature(); } }; struct equalKey { bool operator() (const osl::SimpleState &s1, const osl::SimpleState &s2) const { return s1 == s2; } }; struct State { State() : count(0) { } int count; std::vector moves; }; void find_all(const int num_ply, const int threshold, bool save, const std::vector &files) { std::unordered_map states; for (size_t index = 0; index < files.size(); index++) { osl::record::KisenFile kisen(files[index]); for (size_t i = 0; i < kisen.size(); i++) { const auto moves = kisen.moves(i); osl::NumEffectState state(kisen.initialState()); size_t j = 0; for (; j < moves.size() && (int)j < num_ply; j++) { const osl::Square opKingSquare = state.kingSquare(alt(state.turn())); if (state.hasEffectAt(state.turn(), opKingSquare)) { break; } state.makeMove(moves[j]); } if ((int)j == num_ply) { auto it = states.find(state); if (it != states.end()) { (it->second.count)++; } else { State s; s.count = 1; for (int k = 0; k < num_ply; k++) { s.moves.push_back(moves[k]); } states[state] = s; } } } } int index = 1; for (auto it = states.cbegin(); it != states.cend(); ++it) { if (it->second.count >= threshold) { std::cout << index << " (" << it->second.count << ")" << std::endl; std::cout << it->first; std::ofstream output; if (save) { std::ostringstream oss(std::ostringstream::out); oss << index << ".csa"; const std::string &filename = oss.str(); output.open(filename.c_str()); output << "PI" << std::endl << "+" << std::endl; } const auto &moves = it->second.moves; for (size_t i = 0; i < moves.size(); i++) { std::cout << osl::csa::show(moves[i]) << " "; if (save) { output << osl::csa::show(moves[i]) << std::endl; } } if (save) { output.close(); } std::cout << std::endl; index++; } } } int main(int argc, char **argv) { int num_ply; int threshold; bool save_moves; boost::program_options::options_description command_line_options; command_line_options.add_options() ("num-ply", boost::program_options::value(&num_ply)->default_value(10), "Show states after this number of plies are played") ("threshold", boost::program_options::value(&threshold)->default_value(10), "Each state must appear this number of times to be shown") ("save", boost::program_options::value(&save_moves)->default_value(false), "Save moves leading to states to files in CSA format") ("input-file", boost::program_options::value< std::vector >(), "input files in kisen format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] kisen-file" << std::endl; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] kisen-file" << std::endl; std::cerr << command_line_options << std::endl; return 1; } const std::vector files = vm["input-file"].as< std::vector >(); find_all(num_ply, threshold, save_moves, files); return 0; } libosl-0.8.0.orig/sample/record/wdoor-to-kisen.sh0000755000000000000000000000046211210167401020412 0ustar rootroot#!/bin/sh # # ¤½¤Î´ýÉè¥ê¥¹¥È¤ò¤â¤È¤Ë¡¢.kif¤òºîÀ® # bjam release smp=off csa-to-kisen && \ cat $filename.files | ../../build/sample/record/gcc-4.3.3/release/address-model-64/architecture-x86/instruction-set-athlon64/qt3support-on/smp-off/csa-to-kisen -o $filename.kif 2>&1 | tee wdoor-to-kisen.log exit 0 libosl-0.8.0.orig/sample/record/csajapanize.cc0000644000000000000000000000350712316770314020007 0ustar rootroot/* csajapanize.cc */ #include "osl/record/csaRecord.h" #include "osl/record/record.h" #include "osl/record/ki2.h" #include "osl/misc/iconvConvert.h" #include #include #include using namespace osl; using record::SearchInfo; void process(int move_number, const NumEffectState& src, const std::vector& history, const SearchInfo& info) { auto moves = info.moves; if (moves.empty()) return; std::ostringstream ss; NumEffectState state = src; for (int i=0; i moves; std::vector times; std::vector comments; std::vector info; record.load(moves, times, comments, info); if (info.empty() || info.back().moves.empty()) continue; while (last_output < (int)info.size()) { if (last_output > 0) process(last_output, csa.initialState(), moves, info[last_output]); ++last_output; } } catch (CsaIOError& e) { if (last_output) { std::cerr << "oops " << e.what() << ' ' << last_output << '\n'; std::cerr << all; } } } } libosl-0.8.0.orig/sample/record/csa-to-kifu.cc0000644000000000000000000001014412316770314017634 0ustar rootroot/* csa-to-kifu.cc */ #include "osl/record/kanjiPrint.h" #include "osl/record/kanjiCode.h" #include "osl/record/ki2.h" #include "osl/record/csaRecord.h" #include "osl/misc/iconvConvert.h" #include #include #include #include #include #include #include #include namespace po = boost::program_options; using namespace osl; std::string header; std::vector files; void run(const std::string& filename); int main(int argc, char **argv) { boost::program_options::options_description command_line_options; command_line_options.add_options() ("header,h", boost::program_options::value(&header)->default_value(""), "header for kifu-file") ("input-file", boost::program_options::value< std::vector >(), "input files in csa format (.csa)") ("help,h", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); files = vm["input-file"].as< std::vector >(); if (vm.count("help")) { std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << command_line_options << std::endl; return 1; } try { for (size_t i=0; i moves; std::vector time; std::vector search_info; std::vector raw_comments; record.load(moves, time, raw_comments, search_info); NumEffectState state(file.initialState()); CArray total = {{0,0}}; for (size_t i=0; i i) { total[i%2] += time[i]; ss << "(" << std::setw(2) << std::setfill(' ') << time[i]/60 << ':' << std::setw(2) << std::setfill('0') << time[i]%60 << "/" << std::setw(2) << total[i%2]/60/60 << ':' << std::setw(2) << total[i%2]/60%60 << ':' << std::setw(2) << total[i%2]%60 << ")"; } ss << "\r\n"; state.makeMove(moves[i]); if (search_info.size() > i && ! search_info[i].moves.empty()) { ss << IconvConvert::convert("UTF-8", "EUC-JP", "*読筋 ") << search_info[i].value << " "; NumEffectState copy(state); for (size_t j=0; j #include #include using namespace osl; void usage(const char *prog) { using namespace std; cerr << "Usage: " << prog << " [-N atmost-N-games] [-k kisen_fileName] csa-filenames " << endl; // kisenファイル 㨠csaファイル ã‚’å†ç”Ÿ exit(1); } void processKifu (std::vector const& moves) { NumEffectState state; std::cout << state << std::endl; for (size_t i=0; i ç›´å‰ã®æ‰‹ãŒéžåˆæ³•手 std::cerr << "e"; // state; break; } state.makeMove(moves[i]); std::cout << state << std::endl; } std::cout << state << std::endl; } int main(int argc, char **argv) { const char *program_name = argv[0]; bool error_flag = false; bool verbose = false; const char *kisen_filename = 0; extern char *optarg; extern int optind; char c; size_t num_records = 1; while ((c = getopt(argc, argv, "N:k:vh")) != EOF) { switch(c) { case 'k': kisen_filename = optarg; break; case 'N': num_records = atoi(optarg); break; case 'v': verbose = true; break; default: error_flag = true; } } argc -= optind; argv += optind; if (error_flag) usage(program_name); try { nice(20); size_t record_processed = 0; //最åˆã¯ Kisenãƒ•ã‚¡ã‚¤ãƒ«ã‚’å‡¦ç† if (kisen_filename) { KisenFile kisen_file(kisen_filename); for (size_t i=0; i num_records) break; const auto moves=kisen_file.moves(i); processKifu (moves); } } //次㫠CSAãƒ•ã‚¡ã‚¤ãƒ«ã‚’å‡¦ç† for (int i=0; i num_records) break; CsaFile file(argv [i]); const auto moves=file.load().moves(); processKifu (moves); } } catch (std::exception& e) { std::cerr << e.what() << "\n"; return 1; } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/record/all-states2.cc0000644000000000000000000000621512316770314017651 0ustar rootroot#include "osl/numEffectState.h" #include "osl/hashKey.h" #include "osl/record/kisen.h" #include "osl/csa.h" #include #include #include #include #include #include struct hash { unsigned long operator() (const osl::SimpleState &state) const { return osl::hash::HashKey(state).signature(); } }; void find_all(const int num_ply, const int threshold, bool save, const std::vector &files) { std::unordered_set states; for (size_t index = 0; index < files.size(); index++) { osl::record::KisenFile kisen(files[index]); for (size_t i = 0; i < kisen.size(); i++) { const auto moves = kisen.moves(i); osl::NumEffectState state(kisen.initialState()); states.insert(state); for (size_t j = 0; j < moves.size() && j < static_cast(num_ply); j++) { const osl::Square opKingSquare = state.kingSquare(alt(state.turn())); if (state.hasEffectAt(state.turn(), opKingSquare)) { break; } state.makeMove(moves[j]); states.insert(state); } } } int index = 0; for (auto it=states.begin(); it != states.end(); ++it) { if (save) { std::ofstream output; output.open((boost::format("%05d.csa") % index++).str().c_str()); output << *it; output.close(); } else { std::cout << *it; } } } int main(int argc, char **argv) { int num_ply; int threshold; bool save_moves; boost::program_options::options_description command_line_options; command_line_options.add_options() ("num-ply", boost::program_options::value(&num_ply)->default_value(10), "Show states after this number of plies are played") ("threshold", boost::program_options::value(&threshold)->default_value(10), "Each state must appear this number of times to be shown") ("save", boost::program_options::value(&save_moves)->default_value(false), "Save moves leading to states to files in CSA format") ("input-file", boost::program_options::value< std::vector >(), "input files in kisen format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] kisen-file" << std::endl; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] kisen-file" << std::endl; std::cerr << command_line_options << std::endl; return 1; } const std::vector files = vm["input-file"].as< std::vector >(); find_all(num_ply, threshold, save_moves, files); return 0; } libosl-0.8.0.orig/sample/record/find-states.cc0000644000000000000000000001066612316770314017744 0ustar rootroot#include "osl/numEffectState.h" #include "osl/hashKey.h" #include "osl/csa.h" #include "osl/record/kisen.h" #include "osl/record/csaRecord.h" #include #include #include #include #include struct hash { unsigned long operator() (const osl::SimpleState &state) const { return osl::hash::HashKey(state).signature(); } }; class StatePredicate { public: StatePredicate(const std::vector &filenames) { } virtual ~StatePredicate() { } virtual bool match (const osl::NumEffectState &state) const { return false; } virtual bool isLoaded() const { return false; } }; class CsaPredicate : public StatePredicate { public: CsaPredicate(const std::vector &filenames) : StatePredicate(filenames) { for (size_t i = 0; i < filenames.size(); ++i) { osl::CsaFile file(filenames[i]); states.insert(file.initialState()); } } ~CsaPredicate() { } bool match (const osl::NumEffectState &state) const { return states.find(state) != states.end(); } bool isLoaded() const { return !states.empty(); } private: std::unordered_set states; }; class PieceStandPredicate : public StatePredicate { private: bool match(const osl::NumEffectState &state, osl::Player player) const { return state.countPiecesOnStand(player) == 1 && state.countPiecesOnStand(player) == 1 && state.countPiecesOnStand(player) == 0 && state.countPiecesOnStand(player) == 1 && state.countPiecesOnStand(player) == 3 && state.countPiecesOnStand(player) == 3; } public: PieceStandPredicate(const std::vector &filenames) : StatePredicate(filenames) { } bool match (const osl::NumEffectState &state) const { return match(state, osl::BLACK) || match(state, osl::WHITE); } bool isLoaded() const { return true; } }; int main(int argc, char **argv) { std::string kisen_filename, predicate_name; boost::program_options::options_description command_line_options; command_line_options.add_options() ("kisen", boost::program_options::value(&kisen_filename)-> default_value(""), "Kisen filename to search") ("predicate", boost::program_options::value(&predicate_name)-> default_value("csa"), "Predicate to use. Valid options are csa and stand") ("input-file", boost::program_options::value< std::vector >(), "input files in kisen format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] CSA_FILES" << std::endl; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] CSA_FILES" << std::endl; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) files = vm["input-file"].as< std::vector >(); std::unique_ptr predicate; if (predicate_name == "csa") { predicate.reset(new CsaPredicate(files)); } else if (predicate_name == "stand") { predicate.reset(new PieceStandPredicate(files)); } else { std::cerr << "Unknown predicate " << predicate_name; return 1; } if (!predicate->isLoaded()) { std::cerr << "No target" << std::endl; } osl::record::KisenFile kisen(kisen_filename); for (size_t i = 0; i < kisen.size(); i++) { const auto moves = kisen.moves(i); auto state = kisen.initialState(); for (size_t j = 0; j < moves.size(); j++) { const osl::Square opKingSquare = state.kingSquare(alt(state.turn())); if (state.hasEffectAt(state.turn(), opKingSquare)) { break; } state.makeMove(moves[j]); if (predicate->match(state)) { std::cout << i << " " << j << std::endl << state; } } } return 0; } libosl-0.8.0.orig/sample/record/count-win-loss.cc0000644000000000000000000001540612316770314020421 0ustar rootroot#include "osl/record/csaRecord.h" #include "osl/record/checkDuplicate.h" #include #include #include #include #include #include #include #include /**< max players */ static const unsigned int MAX_PLAYERS = 20; /**< player and his/her id */ typedef std::unordered_map players_t; static players_t players; /**< player_a, player_b, a's black 0 or white 1, [wins, losses, others] */ typedef boost::multi_array array_t; array_t winloss(boost::extents[MAX_PLAYERS][MAX_PLAYERS][2][3]); enum GameResult { BLACK_WIN = 0, WHITE_WIN, OTHERS }; const std::string& getPlayerName(const unsigned int id) { players_t::const_iterator each_player = players.begin(); for (; each_player != players.end(); ++each_player) { if (each_player->second == id) break; } assert(each_player != players.end()); return each_player->first; } unsigned int setPlayer(const std::string& player) { players_t::const_iterator hit = players.find(player); if (hit == players.end()) { // new player if (players.size() >= MAX_PLAYERS) { std::cerr << "No longer accomodate a new player.\n"; exit(-1); } const unsigned int new_id = players.size(); players.insert(std::make_pair(player, new_id)); return new_id; } else { return hit->second; } } void increment(unsigned int black, unsigned int white, GameResult gr) { // player_a is black winloss[black][white][0][static_cast(gr)] += 1; // player_a is white if (gr == BLACK_WIN) { winloss[white][black][1][1] += 1; // player_a lost } else if (gr == WHITE_WIN) { winloss[white][black][1][0] += 1; // player_a won } else { assert(gr == OTHERS); winloss[white][black][1][2] += 1; // others } } GameResult getGameResult(const std::string& csa_file, const std::vector& moves) { std::ifstream in(csa_file.c_str()); if (!in) { std::cerr << "File not found: " << csa_file << "\n"; exit(-1); } bool hit = false; std::string line; while (std::getline(in, line)) { if (line.find("%TORYO") != std::string::npos) { hit = true; break; } } if (hit) { return (moves.size() % 2 == 1 ? BLACK_WIN : WHITE_WIN); } else { return OTHERS; } } void readFile(const std::string& csa_file, osl::record::CheckDuplicate& duplicates) { const osl::CsaFile csa(csa_file); const auto& record = csa.load(); const auto moves = record.moves(); if (duplicates.regist(moves)) return; const std::string& black = record.player[osl::BLACK]; const std::string& white = record.player[osl::WHITE]; const unsigned int black_id = setPlayer(black); const unsigned int white_id = setPlayer(white); const GameResult gr = getGameResult(csa_file, moves); increment(black_id, white_id, gr); } void printTotal(std::ostream& out) { out << "=== Total [ #wins / #losses / #others ] ===\n"; for (unsigned int player_a = 0; player_a < players.size(); ++player_a) { for (unsigned int player_b = 0; player_b < players.size(); ++player_b) { if (player_a == player_b) continue; out << boost::format("%- 17s ") % getPlayerName(player_a); unsigned int wins = 0, losses = 0, others = 0; wins += winloss[player_a][player_b][0][0]; // a is black wins += winloss[player_a][player_b][1][0]; // a is white losses += winloss[player_a][player_b][0][1]; // a is black losses += winloss[player_a][player_b][1][1]; others += winloss[player_a][player_b][0][2]; // a is black others += winloss[player_a][player_b][1][2]; out << boost::format("%5d/%5d/%5d ") % wins % losses % others; out << boost::format("%- 17s ") % getPlayerName(player_b); } out << "\n"; } out << "\n"; } void printResult(std::ostream& out) { out << "=== Left players are BLACK [ #wins / #losses / #others ] ===\n"; out << boost::format("%= 17s ") % ""; for (unsigned int player_a = 0; player_a < players.size(); ++player_a) { out << boost::format("%= 17s ") % getPlayerName(player_a); } out << "\n"; for (unsigned int player_a = 0; player_a < players.size(); ++player_a) { out << boost::format("%= 17s ") % getPlayerName(player_a); for (unsigned int player_b = 0; player_b < players.size(); ++player_b) { if (player_a == player_b) { out << boost::format("%= 17s ") % "-"; continue; } out << boost::format("%5d/%5d/%5d ") % winloss[player_a][player_b][0][0] % winloss[player_a][player_b][0][1] % winloss[player_a][player_b][0][2]; } out << "\n"; } out << "\n"; } int main(int argc, char **argv) { std::string kisen_filename; boost::program_options::options_description command_line_options; command_line_options.add_options() ("input-file", boost::program_options::value >(), "input files in the CSA format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) { const std::vector temp = vm["input-file"].as >(); files.insert(files.end(), temp.begin(), temp.end()); } else { std::string line; while(std::getline(std::cin , line)) { boost::algorithm::trim(line); files.push_back(line); } } osl::record::CheckDuplicate check_duplicate; for (const std::string& file: files) { readFile(file, check_duplicate); } std::locale::global(std::locale("")); printResult(std::cout); printTotal(std::cout); check_duplicate.print(std::cout); return 0; } /* vim: set ts=2 sw=2 ft=cpp : */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 libosl-0.8.0.orig/sample/record/first-search-eval.cc0000644000000000000000000001050412316770314021031 0ustar rootroot//#include "osl/misc/math.h" #include "osl/record/csaRecord.h" #include "osl/record/checkDuplicate.h" #include "osl/record/record.h" #include "osl/record/searchInfo.h" #include "osl/misc/math.h" #include #include #include #include #include #include typedef std::vector value_t; typedef std::pair pair_t; typedef std::map map_t; void logValue(const std::string& player, const std::string& turn, const int value, const std::string& csa_file) { const std::string log_file = player + "_" + turn + ".log"; std::ofstream out(log_file.c_str(), std::ios::app); out << value << "\t" << csa_file << "\n"; } /** * Return true when reading a csa_file for the fist time; * false otherwise. */ void readFile(const std::string& csa_file, map_t& map) { const osl::CsaFile csa(csa_file); const auto& record = csa.load(); // black for (size_t i=0; i < record.moves().size(); i += 2) { if (record.move_info[i].isValid()) { const std::string player = record.player[osl::BLACK]; const int eval = record.move_info[i].value; pair_t& pair = map[player]; value_t& values = pair.first; values.push_back(eval); logValue(player, "black", eval, csa_file); break; } } // white for (size_t i=1; i < record.moves().size(); i += 2) { if (record.move_info[i].isValid()) { const std::string player = record.player[osl::WHITE]; const int eval = record.move_info[i].value; pair_t& pair = map[player]; value_t& values = pair.second; values.push_back(eval); logValue(player, "white", eval, csa_file); break; } } } void showResult(const map_t& map) { for (const map_t::value_type& vt: map) { std::cout << "===== " << vt.first << " =====\n"; { int sum, mean, var, std_dev, skew, kurt; osl::misc::computeStats(vt.second.first.begin(), vt.second.first.end(), sum, mean, var, std_dev, skew, kurt); std::cout << "[BLACK] mean: " << mean << ", std_dev: " << std_dev << std::endl; } { int sum, mean, var, std_dev, skew, kurt; osl::misc::computeStats(vt.second.second.begin(), vt.second.second.end(), sum, mean, var, std_dev, skew, kurt); std::cout << "[WHITE] mean: " << mean << ", std_dev: " << std_dev << std::endl; } } } int main(int argc, char **argv) { namespace bp = boost::program_options; bp::options_description command_line_options; command_line_options.add_options() ("input-file", bp::value >(), "input files in the CSA format") ("help", "Show help message"); bp::variables_map vm; bp::positional_options_description p; p.add("input-file", -1); try { bp::store( bp::command_line_parser(argc, argv).options(command_line_options).positional(p).run(), vm); bp::notify(vm); if (vm.count("help")) { std::cerr << "Calculate evaluation values for the initial search moves after finishing opening moves.\n"; std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Calculate evaluation values for the initial search moves after finishing opening moves.\n"; std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) { const std::vector temp = vm["input-file"].as >(); files.insert(files.end(), temp.begin(), temp.end()); } else { std::string line; while(std::getline(std::cin , line)) { boost::algorithm::trim(line); files.push_back(line); } } map_t map; for (const std::string& file: files) { readFile(file, map); } showResult(map); return 0; } /* vim: set ts=2 sw=2 ft=cpp : */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 libosl-0.8.0.orig/sample/record/checkmate-kisen.cc0000644000000000000000000001675212320177344020557 0ustar rootroot#include "osl/numEffectState.h" #include "osl/hashKey.h" #include "osl/state/historyState.h" #include "osl/record/kisen.h" #include "osl/record/csaRecord.h" #include "osl/checkmate/dualDfpn.h" #include "osl/eval/see.h" #include "osl/misc/filePath.h" #include "osl/oslConfig.h" #include #include #include #include #include #include #include #include #include #include static std::vector convert_from_first(osl::NumEffectState state, const std::vector &in, size_t checkmate_limit) { osl::DualDfpn dfpn; std::vector out; for (osl::Move move: in) { const int see = osl::See::see (state, move, state.pin(state.turn()), state.pin(alt(state.turn()))); out.push_back(move); state.makeMove(move); if (state.inCheck() && see < 0 && dfpn.isLosingState(checkmate_limit, state, osl::HashKey(state), osl::PathEncoding(state.turn()))) break; } return out; } static std::vector trim_last(osl::NumEffectState initial, const std::vector &in, size_t checkmate_limit) { std::vector out; if (in.empty()) return out; osl::DualDfpn dfpn; osl::HistoryState history(initial); for (osl::Move move: in) history.makeMove(move); const osl::Player last_played = in.back().player(); int length = in.size(); for (; length > 0; length -= 2) { osl::NumEffectState current = history.state(); assert(current.turn() == alt(last_played)); if (! current.inCheck()) break; if (! dfpn.isLosingState(checkmate_limit, current, osl::HashKey(current), osl::PathEncoding(current.turn()))) break; history.unmakeMove(); history.unmakeMove(); if (length + 50 < in.size()) break; } out = in; out.resize(length); return out; } static void convert(const std::vector &input_filename, const std::string &output_kisen_filename, size_t checkmate_limit, bool output_ipx, bool trim) { namespace acc = boost::accumulators; acc::accumulator_set > accumulator; std::ofstream ofs(output_kisen_filename.c_str()); osl::KisenWriter ks(ofs); std::unique_ptr ipx_writer; std::unique_ptr ipx_ofs; if (output_ipx) { const boost::filesystem::path ipx_path = boost::filesystem::change_extension(boost::filesystem::path(output_kisen_filename), ".ipx"); const std::string ipx = osl::misc::file_string(ipx_path); ipx_ofs.reset(new std::ofstream(ipx.c_str())); ipx_writer.reset(new osl::record::KisenIpxWriter(*ipx_ofs)); } for (size_t i = 0; i < input_filename.size(); ++i) { osl::KisenFile kisen(input_filename[i]); osl::KisenIpxFile ipx(kisen.ipxFileName()); std::queue>> queue; const osl::NumEffectState initial = kisen.initialState(); size_t started = 0, concurrency = osl::OslConfig::concurrency(); while (started < std::min(concurrency, kisen.size())) { auto moves = kisen.moves(started++); queue.emplace(std::async(std::launch::async, [=](){ if (trim) return trim_last(initial, moves, checkmate_limit); else return convert_from_first(initial, moves, checkmate_limit); })); } for (size_t j=0; j= 256) std::cerr << "long record " << j << ' ' << new_moves.size() << "\n"; ks.save(new_record.record); if (output_ipx) { ipx_writer->save(new_record, ipx.rating(j, osl::BLACK),ipx.rating(j, osl::WHITE), ipx.title(j, osl::BLACK), ipx.title(j, osl::WHITE)); } if ((j % 1000) == 999) std::cerr << input_filename[i] << " " << j << " max " << acc::max(accumulator) << " mean " << acc::mean(accumulator) << "\n"; } std::cerr << input_filename[i] << " max " << acc::max(accumulator) << " mean " << acc::mean(accumulator) << "\n"; } } int main(int argc, char **argv) { bool output_ipx, trim; std::string kisen_filename; size_t checkmate_limit; int concurrency; boost::program_options::options_description command_line_options; command_line_options.add_options() ("trim-from-last", boost::program_options::value(&trim)->default_value(true), "trim last checkmate sequence") ("output-ipx", boost::program_options::value(&output_ipx)->default_value(true), "Whether output IPX file in addition to KIF file") ("output-kisen-filename,o", boost::program_options::value(&kisen_filename)-> default_value("test.kif"), "Output filename of Kisen file") ("checkmate-limit,l", boost::program_options::value(&checkmate_limit)->default_value(1000), "Whether output IPX file in addition to KIF file") ("num-cpus,N", boost::program_options::value(&concurrency)->default_value(std::thread::hardware_concurrency()), "concurrency") ("input-file", boost::program_options::value< std::vector >(), "input files in kisen format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] kisen-files\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] kisen-files\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) files = vm["input-file"].as >(); osl::OslConfig::setUp(); osl::OslConfig::setNumCPUs(concurrency); convert(files, kisen_filename, checkmate_limit, output_ipx, trim); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/record/check-kisen.cc0000644000000000000000000000263712316770314017706 0ustar rootroot#include "osl/numEffectState.h" #include "osl/record/kisen.h" #include void usage (const char *program_name) { std::cerr << "Usage: " << program_name << " KISEN-FILE [out]" << std::endl; exit(1); } void check_all(const char*filename, const char *output) { osl::record::KisenFile kisen(filename); std::unique_ptr os; if (output) { os.reset(new std::ofstream(output)); } for (size_t i = 0; i < kisen.size(); i++) { std::cout << i; if ((i % 16) == 15 || i + 1 == kisen.size()) std::cout << std::endl; else std::cout << ' '; osl::NumEffectState state(kisen.initialState()); std::vector moves; size_t j = 0; try { moves = kisen.moves(i); for (; j < moves.size(); j++) { const osl::Square opKingSquare = state.kingSquare(alt(state.turn())); if (state.hasEffectAt(state.turn(), opKingSquare)) { if (j) --j; break; } state.makeMove(moves[j]); } moves.resize(j); } catch (osl::csa::CsaIOError& e) { std::cerr << e.what(); } if (os) { osl::record::KisenWriter out(*os); out.save({kisen.initialState(), moves}); } } } int main(int argc, char **argv) { if (! (argc == 2 || argc == 3)) usage(argv[0]); check_all(argv[1], (argc == 3) ? argv[2] : ""); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/record/show-ki2-all.sh0000755000000000000000000000034511210234410017735 0ustar rootroot#!/usr/bin/zsh dir="${1:-../../../2chkifu}" for i in $dir/*.(ki2|KI2) do basename="$(basename $i)" echo "$i" "$(dirname $0)/show-ki2" -q $i if [ $? -ne 0 ];then echo "ERROR: $i" move "$i" "$dir/ERROR" fi done libosl-0.8.0.orig/sample/record/win-rate-openingbook-weight-level.cc0000644000000000000000000002014412316770314024143 0ustar rootroot#include "osl/oslConfig.h" #include "osl/game_playing/weightTracer.h" #include "osl/record/csaRecord.h" #include "osl/record/checkDuplicate.h" #include "osl/book/openingBook.h" #include #include #include #include #include #include #include using namespace osl; enum GameResult { BLACK_WIN = 0, WHITE_WIN, OTHERS }; struct WinLoss { unsigned int wins; unsigned int losses; WinLoss() : wins(0), losses(0) {} double getRate() const { if (isEmpty()) return 0.0; return 1.0*wins/(wins+losses); } bool isEmpty() const { return (wins + losses) == 0; } }; std::ostream& operator<<(std::ostream& out, const WinLoss& wl) { out << boost::format("%5.3f (#wins=%6d, #losses=%6d)") % wl.getRate() % wl.wins % wl.losses; return out; } struct Result { enum {MAX_LEVEL = 99, MAX_DEPTH = 999}; /**< n-th move, n-th level, [wins, losses] */ typedef boost::multi_array array_t; array_t winloss; unsigned int top_level; unsigned int top_depth; Result() : winloss(boost::extents[MAX_DEPTH][MAX_LEVEL][2]), top_level(0), top_depth(0) {} void add(const unsigned int depth, const unsigned int level, const bool win) { assert(depth < MAX_DEPTH); assert(level < MAX_LEVEL); if (win) winloss[depth][level][0] += 1; else winloss[depth][level][1] += 1; top_level = std::max(top_level, level); top_depth = std::max(top_depth, depth); } bool printAtDepth(std::ostream& out, const unsigned int depth) const; void printByLevel(std::ostream& out) const; void printByDepth(std::ostream& out) const; void showLevels(std::ostream& out, std::vector& vector) const; }; void Result::showLevels(std::ostream& out, std::vector& vector) const { // GC std::vector::reverse_iterator empty = vector.rbegin(); for (/*none*/; empty != vector.rend(); ++empty) { if (!empty->isEmpty()) break; } vector.erase(empty.base(), vector.end()); unsigned int level = 1; for (const WinLoss& wl: vector) { out << boost::format("%2d: %s\n") % level++ % wl; } } bool Result::printAtDepth(std::ostream& out, const unsigned int depth) const { std::vector vector; for(unsigned int level=0; level < MAX_LEVEL; ++level) { WinLoss wl; wl.wins += winloss[depth][level][0]; wl.losses += winloss[depth][level][1]; vector.push_back(wl); } showLevels(out, vector); return vector.empty(); } void Result::printByDepth(std::ostream& out) const { for (unsigned int depth=1; depth < top_depth; ++depth) { out << boost::format("\n>> Depth %2d\n") % depth; printAtDepth(out, depth); } } void Result::printByLevel(std::ostream& out) const { std::vector vector; for(unsigned int level=0; level < MAX_LEVEL; ++level) { WinLoss wl; for (unsigned int depth=0; depth < MAX_DEPTH; ++depth) { wl.wins += winloss[depth][level][0]; wl.losses += winloss[depth][level][1]; } vector.push_back(wl); } showLevels(out, vector); } // ============================================== // Global variables // ============================================== static Result result; osl::book::WeightedBook book(osl::OslConfig::openingBook()); // ============================================== // Functions // ============================================== GameResult getGameResult(const std::string& csa_file, const std::vector& moves) { std::ifstream in(csa_file.c_str()); if (!in) { std::cerr << "File not found: " << csa_file << "\n"; exit(-1); } bool hit = false; std::string line; while (std::getline(in, line)) { if (line.find("%TORYO") != std::string::npos) { hit = true; break; } } if (hit) { return (moves.size() % 2 == 1 ? BLACK_WIN : WHITE_WIN); } else { return OTHERS; } } void increment(const std::vector& moves, const Player player, const bool win) { int stateIndex = ::book.startState(); Player turn = BLACK; unsigned int depth = 1; for (const Move& move: moves) { osl::book::WeightedBook::WMoveContainer wmoves = ::book.moves(stateIndex, (player == turn ? false : true)); std::sort(wmoves.begin(), wmoves.end(), osl::book::WMoveSort()); /* * It ends if a move that is not included in the book is played. */ osl::book::WeightedBook::WMoveContainer::iterator found = wmoves.begin(); for (/*none*/; found != wmoves.end(); ++found) { if (found->move == move) break; } if (found == wmoves.end()) return; // finish this record /* * Increment */ if (turn == player) { const unsigned int level = std::distance(wmoves.begin(), found); // 1, 2, ... result.add(depth, level, win); } /* * Prepare for the next iteration */ turn = alt(turn); depth += 1; stateIndex = found->stateIndex(); } // each move } void readFile(const std::string& player_name, const std::string& csa_file, osl::record::CheckDuplicate& duplicates) { const osl::CsaFile csa(csa_file); const auto& record = csa.load(); const auto moves = record.moves(); const GameResult gr = getGameResult(csa_file, moves); if (gr == OTHERS) return; if (duplicates.regist(moves)) return; const std::string& black = record.player[BLACK]; const std::string& white = record.player[WHITE]; Player player = BLACK; bool win = true; if (black.find(player_name) != std::string::npos) { player = BLACK; win = (gr == BLACK_WIN); } else if (white.find(player_name) != std::string::npos) { player = WHITE; win = (gr == WHITE_WIN); } else { std::cerr << "Ignore this play: " << csa_file << "\n"; return; } increment(moves, player, win); } int main(int argc, char **argv) { std::string player_name; boost::program_options::options_description command_line_options; command_line_options.add_options() ("input-file", boost::program_options::value >(), "input files in the CSA format") ("player", boost::program_options::value(&player_name)->default_value("gps"), "input files in the CSA format") ("help", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) { const std::vector temp = vm["input-file"].as >(); files.insert(files.end(), temp.begin(), temp.end()); } else { std::string line; while(std::getline(std::cin , line)) { boost::algorithm::trim(line); files.push_back(line); } } osl::record::CheckDuplicate check_duplicate; for (const std::string& file: files) { readFile(player_name, file, check_duplicate); } result.printByLevel(std::cout); result.printByDepth(std::cout); std::locale::global(std::locale("")); check_duplicate.print(std::cout); return 0; } /* vim: set ts=2 sw=2 ft=cpp : */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 libosl-0.8.0.orig/sample/record/kisen-to-csa.cc0000644000000000000000000000161212316770314020007 0ustar rootroot#include "osl/numEffectState.h" #include "osl/record/kisen.h" #include "osl/record/csaRecord.h" #include #include void usage (const char *program_name) { std::cerr << "Usage: " << program_name << " KISENFILE INDEX CSAFILE" << std::endl; exit(1); } void convert(const char*kisen_filename, const char *csa_filename, size_t i) { osl::record::KisenFile kisen(kisen_filename); std::ofstream ofs(csa_filename); if (i < kisen.size()) { osl::NumEffectState state = kisen.initialState(); ofs << state; const auto& moves = kisen.moves(i); for (size_t j = 0; j < moves.size(); ++j) { ofs << osl::csa::show(moves[j]) << std::endl; } } else { std::cerr << "Index out of bounds: " << i << std::endl; } } int main(int argc, char **argv) { if (argc != 4) usage(argv[0]); convert(argv[1], argv[3], atoi(argv[2])); return 0; } libosl-0.8.0.orig/sample/record/move_iregular_records.rb0000755000000000000000000000115311005075115022103 0ustar rootroot#!/usr/bin/ruby # # Move Komaochi (hadicapped game) records # require 'find' require 'nkf' require 'fileutils' dir = ARGV.shift Dir.glob(File.join(dir, "*.ki2")) do |path| puts "Processing... #{path}" sjis = open(path, "r") {|f| f.read} euc = NKF.nkf("-Se", sjis) if /^¼ê¹ç³ä¡§/ =~ euc to_path = File.join(File.dirname(path), "KOMAOCHI", File.basename(path)) puts "mv #{path} #{to_path}" FileUtils.mv(path, to_path) elsif /ȿ§¾¡¤Á/ =~ euc to_path = File.join(File.dirname(path), "ILLEGAL", File.basename(path)) puts "mv #{path} #{to_path}" FileUtils.mv(path, to_path) end end libosl-0.8.0.orig/sample/record/show-ki2.cc0000644000000000000000000000461412316770314017162 0ustar rootroot/* show-ki2.cc */ #include "osl/record/kanjiMove.h" #include "osl/record/ki2.h" #include #include #include #include #include #include #include #include using namespace boost::lambda; bool quiet = false; void process( const std::string& file_name) { std::cout << "Processing... " << file_name << std::endl; osl::Ki2File ki2(file_name, !quiet); if (quiet) return; const osl::Record record = ki2.load(); const std::vector moves = record.moves(); std::for_each(moves.begin(), moves.end(), std::cout << _1 << "\n" ); } /** * Show .ki2 files (known as 2ch format). * * Record database: http://wiki.optus.nu/shogi/index.php?page=FrontPage * Archive to download: http://maris-stella.hp.infoseek.co.jp/ * Note that the archiver called DGCA format only supports Windows. */ int main(int argc, char **argv) { boost::program_options::options_description command_line_options; command_line_options.add_options() ("quiet,q", "quiet output") ("input-file", boost::program_options::value< std::vector >(), "input files in ki2 format (.ki2)") ("help,h", "Show help message"); boost::program_options::variables_map vm; boost::program_options::positional_options_description p; p.add("input-file", -1); try { boost::program_options::store( boost::program_options::command_line_parser( argc, argv).options(command_line_options).positional(p).run(), vm); boost::program_options::notify(vm); if (vm.count("help")) { std::cout << "Usage: " << argv[0] << " [options] ki2-file [ki2-file...]" << std::endl; std::cout << command_line_options << std::endl; return 0; } if (vm.count("quiet")) quiet = true; } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Usage: " << argv[0] << " [options] ki2-file [ki2-file...]" << std::endl; std::cerr << command_line_options << std::endl; return 1; } const std::vector files = vm["input-file"].as< std::vector >(); std::for_each(files.begin(), files.end(), [](std::string f){ process(f); }); return 0; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/record/unique-csa.cc0000644000000000000000000000465512316770314017576 0ustar rootroot#include "osl/record/csaRecord.h" #include "osl/record/checkDuplicate.h" #include #include #include #include #include /** * Return true when reading a csa_file for the fist time; * false otherwise. */ bool readFile(const std::string& csa_file, osl::record::CheckDuplicate& duplicates) { const osl::CsaFileMinimal csa(csa_file); const auto& record = csa.load(); const auto moves = record.moves; return !duplicates.regist(moves); } int main(int argc, char **argv) { namespace bp = boost::program_options; bp::options_description command_line_options; command_line_options.add_options() ("input-file", bp::value >(), "input files in the CSA format") ("help", "Show help message"); bp::variables_map vm; bp::positional_options_description p; p.add("input-file", -1); try { bp::store( bp::command_line_parser(argc, argv).options(command_line_options).positional(p).run(), vm); bp::notify(vm); if (vm.count("help")) { std::cerr << "Filter duplicated records from specified CSA files.\n"; std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cout << command_line_options << std::endl; return 0; } } catch (std::exception &e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << "Filter duplicated records from specified CSA files.\n"; std::cerr << "Usage: " << argv[0] << " [options] csa-file [...]\n"; std::cerr << " " << argv[0] << " [options]\n"; std::cerr << command_line_options << std::endl; return 1; } std::vector files; if (vm.count("input-file")) { const std::vector temp = vm["input-file"].as >(); files.insert(files.end(), temp.begin(), temp.end()); } else { std::string line; while(std::getline(std::cin , line)) { boost::algorithm::trim(line); files.push_back(line); } } osl::record::CheckDuplicate check_duplicate; for (const std::string& file: files) { if (readFile(file, check_duplicate)) std::cout << file << std::endl; } check_duplicate.print(std::cerr); return 0; } /* vim: set ts=2 sw=2 ft=cpp : */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 libosl-0.8.0.orig/sample/record/kakinoki-to-csa.cc0000644000000000000000000000232212316770314020475 0ustar rootroot/* kakinoki-to-csa.cc */ #include "osl/record/kakinoki.h" #include "osl/record/ki2.h" #include "osl/csa.h" #include #include #include using namespace osl; void convert(const char *filename) { std::vector moves; std::vector time; Record record; NumEffectState state; if (boost::algorithm::iends_with(filename, ".ki2")) { Ki2File file(filename); record = file.load(); state = file.initialState(); } else { KakinokiFile file(filename); record = file.load(); state = file.initialState(); } std::cout << "N+" << record.player[BLACK] << std::endl; std::cout << "N-" << record.player[WHITE] << std::endl; record.load(moves, time); std::cout << state; for (size_t i=0; i #include #include using namespace osl; int main(int argc, char **argv) { std::vector results(9, 0); for (int i=1; i(results.at(0)) << std::endl; std::cout << "BLACK_WIN " << boost::lexical_cast(results.at(1)) << std::endl; std::cout << "WHITE_WIN " << boost::lexical_cast(results.at(2)) << std::endl; std::cout << "SENNNICHITE " << boost::lexical_cast(results.at(3)) << std::endl; std::cout << "JISHOGI " << boost::lexical_cast(results.at(4)) << std::endl; std::cout << "BLACK_WIN_256 " << boost::lexical_cast(results.at(5)) << std::endl; std::cout << "WIHTE_WIN_256 " << boost::lexical_cast(results.at(6)) << std::endl; std::cout << "SENNNICHITE_256 " << boost::lexical_cast(results.at(7)) << std::endl; std::cout << "JISHOGI_256 " << boost::lexical_cast(results.at(8)) << std::endl; return 0; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/sample/pass.cc0000644000000000000000000000462112316770314015205 0ustar rootroot#include "osl/eval/openMidEndingEval.h" #include "osl/game_playing/alphaBetaPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/progress.h" #include "osl/record/kisen.h" #include "osl/search/moveWithComment.h" #include "osl/sennichite.h" #include #include namespace po = boost::program_options; int main(int argc, char **argv) { std::string kisen_filename; int kisen_index; po::options_description options("Options"); options.add_options() ("kisen,k", po::value(&kisen_filename), "kisen filename") ("index,i", po::value(&kisen_index)->default_value(0)) ("help", "produce help message") ; po::positional_options_description p; po::variables_map vm; try { po::store(po::command_line_parser(argc, argv). options(options).positional(p).run(), vm); notify(vm); if (vm.count("help")) { std::cout << options << std::endl; return 0; } } catch (std::exception& e) { std::cerr << "error in parsing options" << std::endl << e.what() << std::endl; std::cerr << options << std::endl; return 1; } osl::record::KisenFile kisen(kisen_filename); osl::NumEffectState state(kisen.initialState()); auto moves = kisen.moves(kisen_index); osl::eval::ml::OpenMidEndingEval::setUp(); osl::progress::ml::NewProgress::setUp(); osl::game_playing::GameState game_state(state); osl::game_playing::AlphaBeta2OpenMidEndingEvalPlayer player; player.setDepthLimit(600, 400, 200); if (osl::OslConfig::isMemoryLimitEffective()) { player.setTableLimit(std::numeric_limits::max(), 200); player.setNodeLimit(std::numeric_limits::max()); } for (size_t i = 0; i < moves.size() + 1; ++i) { if (!game_state.state().inCheck()) { osl::search::MoveWithComment result = player.selectBestMove(game_state, 0, 0, 10); osl::NumEffectState state2(game_state.state()); state2.changeTurn(); osl::game_playing::GameState game_state2(state2); osl::search::MoveWithComment pass_result = player.selectBestMove(game_state2, 0, 0, 10); int diff = result.value - pass_result.value; std::cout << i << " " << result.value << " " << pass_result.value << " " << (i % 2 == 0 ? diff : -diff) << std::endl; } if (i < moves.size()) { game_state.pushMove(moves[i]); } } return 0; } libosl-0.8.0.orig/makefile.local.sample0000644000000000000000000000540712206077241016520 0ustar rootroot### -------- -------- -------- -------- -------- ### build options ### -------- -------- -------- -------- -------- ###### CPUOPTION (default: -march=native) ### build option for smp (need more memory than sequential version) CPUOPTION = -march=native -DOSL_SMP ### specialized build for endgame analysis or checkmate search (need more memory than above) CPUOPTION = -march=native -DOSL_SMP -DOSL_DFPN_SMP_SEARCH -DMORE_CHECKMATE_IF_CAPTURE_MAJOR CPUOPTION = -march=native -DOSL_SMP -DOSL_DFPN_SMP_SEARCH -DOSL_DFPN_MAX_DEPTH=2048 ### for gcc-4.[1-3] CPUOPTION = -march=native -fno-strict-aliasing ###### postfix of boost library (default: null) BOOST_POSTFIX = -gcc BOOST_POSTFIX_MT = -gcc-mt ###### path to gcc (default: g++) GXX = /usr/local/gcc-4.4/bin/g++ CXX = /usr/local/gcc-4.4/bin/g++ CXX_HOME = /usr/local/gcc-4.4 ###### path to library INCLUDES += -I/usr/include/boost-1_40_0 ### -------- -------- -------- -------- -------- ### examples ### -------- -------- -------- -------- -------- ### linux # ### FreeBSD CXXOPTFLAGS += -O2 CPUOPTION = -march=native -fno-strict-aliasing LDFLAGS += -L/usr/local/lib -pthread INCLUDES += -I/usr/local/include -I/usr/X11R6/include QMAKEENV = QMAKESPEC=freebsd-g++ QTDIR=/usr/X11R6 LOADLIBES += -lkvm -liconv ### snow leopard CPUOPTION = -march=core2 USE_TBB_SCALABLE_ALLOCATOR = 1 USE_TCMALLOC = 0 LOADLIBES += -lboost_system -liconv QMAKEENV = QMAKESPEC=macx-g++ QMAKEPATH = /Developer/Tools/Qt ### -------- -------- -------- -------- -------- ### performance options ### -------- -------- -------- -------- -------- ##### memory allocator ### tcmalloc (recommended in Linux) (default: 1) USE_TCMALLOC = 1 ### specify version # (e.g., g++ 4.7.3 Ubuntu 13.04) # TCMALLOC = gperftools-2.1 TCMALLOC = google-perftools-1.7 # TCMALLOC = tcmalloc-0.93 ### TBB allocator (intel threading building blocks) (recommended in Mac OS X) (default: 0) USE_TBB_SCALABLE_ALLOCATOR = 1 ### boost::fast_pool_allocator (maybe useful in Windows XP) (default: 0) USE_BOOST_POOL_ALLOCATOR = 1 ##### TBB containers: slight gain in efficiency with a bit more memory use (default: 0, OSL_SMP only) USE_TBB = 1 ### -------- -------- -------- -------- -------- ### options for developer ### -------- -------- -------- -------- -------- # gdb debug 中以外ã¯ãŠã™ã™ã‚ (testã®å®Ÿè¡ŒãŒé€Ÿã„) CXXOPTFLAGS += -O # 詰将棋デãƒãƒƒã‚° single thread only CXXOPTFLAGS += -DCHECKMATE_DEBUG # ntesuki を使ã†å ´åˆ #USE_NTESUKI = true # # icc 用 # LDFLAGS += -L/opt/intel/compiler70/ia32/lib # INCLUDES += -I /usr/local/include # cygwin gcc 3.4.4 WARN_FIELD_INITIALIZER= INCLUDES += -I/usr/include/boost-1_33_1 CXXOPTFLAGS = -O CPUOPTION= -march=pentium-m # USE_GPL_POOL_ALLOCATOR = 0 BOOST_POSTFIX = -gcc-mt BOOST_POSTFIX_MT = -gcc-mt libosl-0.8.0.orig/doc/0000755000000000000000000000000012316770314013211 5ustar rootrootlibosl-0.8.0.orig/doc/Doxyfile0000644000000000000000000011521412316770314014723 0ustar rootroot# Doxyfile 1.2.18 # This file describes the settings to be used by the documentation system # doxygen (www.doxygen.org) for a project # # All text after a hash (#) is considered a comment and will be ignored # The format is: # TAG = value [value, ...] # For lists items can also be appended using: # TAG += value [value, ...] # Values that contain spaces should be placed between quotes (" ") #--------------------------------------------------------------------------- # General configuration options #--------------------------------------------------------------------------- # The PROJECT_NAME tag is a single word (or a sequence of words surrounded # by quotes) that should identify the project. PROJECT_NAME = # The PROJECT_NUMBER tag can be used to enter a project or revision number. # This could be handy for archiving the generated documentation or # if some version control system is used. PROJECT_NUMBER = # The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) # base path where the generated documentation will be put. # If a relative path is entered, it will be relative to the location # where doxygen was started. If left blank the current directory will be used. OUTPUT_DIRECTORY = # The OUTPUT_LANGUAGE tag is used to specify the language in which all # documentation generated by doxygen is written. Doxygen will use this # information to generate all constant output in the proper language. # The default language is English, other supported languages are: # Brazilian, Catalan, Chinese, Chinese-Traditional, Croatian, Czech, Danish, Dutch, # Finnish, French, German, Greek, Hungarian, Italian, Japanese, Japanese-en # (Japanese with english messages), Korean, Norwegian, Polish, Portuguese, # Romanian, Russian, Serbian, Slovak, Slovene, Spanish, Swedish and Ukrainian. OUTPUT_LANGUAGE = Japanese # If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in # documentation are documented, even if no documentation was available. # Private class members and static file members will be hidden unless # the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES EXTRACT_ALL = YES # If the EXTRACT_PRIVATE tag is set to YES all private members of a class # will be included in the documentation. EXTRACT_PRIVATE = YES # If the EXTRACT_STATIC tag is set to YES all static members of a file # will be included in the documentation. EXTRACT_STATIC = YES # If the EXTRACT_LOCAL_CLASSES tag is set to YES classes (and structs) # defined locally in source files will be included in the documentation. # If set to NO only classes defined in header files are included. EXTRACT_LOCAL_CLASSES = YES # If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all # undocumented members of documented classes, files or namespaces. # If set to NO (the default) these members will be included in the # various overviews, but no documentation section is generated. # This option has no effect if EXTRACT_ALL is enabled. HIDE_UNDOC_MEMBERS = NO # If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all # undocumented classes that are normally visible in the class hierarchy. # If set to NO (the default) these class will be included in the various # overviews. This option has no effect if EXTRACT_ALL is enabled. HIDE_UNDOC_CLASSES = NO # If the HIDE_FRIEND_COMPOUNDS tag is set to YES, Doxygen will hide all # friend (class|struct|union) declarations. # If set to NO (the default) these declarations will be included in the # documentation. HIDE_FRIEND_COMPOUNDS = NO # If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will # include brief member descriptions after the members that are listed in # the file and class documentation (similar to JavaDoc). # Set to NO to disable this. BRIEF_MEMBER_DESC = YES # If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend # the brief description of a member or function before the detailed description. # Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the # brief descriptions will be completely suppressed. REPEAT_BRIEF = YES # If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then # Doxygen will generate a detailed section even if there is only a brief # description. ALWAYS_DETAILED_SEC = NO # If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all inherited # members of a class in the documentation of that class as if those members were # ordinary class members. Constructors, destructors and assignment operators of # the base classes will not be shown. INLINE_INHERITED_MEMB = NO # If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full # path before files name in the file list and in the header files. If set # to NO the shortest path that makes the file name unique will be used. FULL_PATH_NAMES = NO # If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag # can be used to strip a user defined part of the path. Stripping is # only done if one of the specified strings matches the left-hand part of # the path. It is allowed to use relative paths in the argument list. STRIP_FROM_PATH = # The INTERNAL_DOCS tag determines if documentation # that is typed after a \internal command is included. If the tag is set # to NO (the default) then the documentation will be excluded. # Set it to YES to include the internal documentation. INTERNAL_DOCS = NO # Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct # doxygen to hide any special comment blocks from generated source code # fragments. Normal C and C++ comments will always remain visible. STRIP_CODE_COMMENTS = YES # If the CASE_SENSE_NAMES tag is set to NO then Doxygen will only generate # file names in lower case letters. If set to YES upper case letters are also # allowed. This is useful if you have classes or files whose names only differ # in case and if your file system supports case sensitive file names. Windows # users are adviced to set this option to NO. CASE_SENSE_NAMES = YES # If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter # (but less readable) file names. This can be useful is your file systems # doesn't support long names like on DOS, Mac, or CD-ROM. SHORT_NAMES = NO # If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen # will show members with their full class and namespace scopes in the # documentation. If set to YES the scope will be hidden. HIDE_SCOPE_NAMES = NO # If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen # will generate a verbatim copy of the header file for each class for # which an include is specified. Set to NO to disable this. VERBATIM_HEADERS = YES # If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen # will put list of the files that are included by a file in the documentation # of that file. SHOW_INCLUDE_FILES = YES # If the JAVADOC_AUTOBRIEF tag is set to YES then Doxygen # will interpret the first line (until the first dot) of a JavaDoc-style # comment as the brief description. If set to NO, the JavaDoc # comments will behave just like the Qt-style comments (thus requiring an # explict @brief command for a brief description. JAVADOC_AUTOBRIEF = YES # The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make Doxygen # treat a multi-line C++ special comment block (i.e. a block of //! or /// # comments) as a brief description. This used to be the default behaviour. # The new default is to treat a multi-line C++ comment block as a detailed # description. Set this tag to YES if you prefer the old behaviour instead. MULTILINE_CPP_IS_BRIEF = NO # If the DETAILS_AT_TOP tag is set to YES then Doxygen # will output the detailed description near the top, like JavaDoc. # If set to NO, the detailed description appears after the member # documentation. DETAILS_AT_TOP = NO # If the INHERIT_DOCS tag is set to YES (the default) then an undocumented # member inherits the documentation from any documented member that it # reimplements. INHERIT_DOCS = YES # If the INLINE_INFO tag is set to YES (the default) then a tag [inline] # is inserted in the documentation for inline members. INLINE_INFO = YES # If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen # will sort the (detailed) documentation of file and class members # alphabetically by member name. If set to NO the members will appear in # declaration order. SORT_MEMBER_DOCS = YES # If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC # tag is set to YES, then doxygen will reuse the documentation of the first # member in the group (if any) for the other members of the group. By default # all members of a group must be documented explicitly. DISTRIBUTE_GROUP_DOC = NO # The TAB_SIZE tag can be used to set the number of spaces in a tab. # Doxygen uses this value to replace tabs by spaces in code fragments. TAB_SIZE = 8 # The GENERATE_TODOLIST tag can be used to enable (YES) or # disable (NO) the todo list. This list is created by putting \todo # commands in the documentation. GENERATE_TODOLIST = YES # The GENERATE_TESTLIST tag can be used to enable (YES) or # disable (NO) the test list. This list is created by putting \test # commands in the documentation. GENERATE_TESTLIST = YES # The GENERATE_BUGLIST tag can be used to enable (YES) or # disable (NO) the bug list. This list is created by putting \bug # commands in the documentation. GENERATE_BUGLIST = YES # The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or # disable (NO) the deprecated list. This list is created by putting \deprecated commands in the documentation. GENERATE_DEPRECATEDLIST= YES # This tag can be used to specify a number of aliases that acts # as commands in the documentation. An alias has the form "name=value". # For example adding "sideeffect=\par Side Effects:\n" will allow you to # put the command \sideeffect (or @sideeffect) in the documentation, which # will result in a user defined paragraph with heading "Side Effects:". # You can put \n's in the value part of an alias to insert newlines. ALIASES = # The ENABLED_SECTIONS tag can be used to enable conditional # documentation sections, marked by \if sectionname ... \endif. ENABLED_SECTIONS = # The MAX_INITIALIZER_LINES tag determines the maximum number of lines # the initial value of a variable or define consist of for it to appear in # the documentation. If the initializer consists of more lines than specified # here it will be hidden. Use a value of 0 to hide initializers completely. # The appearance of the initializer of individual variables and defines in the # documentation can be controlled using \showinitializer or \hideinitializer # command in the documentation regardless of this setting. MAX_INITIALIZER_LINES = 30 # Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources # only. Doxygen will then generate output that is more tailored for C. # For instance some of the names that are used will be different. The list # of all members will be omitted, etc. OPTIMIZE_OUTPUT_FOR_C = NO # Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java sources # only. Doxygen will then generate output that is more tailored for Java. # For instance namespaces will be presented as packages, qualified scopes # will look different, etc. OPTIMIZE_OUTPUT_JAVA = NO # Set the SHOW_USED_FILES tag to NO to disable the list of files generated # at the bottom of the documentation of classes and structs. If set to YES the # list will mention the files that were used to generate the documentation. SHOW_USED_FILES = YES #--------------------------------------------------------------------------- # configuration options related to warning and progress messages #--------------------------------------------------------------------------- # The QUIET tag can be used to turn on/off the messages that are generated # by doxygen. Possible values are YES and NO. If left blank NO is used. QUIET = NO # The WARNINGS tag can be used to turn on/off the warning messages that are # generated by doxygen. Possible values are YES and NO. If left blank # NO is used. WARNINGS = YES # If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings # for undocumented members. If EXTRACT_ALL is set to YES then this flag will # automatically be disabled. WARN_IF_UNDOCUMENTED = YES # The WARN_FORMAT tag determines the format of the warning messages that # doxygen can produce. The string should contain the $file, $line, and $text # tags, which will be replaced by the file and line number from which the # warning originated and the warning text. WARN_FORMAT = "$file:$line: $text" # The WARN_LOGFILE tag can be used to specify a file to which warning # and error messages should be written. If left blank the output is written # to stderr. WARN_LOGFILE = doxygen.err #--------------------------------------------------------------------------- # configuration options related to the input files #--------------------------------------------------------------------------- # The INPUT tag can be used to specify the files and/or directories that contain # documented source files. You may enter file names like "myfile.cpp" or # directories like "/usr/src/myproject". Separate the files or directories # with spaces. INPUT = ../core/osl ../std/osl ../extra/osl # If the value of the INPUT tag contains directories, you can use the # FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp # and *.h) to filter out the source-files in the directories. If left # blank the following patterns are tested: # *.c *.cc *.cxx *.cpp *.c++ *.java *.ii *.ixx *.ipp *.i++ *.inl *.h *.hh *.hxx *.hpp # *.h++ *.idl *.odl FILE_PATTERNS = *.h *.hpp *.cc *.tcc # The RECURSIVE tag can be used to turn specify whether or not subdirectories # should be searched for input files as well. Possible values are YES and NO. # If left blank NO is used. RECURSIVE = YES # The EXCLUDE tag can be used to specify files and/or directories that should # excluded from the INPUT source files. This way you can easily exclude a # subdirectory from a directory tree whose root is specified with the INPUT tag. EXCLUDE = ../lib/third_party # The EXCLUDE_SYMLINKS tag can be used select whether or not files or directories # that are symbolic links (a Unix filesystem feature) are excluded from the input. EXCLUDE_SYMLINKS = NO # If the value of the INPUT tag contains directories, you can use the # EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude # certain files from those directories. EXCLUDE_PATTERNS = */experimental/* # The EXAMPLE_PATH tag can be used to specify one or more files or # directories that contain example code fragments that are included (see # the \include command). EXAMPLE_PATH = # If the value of the EXAMPLE_PATH tag contains directories, you can use the # EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp # and *.h) to filter out the source-files in the directories. If left # blank all files are included. EXAMPLE_PATTERNS = # If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be # searched for input files to be used with the \include or \dontinclude # commands irrespective of the value of the RECURSIVE tag. # Possible values are YES and NO. If left blank NO is used. EXAMPLE_RECURSIVE = NO # The IMAGE_PATH tag can be used to specify one or more files or # directories that contain image that are included in the documentation (see # the \image command). IMAGE_PATH = # The INPUT_FILTER tag can be used to specify a program that doxygen should # invoke to filter for each input file. Doxygen will invoke the filter program # by executing (via popen()) the command , where # is the value of the INPUT_FILTER tag, and is the name of an # input file. Doxygen will then use the output that the filter program writes # to standard output. INPUT_FILTER = # If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using # INPUT_FILTER) will be used to filter the input files when producing source # files to browse (i.e. when SOURCE_BROWSER is set to YES). FILTER_SOURCE_FILES = NO #--------------------------------------------------------------------------- # configuration options related to source browsing #--------------------------------------------------------------------------- # If the SOURCE_BROWSER tag is set to YES then a list of source files will # be generated. Documented entities will be cross-referenced with these sources. SOURCE_BROWSER = YES # Setting the INLINE_SOURCES tag to YES will include the body # of functions and classes directly in the documentation. # INLINE_SOURCES = YES INLINE_SOURCES = NO # If the REFERENCED_BY_RELATION tag is set to YES (the default) # then for each documented function all documented # functions referencing it will be listed. REFERENCED_BY_RELATION = YES # If the REFERENCES_RELATION tag is set to YES (the default) # then for each documented function all documented entities # called/used by that function will be listed. REFERENCES_RELATION = YES #--------------------------------------------------------------------------- # configuration options related to the alphabetical class index #--------------------------------------------------------------------------- # If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index # of all compounds will be generated. Enable this if the project # contains a lot of classes, structs, unions or interfaces. ALPHABETICAL_INDEX = YES # If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then # the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns # in which this list will be split (can be a number in the range [1..20]) COLS_IN_ALPHA_INDEX = 5 # In case all classes in a project start with a common prefix, all # classes will be put under the same header in the alphabetical index. # The IGNORE_PREFIX tag can be used to specify one or more prefixes that # should be ignored while generating the index headers. IGNORE_PREFIX = #--------------------------------------------------------------------------- # configuration options related to the HTML output #--------------------------------------------------------------------------- # If the GENERATE_HTML tag is set to YES (the default) Doxygen will # generate HTML output. GENERATE_HTML = YES # The HTML_OUTPUT tag is used to specify where the HTML docs will be put. # If a relative path is entered the value of OUTPUT_DIRECTORY will be # put in front of it. If left blank `html' will be used as the default path. HTML_OUTPUT = html # The HTML_FILE_EXTENSION tag can be used to specify the file extension for # each generated HTML page (for example: .htm,.php,.asp). If it is left blank # doxygen will generate files with .html extension. HTML_FILE_EXTENSION = .html # The HTML_HEADER tag can be used to specify a personal HTML header for # each generated HTML page. If it is left blank doxygen will generate a # standard header. HTML_HEADER = # The HTML_FOOTER tag can be used to specify a personal HTML footer for # each generated HTML page. If it is left blank doxygen will generate a # standard footer. HTML_FOOTER = # The HTML_STYLESHEET tag can be used to specify a user defined cascading # style sheet that is used by each HTML page. It can be used to # fine-tune the look of the HTML output. If the tag is left blank doxygen # will generate a default style sheet HTML_STYLESHEET = # If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes, # files or namespaces will be aligned in HTML using tables. If set to # NO a bullet list will be used. HTML_ALIGN_MEMBERS = YES # If the GENERATE_HTMLHELP tag is set to YES, additional index files # will be generated that can be used as input for tools like the # Microsoft HTML help workshop to generate a compressed HTML help file (.chm) # of the generated HTML documentation. GENERATE_HTMLHELP = NO # If the GENERATE_HTMLHELP tag is set to YES, the CHM_FILE tag can # be used to specify the file name of the resulting .chm file. You # can add a path in front of the file if the result should not be # written to the html output dir. CHM_FILE = # If the GENERATE_HTMLHELP tag is set to YES, the HHC_LOCATION tag can # be used to specify the location (absolute path including file name) of # the HTML help compiler (hhc.exe). If non empty doxygen will try to run # the html help compiler on the generated index.hhp. HHC_LOCATION = # If the GENERATE_HTMLHELP tag is set to YES, the GENERATE_CHI flag # controls if a separate .chi index file is generated (YES) or that # it should be included in the master .chm file (NO). GENERATE_CHI = NO # If the GENERATE_HTMLHELP tag is set to YES, the BINARY_TOC flag # controls whether a binary table of contents is generated (YES) or a # normal table of contents (NO) in the .chm file. BINARY_TOC = NO # The TOC_EXPAND flag can be set to YES to add extra items for group members # to the contents of the Html help documentation and to the tree view. TOC_EXPAND = NO # The DISABLE_INDEX tag can be used to turn on/off the condensed index at # top of each HTML page. The value NO (the default) enables the index and # the value YES disables it. DISABLE_INDEX = NO # This tag can be used to set the number of enum values (range [1..20]) # that doxygen will group on one line in the generated HTML documentation. ENUM_VALUES_PER_LINE = 4 # If the GENERATE_TREEVIEW tag is set to YES, a side panel will be # generated containing a tree-like index structure (just like the one that # is generated for HTML Help). For this to work a browser that supports # JavaScript and frames is required (for instance Mozilla, Netscape 4.0+, # or Internet explorer 4.0+). Note that for large projects the tree generation # can take a very long time. In such cases it is better to disable this feature. # Windows users are probably better off using the HTML help feature. GENERATE_TREEVIEW = NO # If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be # used to set the initial width (in pixels) of the frame in which the tree # is shown. TREEVIEW_WIDTH = 250 #--------------------------------------------------------------------------- # configuration options related to the LaTeX output #--------------------------------------------------------------------------- # If the GENERATE_LATEX tag is set to YES (the default) Doxygen will # generate Latex output. GENERATE_LATEX = YES # The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. # If a relative path is entered the value of OUTPUT_DIRECTORY will be # put in front of it. If left blank `latex' will be used as the default path. LATEX_OUTPUT = latex # The LATEX_CMD_NAME tag can be used to specify the LaTeX command name to be invoked. If left blank `latex' will be used as the default command name. LATEX_CMD_NAME = latex # The MAKEINDEX_CMD_NAME tag can be used to specify the command name to # generate index for LaTeX. If left blank `makeindex' will be used as the # default command name. MAKEINDEX_CMD_NAME = makeindex # If the COMPACT_LATEX tag is set to YES Doxygen generates more compact # LaTeX documents. This may be useful for small projects and may help to # save some trees in general. COMPACT_LATEX = NO # The PAPER_TYPE tag can be used to set the paper type that is used # by the printer. Possible values are: a4, a4wide, letter, legal and # executive. If left blank a4wide will be used. PAPER_TYPE = a4wide # The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX # packages that should be included in the LaTeX output. EXTRA_PACKAGES = # The LATEX_HEADER tag can be used to specify a personal LaTeX header for # the generated latex document. The header should contain everything until # the first chapter. If it is left blank doxygen will generate a # standard header. Notice: only use this tag if you know what you are doing! LATEX_HEADER = # If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated # is prepared for conversion to pdf (using ps2pdf). The pdf file will # contain links (just like the HTML output) instead of page references # This makes the output suitable for online browsing using a pdf viewer. PDF_HYPERLINKS = NO # If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of # plain latex in the generated Makefile. Set this option to YES to get a # higher quality PDF documentation. USE_PDFLATEX = NO # If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode. # command to the generated LaTeX files. This will instruct LaTeX to keep # running if errors occur, instead of asking the user for help. # This option is also used when generating formulas in HTML. LATEX_BATCHMODE = NO #--------------------------------------------------------------------------- # configuration options related to the RTF output #--------------------------------------------------------------------------- # If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output # The RTF output is optimised for Word 97 and may not look very pretty with # other RTF readers or editors. GENERATE_RTF = NO # The RTF_OUTPUT tag is used to specify where the RTF docs will be put. # If a relative path is entered the value of OUTPUT_DIRECTORY will be # put in front of it. If left blank `rtf' will be used as the default path. RTF_OUTPUT = rtf # If the COMPACT_RTF tag is set to YES Doxygen generates more compact # RTF documents. This may be useful for small projects and may help to # save some trees in general. COMPACT_RTF = NO # If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated # will contain hyperlink fields. The RTF file will # contain links (just like the HTML output) instead of page references. # This makes the output suitable for online browsing using WORD or other # programs which support those fields. # Note: wordpad (write) and others do not support links. RTF_HYPERLINKS = NO # Load stylesheet definitions from file. Syntax is similar to doxygen's # config file, i.e. a series of assigments. You only have to provide # replacements, missing definitions are set to their default value. RTF_STYLESHEET_FILE = # Set optional variables used in the generation of an rtf document. # Syntax is similar to doxygen's config file. RTF_EXTENSIONS_FILE = #--------------------------------------------------------------------------- # configuration options related to the man page output #--------------------------------------------------------------------------- # If the GENERATE_MAN tag is set to YES (the default) Doxygen will # generate man pages GENERATE_MAN = NO # The MAN_OUTPUT tag is used to specify where the man pages will be put. # If a relative path is entered the value of OUTPUT_DIRECTORY will be # put in front of it. If left blank `man' will be used as the default path. MAN_OUTPUT = man # The MAN_EXTENSION tag determines the extension that is added to # the generated man pages (default is the subroutine's section .3) MAN_EXTENSION = .3 # If the MAN_LINKS tag is set to YES and Doxygen generates man output, # then it will generate one additional man file for each entity # documented in the real man page(s). These additional files # only source the real man page, but without them the man command # would be unable to find the correct page. The default is NO. MAN_LINKS = NO #--------------------------------------------------------------------------- # configuration options related to the XML output #--------------------------------------------------------------------------- # If the GENERATE_XML tag is set to YES Doxygen will # generate an XML file that captures the structure of # the code including all documentation. Note that this # feature is still experimental and incomplete at the # moment. GENERATE_XML = NO # The XML_SCHEMA tag can be used to specify an XML schema, # which can be used by a validating XML parser to check the # syntax of the XML files. XML_SCHEMA = # The XML_DTD tag can be used to specify an XML DTD, # which can be used by a validating XML parser to check the # syntax of the XML files. XML_DTD = #--------------------------------------------------------------------------- # configuration options for the AutoGen Definitions output #--------------------------------------------------------------------------- # If the GENERATE_AUTOGEN_DEF tag is set to YES Doxygen will # generate an AutoGen Definitions (see autogen.sf.net) file # that captures the structure of the code including all # documentation. Note that this feature is still experimental # and incomplete at the moment. GENERATE_AUTOGEN_DEF = NO #--------------------------------------------------------------------------- # Configuration options related to the preprocessor #--------------------------------------------------------------------------- # If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will # evaluate all C-preprocessor directives found in the sources and include # files. ENABLE_PREPROCESSING = YES # If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro # names in the source code. If set to NO (the default) only conditional # compilation will be performed. Macro expansion can be done in a controlled # way by setting EXPAND_ONLY_PREDEF to YES. MACRO_EXPANSION = NO # If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES # then the macro expansion is limited to the macros specified with the # PREDEFINED and EXPAND_AS_PREDEFINED tags. EXPAND_ONLY_PREDEF = NO # If the SEARCH_INCLUDES tag is set to YES (the default) the includes files # in the INCLUDE_PATH (see below) will be search if a #include is found. SEARCH_INCLUDES = YES # The INCLUDE_PATH tag can be used to specify one or more directories that # contain include files that are not input files but should be processed by # the preprocessor. INCLUDE_PATH = # You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard # patterns (like *.h and *.hpp) to filter out the header-files in the # directories. If left blank, the patterns specified with FILE_PATTERNS will # be used. INCLUDE_FILE_PATTERNS = # The PREDEFINED tag can be used to specify one or more macro names that # are defined before the preprocessor is started (similar to the -D option of # gcc). The argument of the tag is a list of macros of the form: name # or name=definition (no spaces). If the definition and the = are # omitted =1 is assumed. PREDEFINED = # If the MACRO_EXPANSION and EXPAND_PREDEF_ONLY tags are set to YES then # this tag can be used to specify a list of macro names that should be expanded. # The macro definition that is found in the sources will be used. # Use the PREDEFINED tag if you want to use a different macro definition. EXPAND_AS_DEFINED = # If the SKIP_FUNCTION_MACROS tag is set to YES (the default) then # doxygen's preprocessor will remove all function-like macros that are alone # on a line, have an all uppercase name, and do not end with a semicolon. Such # function macros are typically used for boiler-plate code, and will confuse the # parser if not removed. SKIP_FUNCTION_MACROS = YES #--------------------------------------------------------------------------- # Configuration::addtions related to external references #--------------------------------------------------------------------------- # The TAGFILES tag can be used to specify one or more tagfiles. TAGFILES = # When a file name is specified after GENERATE_TAGFILE, doxygen will create # a tag file that is based on the input files it reads. GENERATE_TAGFILE = # If the ALLEXTERNALS tag is set to YES all external classes will be listed # in the class index. If set to NO only the inherited external classes # will be listed. ALLEXTERNALS = NO # If the EXTERNAL_GROUPS tag is set to YES all external groups will be listed # in the modules index. If set to NO, only the current project's groups will # be listed. EXTERNAL_GROUPS = YES # The PERL_PATH should be the absolute path and name of the perl script # interpreter (i.e. the result of `which perl'). PERL_PATH = /usr/bin/perl #--------------------------------------------------------------------------- # Configuration options related to the dot tool #--------------------------------------------------------------------------- # If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will # generate a inheritance diagram (in Html, RTF and LaTeX) for classes with base or # super classes. Setting the tag to NO turns the diagrams off. Note that this # option is superceded by the HAVE_DOT option below. This is only a fallback. It is # recommended to install and use dot, since it yield more powerful graphs. CLASS_DIAGRAMS = YES # If set to YES, the inheritance and collaboration graphs will hide # inheritance and usage relations if the target is undocumented # or is not a class. HIDE_UNDOC_RELATIONS = YES # If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is # available from the path. This tool is part of Graphviz, a graph visualization # toolkit from AT&T and Lucent Bell Labs. The other options in this section # have no effect if this option is set to NO (the default) HAVE_DOT = YES # If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen # will generate a graph for each documented class showing the direct and # indirect inheritance relations. Setting this tag to YES will force the # the CLASS_DIAGRAMS tag to NO. CLASS_GRAPH = YES # If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen # will generate a graph for each documented class showing the direct and # indirect implementation dependencies (inheritance, containment, and # class references variables) of the class with other documented classes. COLLABORATION_GRAPH = YES # If set to YES, the inheritance and collaboration graphs will show the # relations between templates and their instances. TEMPLATE_RELATIONS = YES # If the ENABLE_PREPROCESSING, SEARCH_INCLUDES, INCLUDE_GRAPH, and HAVE_DOT # tags are set to YES then doxygen will generate a graph for each documented # file showing the direct and indirect include dependencies of the file with # other documented files. INCLUDE_GRAPH = YES # If the ENABLE_PREPROCESSING, SEARCH_INCLUDES, INCLUDED_BY_GRAPH, and # HAVE_DOT tags are set to YES then doxygen will generate a graph for each # documented header file showing the documented files that directly or # indirectly include this file. INCLUDED_BY_GRAPH = YES # If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen # will graphical hierarchy of all classes instead of a textual one. GRAPHICAL_HIERARCHY = YES # The DOT_IMAGE_FORMAT tag can be used to set the image format of the images # generated by dot. Possible values are png, jpg, or gif # If left blank png will be used. DOT_IMAGE_FORMAT = gif # The tag DOT_PATH can be used to specify the path where the dot tool can be # found. If left blank, it is assumed the dot tool can be found on the path. DOT_PATH = # The DOTFILE_DIRS tag can be used to specify one or more directories that # contain dot files that are included in the documentation (see the # \dotfile command). DOTFILE_DIRS = # The MAX_DOT_GRAPH_WIDTH tag can be used to set the maximum allowed width # (in pixels) of the graphs generated by dot. If a graph becomes larger than # this value, doxygen will try to truncate the graph, so that it fits within # the specified constraint. Beware that most browsers cannot cope with very # large images. MAX_DOT_GRAPH_WIDTH = 1024 # The MAX_DOT_GRAPH_HEIGHT tag can be used to set the maximum allows height # (in pixels) of the graphs generated by dot. If a graph becomes larger than # this value, doxygen will try to truncate the graph, so that it fits within # the specified constraint. Beware that most browsers cannot cope with very # large images. MAX_DOT_GRAPH_HEIGHT = 1024 # If the GENERATE_LEGEND tag is set to YES (the default) Doxygen will # generate a legend page explaining the meaning of the various boxes and # arrows in the dot generated graphs. GENERATE_LEGEND = YES # If the DOT_CLEANUP tag is set to YES (the default) Doxygen will # remove the intermedate dot files that are used to generate # the various graphs. DOT_CLEANUP = YES #--------------------------------------------------------------------------- # Configuration::addtions related to the search engine #--------------------------------------------------------------------------- # The SEARCHENGINE tag specifies whether or not a search engine should be # used. If set to NO the values of all tags below this one will be ignored. SEARCHENGINE = YES # The CGI_NAME tag should be the name of the CGI script that # starts the search engine (doxysearch) with the correct parameters. # A script with this name will be generated by doxygen. CGI_NAME = search.cgi # The CGI_URL tag should be the absolute URL to the directory where the # cgi binaries are located. See the documentation of your http daemon for # details. CGI_URL = file:///home/www/osl/osl/doc # The DOC_URL tag should be the absolute URL to the directory where the # documentation is located. If left blank the absolute path to the # documentation, with file:// prepended to it, will be used. DOC_URL = # The DOC_ABSPATH tag should be the absolute path to the directory where the # documentation is located. If left blank the directory on the local machine # will be used. DOC_ABSPATH = # The BIN_ABSPATH tag must point to the directory where the doxysearch binary # is installed. BIN_ABSPATH = /usr/local/bin/ # The EXT_DOC_PATHS tag can be used to specify one or more paths to # documentation generated for other projects. This allows doxysearch to search # the documentation for these projects as well. EXT_DOC_PATHS = libosl-0.8.0.orig/doc/.htaccess0000644000000000000000000000005110753257300015001 0ustar rootrootAddType "text/html; charset=euc-jp" html libosl-0.8.0.orig/doc/Makefile0000644000000000000000000000025510342606424014650 0ustar rootrootDOXYGEN ?= doxygen all: doxygen find . -name '*.html' -exec perl -pi -e 's/td nowrap/td/g' {} \; clean: rm -f doxygen.err rm -rf html rm -rf latex .PHONY: all clean libosl-0.8.0.orig/full/0000755000000000000000000000000013016502474013404 5ustar rootrootlibosl-0.8.0.orig/full/osl/0000755000000000000000000000000013016502474014201 5ustar rootrootlibosl-0.8.0.orig/full/osl/state/0000755000000000000000000000000012316770314015323 5ustar rootrootlibosl-0.8.0.orig/full/osl/state/historyState.cc0000644000000000000000000000252312316770314020336 0ustar rootroot/* historyState.cc */ #include "osl/state/historyState.h" osl::state::HistoryState::HistoryState() : dirty(false) { assert(current.isConsistent()); assert(initial_state.isConsistent()); } osl::state::HistoryState::HistoryState(const SimpleState& initial) : initial_state(initial), current(initial), dirty(false) { assert(current.isConsistent()); assert(initial_state.isConsistent()); } osl::state::HistoryState::~HistoryState() { } void osl::state::HistoryState::setRoot(const SimpleState& initial) { initial_state = current = NumEffectState(initial); moves.clear(); dirty = false; } void osl::state::HistoryState::makeMove(Move move) { if (dirty) update(); moves.push_back(move); current.makeMove(move); } void osl::state::HistoryState::unmakeMove() { dirty = true; moves.pop_back(); } void osl::state::HistoryState::makeMovePass() { makeMove(Move::PASS(state().turn())); } void osl::state::HistoryState::unmakeMovePass() { assert(! moves.empty() && moves.back().isPass()); if (! dirty) { moves.pop_back(); current.changeTurn(); return; } unmakeMove(); } void osl::state::HistoryState::update() const { current = initial_state; for (size_t i=0; i namespace osl { namespace state { class HistoryState #if OSL_WORDSIZE == 32 : public misc::Align16New #endif { NumEffectState initial_state; mutable NumEffectState current; mutable bool dirty; std::vector moves; public: HistoryState(); explicit HistoryState(const SimpleState& initial); ~HistoryState(); void setRoot(const SimpleState&); void makeMove(Move move); void unmakeMove(); void makeMovePass(); void unmakeMovePass(); const NumEffectState& state() const { if (dirty) update(); return current; } operator const NumEffectState& () const { return state(); } const NumEffectState& initialState() const { return initial_state; } bool empty() const { return moves.empty(); } const std::vector& history() const { return moves; } bool isConsistent() const { return state().isConsistent(); } private: void update() const; }; class DoUndoMoveLock { HistoryState& state; public: DoUndoMoveLock(HistoryState& s, Move move) : state(s) { state.makeMove(move); } ~DoUndoMoveLock() { state.unmakeMove(); } }; } using state::HistoryState; using state::DoUndoMoveLock; } #endif /* _HISTORYSTATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/0000755000000000000000000000000012316770314016341 5ustar rootrootlibosl-0.8.0.orig/full/osl/threatmate/richPredictor.h0000644000000000000000000000064612316770314021321 0ustar rootroot/* richPredictor.h */ #ifndef _RICHPREDICTOR_H #define _RICHPREDICTOR_H #include "osl/numEffectState.h" namespace osl { namespace threatmate { class RichPredictor { public: double predict(const NumEffectState& state, const Move move); }; } // namespace threatmate } // namespace osl #endif /* _RICHPREDICTOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/kfendPredictor.cc0000644000000000000000000000121212316770314021607 0ustar rootroot/* kfendPredictor.cc */ #include "osl/threatmate/kfendPredictor.h" #include "osl/effect_util/neighboring8Direct.h" bool osl::threatmate::KfendPredictor::predict(const NumEffectState& state, const Move move){ const Player turn = alt(state.turn()); const Square opKingSquare = state.kingSquare(alt(turn)); // Capture Piece if (move.capturePtype()) return true; // Add Effect for King's Neighboring8 if ( Neighboring8Direct::hasEffect(state, newPtypeO(turn, move.ptype()), move.to(), opKingSquare) ) return true; return false; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/mlPredictor.cc0000644000000000000000000000422312316770314021135 0ustar rootroot/* mlPredictor.cc */ #include "osl/threatmate/mlPredictor.h" #include "osl/progress.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/bits/king8Info.h" #include const double predictor_coef[5][9] = { // all {-3.7460724, 1.5899403, 1.5218839, 1.8912265, 2.2698081, 2.9564733, 1.8364091, 0.4818582, 0.2046128}, // ~ 100 nodes { -4.502173, 1.866922, 1.075071, 1.785152, 2.904015, 3.546099, 2.217401, 1.037181, 0.198456}, // ~ 1,000 nodes {-4.2651299, 1.8346520, 1.4515673, 1.8766168, 2.8202449, 3.2856799, 2.0692834, 0.7330482, 0.2069689}, // 1,000 ~ 10,000 nodes {-3.8450811, 1.5901365, 1.6039122, 1.9947154, 2.2830698, 2.9788201, 1.8998258, 0.4654985, 0.2174952}, // 10,000 ~ {-3.3149250, 1.3827221, 1.4877458, 1.8048604, 1.6804844, 2.7207930, 1.6221641, 0.3460561, 0.1866114,} }; double osl::threatmate::MlPredictor::predict(const NumEffectState& state, const Move move, size_t index){ const Player turn = alt(state.turn()); const Square oking = state.kingSquare(alt(turn)); King8Info K(state.Iking8Info(alt(turn))); NewProgress tprogress(state); const double* coef = predictor_coef[index]; double sum = coef[0]; const int npiece = (int)(move.capturePtype()); if (npiece) { for (int i=0; i<3; i++) if (npiece%8 == i+5) sum += coef[i+1]; if (npiece == 9) sum += coef[4]; } int moveCandidate; if(turn==BLACK) moveCandidate=K.countMoveCandidate(state); else moveCandidate=K.countMoveCandidate(state); sum += coef[5] * ( Neighboring8Direct::hasEffect(state, newPtypeO(turn, move.ptype()), move.to(), oking) ) + coef[6] * moveCandidate + coef[7] * ( misc::BitOp::countBit(K.dropCandidate()) )+ coef[8] * ( tprogress.progressAttack(alt(turn)).value() ); return sum; } double osl::threatmate::MlPredictor::probability(const NumEffectState& state, const Move move, size_t index){ return 1.0 / (1.0 + exp (- predict(state,move,index) )); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/kfendPredictor.h0000644000000000000000000000065112316770314021457 0ustar rootroot/* kfendPredictor.h */ #ifndef _KFENDPREDICTOR_H #define _KFENDPREDICTOR_H #include "osl/numEffectState.h" namespace osl { namespace threatmate { class KfendPredictor { public: bool predict(const NumEffectState& state, const Move move); }; } // namespace threatmate } // namespace osl #endif /* _KFENDPREDICTOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/richPredictor.cc0000644000000000000000000000517112316770314021455 0ustar rootroot/* richPredictor.cc */ #include "osl/threatmate/richPredictor.h" #include "osl/additionalEffect.h" double osl::threatmate::RichPredictor::predict(const NumEffectState& state, const Move move){ const Player turn = alt(state.turn()); const Square opKingSquare = state.kingSquare(alt(turn)); const int x = opKingSquare.x(); const int y = opKingSquare.y(); const Square to = move.to(); const int distance_m = abs(x - to.x()) + abs(y - to.y()); const int sign = -1 + 2 * (turn == BLACK); const int min = -1; const int max = 1; // Kiki around opKing int add_effect = 0; int effect_b = 0; int effect_w = 0; int effect_e = 0; for (int i=min; i<=max; i++) for (int j=min; j<=max; j++){ Square pos(x+j, y+i); if (pos.isOnBoard()){ int eff_w = state.countEffect(alt(turn),pos); effect_w += eff_w; add_effect += AdditionalEffect::count(state,turn, pos); int eff_b = state.countEffect(turn,pos); effect_b += eff_b; effect_e += (eff_b > eff_w); } } // King's Escape path int escapeKing = 0; for (int i=min; i<=max; i++) for (int j=min; j<=max; j++){ Square pos(x+j, y+i); if (pos.isOnBoard()){ Piece pieceOnBoard = state.pieceOnBoard(pos); if ((pieceOnBoard == Piece::EMPTY()) || (pieceOnBoard.owner() != alt(turn))) escapeKing += (!state.hasEffectAt(turn, pos)); } } // Capture Ptype const double coefCapture[16] ={0.0, 0.0, 0.0, 0.0, 0.0, 5.06, 4.73, 7.70, 0.0, 9.78, 0.0, 0.0, 0.0, 5.06, 4.73, 7.70}; const double neigh[9] ={14.52, 9.13, 8.26, 0.39, 0.0, 11.87, 0.53, 11.30, 15.06}; double neigh8 = 0.0; for (int i=min; i<=max; i++) for (int j=min; j<=max; j++){ Square pos(x+sign*j, y+sign*i); if (pos.isOnBoard()) neigh8 += neigh[3*(i+1)+j+1]*state.hasEffectByPiece(state.pieceOnBoard(to), pos); } const double value_p = 9.62*(double)state.countPiecesOnStand(turn, ROOK) + 6.07*(double)state.countPiecesOnStand(turn, BISHOP) + 8.27*(double)state.countPiecesOnStand(turn, GOLD) + 5.64*(double)state.countPiecesOnStand(turn, SILVER) + 4.06*(double)state.countPiecesOnStand(turn, KNIGHT) + 2.77*(double)state.countPiecesOnStand(turn, LANCE) + 1.05*(double)state.countPiecesOnStand(turn, PAWN); double est = 45.07 + neigh8 + 10.20*(double)add_effect + 6.41*(double)effect_b - 1.24*(double)effect_w + 13.79*(double)effect_e - 1.98*(double)escapeKing - 3.11*(double)distance_m + value_p + coefCapture[move.capturePtype()]; return est; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/treePredictor.h0000644000000000000000000000075312316770314021332 0ustar rootroot/* treePredictor.h */ #ifndef _TREEPREDICTOR_H #define _TREEPREDICTOR_H #include "osl/numEffectState.h" namespace osl { namespace threatmate { class TreePredictor { public: bool predict(const NumEffectState& state, const Move move); double probability(const NumEffectState& state, const Move move); }; } // namespace threatmate } // namespace osl #endif /* _TREEPREDICTOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/treePredictor.cc0000644000000000000000000000416712316770314021473 0ustar rootroot/* treePredictor.cc */ #include "osl/threatmate/treePredictor.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/progress.h" #include "osl/bits/king8Info.h" bool osl::threatmate::TreePredictor::predict(const NumEffectState& state, const Move move){ const Player turn = alt(state.turn()); progress::NewProgress tprogress(state); const int progress = (tprogress.progressAttack(alt(turn)).value()); if (Neighboring8Direct::hasEffect(state, newPtypeO(turn, move.ptype()), move.to(), state.kingSquare(alt(turn)))){ King8Info K(state.Iking8Info(alt(turn))); if(progress>=5 || K.dropCandidate()) return true; if(turn==BLACK) return K.hasMoveCandidate(state); else return K.hasMoveCandidate(state); } if (progress > 5 ) { if (! isPiece( move.capturePtype() ) ) return false; if ( isMajor(move.capturePtype()) || (move.capturePtype() == SILVER) || (move.capturePtype() == PSILVER)|| (move.capturePtype() == GOLD) ) return true; } return false; } double osl::threatmate::TreePredictor::probability(const NumEffectState& state, const Move move){ const Player turn = alt(state.turn()); osl::progress::ml::NewProgress tprogress(state); const int progress = (tprogress.progressAttack(alt(turn)).value()); if (Neighboring8Direct::hasEffect(state, newPtypeO(turn, move.ptype()), move.to(), state.kingSquare(alt(turn)))){ if (progress > 4) { if (progress > 5) return 0.87601; return 0.69349; } King8Info K(state.Iking8Info(alt(turn))); if (K.dropCandidate() ) return 0.5637; if(turn==BLACK){ if(K.hasMoveCandidate(state)) return 0.89933; } else if(K.hasMoveCandidate(state)) return 0.89933; return 0.22403; } if (progress < 5 ) return 0.041633; if (move.capturePtype() == GOLD) return 0.81872; if (move.capturePtype() == SILVER) return 0.78608; if (move.capturePtype() == ROOK) return 0.83592; if (move.capturePtype() == BISHOP) return 0.84542; return 0.14094; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/threatmate/mlPredictor.h0000644000000000000000000000100312316770314020770 0ustar rootroot/* mlPredictor.h */ #ifndef _MLPREDICTOR_H #define _MLPREDICTOR_H #include "osl/numEffectState.h" namespace osl { namespace threatmate { class MlPredictor { public: double predict(const NumEffectState& state, const Move move, size_t index=0); double probability(const NumEffectState& state, const Move move, size_t index=0); }; } // namespace threatmate } // namespace osl #endif /* _MLPREDICTOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/annotate/0000755000000000000000000000000012316770314016014 5ustar rootrootlibosl-0.8.0.orig/full/osl/annotate/facade.h0000644000000000000000000000067312316770314017376 0ustar rootroot/* facade.h */ #ifndef OSL_ANNOTATE_FACADE_H #define OSL_ANNOTATE_FACADE_H #include "osl/annotate/analysesResult.h" #include "osl/numEffectState.h" #include namespace osl { namespace annotate { void analyze(const NumEffectState& src, const std::vector& moves, int last_move, AnalysesResult&); } } #endif /* OSL_ANNOTATE_FACADE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/annotate/analysesResult.cc0000644000000000000000000000474612316770314021354 0ustar rootroot/* analysesResult.cc */ #include "osl/annotate/analysesResult.h" #include "osl/container.h" #include bool osl::annotate::operator==(const AnalysesResult& l, const AnalysesResult& r) { return l.repetition == r.repetition && l.checkmate == r.checkmate && l.checkmate_win == r.checkmate_win && l.threatmate == r.threatmate && l.escape_from_check == r.escape_from_check && l.threatmate_probability == r.threatmate_probability && l.threatmate_node_count == r.threatmate_node_count && l.checkmate_for_capture == r.checkmate_for_capture && l.checkmate_for_escape == r.checkmate_for_escape && l.threatmate_if_more_pieces == r.threatmate_if_more_pieces; } std::ostream& osl::annotate::operator<<(std::ostream& os, Trivalent t) { static const CArray str = {{ "False", "Unknown", "True", }}; return os << str[t+1]; } #define out(os, shared, x) os << #x << " " << shared.x << " " template void outt(std::ostream& os, const T& a, const char *str) { if (a != T()) os << str << " " << a << " "; } #define outif(os, shared, x) outt(os, shared.x, #x) std::ostream& osl::annotate::operator<<(std::ostream& os, const AnalysesResult& shared) { if (! shared.repetition.empty()) { os << "repetition "; for (int p: shared.repetition) os << p << " "; os << " "; } if (shared.checkmate != False) out(os, shared, checkmate); if (shared.threatmate != False) out(os, shared, threatmate); if (shared.escape_from_check != False) out(os, shared, escape_from_check); outif(os, shared, checkmate_move); outif(os, shared, threatmate_move); outif(os, shared, threatmate_probability); outif(os, shared, threatmate_node_count); outif(os, shared, checkmate_for_capture.safe_count); outif(os, shared, checkmate_for_capture.checkmate_count); outif(os, shared, checkmate_for_capture.see_plus_checkmate_count); outif(os, shared, checkmate_for_escape.safe_count); outif(os, shared, checkmate_for_escape.checkmate_count); if (! shared.threatmate_if_more_pieces.hand_ptype.empty()) { os << "hand "; for (Ptype ptype: shared.threatmate_if_more_pieces.hand_ptype) os << ptype << " "; os << " "; } if (! shared.threatmate_if_more_pieces.board_ptype.empty()) { os << "board "; for (Piece piece: shared.threatmate_if_more_pieces.board_ptype) os << piece << " "; os << " "; } return os; } #undef out // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/annotate/analysesResult.h0000644000000000000000000000431312316770314021204 0ustar rootroot/* analysesResult.h */ #ifndef OSL_ANNOTATE_ANALYSESRESULT_H #define OSL_ANNOTATE_ANALYSESRESULT_H #include "osl/basic_type.h" #include #include namespace osl { namespace annotate { enum Trivalent { Unknown=0, True=1, False=-1 }; struct AnalysesResult { struct CheckmateForCapture { int safe_count, checkmate_count, see_plus_checkmate_count; CheckmateForCapture() : safe_count(0), checkmate_count(0), see_plus_checkmate_count(0) { } bool operator==(const CheckmateForCapture& r) const { return safe_count == r.safe_count && checkmate_count == r.checkmate_count && see_plus_checkmate_count == r.see_plus_checkmate_count; } }; struct CheckmateForEscape { int safe_count, checkmate_count; CheckmateForEscape() : safe_count(0), checkmate_count(0) { } bool operator==(const CheckmateForEscape& r) const { return safe_count == r.safe_count && checkmate_count == r.checkmate_count; } }; struct ThreatmateIfMorePieces { std::vector hand_ptype; std::vector board_ptype; bool operator==(const ThreatmateIfMorePieces& r) const { return hand_ptype == r.hand_ptype && board_ptype == r.board_ptype; } }; struct Vision { std::vector pv; int eval, cur_eval; }; std::vector repetition; Trivalent checkmate, checkmate_win, threatmate, escape_from_check; Move checkmate_move, threatmate_move; double threatmate_probability; size_t threatmate_node_count; CheckmateForCapture checkmate_for_capture; CheckmateForEscape checkmate_for_escape; ThreatmateIfMorePieces threatmate_if_more_pieces; Vision vision; AnalysesResult() : checkmate(Unknown), checkmate_win(Unknown), threatmate(Unknown), escape_from_check(Unknown), threatmate_probability(0), threatmate_node_count(0) { } }; bool operator==(const AnalysesResult& l, const AnalysesResult& r); std::ostream& operator<<(std::ostream&, Trivalent); std::ostream& operator<<(std::ostream&, const AnalysesResult&); } } #endif /* OSL_ANNOTATE_ANALYSESRESULT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/annotate/analyzer.cc0000644000000000000000000002610712316770314020156 0ustar rootroot/* analyzer.cc */ #include "osl/annotate/analyzer.h" #include "osl/checkmate/dualDfpn.h" #include "osl/checkmate/dfpn.h" #ifdef OSL_DFPN_SMP # include "osl/checkmate/dfpnParallel.h" #endif #include "osl/threatmate/mlPredictor.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/eval/see.h" #include "osl/eval/openMidEndingEval.h" #include "osl/game_playing/alphaBetaPlayer.h" #include "osl/game_playing/gameState.h" const int checkmate_limit = 1000000/2; osl::annotate:: Analyzer::~Analyzer() { } osl::annotate::Trivalent osl::annotate:: Analyzer::isCheckmate(NumEffectState& state, Move& best_move, bool attack, size_t *node_count) { #ifdef OSL_DFPN_SMP checkmate::DfpnParallel dfpn; #else checkmate::Dfpn dfpn; #endif checkmate::DfpnTable table(attack ? state.turn() : alt(state.turn())); dfpn.setTable(&table); const PathEncoding path(state.turn()); Move test; const ProofDisproof pdp = attack ? dfpn.hasCheckmateMove(state, HashKey(state), path, checkmate_limit, test) : dfpn.hasEscapeMove(state, HashKey(state), path, checkmate_limit*2, Move::PASS(alt(state.turn()))); if (node_count) *node_count = dfpn.nodeCount(); if (pdp.isCheckmateSuccess()) { best_move = test; return True; } return pdp.isFinal() ? False : Unknown; } void osl::annotate:: RepetitionAnalyzer::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& moves, int last_move) { shared.repetition.clear(); NumEffectState state; // assume initial position HashKey key(state); std::vector keys; for (int i=0; i<=last_move; ++i) { Move move = moves[i]; keys.push_back(key); if (! state.isValidMove(move)) return; key = key.newMakeMove(move); state.makeMove(move); } if (HashKey(src) != key) return; for (size_t i=0; i& /*moves*/, int /*last_move*/) { if (! src.inCheck()) { shared.checkmate = False; return; } NumEffectState s(src); Move dummy; shared.checkmate = isCheckmate(s, dummy, false); } void osl::annotate:: CheckmateWin::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& /*moves*/, int /*last_move*/) { if (src.inCheck()) { shared.checkmate_win = False; return; } NumEffectState s(src); shared.checkmate_win = isCheckmate(s, shared.checkmate_move, true); } void osl::annotate:: EscapeFromCheck::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& moves, int last_move) { shared.escape_from_check = matchMain(src, moves, last_move) ? True : False; } bool osl::annotate:: EscapeFromCheck::matchMain(const NumEffectState& src, const std::vector& moves, int last_move) { if (last_move < 0) return false; if (moves[last_move].ptype() == KING) { if (src.hasEffectAt(src.turn(), moves[last_move].from())) return true; if (moves[last_move].capturePtype() != PTYPE_EMPTY) { const PtypeO captured = moves[last_move].capturePtypeO(); if (src.hasEffectIf(captured, moves[last_move].to(), moves[last_move].from())) return true; } return false; } const PieceMask pin = src.pin(alt(src.turn())); if (pin.test(src.pieceAt(moves[last_move].to()).number())) return true; if (moves[last_move].capturePtype() != PTYPE_EMPTY) { const PtypeO captured = moves[last_move].capturePtypeO(); if (src.hasEffectIf(captured, moves[last_move].to(), src.kingSquare(alt(src.turn())))) return true; } return false; } void osl::annotate:: ThreatmateAnalyzer::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& moves, int last_move) { if (src.inCheck()) { shared.threatmate = False; return; } NumEffectState s(src); s.changeTurn(); shared.threatmate = isCheckmate(s, shared.threatmate_move, true, &shared.threatmate_node_count); threatmate::MlPredictor predictor; shared.threatmate_probability = (last_move >= 0) ? predictor.probability(src, moves[last_move]) : 0.0; } void osl::annotate:: CheckmateForCapture::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& history, int last_move) { if (last_move < 0 || shared.escape_from_check == True) return; const Square last_to = history[last_move].to(); if (! src.hasEffectAt(src.turn(), last_to)) return; MoveVector all, moves; src.generateLegal(all); for (Move m: all) if (m.to() == last_to) moves.push_back(m); if (moves.empty()) return; for (Move move: moves) { DualDfpn dfpn; NumEffectState s(src); s.makeMove(move); Move checkmate_move; const bool checkmate #ifdef OSL_DFPN_SMP = dfpn.isWinningStateParallel(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), checkmate_move, move); #else = dfpn.isWinningState(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), checkmate_move, move); #endif if (checkmate) { ++shared.checkmate_for_capture.checkmate_count; if (See::see(src, move) > 0) ++shared.checkmate_for_capture.see_plus_checkmate_count; } else ++shared.checkmate_for_capture.safe_count; } } void osl::annotate:: CheckmateForEscape::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& history, int last_move) { if (last_move < 0) return; const Square last_to = history[last_move].to(); if (! src.inCheck() || src.hasEffectAt(src.turn(), last_to)) return; // å–れãªã„王手 MoveVector moves; src.generateLegal(moves); if (moves.empty()) return; for (Move move: moves) { // treat chuai as safe const Square to = move.to(); if (src.hasEffectAt(alt(src.turn()), to) && (src.countEffect(src.turn(), to) - (move.isDrop() ? 0 : 1) == 0)) { ++shared.checkmate_for_escape.safe_count; continue; } DualDfpn dfpn; NumEffectState s(src); s.makeMove(move); Move checkmate_move; const bool checkmate #ifdef OSL_DFPN_SMP = dfpn.isWinningStateParallel(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), checkmate_move, move); #else = dfpn.isWinningState(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), checkmate_move, move); #endif if (checkmate) ++shared.checkmate_for_escape.checkmate_count; else ++shared.checkmate_for_escape.safe_count; } } bool osl::annotate:: ThreatmateIfMorePieces::suitable(const NumEffectState& state, Piece p) { // 外ã™å¯¾è±¡ // - å–ã‚‹å´ãŒé•·ã„利ãã§ã€å®ˆå‚™å´ã‹ã‚‰åˆ©ãã‚り ... 利ããŒå¤–れるã¨è‰²ã€…ãŠã“りやã™ã„ // - å–られる駒ãŒçމã®å‘¨å›²ã«åˆ©ã„ã¦ã„ã¦ã€å®ˆå‚™å´ã‹ã‚‰åˆ©ãã‚り .. å–り返ã—ã®å½±éŸ¿ãŒå¤§ãã„ if (state.hasEffectAt(p.owner(), p.square())) { if (state.longEffectAt(p.square(), alt(p.owner())).any()) return false; if (Neighboring8Direct::hasEffect (state, p.ptypeO(), p.square(), state.kingSquare(p.owner()))) return false; } return true; } void osl::annotate:: ThreatmateIfMorePieces::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& /*history*/, int last_move) { if (last_move < 0) return; if (src.inCheck() || shared.threatmate == True) return; const PieceMask effected_pieces = src.effectedMask(alt(src.turn())) & src.piecesOnBoard(src.turn()); for (Ptype ptype: PieceStand::order) { DualDfpn dfpn; if (src.hasPieceOnStand(src.turn(), ptype)) { NumEffectState s(src.emulateHandPiece(src.turn(), alt(src.turn()), ptype)); s.setTurn(alt(src.turn())); Move hand_move; const bool threatmate #ifdef OSL_DFPN_SMP = dfpn.isWinningStateParallel(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), hand_move, Move::PASS(alt(s.turn()))); #else = dfpn.isWinningState(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), hand_move, Move::PASS(alt(s.turn()))); #endif if (threatmate) shared.threatmate_if_more_pieces.hand_ptype.push_back(ptype); continue; } mask_t m = effected_pieces.getMask(Ptype_Table.getIndex(ptype)) & Ptype_Table.getMaskLow(ptype); if (! m.any()) continue; Piece p = src.pieceOf(m.takeOneBit()); while (m.any() && !suitable(src, p)) p = src.pieceOf(m.takeOneBit()); if (! suitable(src, p)) continue; assert(p.isOnBoard()); assert(unpromote(p.ptype()) == ptype); NumEffectState s(src.emulateCapture(p, alt(src.turn()))); s.setTurn(alt(src.turn())); if (s.inCheck() || s.inCheck(alt(s.turn()))) continue; Move board_move; const bool threatmate #ifdef OSL_DFPN_SMP = dfpn.isWinningStateParallel(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), board_move, Move::PASS(alt(s.turn()))); #else = dfpn.isWinningState(checkmate_limit, s, HashKey(s), PathEncoding(s.turn()), board_move, Move::PASS(alt(s.turn()))); #endif if (threatmate) shared.threatmate_if_more_pieces.board_ptype.push_back(p); } } namespace osl { namespace { MoveWithComment do_search(const NumEffectState& src, int seconds) { game_playing::AlphaBeta2OpenMidEndingEvalPlayer player; player.setNextIterationCoefficient(1.0); player.setVerbose(0); player.setTableLimit(100000, 200); game_playing::GameState state(src); search::TimeAssigned time(milliseconds(seconds*1000)); return player.searchWithSecondsForThisMove(state, time); } } } void osl::annotate:: Vision3::match(AnalysesResult& shared, const NumEffectState& src, const std::vector& history, int last_move) { if (last_move < 0) return; if (src.inCheck() || shared.threatmate == True || shared.checkmate == True || shared.checkmate_win == True || shared.escape_from_check == True) return; // better to takeback? search::MoveWithComment response = do_search(src, 1); if (! response.move.isNormal() || response.move.to() == history[last_move].to()) return; NumEffectState s = src; s.changeTurn(); // get pv after pass MoveWithComment pv = do_search(s, 2); if (! pv.move.isNormal()) return; if (See::see(s, pv.move) > 0) { if (pv.move.from() == history[last_move].to()) return; const Piece p = s.pieceAt(pv.move.to()); if (p.isPiece() && ! s.hasEffectAt(alt(s.turn()), pv.move.to()) && src.effectedChanged(alt(s.turn())).test(p.number())) return; } typedef eval::ml::OpenMidEndingEval eval_t; shared.vision.cur_eval = eval_t(s).value() * 200.0/eval_t::captureValue(newPtypeO(WHITE,PAWN)); if (pv.value*eval::delta(s.turn()) < shared.vision.cur_eval*eval::delta(s.turn())+200 || abs(shared.vision.cur_eval) >= 1000) return; shared.vision.eval = pv.value; shared.vision.pv.push_back(pv.move); for (Move m: pv.moves) shared.vision.pv.push_back(m); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/annotate/anno-facade.cc0000644000000000000000000000225212316770314020460 0ustar rootroot#include "osl/annotate/facade.h" #include "osl/annotate/analyzer.h" #include "osl/progress.h" #include "osl/eval/openMidEndingEval.h" #include void osl::annotate:: analyze(const NumEffectState& src, const std::vector& moves, int last_move, AnalysesResult& result) { static boost::ptr_vector analyzers; static bool initialized = false; if (! initialized) { analyzers.push_back(new RepetitionAnalyzer); analyzers.push_back(new CheckmateAnalyzer); analyzers.push_back(new CheckmateWin); analyzers.push_back(new EscapeFromCheck); analyzers.push_back(new CheckmateForCapture); analyzers.push_back(new ThreatmateAnalyzer); analyzers.push_back(new CheckmateForEscape); analyzers.push_back(new ThreatmateIfMorePieces); analyzers.push_back(new Vision3); progress::ml::NewProgress::setUp(); eval::ml::OpenMidEndingEval::setUp(); initialized = true; } result = AnalysesResult(); for (Analyzer& a: analyzers) { a.match(result, src, moves, last_move); if (result.checkmate == True) break; } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/annotate/analyzer.h0000644000000000000000000000515012316770314020013 0ustar rootroot/* analyzer.h */ #ifndef OSL_ANNOTATE_ANALYZER_H #define OSL_ANNOTATE_ANALYZER_H #include "osl/annotate/analysesResult.h" #include "osl/numEffectState.h" #include namespace osl { namespace annotate { class Analyzer { public: virtual ~Analyzer(); virtual void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move)=0; static Trivalent isCheckmate(NumEffectState& state, Move& best_move, bool attack=true, size_t *node_count=0); }; /** åƒæ—¥æ‰‹æ¨¡æ§˜(åŒä¸€å±€é¢)ã®æ¤œçŸ¥ */ class RepetitionAnalyzer : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; /** 指ã—ãŸçŽ‹æ‰‹ãŒæ­£è§£ã§è©°ã¿ */ class CheckmateAnalyzer : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; /** 手番å´ãŒæ­£ã—ãæŒ‡ã›ã°è©°ã¿ */ class CheckmateWin : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; class EscapeFromCheck : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); static bool matchMain(const NumEffectState& src, const std::vector& moves, int last_move); }; class ThreatmateAnalyzer : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; class CheckmateForCapture : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; class CheckmateForEscape : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; class ThreatmateIfMorePieces : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); static bool suitable(const NumEffectState& state, Piece p); }; class Vision3 : public Analyzer { public: void match(AnalysesResult&, const NumEffectState& src, const std::vector& moves, int last_move); }; } } #endif /* OSL_ANNOTATE_ANALYZER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/move-phash.c0000644000000000000000000005704612316770314016432 0ustar rootroot// http://burtleburtle.net/bob/hash/perfect.html /* A way to make the 1-byte values in tab bigger */ uint16_t scramble[] = { 0x0000, 0x1a12, 0x25b0, 0x38eb, 0x3348, 0x06b0, 0x268b, 0x197a, 0x26c2, 0x1fea, 0x0c1a, 0x1c4f, 0x0cc4, 0x3c76, 0x2387, 0x002e, 0x3925, 0x3215, 0x1a49, 0x136c, 0x08b4, 0x3932, 0x3c43, 0x0674, 0x3e2f, 0x1f4b, 0x26ef, 0x27dd, 0x2e77, 0x2fc6, 0x2555, 0x03e7, 0x38a4, 0x19c7, 0x2798, 0x275f, 0x2293, 0x0c9c, 0x2f50, 0x3c35, 0x0eb6, 0x3177, 0x199b, 0x2b90, 0x1abe, 0x2c44, 0x06e8, 0x346c, 0x0314, 0x3bd4, 0x30c7, 0x2972, 0x3390, 0x1814, 0x2864, 0x0038, 0x2768, 0x3621, 0x2052, 0x0d91, 0x0b56, 0x2178, 0x1831, 0x075b, 0x2773, 0x3091, 0x14fd, 0x1764, 0x060c, 0x013f, 0x09a6, 0x08f6, 0x275d, 0x266b, 0x09ba, 0x04c8, 0x0747, 0x1c9b, 0x3464, 0x2843, 0x19c2, 0x1f50, 0x3a70, 0x0e1e, 0x3b21, 0x2b2d, 0x2044, 0x0b6e, 0x3744, 0x046c, 0x3701, 0x1c6b, 0x05a2, 0x1303, 0x1d58, 0x3790, 0x0857, 0x1a54, 0x0eef, 0x2074, 0x1563, 0x08e3, 0x07aa, 0x16c9, 0x3ed7, 0x1466, 0x209c, 0x11ba, 0x0e8f, 0x1860, 0x13bd, 0x1436, 0x23d3, 0x3a79, 0x22a6, 0x1f0f, 0x290d, 0x0386, 0x0a3f, 0x2920, 0x1ba2, 0x1523, 0x03e4, 0x1c29, 0x3ef9, 0x0398, 0x0d94, 0x2451, 0x071b, 0x0167, 0x2785, 0x254e, 0x01af, 0x2183, 0x2892, 0x38d4, 0x1a91, 0x2522, 0x0c79, 0x29eb, 0x2d29, 0x15b6, 0x21fa, 0x3df5, 0x3008, 0x0bff, 0x32f7, 0x0a09, 0x05cb, 0x3d13, 0x3b70, 0x149c, 0x2e63, 0x2fc9, 0x0ab2, 0x2df2, 0x08e1, 0x267e, 0x194c, 0x332d, 0x2060, 0x06e4, 0x240b, 0x2a05, 0x2ee5, 0x3e1e, 0x07c3, 0x35a4, 0x38aa, 0x27e6, 0x0bb1, 0x174a, 0x2499, 0x1b1b, 0x33d6, 0x2689, 0x3aec, 0x3aac, 0x1aa5, 0x3da0, 0x3295, 0x20e1, 0x3e2e, 0x36a3, 0x21c6, 0x3720, 0x2767, 0x30f0, 0x1b3b, 0x2357, 0x148f, 0x2ec5, 0x23be, 0x1b34, 0x19f5, 0x0e1f, 0x0e4e, 0x3cc3, 0x3d1a, 0x386f, 0x09e6, 0x092c, 0x0ad9, 0x0625, 0x3fb0, 0x2a81, 0x1f4d, 0x287d, 0x0354, 0x3a14, 0x2dd0, 0x0224, 0x2479, 0x2a1a, 0x0e18, 0x34c9, 0x1fb7, 0x17b6, 0x180a, 0x1877, 0x1aad, 0x13ac, 0x2978, 0x3332, 0x1d17, 0x2a24, 0x1478, 0x2136, 0x2498, 0x078a, 0x16c1, 0x1f0e, 0x2b96, 0x14ab, 0x300e, 0x011e, 0x2350, 0x32f2, 0x1cfb, 0x2efe, 0x31cf, 0x0262, 0x219d, 0x07c0, 0x38ca, 0x2bc3, 0x36bc, 0x39ee, 0x313e, 0x35d8, 0x220f, 0x0bc1, 0x2244, 0x152c, 0x1971, 0x2161, }; /* small adjustments to _a_ to make values distinct */ uint8_t tab[] = { 11,54,10,23,15,18,2,74,0,75,83,32,58,18,65,68, 16,0,41,0,35,8,12,0,11,2,0,0,0,5,0,0, 8,14,23,7,2,69,0,0,0,0,0,0,0,0,0,0, 0,27,0,3,0,28,0,11,20,4,0,0,56,0,0,8, 3,1,21,0,13,45,18,14,52,27,9,22,43,3,20,34, 3,0,16,68,16,0,0,0,3,41,11,6,6,23,61,10, 0,5,0,0,84,0,12,14,0,4,24,14,0,0,0,0, 0,15,6,7,0,13,10,61,0,0,94,15,0,0,0,0, 7,21,1,0,3,0,2,0,14,3,16,0,18,42,19,0, 0,8,0,7,24,4,0,0,0,16,17,13,4,34,0,15, 0,0,0,0,0,0,0,18,0,17,26,0,0,0,0,0, 0,0,0,0,40,0,20,0,0,3,15,48,0,32,0,0, 0,6,22,0,2,10,13,0,1,12,35,9,6,5,42,0, 9,0,0,16,63,12,9,70,0,9,19,0,94,5,0,2, 0,0,0,17,0,0,0,0,0,0,53,0,52,10,28,0, 10,0,15,33,0,0,15,23,0,27,8,0,0,10,7,0, 0,43,0,0,0,17,0,32,29,21,63,0,11,39,25,0, 8,19,6,11,0,17,0,89,7,27,9,160,67,30,0,33, 0,0,18,0,0,3,87,0,0,5,6,3,0,0,4,36, 22,5,0,0,0,0,1,0,0,0,0,0,0,0,9,16, 0,20,0,0,0,8,0,33,43,36,0,24,0,80,39,20, 16,0,1,51,21,60,41,23,37,29,0,43,11,12,28,0, 0,14,7,0,0,0,21,0,0,0,53,45,0,0,7,57, 1,0,16,187,0,17,0,0,0,0,110,40,0,0,0,0, 0,0,161,0,42,28,0,0,0,14,0,0,0,16,0,8, 3,0,17,0,24,42,0,17,4,5,30,45,7,13,29,94, 47,76,5,25,0,7,0,34,0,23,55,0,0,24,14,0, 0,0,0,0,0,0,42,0,3,0,25,44,0,0,18,0, 40,51,0,37,0,18,0,27,10,45,0,49,19,97,8,7, 35,82,6,0,48,6,4,0,3,55,5,80,32,68,8,11, 0,10,0,0,0,52,3,68,0,2,0,0,0,9,0,52, 0,0,14,0,0,0,0,0,7,0,0,19,25,10,0,0, 19,14,0,0,27,0,0,0,0,0,0,0,0,0,0,12, 0,0,0,5,30,7,0,14,2,49,63,5,0,11,0,0, 92,62,116,13,17,68,14,34,4,20,33,1,0,0,0,5, 73,0,0,0,37,0,15,2,119,13,2,17,114,0,4,13, 62,0,5,0,0,7,6,36,8,0,0,190,0,0,0,0, 18,10,44,3,0,9,14,0,10,24,38,0,0,37,60,0, 62,45,36,38,10,58,34,32,30,15,8,20,16,34,14,41, 35,6,50,0,43,0,17,0,140,12,101,0,235,31,108,68, 0,0,0,0,13,3,0,12,7,0,192,76,34,0,0,0, 0,62,59,0,0,43,90,0,22,0,5,14,32,0,7,0, 128,29,15,81,9,91,5,0,103,39,15,0,13,115,45,16, 0,1,0,31,36,93,0,8,11,111,0,13,60,99,0,21, 0,10,0,0,0,0,0,0,8,0,0,0,12,32,155,0, 27,6,22,0,0,82,43,31,55,46,0,20,0,19,42,0, 10,55,1,23,156,34,44,31,38,60,8,40,175,5,32,20, 0,180,13,11,0,201,120,7,90,203,0,18,0,217,22,14, 16,0,0,0,17,0,5,0,7,28,0,0,22,8,11,0, 0,0,46,33,0,0,0,0,0,0,0,0,82,28,0,0, 0,0,0,29,23,33,0,12,2,0,110,107,7,31,34,87, 0,0,76,11,0,4,6,5,8,34,8,0,9,61,50,47, 14,0,0,77,44,0,13,15,53,0,0,8,36,48,144,3, 14,0,0,0,0,0,17,58,34,7,0,0,0,0,0,0, 37,0,0,15,0,3,0,19,0,16,5,20,0,7,78,130, 12,160,2,61,1,6,0,7,31,12,21,0,11,4,1,49, 0,0,0,8,0,0,18,0,0,0,0,11,0,0,0,32, 0,0,0,0,7,0,49,0,52,0,0,218,16,1,0,46, 19,0,93,0,24,39,0,51,57,0,0,23,89,24,0,19, 59,37,11,9,26,73,38,10,60,101,16,4,14,148,17,46, 31,0,15,8,24,24,36,9,10,1,0,67,5,9,0,0, 22,0,0,0,0,0,0,0,1,72,0,0,9,0,12,30, 115,41,0,8,116,7,17,2,124,0,23,11,4,0,83,32, 8,6,12,31,48,16,17,22,36,174,1,48,22,24,5,36, 33,0,25,10,10,5,12,0,37,10,2,12,2,23,24,18, 18,0,28,0,0,47,33,32,9,60,27,15,13,4,43,0, 62,0,9,71,0,74,0,0,0,0,0,0,0,0,0,0, 0,3,11,43,0,6,7,1,29,31,18,87,0,0,13,16, 41,4,41,42,28,11,8,59,7,7,30,93,21,0,26,13, 30,12,14,0,37,0,247,0,80,14,111,0,2,7,140,0, 0,143,17,0,15,0,1,33,16,0,18,0,0,0,0,0, 14,28,0,20,0,6,0,5,43,0,0,14,1,0,0,9, 1,15,1,7,16,41,61,0,5,9,113,30,4,16,29,47, 14,7,0,45,107,0,0,21,0,6,5,0,8,19,1,14, 0,0,0,0,0,0,64,0,36,0,70,0,0,0,67,0, 0,0,25,20,114,0,14,43,0,29,1,101,20,0,0,36, 10,4,8,0,0,60,4,0,3,39,7,0,16,21,34,20, 24,3,38,5,0,11,0,6,0,45,29,73,0,4,64,76, 0,0,0,47,0,0,0,0,0,39,14,0,0,34,22,0, 0,0,31,0,0,0,0,0,0,11,42,2,0,9,0,2, 0,9,0,27,0,13,0,17,0,182,62,54,36,61,0,72, 7,14,16,18,15,19,33,63,2,77,237,31,12,103,39,0, 0,0,33,0,0,0,8,0,0,0,52,18,0,0,8,74, 0,60,0,0,0,0,31,0,0,0,0,0,0,0,81,28, 0,35,0,0,0,10,0,51,32,62,58,0,0,70,48,0, 50,18,0,84,38,10,9,50,29,26,7,8,8,4,0,66, 0,17,44,0,0,0,7,0,0,34,2,6,0,39,9,60, 0,0,3,20,3,41,0,0,0,0,42,40,0,0,0,0, 0,8,118,28,30,3,0,30,57,39,0,4,70,47,0,10, 11,88,0,0,30,92,1,0,1,44,40,0,19,213,23,1, 0,4,94,0,0,9,0,10,0,0,5,0,0,3,16,20, 0,0,0,0,0,0,0,19,47,13,0,37,0,0,0,152, 10,33,0,0,0,0,101,0,0,2,0,21,0,0,0,246, 6,0,39,0,1,35,10,92,10,6,6,22,9,29,45,10, 51,32,0,20,0,29,0,3,0,112,0,0,0,13,0,0, 0,0,72,0,0,0,0,0,0,0,104,3,6,0,60,63, 0,72,50,18,24,0,0,16,0,0,0,0,9,0,18,0, 0,58,0,0,52,21,0,0,27,25,36,0,12,31,0,0, 2,15,7,4,16,12,1,17,19,14,6,39,8,71,0,2, 75,0,102,0,36,0,0,0,77,7,22,19,121,11,87,24, 7,0,0,0,18,49,0,27,0,0,0,0,0,0,0,0, 6,58,0,122,0,29,0,0,9,40,0,0,0,23,0,54, 13,13,20,2,0,5,70,16,0,19,43,7,9,20,14,4, 0,0,60,0,10,0,3,0,0,0,8,19,0,2,1,0, 0,0,0,0,0,0,0,0,89,11,153,0,0,0,0,0, 66,103,0,0,4,0,241,226,28,14,0,11,0,98,35,123, 165,75,5,44,189,16,25,27,9,41,3,34,62,0,7,17, 0,194,159,24,0,67,32,8,19,235,21,11,74,0,22,93, 25,28,0,0,0,0,0,0,88,32,0,0,31,0,43,0, 0,0,27,0,0,36,38,0,15,0,21,16,37,0,62,49, 10,0,0,0,7,11,12,53,4,0,27,22,37,0,17,0, 0,8,0,7,0,92,0,29,34,0,0,35,5,237,0,1, 14,0,16,20,29,0,50,1,118,201,0,0,23,3,119,0, 0,68,27,5,23,84,0,0,0,0,0,0,150,8,0,23, 0,32,0,0,0,12,0,7,0,48,35,0,0,53,0,1, 62,61,9,20,18,0,8,22,22,0,12,1,19,0,4,17, 11,0,26,0,4,0,87,0,19,13,0,0,2,27,214,0, 127,0,0,0,0,0,66,0,0,56,0,0,0,0,0,0, 0,29,0,11,0,5,0,0,26,68,18,48,59,0,87,27, 0,0,1,3,0,3,26,8,20,26,34,42,197,22,127,12, 40,63,0,1,0,52,0,0,75,9,0,46,11,0,26,128, 0,0,0,0,0,0,14,0,5,0,13,58,29,0,0,0, 64,53,54,34,9,5,91,50,3,108,246,0,37,2,0,55, 14,27,3,22,12,24,20,58,17,11,108,2,30,237,29,27, 0,0,0,1,14,0,43,22,3,0,78,128,0,0,61,3, 15,0,65,0,0,0,0,0,0,10,13,0,19,0,0,66, 104,124,0,17,130,0,82,0,0,0,0,9,151,0,0,25, 9,21,5,3,0,163,43,78,22,35,28,32,21,72,4,8, 1,39,96,1,22,34,6,0,3,8,1,1,18,32,2,0, 0,33,0,0,0,13,0,37,29,0,0,0,7,3,0,0, 23,0,9,12,0,0,7,0,0,0,0,0,0,0,12,0, 0,8,0,26,0,70,11,16,48,19,10,3,0,17,3,7, 1,117,19,0,2,6,3,0,5,32,25,95,0,24,31,0, 0,11,0,0,30,16,0,0,0,6,0,161,5,19,0,43, 0,0,18,0,55,0,44,97,0,43,0,0,0,0,0,0, 0,23,11,0,40,88,0,0,15,93,18,17,0,64,3,63, 4,6,0,0,25,0,39,17,49,33,105,7,21,8,34,24, 11,33,36,5,0,32,54,11,18,0,55,0,11,36,62,0, 0,0,0,0,0,0,28,0,66,0,0,45,0,59,0,0, 0,44,0,20,0,43,0,12,0,0,0,50,5,0,0,32, 32,12,16,0,66,8,23,0,0,13,0,6,5,0,12,37, 50,36,0,0,0,43,0,0,61,0,6,42,0,0,22,0, 0,0,0,10,0,0,0,0,0,0,46,0,57,8,1,1, 0,20,48,28,0,87,16,163,52,9,117,23,0,22,0,33, 0,28,0,12,28,27,0,61,0,33,0,6,0,29,0,0, 31,0,9,0,35,0,16,0,7,106,14,0,32,13,51,40, 61,14,0,0,0,10,0,0,113,4,41,0,60,69,31,0, 21,0,27,0,0,0,105,0,0,0,0,0,0,0,55,0, 59,28,0,30,52,85,0,13,70,0,0,2,38,5,0,28, 15,51,1,0,56,39,36,0,6,40,5,50,3,106,0,8, 0,21,18,0,0,3,48,45,36,23,9,81,0,0,40,8, 39,0,0,41,34,0,0,0,0,0,0,24,0,0,0,0, 2,12,0,0,31,15,0,0,0,27,0,17,0,16,25,0, 1,53,0,0,29,13,54,25,34,25,0,10,5,27,0,0, 0,0,0,17,0,52,28,8,105,0,30,0,125,59,93,0, 0,0,0,0,0,0,62,21,12,70,0,0,0,0,43,93, 0,28,0,14,32,22,0,6,0,21,0,0,0,23,0,108, 103,77,6,33,11,39,8,0,35,30,52,11,13,22,2,0, 0,9,26,14,11,0,0,223,86,7,118,0,21,0,28,0, 0,0,49,0,0,0,0,0,0,0,49,0,3,0,0,29, 17,0,0,70,0,0,0,0,0,0,0,0,0,0,0,64, 0,26,87,21,0,0,38,9,0,0,0,63,37,5,0,11, 14,57,27,170,46,26,19,24,85,20,4,34,19,72,76,14, 86,0,0,20,0,46,0,0,40,0,3,0,78,41,28,0, 16,0,0,0,76,62,0,13,0,0,8,0,0,0,0,0, 40,0,0,0,9,0,0,0,16,22,0,13,75,19,0,17, 0,0,14,29,0,0,5,32,0,57,2,20,0,5,10,22, 12,0,0,26,31,0,48,1,6,34,0,15,10,0,0,105, 0,0,0,0,26,0,0,32,10,15,0,0,4,0,0,0, 7,0,0,48,1,73,0,67,0,40,0,80,9,0,0,0, 0,70,65,0,92,24,87,5,0,11,41,13,0,0,111,8, 0,0,0,23,64,0,0,0,11,0,2,0,0,0,14,0, 14,0,0,0,0,0,0,0,8,0,3,0,43,5,0,63, 32,32,0,0,69,0,0,13,0,71,39,32,0,3,0,88, 6,157,0,8,32,71,50,24,131,0,73,15,34,21,64,34, 103,4,0,55,19,0,0,7,3,10,16,0,7,0,47,0, 18,0,0,13,19,0,0,0,0,42,5,19,20,15,49,0, 70,0,25,0,8,14,144,0,0,0,0,0,27,36,0,0, 0,0,0,12,0,24,32,1,0,21,0,3,0,5,0,2, 14,76,7,28,24,16,14,0,0,0,9,47,7,0,30,15, 34,23,0,1,8,36,89,99,0,58,56,0,5,0,15,0, 0,53,9,0,21,0,0,0,16,0,0,0,0,0,0,0, 41,2,57,5,83,156,66,58,23,0,24,36,0,48,4,4, 141,10,4,251,4,158,34,14,13,0,108,1,6,22,44,28, 10,14,0,0,40,2,0,0,0,0,1,0,5,0,0,54, 0,0,0,0,18,0,0,0,0,0,0,28,14,25,0,8, 0,0,3,75,0,155,12,57,0,58,0,7,22,25,0,94, 78,7,36,10,0,145,80,20,0,40,15,7,0,39,31,11, 35,10,0,10,12,14,10,0,8,0,0,2,50,0,0,10, 24,22,0,0,0,0,0,0,36,0,0,0,0,0,45,0, 3,0,0,35,0,0,52,45,0,42,16,8,0,40,0,1, 61,33,21,36,14,0,26,26,11,76,3,21,156,0,7,18, 1,5,114,142,0,62,24,0,2,13,36,2,15,5,7,52, 0,33,61,0,94,3,0,46,0,56,0,26,19,21,0,0, 19,0,66,55,0,0,0,0,0,0,0,0,0,0,0,0, 0,41,23,19,0,10,48,19,20,45,65,18,0,58,5,48, 4,2,3,0,12,33,45,144,9,0,6,72,3,5,0,0, 0,65,84,23,0,19,0,22,9,0,0,0,20,0,0,0, 0,0,98,12,0,0,55,5,0,0,0,0,0,0,0,0, 5,43,20,4,0,28,0,16,4,5,57,12,0,7,56,15, 12,10,9,55,5,10,11,16,25,49,10,17,8,35,18,35, 14,30,0,90,0,0,38,27,59,0,31,0,100,27,68,42, 0,0,0,0,0,24,0,0,75,0,7,9,0,19,39,0, 43,0,50,48,94,29,0,46,0,14,18,41,0,2,4,7, 47,18,76,50,22,8,1,47,9,16,12,134,4,7,18,174, 18,0,14,5,17,144,13,10,7,37,183,0,34,0,210,0, 0,0,0,0,0,0,0,0,0,56,45,0,58,80,0,38, 229,37,0,7,32,0,0,3,0,69,0,5,0,15,0,9, 9,193,0,58,12,3,0,59,10,12,0,28,0,58,55,36, 43,4,33,0,36,15,16,21,7,14,2,0,102,82,4,21, 77,12,11,25,0,74,23,99,1,63,37,15,0,1,6,116, 17,0,1,0,0,0,59,0,0,0,0,0,0,0,0,65, 62,19,0,46,0,4,33,34,0,15,0,28,0,0,0,4, 83,11,9,0,7,2,30,0,179,0,19,45,36,20,92,0, 0,38,0,0,34,30,0,0,2,1,32,0,23,18,66,0, 0,0,20,19,11,0,13,0,0,0,10,0,0,0,0,0, 0,2,0,9,24,6,0,5,0,8,0,38,0,3,0,11, 2,19,18,0,31,13,39,59,28,30,56,0,4,19,17,0, 0,5,0,0,86,18,42,93,40,0,38,0,0,10,19,0, 0,0,0,0,1,0,20,0,22,0,0,0,0,0,45,15, 52,133,0,50,42,87,0,0,0,13,45,6,0,33,0,41, 3,5,0,72,64,120,42,0,72,1,0,0,26,4,32,19, 0,82,0,0,0,20,0,0,14,18,23,0,24,0,99,0, 0,0,17,0,0,0,0,0,35,0,112,30,45,21,0,0, 116,41,13,42,0,0,0,0,0,0,0,0,5,36,0,0, 0,79,0,16,144,0,44,33,70,44,0,8,52,28,0,14, 41,36,8,12,21,11,0,56,51,59,6,11,15,231,9,21, 0,60,45,3,13,0,75,10,7,0,0,11,0,0,0,25, 0,0,0,0,1,0,96,23,29,0,0,0,0,0,0,0, 0,0,0,35,0,85,26,55,133,20,0,88,74,0,125,30, 12,72,94,0,3,75,40,9,31,18,21,29,37,62,31,28, 40,0,0,0,131,116,0,23,31,28,39,0,83,0,0,0, 0,0,0,0,0,0,0,56,0,29,0,11,2,0,25,0, 6,0,147,9,28,1,141,0,0,10,0,13,74,54,76,38, 17,174,61,6,0,22,8,34,4,140,3,77,14,192,14,13, 93,0,0,24,12,154,0,38,77,0,12,0,118,0,106,0, 143,0,0,236,0,0,0,0,13,0,0,0,59,0,0,6, 4,66,0,46,1,8,0,12,8,67,0,41,0,30,0,9, 70,0,43,2,9,7,16,3,0,20,58,21,0,100,26,9, 17,0,74,0,12,0,0,2,10,0,33,0,3,0,22,0, 123,2,0,15,8,0,149,6,32,55,99,26,25,0,185,11, 15,0,0,111,0,0,0,62,0,0,0,0,0,38,0,0, 1,0,32,91,0,2,141,56,0,0,23,10,0,48,0,9, 28,142,40,45,15,28,32,30,19,63,69,58,19,89,15,28, 50,0,136,11,19,0,0,10,67,31,13,0,0,20,42,0, 0,22,4,0,14,0,0,254,5,3,0,0,0,0,0,0, 0,0,8,12,17,0,0,11,0,52,0,24,0,59,0,19, 24,61,0,0,56,23,1,18,45,174,57,111,27,181,16,5, 0,45,56,3,14,22,9,5,15,0,50,94,14,0,100,0, 0,0,0,0,140,0,0,0,0,0,16,0,13,30,0,0, 193,0,10,42,0,0,22,10,0,34,0,29,0,3,0,4, 7,138,40,33,6,0,132,70,60,17,2,7,67,9,18,75, 10,25,70,13,4,0,0,0,2,0,17,44,6,0,38,0, 74,0,0,32,0,0,0,0,5,21,0,0,0,0,0,0, 39,0,20,30,0,0,1,43,0,32,0,83,0,38,0,13, 0,79,58,21,45,2,8,12,0,54,9,4,0,85,37,18, 88,14,0,0,8,29,17,0,12,13,100,0,89,62,50,131, 0,7,0,10,0,0,0,0,37,9,0,0,39,11,0,0, 7,6,0,0,0,0,18,0,0,0,0,0,0,0,0,90, 21,0,12,0,8,0,7,0,8,0,251,33,14,8,106,28, 11,6,0,45,58,0,0,18,22,68,0,7,38,31,120,0, 0,4,5,0,0,46,0,9,127,0,0,13,70,83,0,0, 0,87,0,27,2,76,0,0,0,0,0,0,0,0,0,0, 131,0,50,0,2,0,55,0,32,10,61,0,9,120,0,0, 22,25,43,15,0,3,20,19,0,32,65,46,42,44,84,152, 61,0,85,0,4,0,3,0,0,37,7,88,0,115,16,59, 0,0,0,0,0,0,50,0,0,0,0,29,0,0,11,0, 0,28,112,47,3,133,0,0,0,138,1,0,8,194,54,0, 2,34,233,7,25,56,32,13,61,0,67,11,32,152,162,108, 0,13,2,0,21,6,35,0,0,35,20,32,169,47,19,122, 0,0,0,0,0,0,0,0,0,0,23,0,0,17,27,175, 0,77,0,55,0,95,31,0,0,105,5,39,32,167,0,12, 15,0,8,0,25,34,8,0,66,0,27,0,0,0,0,0, 18,111,1,0,5,95,10,68,1,37,0,3,0,5,0,0, 0,49,0,11,36,0,0,78,28,0,0,2,14,0,12,3, 20,17,0,60,10,28,0,0,0,0,0,0,0,23,0,0, 19,0,20,43,7,0,56,0,8,0,0,21,38,0,15,50, 65,50,65,26,41,34,45,2,26,80,41,2,9,3,109,0, 1,84,45,63,0,40,6,44,40,180,1,42,0,191,0,28, 0,0,0,12,51,37,32,56,0,16,56,0,0,0,0,0, 0,69,0,54,0,28,0,68,0,5,45,0,26,19,39,132, 1,83,151,3,0,6,56,4,0,98,61,48,59,70,31,1, 194,0,9,4,199,0,75,15,209,165,31,0,237,27,0,0, 0,0,0,0,0,38,37,3,0,0,6,0,0,7,39,0, 17,0,0,0,28,0,75,147,33,14,9,0,0,20,25,2, 28,22,0,158,8,60,71,53,7,5,25,110,18,2,22,197, 43,0,97,58,35,58,144,6,253,0,0,0,254,0,0,17, 0,0,71,0,0,0,0,0,0,0,0,62,146,18,4,0, 0,0,0,0,52,83,0,0,0,0,0,0,6,129,0,0, 5,0,153,0,8,0,0,0,67,8,7,30,81,23,0,0, 0,1,2,28,2,76,31,43,14,54,7,74,193,21,27,133, 0,35,0,20,0,36,0,1,0,0,3,10,0,0,38,11, 0,154,0,0,0,0,0,0,75,87,0,59,0,0,0,0, 9,0,0,45,11,0,0,23,23,67,95,15,139,0,0,56, 0,87,30,7,0,7,23,17,0,18,2,13,6,48,100,20, 51,11,0,113,0,46,0,5,60,0,37,47,65,0,12,150, 0,0,0,0,0,0,0,77,173,33,0,0,23,0,0,0, 0,71,0,79,22,13,115,58,1,53,26,42,2,0,40,112, 15,176,0,6,15,21,17,14,2,7,0,24,21,78,50,5, 4,0,0,0,9,25,21,0,13,1,0,60,3,53,0,0, 0,21,0,0,0,0,0,0,53,0,0,0,3,34,0,2, 15,38,67,19,85,29,24,61,95,32,35,0,10,36,32,1, 86,4,9,86,22,1,8,15,3,2,24,34,70,41,33,12, 59,0,0,115,11,0,0,23,28,80,0,43,3,33,39,8, 0,48,0,1,6,14,0,36,24,124,0,177,6,7,0,15, 12,18,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,8,0,0,0,125,61,0,98,0,10,0,162,13,78, 18,0,121,40,4,121,5,11,27,0,27,0,77,0,20,3, 0,0,7,122,0,35,60,137,38,182,2,41,35,31,1,188, 0,125,0,0,33,39,0,45,0,0,207,0,0,0,0,0, 70,13,17,0,71,0,4,0,0,216,56,0,0,25,121,0, 9,3,83,19,26,20,35,7,0,6,28,16,54,9,71,34, 49,1,8,0,7,16,10,0,4,0,0,0,75,0,21,10, 0,0,0,0,26,3,0,0,106,0,31,16,103,44,0,0, 0,0,0,0,0,0,0,10,12,0,0,91,40,0,25,57, 9,5,90,10,14,0,20,5,84,19,32,141,46,11,99,26, 16,13,46,0,77,52,27,0,0,0,88,213,3,3,4,0, 0,0,0,0,0,0,0,0,47,82,0,0,0,6,0,20, 92,0,10,37,0,0,14,70,167,0,11,38,121,0,151,0, 90,12,10,1,60,52,81,2,98,113,93,17,68,28,30,25, 29,10,0,48,0,11,59,166,22,40,186,20,35,31,13,8, 0,69,0,41,0,18,28,45,58,14,0,0,81,2,0,0, 6,20,0,0,0,0,42,0,0,0,0,0,0,0,0,89, 14,0,0,0,13,13,16,54,36,8,5,18,27,148,0,0, 32,1,22,0,189,68,10,0,97,6,52,98,24,13,26,0, 0,5,0,10,0,9,0,28,0,19,0,0,44,0,0,0, 9,0,125,0,0,8,0,0,0,0,17,0,0,0,0,0, 16,53,13,0,61,0,11,0,39,0,152,6,13,75,31,149, 62,78,17,15,151,0,18,10,0,9,54,108,26,126,42,11, 127,38,76,0,137,17,48,0,58,77,7,0,160,134,36,98, 0,0,0,0,0,71,56,0,193,0,0,28,0,56,0,0, 0,203,61,0,0,149,0,1,17,19,12,22,12,80,118,29, 0,147,196,97,12,7,74,31,0,1,197,4,0,14,174,9, 49,0,197,0,12,0,11,0,0,34,37,78,0,40,57,57, 0,0,72,0,0,0,0,0,18,31,0,40,0,123,7,15, 20,208,16,173,26,66,20,0,14,0,75,0,0,67,0,0, 103,0,32,0,28,44,112,75,49,0,37,14,3,0,0,87, 12,70,82,12,3,65,58,237,71,15,51,39,18,0,130,33, 0,217,1,50,0,200,0,0,0,86,25,50,53,153,2,23, 38,49,46,26,0,9,0,44,0,0,0,0,0,83,0,0, 31,0,8,37,0,0,0,0,0,0,0,18,34,0,11,0, 1,5,77,31,19,43,10,17,5,9,0,0,3,80,20,160, 54,0,0,35,0,0,0,17,121,103,0,7,16,0,0,8, 3,0,0,0,98,21,2,0,0,63,0,62,0,0,0,0, 146,160,0,167,144,55,0,6,88,0,63,136,21,0,39,0, 40,34,11,28,25,125,9,43,39,0,79,30,22,31,31,33, 97,0,14,148,73,54,9,62,101,15,107,34,168,0,0,26, 0,0,0,0,0,0,201,18,34,201,45,0,0,0,0,0, 0,0,0,205,0,163,0,102,15,65,131,0,0,171,13,0, 0,22,199,45,149,1,30,17,0,115,86,2,47,121,5,31, 122,0,53,5,140,0,48,0,0,215,232,0,190,0,0,0, 0,39,0,0,0,0,0,0,0,0,216,4,192,0,124,0, 0,0,0,173,0,30,0,0,0,0,0,0,0,45,0,0, 4,0,37,0,6,0,3,16,59,25,21,17,61,3,41,38, 0,18,46,12,0,23,31,13,19,8,63,8,0,60,41,37, 0,68,0,141,0,145,0,63,172,0,3,88,10,0,10,14, 216,5,0,32,0,0,0,0,21,54,0,0,0,0,0,0, 51,0,168,0,1,0,0,0,34,105,254,32,69,48,0,0, 0,16,3,46,0,0,8,25,193,10,61,44,57,67,5,22, 0,38,0,13,0,177,0,17,0,0,35,16,0,0,16,32, 0,0,0,0,20,0,0,173,147,121,0,1,0,145,0,0, 200,27,37,113,238,9,18,0,76,74,10,0,8,40,59,43, 11,1,126,20,55,13,53,17,114,41,111,32,0,14,63,150, 29,0,60,38,76,0,190,84,36,0,98,35,89,96,126,160, 66,0,0,0,0,0,0,0,86,0,0,0,0,6,0,18, 12,134,0,5,8,167,0,19,2,50,17,19,9,76,200,12, 56,53,60,19,88,18,0,16,11,40,25,14,36,123,0,7, 45,0,20,0,21,0,1,0,4,23,0,192,32,4,0,0, 0,161,32,72,93,1,73,30,17,78,4,37,27,74,32,87, 14,14,66,2,0,0,0,0,0,0,0,0,0,82,87,0, 25,0,20,0,83,63,5,0,0,0,35,0,0,0,11,0, 70,27,113,3,4,12,26,5,3,27,135,1,7,15,92,37, 55,192,0,98,0,51,0,31,9,80,0,9,8,36,0,19, 0,67,0,0,10,53,0,0,0,0,0,0,0,0,0,0, 96,0,0,120,1,0,137,0,101,0,184,94,0,20,0,29, 10,77,3,40,5,65,154,56,44,3,35,90,116,28,21,4, 22,68,60,0,13,0,36,0,4,150,20,0,15,0,46,11, 0,0,0,0,130,68,0,0,28,16,0,29,37,0,0,0, 82,0,17,0,0,11,36,66,55,46,20,15,0,95,18,94, 98,63,93,3,0,58,17,5,152,183,121,6,0,34,22,0, 34,0,13,0,44,63,18,0,91,0,31,0,16,0,73,234, 0,10,0,0,0,0,0,0,0,33,0,0,41,0,223,14, 0,0,0,192,0,0,0,0,12,0,17,170,21,0,0,20, 0,6,0,15,0,3,0,12,189,7,14,44,8,17,41,13, 0,75,52,106,31,1,105,14,184,231,80,11,13,62,9,39, 0,0,74,0,0,3,94,0,0,1,0,7,13,83,0,106, 0,40,42,5,0,0,99,0,0,0,0,0,0,30,0,30, 0,117,52,0,14,192,21,0,0,0,106,0,0,0,71,0, 0,63,129,53,53,33,197,11,74,22,0,6,25,25,43,0, 0,96,77,0,46,12,57,0,8,16,130,100,110,59,9,112, 0,188,6,173,0,7,54,41,0,70,66,30,0,0,0,0, 0,126,188,91,0,145,100,17,36,2,101,22,128,0,162,27, 0,2,24,129,18,102,51,91,2,34,96,53,6,64,71,18, 169,0,152,40,7,5,0,38,0,1,0,14,0,9,0,27, 0,0,0,0,0,0,43,35,11,26,112,0,0,0,53,0, 0,0,64,14,0,0,116,28,0,0,6,0,0,0,10,0, 23,12,36,43,60,171,85,53,7,158,0,9,96,12,183,76, 16,48,36,0,1,0,8,0,0,7,61,0,0,16,0,11, 0,0,133,0,0,0,0,0,0,0,0,35,230,40,155,0, 0,85,0,12,0,0,3,189,0,118,91,34,33,0,160,0, 77,145,16,0,52,103,28,73,44,0,1,0,27,0,17,0, 0,130,89,36,121,30,154,4,39,163,178,31,20,136,37,43, 203,38,46,0,207,88,0,0,0,224,56,97,0,109,53,35, 0,0,197,167,0,19,0,0,0,0,0,0,0,0,108,44, 0,133,15,0,139,0,92,0,50,45,42,0,7,23,79,0, 27,49,0,40,31,0,74,80,234,24,226,43,54,15,142,51, 214,4,0,0,222,89,0,93,127,0,122,0,200,0,0,48, 0,0,0,0,0,0,4,0,0,0,30,0,0,0,0,0, 24,0,0,0,20,1,65,85,13,0,0,0,40,51,0,0, 6,68,208,3,12,114,178,0,74,109,77,0,11,97,194,0, 120,0,0,0,0,0,0,0,0,23,0,2,83,16,0,183, 0,0,0,0,0,0,0,110,210,0,0,0,0,0,0,6, 128,237,92,224,26,209,34,14,65,0,246,190,12,0,66,0, 70,47,124,45,60,6,52,4,114,28,125,2,17,43,180,71, 0,40,67,0,0,75,7,0,174,7,11,31,0,90,0,41, 13,0,0,75,0,0,0,0,0,9,0,48,247,0,23,99, 0,0,29,118,96,0,0,0,0,0,0,0,0,10,0,0, 6,0,20,74,1,0,91,44,3,148,18,0,16,52,3,0, 73,29,79,5,19,29,93,8,121,8,77,0,171,11,0,21, 16,0,0,41,40,60,0,0,0,62,0,44,0,45,26,0, 177,0,0,0,0,195,0,1,0,6,0,0,0,0,0,0, 36,149,48,0,55,120,0,0,38,71,27,0,32,36,35,0, 68,1,15,156,40,11,74,3,152,10,90,22,15,2,127,160, 53,0,0,4,7,0,18,37,14,82,121,0,48,13,65,0, 0,0,0,0,87,51,136,44,0,0,124,0,3,41,0,0, 16,33,0,0,29,0,0,62,14,0,7,0,10,243,78,71, 16,9,38,18,178,174,23,25,0,0,13,20,136,13,50,44, 0,0,96,0,0,156,185,240,0,168,0,42,0,173,0,31, 33,2,0,0,0,0,0,0,71,116,0,0,236,0,142,4, 28,29,0,0,21,163,0,2,3,0,13,67,61,0,11,82, 181,39,114,38,199,27,175,7,0,16,152,15,38,44,21,13, 62,164,110,83,37,0,150,0,169,117,0,80,0,206,0,109, 11,0,0,1,160,0,41,25,108,0,0,112,9,1,0,227, 0,0,0,22,0,11,0,0,0,0,0,0,0,128,0,0, 9,0,0,232,6,0,67,70,2,0,2,0,3,0,0,0, 0,80,0,37,137,8,0,57,21,37,195,45,0,29,125,42, 5,1,0,0,6,27,92,0,53,0,0,91,24,212,0,1, 0,58,0,0,106,81,53,163,0,0,37,0,0,0,0,0, 61,0,2,22,77,0,0,50,58,91,36,128,94,0,95,22, 50,9,14,22,0,139,57,1,22,31,67,0,0,23,118,8, 22,0,0,146,34,0,0,0,0,40,0,53,49,86,0,81, 0,0,0,0,0,20,57,0,8,74,0,0,0,27,0,0, 0,148,7,52,45,140,23,9,69,0,17,0,112,0,3,53, 11,0,1,20,57,27,14,38,112,32,17,3,105,0,10,2, 196,191,42,44,19,0,23,0,0,0,84,214,0,112,61,181, 0,0,0,0,0,0,0,0,0,111,0,0,72,57,166,30, 19,70,1,164,16,56,94,69,48,0,67,0,11,0,15,0, 42,13,65,36,0,40,103,9,5,0,45,22,55,45,62,14, 6,31,7,68,22,51,6,6,15,44,49,0,0,47,83,7, 82,61,158,0,119,151,93,71,53,0,60,78,29,37,8,169, 92,81,21,0,0,92,0,0,0,0,0,0,0,0,51,7, 0,110,63,129,31,0,202,118,0,0,1,33,161,0,142,5, 25,12,147,8,0,27,65,11,36,106,37,88,78,93,12,28, 0,0,133,15,0,0,39,92,16,28,0,113,0,0,0,170, 0,0,0,0,0,2,86,179,0,0,0,30,0,0,0,0, 68,26,41,0,0,26,191,0,0,0,18,0,0,0,14,0, 188,66,47,30,57,98,129,13,66,28,79,72,47,95,90,103, 22,0,87,0,38,91,8,0,0,67,0,0,0,44,0,0, 0,0,0,0,0,0,147,0,18,3,1,0,0,0,252,154, 0,106,23,22,0,0,215,103,53,0,20,0,35,13,8,0, 11,0,173,68,7,87,107,94,29,2,64,65,32,88,41,153, 74,49,0,22,29,0,84,133,0,12,0,26,0,3,0,117, 0,0,1,5,0,0,0,0,0,0,28,126,0,156,25,0, 0,0,195,84,0,0,46,16,0,0,39,0,0,0,10,0, 0,115,63,0,108,61,60,53,121,29,202,0,88,7,115,0, 208,102,0,121,92,0,0,23,89,44,37,10,17,0,123,45, 80,81,59,64,23,0,70,73,0,0,69,228,0,0,44,92, 0,178,185,164,0,0,0,0,0,0,0,0,0,0,0,230, 0,0,117,0,0,31,58,10,120,0,16,0,107,0,9,0, 2,13,120,5,0,106,0,0,24,0,30,28,67,64,127,34, 0,96,128,0,81,107,56,0,0,82,77,106,0,40,0,75, 0,52,0,82,0,0,32,179,0,0,118,0,0,0,0,0, 22,48,20,92,17,94,14,152,20,0,90,0,9,90,88,154, 94,28,155,162,70,119,68,84,50,113,17,170,10,5,32,10, 0,90,40,0,0,156,0,10,0,33,0,10,0,210,0,180, 0,0,0,0,46,0,0,10,174,89,42,27,9,223,0,0, 0,3,139,201,202,1,4,51,238,34,13,0,109,0,213,0, 9,133,28,10,5,93,26,11,14,1,0,0,18,90,0,14, 97,197,0,133,44,9,221,39,51,179,0,44,0,0,0,0, 0,0,0,0,0,0,0,0,65,0,0,0,213,188,0,5, 114,85,48,27,0,137,0,0,0,0,0,0,24,0,0,157, 71,122,225,0,133,141,77,0,112,129,13,0,103,20,21,0, 146,9,194,55,8,1,76,30,0,8,25,40,43,4,181,48, 6,0,157,0,22,94,191,139,65,123,70,70,49,157,36,157, 143,0,0,0,0,0,31,57,237,96,0,0,0,0,0,0, 16,0,27,0,19,0,60,15,36,218,14,0,1,115,39,0, 70,24,167,4,229,115,14,2,18,7,36,31,208,3,0,14, 70,19,0,0,95,0,0,0,0,31,196,129,0,125,0,36, 0,0,0,0,83,118,0,0,0,0,186,5,154,180,0,0, 22,181,0,0,48,68,0,91,5,0,0,231,18,0,83,0, 15,143,93,20,24,12,47,44,7,67,159,13,7,33,31,17, 11,37,26,0,3,118,111,0,0,0,0,101,27,0,0,202, 212,52,0,0,0,0,0,0,0,56,0,119,243,0,36,43, 46,18,0,9,38,81,0,0,12,10,0,25,74,0,153,0, 21,0,117,67,133,0,20,56,43,0,15,54,0,151,93,41, 0,185,39,214,0,0,49,0,0,0,0,11,0,237,0,0, 11,0,114,0,24,0,78,0,49,105,0,112,245,90,0,52, 40,33,12,147,0,0,0,0,0,0,0,0,0,40,0,0, 136,0,217,4,0,25,45,121,58,0,54,91,166,14,6,34, 127,17,0,3,216,65,33,8,75,91,46,0,0,58,102,24, 7,0,33,214,29,0,0,2,12,0,89,36,125,0,121,0, 132,63,116,0,0,0,0,40,0,0,0,0,0,0,0,0, 35,0,136,102,5,0,0,0,2,0,20,0,0,0,4,0, 97,3,136,19,0,23,166,123,0,1,100,50,0,7,0,5, 31,0,35,114,131,0,48,0,0,6,27,70,135,8,10,33, 0,0,0,0,0,99,0,148,60,27,0,71,0,0,234,214, 17,25,28,67,14,22,7,143,8,0,3,0,116,0,5,185, 23,18,90,18,3,75,0,19,237,19,72,6,98,94,1,17, 169,209,0,58,228,8,0,97,117,0,0,35,0,136,0,89, 0,39,25,0,0,0,0,0,0,1,0,0,4,42,0,0, 0,162,29,39,0,53,22,213,0,0,98,31,59,0,62,0, 61,135,48,49,15,50,12,46,93,23,25,11,131,0,55,56, }; /* The hash function */ static uint32_t move_phash(uint32_t val) { uint32_t a, b, rsl; val += 0xb7a4157e; val ^= (val >> 16); val += (val << 8); val ^= (val >> 4); b = (val >> 6) & 0x1fff; a = (val + (val << 4)) >> 19; rsl = (a^scramble[tab[b]]); return rsl; } libosl-0.8.0.orig/full/osl/enter_king/0000755000000000000000000000000012316770314016330 5ustar rootrootlibosl-0.8.0.orig/full/osl/enter_king/enterKingUtil.cc0000644000000000000000000001011012316770314021414 0ustar rootroot#include "osl/enter_king/enterKingUtil.h" // 範囲内(x0,y0) - (x1,y1) ã®åˆ©ãã®æ•°ã‚’調ã¹ã‚‹ int osl::enter_king::countEffectInRange(const NumEffectState& state, osl::Player Turn, int x0, int x1, int y0, int y1) { assert(x0 >= 1 && x0 <= 9); assert(x1 >= 1 && x1 <= 9); assert(y0 >= 1 && y0 <= 9); assert(y1 >= 1 && y1 <= 9); assert(x0 <= x1); assert(y0 <= y1); int effect_count = 0; for (int sy = y0; sy <= y1; sy++) for (int sx = x0; sx <= x1; sx++) effect_count += state.countEffect(Turn, osl::Square(sx,sy)); return effect_count; } // target ã®å‰æ–¹ï¼ˆtarget を中心ã¨ã—ãŸå¹…3マス) ã®åˆ©ãã®æ•°ã‚’調ã¹ã‚‹ int osl::enter_king::countEffectInFrontOf(const NumEffectState& state, osl::Player attack, osl::Square target, osl::Player defense) { const int ky = target.y(); // 一番å‰é¢ã«ã„ã‚‹ã®ã§å‰æ–¹ãŒå­˜åœ¨ã—ãªã„ if ((defense == osl::BLACK && ky == 1) || (defense == osl::WHITE && ky == 9)) return 0; const int kx = (target.x() == 1) ? 2 : ((target.x() == 9)? 8 : target.x()); if (defense == osl::BLACK) return osl::enter_king::countEffectInRange(state, attack, kx - 1, kx + 1, 1, ky - 1); else return osl::enter_king::countEffectInRange(state, attack, kx - 1, kx + 1, ky + 1, 9); } // é§’å°ã®é§’ã®ç‚¹æ•°ã‚’æ•°ãˆã‚‹ int osl::enter_king::countPiecePointsOnStand(const NumEffectState& state, osl::Player Turn) { return (5 * state.countPiecesOnStand(Turn) + 5 * state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn)); } // 範囲内(x0,y0) - (x1,y1) ã®é§’ã®ç‚¹æ•°ã‚’返㙠// num_pieces ã«ã¯ç‚¹æ•°ã§ã¯ãªãã€æžšæ•°ã‚’è¶³ã—込む template int osl::enter_king::countPiecePointsInRange(const NumEffectState& state, int& num_pieces, int x0, int x1, int y0, int y1) { assert(x0 >= 1 && x0 <= 9); assert(x1 >= 1 && x1 <= 9); assert(y0 >= 1 && y0 <= 9); assert(y1 >= 1 && y1 <= 9); assert(x0 <= x1); assert(y0 <= y1); int count = 0; for (int sy = y0; sy <= y1; sy++) { for (int sx = x0; sx <= x1; sx++) { osl::Piece pieceOnSquare = state.pieceOnBoard(osl::Square(sx,sy)); if (! pieceOnSquare.isOnBoardByOwner() || pieceOnSquare.ptype() == osl::KING) continue; count += (1 + 4 * isMajor(pieceOnSquare.ptype())); num_pieces++; } } return count; } int osl::enter_king::countPiecePointsInRange(const NumEffectState& state, osl::Player Turn, int& num_pieces, int x0, int x1, int y0, int y1) { if (Turn == osl::BLACK) return osl::enter_king::countPiecePointsInRange(state, num_pieces, x0, x1, y0, y1); else return osl::enter_king::countPiecePointsInRange(state, num_pieces, x0, x1, y0, y1); } // row 行目ã®é§’ã®ç‚¹æ•°ã¨æžšæ•°ã‚’調ã¹ã‚‹ template int osl::enter_king::countPiecePointsOnRow(const NumEffectState& state, int& num_pieces, int row) { return osl::enter_king::countPiecePointsInRange(state, num_pieces, 1, 9, row, row); } int osl::enter_king::countPiecePointsOnRow(const NumEffectState& state, osl::Player Turn, int& num_pieces, int row) { if (Turn == osl::BLACK) return osl::enter_king::countPiecePointsOnRow(state, num_pieces, row); else return osl::enter_king::countPiecePointsOnRow(state, num_pieces, row); } namespace osl { namespace enter_king { template int countPiecePointsInRange (const NumEffectState& state, int& num_pieces, int x0, int x1, int y0, int y1); template int countPiecePointsInRange (const NumEffectState& state, int& num_pieces, int x0, int x1, int y0, int y1); template int countPiecePointsOnRow (const NumEffectState& state, int& num_pieces, int row); template int countPiecePointsOnRow (const NumEffectState& state, int& num_pieces, int row); } } libosl-0.8.0.orig/full/osl/enter_king/simplePredictor.cc0000644000000000000000000002434212316770314022011 0ustar rootroot#include "osl/enter_king/simplePredictor.h" #include "osl/enter_king/enterKingUtil.h" #include namespace { // 入玉ã«å¿…è¦ãªç‚¹æ•°ã¨ç¾åœ¨ã®ç‚¹æ•°ã€èª¿ã¹ãŸè¡Œã®ç‚¹æ•°ã¨æžšæ•°ã‹ã‚‰ // 入玉ã«å¿…è¦ãªé§’ã®æ•°ã‚’返㙠// cur_points ã«points_on_row ã‚’è¶³ã™å‰ã«å‘¼ã¶ int calcNumPiecesNeeded(const int cur_points, const int points_on_row, const int num_pieces_on_row, const int threshold) { if (points_on_row == num_pieces_on_row) return threshold - cur_points; const int points_needed = threshold - cur_points; const int num_major = (points_on_row - num_pieces_on_row) / 4; if (points_needed <= 5 * num_major) return (points_needed + 4) / 5; else return num_major + (points_needed - 5 * num_major); } } // Turn ãŒå…¥çމã§ãる確率を返㙠template double osl::enter_king::SimplePredictor::getProbability(const NumEffectState& state) { // 確率計算用ã®ãƒ‘ラメータ // 最後ã«exp() ã§ç¢ºçŽ‡ã«æˆ»ã™ static const double normal_penalty = log(0.9); static const double strong_penalty = log(0.8); static const double weak_penalty = log(0.95); static const double lower_bound = log(0.05); double prob = 0.0; const osl::Square myKingSquare = state.kingSquare(); const int my_king_y = myKingSquare.y(); const int enemyCampMin = (Turn==osl::BLACK) ? 1 : 7; const int enemyCampMax = enemyCampMin + 2; const int winning_threshold = (Turn==osl::BLACK) ? winning_threshold_black : winning_threshold_white; // 玉ã®y軸を見ã¦å…¥çމã‹ã‚‰ã®è·é›¢ã§ãƒšãƒŠãƒ«ãƒ†ã‚£ã‚’ã‹ã‘ã‚‹ if (my_king_y < enemyCampMin || my_king_y > enemyCampMax) { prob += ((Turn==osl::BLACK)? (my_king_y - enemyCampMax) : (enemyCampMin - my_king_y)) * weak_penalty; } // 敵陣ã«ã‚ã‚‹é§’ã®ç‚¹æ•°ã¨æžšæ•°ã‚’計算 int num_pieces = 0; int cur_piece_points = osl::enter_king::countPiecePointsInRange(state, num_pieces, 1, 9, enemyCampMin, enemyCampMax); // 敵陣ã«é§’ãŒå°‘ãªã„時ã«ãƒšãƒŠãƒ«ãƒ†ã‚£ if (num_pieces == 0) prob += 2 * strong_penalty; else if (num_pieces < 3) prob += normal_penalty; // 自玉ã®å‰æ–¹ã«ã‚る敵ã‹ã‚‰ã®åˆ©ãã®æ•°ã‚’計算 // 相手ã®åˆ©ããŒå¤šã„時ã¯å…¥çމã—ã«ãã„ã®ã§ãƒšãƒŠãƒ«ãƒ†ã‚£ const int opp_effect_kingfront = osl::enter_king::countEffectInFrontOf(state, alt(Turn), myKingSquare, Turn); prob += (opp_effect_kingfront / 4) * strong_penalty; // ボーナス // 王ã®å‰æ–¹ã«æ•µã‹ã‚‰ã®åˆ©ããŒãªã„, 敵陣ã«8枚以上ã®é§’ãŒã‚ã‚‹ if (opp_effect_kingfront == 0 && prob < normal_penalty) prob -= normal_penalty; if (num_pieces > 7 && prob < weak_penalty) prob -= weak_penalty; if (prob < lower_bound) return 0.0; // æŒé§’を点数ã«åŠ ãˆã‚‹ // 入玉ã«å¿…è¦ãªç‚¹æ•°ä»¥ä¸Šãªã‚‰ç¢ºçŽ‡ã‚’è¿”ã™ cur_piece_points += osl::enter_king::countPiecePointsOnStand(state, Turn); if (cur_piece_points >= winning_threshold) return exp(prob); // ä¸è¶³ã—ã¦ã„る点数を補ã†ãŸã‚ã€ä¸­æ®µã‚„自陣ã«ã‚ã‚‹é§’ã‚’æ•µé™£ã¸æŒã£ã¦ã„ã // ãã®ãŸã‚ã®ã‚³ã‚¹ãƒˆ(æžšæ•°)ã§ãƒšãƒŠãƒ«ãƒ†ã‚£ã‚’ã‹ã‘ã‚‹ const int direction = (Turn==osl::BLACK)? 1:-1; const int base_y = (Turn==osl::BLACK)? enemyCampMax : enemyCampMin; double pos_penalty = weak_penalty; for (int yi = 1; yi <= 6; yi++) { if (yi == 5) pos_penalty = normal_penalty; int num_pieces_on_row = 0; // ã‚る行ã®é§’ã®ç‚¹æ•°ã¨æžšæ•°ã‚’計算 const int points_on_row = osl::enter_king::countPiecePointsOnRow(state, num_pieces_on_row, base_y + direction * yi); // å¿…è¦ãªç‚¹æ•°ã«é”ã—ãŸã‚‰ã€å¿…è¦ãªæžšæ•°ã ã‘ペナルティをã‹ã‘ã¦ç¢ºçŽ‡ã‚’è¿”ã™ if (cur_piece_points + points_on_row >= winning_threshold) { prob += calcNumPiecesNeeded(cur_piece_points, points_on_row, num_pieces_on_row, winning_threshold) * pos_penalty; return exp(prob); } // ã¾ã ç‚¹æ•°ãŒä¸è¶³ã—ã¦ã„ã‚‹ã®ã§ã€ç‚¹æ•°ã‚„確率を更新ã—ã¦æ¬¡ã®è¡Œã¸ cur_piece_points += points_on_row; prob += num_pieces_on_row * pos_penalty; if (prob < lower_bound) return 0.0; } // é§’ã®ç‚¹æ•°ãŒè¶³ã‚Šãªã„ã®ã§0.0 を返㙠// 敵陣ã«é§’ãŒã‚れã°è£œãˆã‚‹ã‹ã‚‚ã—れãªã„ return 0.0; } double osl::enter_king::SimplePredictor::getProbability(const NumEffectState& state, const osl::Player Turn) { if (Turn == osl::BLACK) return getProbability(state); else return getProbability(state); } // Turn ãŒå…¥çމã§ãる確率を返㙠// 宣言法ã¸ã®å¯¾å¿œ template double osl::enter_king::SimplePredictor::getProbability27(const NumEffectState& state) { // 確率計算用ã®ãƒ‘ラメータ // 最後ã«exp() ã§ç¢ºçŽ‡ã«æˆ»ã™ static const double normal_penalty = log(0.9); static const double strong_penalty = log(0.8); static const double weak_penalty = log(0.95); static const double lower_bound = log(0.05); double prob = 0.0; const osl::Square myKingSquare = state.kingSquare(); const int my_king_y = myKingSquare.y(); const int enemyCampMin = (Turn==osl::BLACK) ? 1 : 7; const int enemyCampMax = enemyCampMin + 2; const int winning_threshold = (Turn==osl::BLACK) ? winning_threshold_black_27 : winning_threshold_white_27; // 玉ã®y軸を見ã¦å…¥çމã‹ã‚‰ã®è·é›¢ã§ãƒšãƒŠãƒ«ãƒ†ã‚£ã‚’ã‹ã‘ã‚‹ if (my_king_y < enemyCampMin || my_king_y > enemyCampMax) { const int dist = (Turn==osl::BLACK)? (my_king_y - enemyCampMax) : (enemyCampMin - my_king_y); prob += dist * normal_penalty; } // 敵陣ã«ã‚ã‚‹é§’ã®ç‚¹æ•°ã¨æžšæ•°ã‚’計算 (王ã¯é™¤å¤–) int num_pieces = 0; int cur_piece_points = osl::enter_king::countPiecePointsInRange(state, num_pieces, 1, 9, enemyCampMin, enemyCampMax); // 敵陣ã«é§’ãŒå°‘ãªã„時ã«ãƒšãƒŠãƒ«ãƒ†ã‚£ // 宣言法ã§ã¯æ•µé™£ã«çދ以外ã«10æžšã®é§’ãŒå¿…è¦ if (num_pieces == 0) prob += 2 * strong_penalty; else if (num_pieces < 10) prob += ((12 - num_pieces) / 3) * normal_penalty; // 自玉ã®å‰æ–¹ã«ã‚る敵ã‹ã‚‰ã®åˆ©ãã®æ•°ã‚’計算 // 相手ã®åˆ©ããŒå¤šã„時ã¯å…¥çމã—ã«ãã„ã®ã§ãƒšãƒŠãƒ«ãƒ†ã‚£ const int opp_effect_kingfront = osl::enter_king::countEffectInFrontOf(state, alt(Turn), myKingSquare, Turn); prob += (opp_effect_kingfront / 4) * strong_penalty; // ボーナス // 王ã®å‰æ–¹ã«æ•µã‹ã‚‰ã®åˆ©ããŒãªã„ if (opp_effect_kingfront == 0 && prob < normal_penalty) prob -= normal_penalty; if (prob < lower_bound) return 0.0; // æŒé§’を点数ã«åŠ ãˆã‚‹ // 入玉ã«å¿…è¦ãªç‚¹æ•°ä»¥ä¸Šãªã‚‰ç¢ºçŽ‡ã‚’è¿”ã™ cur_piece_points += osl::enter_king::countPiecePointsOnStand(state, Turn); if (cur_piece_points >= winning_threshold) return exp(prob); // ä¸è¶³ã—ã¦ã„る点数を補ã†ãŸã‚ã€ä¸­æ®µã‚„自陣ã«ã‚ã‚‹é§’ã‚’æ•µé™£ã¸æŒã£ã¦ã„ã // ãã®ãŸã‚ã®ã‚³ã‚¹ãƒˆ(æžšæ•°)ã§ãƒšãƒŠãƒ«ãƒ†ã‚£ã‚’ã‹ã‘ã‚‹ const int direction = (Turn==osl::BLACK)? 1:-1; const int base_y = (Turn==osl::BLACK)? enemyCampMax : enemyCampMin; double pos_penalty = weak_penalty; for (int yi = 1; yi <= 6; yi++) { if (yi == 5) pos_penalty = normal_penalty; int num_pieces_on_row = 0; // ã‚る行ã®é§’ã®ç‚¹æ•°ã¨æžšæ•°ã‚’計算 const int points_on_row = osl::enter_king::countPiecePointsOnRow(state, num_pieces_on_row, base_y + direction * yi); // å¿…è¦ãªç‚¹æ•°ã«é”ã—ãŸã‚‰ã€å¿…è¦ãªæžšæ•°ã ã‘ペナルティをã‹ã‘ã¦ç¢ºçŽ‡ã‚’è¿”ã™ if (cur_piece_points + points_on_row >= winning_threshold) { prob += calcNumPiecesNeeded(cur_piece_points, points_on_row, num_pieces_on_row, winning_threshold) * pos_penalty; return exp(prob); } // ã¾ã ç‚¹æ•°ãŒä¸è¶³ã—ã¦ã„ã‚‹ã®ã§ã€ç‚¹æ•°ã‚„確率を更新ã—ã¦æ¬¡ã®è¡Œã¸ cur_piece_points += points_on_row; prob += num_pieces_on_row * pos_penalty; if (prob < lower_bound) return 0.0; } // 自分ã®é§’ã ã‘ã§ã¯ç‚¹æ•°ãŒè¶³ã‚Šãªã„ // 5点以内ãªã‚‰å–れるã‹ã‚‚ã—れãªã„ if (winning_threshold - cur_piece_points <= 5) prob += (winning_threshold - cur_piece_points) * strong_penalty; else return 0.0; if (prob < lower_bound) return 0.0; return exp(prob); } double osl::enter_king::SimplePredictor::getProbability27(const NumEffectState& state, const osl::Player Turn) { if (Turn == osl::BLACK) return getProbability27(state); else return getProbability27(state); } // 入玉ã®äºˆæ¸¬ã‚’行ã†é–¢æ•°. 確率ãŒthreshold ã‚’è¶…ãˆã¦ã„ãŸã‚‰true ãã†ã§ãªã„ãªã‚‰false template bool osl::enter_king::SimplePredictor::predict(const NumEffectState& state, double threshold) { if (getProbability(state) > threshold) return true; return false; } bool osl::enter_king::SimplePredictor::predict(const NumEffectState& state, osl::Player Turn, double threshold) { if (getProbability(state, Turn) > threshold) return true; return false; } // 入玉ã®äºˆæ¸¬ã‚’行ã†é–¢æ•°. 確率ãŒthreshold ã‚’è¶…ãˆã¦ã„ãŸã‚‰true ãã†ã§ãªã„ãªã‚‰false template bool osl::enter_king::SimplePredictor::predict27(const NumEffectState& state, double threshold) { if (getProbability27(state) > threshold) return true; return false; } bool osl::enter_king::SimplePredictor::predict27(const NumEffectState& state, osl::Player Turn, double threshold) { if (getProbability27(state, Turn) > threshold) return true; return false; } namespace osl { namespace enter_king { template double SimplePredictor::getProbability (const NumEffectState& state); template double SimplePredictor::getProbability (const NumEffectState& state); template double SimplePredictor::getProbability27 (const NumEffectState& state); template double SimplePredictor::getProbability27 (const NumEffectState& state); template bool SimplePredictor::predict (const NumEffectState& state, double threshold); template bool SimplePredictor::predict (const NumEffectState& state, double threshold); template bool SimplePredictor::predict27 (const NumEffectState& state, double threshold); template bool SimplePredictor::predict27 (const NumEffectState& state, double threshold); } } libosl-0.8.0.orig/full/osl/enter_king/simplePredictor.h0000644000000000000000000000264212316770314021652 0ustar rootroot/* simplePredictor.h */ #ifndef _SIMPLE_PREDICTOR_H #define _SIMPLE_PREDICTOR_H #include "osl/numEffectState.h" namespace osl { namespace enter_king { // 入玉を予測/判定 // 宣言法ã§ã®å…¥çŽ‰äºˆæ¸¬/判定ã¯åå‰ã®æœ«å°¾ã«27 ã‚’ã¤ã‘ã¦ã„ã‚‹ static const int winning_threshold_black = 24; static const int winning_threshold_white = 24; static const int winning_threshold_black_27 = 28; static const int winning_threshold_white_27 = 27; class SimplePredictor { public: template double getProbability(const osl::NumEffectState& state); double getProbability(const osl::NumEffectState& state, const Player Turn); template double getProbability27(const osl::NumEffectState& state); double getProbability27(const osl::NumEffectState& state, const Player Turn); template bool predict(const osl::NumEffectState& state, double threshold=0.5); bool predict(const osl::NumEffectState& state, const Player Turn, double threshold=0.5); template bool predict27(const osl::NumEffectState& state, double threshold=0.5); bool predict27(const osl::NumEffectState& state, const Player Turn, double threshold=0.5); }; } //namespace enter_king } //namespace osl #endif /* _SIMPLE_PREDICTOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/enter_king/enterKingUtil.h0000644000000000000000000000212212316770314021262 0ustar rootroot/* enterKingUtil.h */ #ifndef _ENTER_KING_UTIL_H #define _ENTER_KING_UTIL_H #include "osl/numEffectState.h" namespace osl { namespace enter_king { int countEffectInRange(const NumEffectState& staet, Player Turn, int x0, int x1, int y0, int y1); int countEffectInFrontOf(const NumEffectState& state, Player attack, Square target, Player defense); int countPiecePointsOnStand(const NumEffectState& state, Player Turn); template int countPiecePointsInRange(const NumEffectState& state, int& num_pieces, int x0, int x1, int y0, int y1); int countPiecePointsInRange(const NumEffectState& state, Player Turn, int& num_pieces, int x0, int x1, int y0, int y1); template int countPiecePointsOnRow(const NumEffectState& state, int& num_pieces, int row); int countPiecePointsOnRow(const NumEffectState& state, Player Turn, int& num_pieces, int row); } //namespace enter_king } //namespace osl #endif /* _ENTER_KING_UTIL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/container/0000755000000000000000000000000012316770314016165 5ustar rootrootlibosl-0.8.0.orig/full/osl/container/pieceValues.cc0000644000000000000000000000255612316770314020751 0ustar rootroot// pieceValues.cc #include "osl/container/pieceValues.h" #include "osl/numEffectState.h" #include #include osl::container:: PieceValues::PieceValues() { } osl::container:: PieceValues::~PieceValues() { } int osl::container:: PieceValues::sum() const { int result = 0; for (int v: *this) { result += v; } return result; } #ifndef MINIMAL void osl::container:: PieceValues::showValues(std::ostream& os, const NumEffectState& state) const { for (int y=1;y<=9;y++) { os << y; for (int x=9;x>0;x--) { const Piece piece = state.pieceOnBoard(Square(x,y)); os << std::setw(7); if (piece.isEmpty()) os << 0; else os << (*this)[piece.number()]; } os << std::endl; } os << "black stand: "; for (int i=0; i namespace osl { class NumEffectState; namespace container { /** * 駒番å·->intã®é…列. å±€é¢ã«å¯¾ã™ã‚‹é§’ã®ä¾¡å€¤ãªã© */ class PieceValues : public CArray { public: PieceValues(); ~PieceValues(); int sum() const; void showValues(std::ostream&, const NumEffectState&) const; }; } // namespace container using container::PieceValues; } // namespace osl #endif // _PIECE_VALUES_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/tripleInt.h0000644000000000000000000001205312316770314016327 0ustar rootroot/* tripleInt.h */ #ifndef EVAL_CONTAINER_TRIPLE_INT_H #define EVAL_CONTAINER_TRIPLE_INT_H #include "osl/carray.h" #include "osl/align16New.h" #include "osl/config.h" #include #if (defined __INTEL_COMPILER || defined __clang__) # include # define __builtin_ia32_pxor128 _mm_xor_si128 # define __builtin_ia32_psubd128 _mm_sub_epi32 # define __builtin_ia32_paddd128 _mm_add_epi32 #endif #ifndef OSL_NO_SSE #if (defined __x86_64__) || (defined __i386__) # ifndef OSL_USE_SSE # define OSL_USE_SSE 1 # endif #else # warning "TripleInt without SSE" #endif #endif namespace osl { namespace container { #ifndef OSL_USE_SSE typedef CArray v4si; typedef CArray v2di; #elif defined __INTEL_COMPILER typedef __v4si v4si; typedef __v2di v2di; #else typedef int v4si __attribute__ ((vector_size (16))); typedef long long v2di __attribute__ ((vector_size (16))); #endif struct TripleInt : public misc::Align16New { union XMM{ CArray iv; v4si v4; v2di v2; } v #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; TripleInt(){ #if OSL_USE_SSE assert(reinterpret_cast(this) % 16 == 0); #endif clear(); } TripleInt(TripleInt const& si){ #if OSL_USE_SSE assert(reinterpret_cast(this) % 16 == 0); v.v4=si.v.v4; #else for(int i=0;i<3;i++) v.iv[i]=si.v.iv[i]; #endif } TripleInt(int a, int b, int c){ #if OSL_USE_SSE assert(reinterpret_cast(this) % 16 == 0); v.v4 = (v4si){a, b, c, 0}; #elif __GNUC__ v.iv = (CArray){{a, b, c, 0}}; #else v.iv[0] = a, v.iv[1] = b, v.iv[2] = c; #endif } void clear() { #if OSL_USE_SSE v.v4=(v4si){ 0, 0, 0, 0 }; #else for(int i=0;i<3;i++) v.iv[i]=0; #endif } int& operator[](int i) { return v.iv[i]; } const int& operator[](int i) const { return v.iv[i]; } TripleInt operator-() const{ TripleInt ret; #if OSL_USE_SSE ret.v.v4=__builtin_ia32_psubd128(ret.v.v4,v.v4); #else for(int i=0;i<3;i++) ret.v.iv[i]= -v.iv[i]; #endif return ret; } TripleInt& operator+=(TripleInt const& si){ #if OSL_USE_SSE v.v4=__builtin_ia32_paddd128(v.v4,si.v.v4); #else for(int i=0;i<3;i++) v.iv[i]+=si.v.iv[i]; #endif return *this; } TripleInt& operator-=(TripleInt const& si){ #if OSL_USE_SSE v.v4=__builtin_ia32_psubd128(v.v4,si.v.v4); #else for(int i=0;i<3;i++) v.iv[i]-=si.v.iv[i]; #endif return *this; } TripleInt& operator*=(int scale){ #if OSL_USE_SSE41 XMM val; unsigned long long scalescale=(unsigned long long )((unsigned int)scale); scalescale|=scalescale<<32ull; val.v2=__builtin_ia32_vec_set_v2di(val.v2,(long long)scalescale,0); val.v2=__builtin_ia32_vec_set_v2di(val.v2,(long long)scalescale,1); v.v4=__builtin_ia32_pmulld128(v.v4,val.v4); #else for(int i=0;i<3;i++) v.iv[i]*=scale; #endif return *this; } TripleInt& operator/=(int div) { for(int i=0;i<3;i++) v.iv[i] /= div; return *this; } TripleInt& operator>>=(int shift) { #if OSL_USE_SSE v.v4= __builtin_ia32_psradi128 (v.v4, shift); #else for(int i=0;i<3;i++) v.iv[i] >>= shift; #endif return *this; } static size_t size() { return 3; } }; inline TripleInt operator+(TripleInt const& si0,TripleInt const& si1) { TripleInt ret(si0); ret+=si1; return ret; } inline TripleInt operator-(TripleInt const& si0,TripleInt const& si1) { TripleInt ret(si0); ret-=si1; return ret; } inline TripleInt operator*(TripleInt const& si0,int scale) { TripleInt ret(si0); ret*=scale; return ret; } inline bool operator==(TripleInt const& l,TripleInt const& r) { for(int i=0;i<3;i++) if (l[i] != r[i]) return false; return true; } class TripleIntPair{ CArray v; public: TripleIntPair() {} const TripleInt& operator[](int i) const{ return v[i]; } const TripleInt& operator[](Player pl) const{ return v[pl]; } TripleInt& operator[](int i){ return v[i]; } TripleInt& operator[](Player pl){ return v[pl]; } TripleIntPair& operator+=(TripleIntPair const& a){ v[0]+=a.v[0]; v[1]+=a.v[1]; return *this; } TripleIntPair& operator-=(TripleIntPair const& a){ v[0]-=a.v[0]; v[1]-=a.v[1]; return *this; } }; inline TripleIntPair operator+(TripleIntPair const& si0,TripleIntPair const& si1) { TripleIntPair ret(si0); ret+=si1; return ret; } inline TripleIntPair operator-(TripleIntPair const& si0,TripleIntPair const& si1) { TripleIntPair ret(si0); ret-=si1; return ret; } inline bool operator==(TripleIntPair const& l,TripleIntPair const& r) { return l[0] == r[0] && l[1] == r[1]; } std::ostream& operator<<(std::ostream& os,TripleInt const& ti); } using container::TripleInt; using container::TripleIntPair; } #endif // EVAL_CONTAINER_TRIPLE_INT_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/c/0000755000000000000000000000000012316770314014425 5ustar rootrootlibosl-0.8.0.orig/full/osl/c/facade.h0000644000000000000000000000246112316770314016004 0ustar rootroot/* facade.h */ #ifndef OSL_FACADE_H #define OSL_FACADE_H extern "C" { extern void osl_init(); // size of move must be at least 8 extern int checkmate_attack(const char *state, int& limit, char *move); extern int checkmate_escape(const char *state, int limit); extern int search(const char *state, int seconds, int verbose, char *move); /** * Converts moves in a USI format string to a Kanji representation. * * @param command a command string for gpsusi. ex. "ki2moves 7g7f 3c3d" * @param out a buffer to return a result string. * @param out_size size of the out buffer. * @return the actual size with which the buffer is filled. It does not * include a null terminator. */ extern int usiMovesToKanji(const char *command, char *out, int out_size); /** * Generates a Kanji position spcified by moves in a USI format string. * * @param moves_str USI moves string. * @param out a buffer to return a result string. * @param out_size size of the out buffer. * @return the actual size with which the buffer is filled. It does not * include a null terminator. */ extern int usiMovesToPositionString(const char *moves_str, char *out, int out_size); } #endif /* OSL_FACADE_H */ // ;;; Local Variables: // ;;; mode:c // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/c/facade.cc0000644000000000000000000000741012316770314016141 0ustar rootroot/* facade.c */ #include "osl/c/facade.h" #include "osl/checkmate/dualDfpn.h" #include "osl/game_playing/alphaBetaPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/usiState.h" #include "osl/game_playing/usiResponse.h" #include "osl/search/simpleHashTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/csa.h" #include "osl/usi.h" #include "osl/record/kanjiPrint.h" #include #include #include #include extern "C" void osl_init() { osl::OslConfig::setUp(); } extern "C" int checkmate_attack(const char *state_str, int& limit, char *move) { osl::DualDfpn checkmate; osl::Move checkmate_move; osl::NumEffectState state(osl::CsaString(state_str).initialState()); osl::HashKey key(state); osl::PathEncoding pe(state.turn()); const bool win = checkmate.isWinningState(limit, state, key, pe, checkmate_move); limit = checkmate.totalNodeCount(); if (win) { const std::string checkmate_move_str = osl::csa::show(checkmate_move); sprintf(move, "%s", checkmate_move_str.c_str()); } return win; } extern "C" int checkmate_escape(const char *state_str, int limit) { osl::DualDfpn checkmate; osl::Move checkmate_move; osl::NumEffectState state(osl::CsaString(state_str).initialState()); osl::HashKey key(state); osl::PathEncoding pe(state.turn()); const bool escape = checkmate.isLosingState(limit, state, key, pe); return escape; } extern "C" int search(const char *state_str, int seconds, int verbose, char *move) { osl::game_playing::AlphaBeta2OpenMidEndingEvalPlayer player; player.setNextIterationCoefficient(1.7); player.setVerbose(verbose); if (osl::OslConfig::isMemoryLimitEffective()) { player.setTableLimit(std::numeric_limits::max(), 200); player.setNodeLimit(std::numeric_limits::max()); } else { player.setTableLimit(3000000, 200); } player.setDepthLimit(2000, 400, 200); osl::game_playing::GameState state(osl::CsaString(state_str).initialState()); osl::Move best_move = player.searchWithSecondsForThisMove(state, osl::search::TimeAssigned(osl::milliseconds(seconds*1000))).move; const std::string best_move_str = osl::csa::show(best_move); sprintf(move, "%s", best_move_str.c_str()); const osl::SimpleHashTable *table = player.table(); const osl::HashKey key(state.state()); const osl::SimpleHashRecord *record = table->find(key); int value = record ? record->lowerBound() : 0; return value; } extern "C" int usiMovesToKanji(const char *command, char *out, int out_size) { assert(out_size>0); osl::game_playing::UsiState usi_state; osl::game_playing::UsiResponse res(usi_state, true, false); std::string ret; res.hasImmediateResponse(std::string(command), ret); const int size = std::min(out_size, static_cast(ret.size())); memcpy(out, ret.c_str(), size); return size; } extern "C" int usiMovesToPositionString(const char *moves_str, char *out, int out_size) { assert(out_size>0); osl::NumEffectState state; std::vector moves; std::istringstream is(moves_str); std::string s; while (is >> s) { const osl::Move move = osl::usi::strToMove(s, state); moves.push_back(move); state.makeMove(move); } assert(!moves.empty()); osl::Move last_move; if (! moves.empty()) { last_move = moves.back(); } std::ostringstream os; osl::record::KanjiPrint printer(os, std::make_shared()); printer.print(state, &last_move); const std::string ret = os.str(); const int size = std::min(out_size, static_cast(ret.size())); memcpy(out, ret.c_str(), size); return size; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/hash/0000755000000000000000000000000013016502474015124 5ustar rootrootlibosl-0.8.0.orig/full/osl/hash/hashRandom.cc0000644000000000000000000000067513016502474017527 0ustar rootroot/* hashRandom.cc */ #include "osl/hash/hashRandom.h" #include "osl/misc/milliSeconds.h" #include osl::CArray osl::hash::HashRandom::table; void osl::hash::HashRandom::setUp(double sigma) { static std::random_device rd; static std::mt19937 mt_random(rd()); std::normal_distribution n(0, sigma); for (size_t i=0; i(n(mt_random))/2*2; } libosl-0.8.0.orig/full/osl/hash/hashRandom.h0000644000000000000000000000123112316770314017360 0ustar rootroot/* hashRandom.h */ #ifndef OSL_HASHRANDOM_H #define OSL_HASHRANDOM_H #include "osl/hashKey.h" #include "osl/container.h" namespace osl { namespace hash { class HashRandom { public: static const size_t Length = 0x1000; private: static CArray table; public: static void setUp(double sigma); static int value(size_t key) { return table[key % Length]; } static int value(const HashKey& key) { return value(key.signature()); } }; } using hash::HashRandom; } #endif /* OSL_HASHRANDOM_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/hash/hashCollision.h0000644000000000000000000000103612316770314020076 0ustar rootroot/* hashCollision.h */ #ifndef _HASHCOLLISION_H #define _HASHCOLLISION_H #include namespace osl { namespace hash { /** * ãƒãƒƒã‚·ãƒ¥ã®è¡çªã‚’検出ã—ãŸæ™‚ã« throw ã™ã‚‹ãŸã‚ã«ä½¿ã†. */ struct HashCollision : std::runtime_error { HashCollision() : std::runtime_error("hash collision") { } }; } // namespace hash using hash::HashCollision; } // namespace osl #endif /* _HASHCOLLISION_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/0000755000000000000000000000000012316770314015136 5ustar rootrootlibosl-0.8.0.orig/full/osl/misc/math.h0000644000000000000000000000450012316770314016237 0ustar rootroot#ifndef OSL_MISC_MATH_H #define OSL_MISC_MATH_H #include #include #include #include namespace osl { namespace misc { /** * Reference: C++ Cookbook, Stephens, Diggins, Turkanis and Cogswell, O'Reilly, */ template T nthPower(T x) { if (N==0) return 1; const T temp = nthPower(x); if (N%2 == 0) return temp * temp; else return temp * temp * x; } template struct SumDiffNthPower { T mean; SumDiffNthPower(T mean) : mean(mean) {} T operator()(T sum, T current) { return sum + nthPower(current - mean); } }; template T nthMoment(Iter_T first, Iter_T last, T mean) { const size_t cnt = distance(first, last); return accumulate(first, last, T(), SumDiffNthPower(mean))/cnt; } template T computeVariance(Iter_T first, Iter_T last, T mean) { return nthMoment(first, last, mean); } template T computeStdDev(Iter_T first, Iter_T last, T mean) { return sqrt(computeVariance(first, last, mean)); } template T computeSkew(Iter_T first, Iter_T last, T mean) { const T m3 = nthMoment(first, last, mean); const T m2 = nthMoment(first, last, mean); return m3 / (m2 * sqrt(m2)); } template T computeKurtosisExcess(Iter_T first, Iter_T last, T mean) { const T m4 = nthMoment(first, last, mean); const T m2 = nthMoment(first, last, mean); return m4 / (m2 * m2) - 3; } template void computeStats(Iter_T first, Iter_T last, T& sum, T& mean, T&var, T&std_dev, T& skew, T& kurt) { const size_t cnt = distance(first, last); sum = accumulate(first, last, T()); mean = sum / cnt; var = computeVariance(first, last, mean); std_dev = sqrt(var); skew = computeSkew(first, last, mean); kurt = computeKurtosisExcess(first, last, mean); } } } #endif /* _MISC_MATH_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/perfmon.h0000644000000000000000000001014512316770314016756 0ustar rootroot#ifndef MISC_PERFMON_H #define MISC_PERFMON_H #if defined(__i386__) || defined(__x86_64__) || defined(_MSC_VER) # define HAVE_TSC 1 #endif #ifndef _MSC_VER # include # ifndef HAVE_TSC # include # endif #endif #include #include #include namespace osl { namespace misc { class PerfMon { #ifdef HAVE_TSC unsigned long long start_time; #else rusage start_time; #endif public: void restart() { #ifdef HAVE_TSC # ifndef _MSC_VER unsigned int ax,dx; asm volatile("rdtsc\nmovl %%eax,%0\nmovl %%edx,%1":"=g"(ax),"=g"(dx): :"eax","edx"); start_time = (static_cast(dx)<<32) + static_cast(ax); # else start_time = 0; # endif #else #ifdef NDEBUG getrusage(RUSAGE_SELF, &start_time); #else int ret=getrusage(RUSAGE_SELF, &start_time); assert(ret==0); #endif #endif } PerfMon() { restart(); } unsigned long long stop(){ #ifdef HAVE_TSC # ifndef _MSC_VER unsigned int ax,dx; asm volatile("rdtsc\nmovl %%eax,%0\nmovl %%edx,%1":"=g"(ax),"=g"(dx): :"eax","edx"); const unsigned long long end_time = ((static_cast(dx)<<32) + static_cast(ax)); return (end_time - PerfMon::start_time); # else return 0; # endif #else rusage end_time; #ifdef NDEBUG getrusage(RUSAGE_SELF,&end_time); #else int ret=getrusage(RUSAGE_SELF,&end_time); assert(ret==0); #endif return (end_time.ru_utime.tv_sec - start_time.ru_utime.tv_sec)*1000000 +(end_time.ru_utime.tv_usec - start_time.ru_utime.tv_usec); #endif } void stop(const char *message,int loop){ const unsigned long long cycles=stop(); PerfMon::message(cycles, message, loop); } static void message(unsigned long long cycles, const char *message,long long int loop); }; class TSC { unsigned long long start_time; unsigned long long sum_time; long long int counter; std::string message; public: TSC(const char *m) :start_time(0ll),sum_time(0ll),counter(0ll),message(m) {} void start() { #ifdef HAVE_TSC # ifndef _MSC_VER unsigned int ax,dx; asm volatile("rdtsc\nmovl %%eax,%0\nmovl %%edx,%1":"=g"(ax),"=g"(dx): :"eax","edx"); start_time = (static_cast(dx)<<32) + static_cast(ax); # else start_time = 0; # endif #endif counter++; } void stop(){ #ifdef HAVE_TSC # ifndef _MSC_VER unsigned int ax,dx; asm volatile("rdtsc\nmovl %%eax,%0\nmovl %%edx,%1":"=g"(ax),"=g"(dx): :"eax","edx"); const unsigned long long end_time = ((static_cast(dx)<<32) + static_cast(ax)); sum_time+=end_time - start_time; # else sum_time = 0; # endif #endif } ~TSC() { PerfMon::message(sum_time,message.c_str(),counter); } }; class Counter { unsigned long long int counter; std::string message; public: Counter(const char *m) :counter(0ll),message(m) {} Counter(std::string const& m) :counter(0ll),message(m) {} void count() { counter++; } ~Counter() { PerfMon::message(0ll,message.c_str(),counter); } }; class CounterPair { unsigned long long int counter1; unsigned long long int counter2; std::string message; public: CounterPair(std::string const& m) :counter1(0ll),counter2(0ll),message(m) {} CounterPair(const char *file, const char *function, int line); void count1() { counter1++; } void count2() { counter2++; } ~CounterPair(); }; #ifndef _MSC_VER class MeasureTimeLock { timeval start; std::ostream& os; char const* message; public: MeasureTimeLock (std::ostream& os, char const* message) : os (os), message (message) { #ifndef NDEBUG int ret = #endif gettimeofday(&start, NULL); assert(ret == 0); } ~MeasureTimeLock(); }; #endif } // namespace misc } // namespace osl #endif /* MISC_PERFMON_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/perfmon.cc0000644000000000000000000000300412316770314017110 0ustar rootroot/* perfmon.cc */ #include "osl/misc/perfmon.h" #include #include #include #ifndef _MSC_VER void osl::misc::PerfMon::message(unsigned long long cycles, const char *message,long long int loop) { #ifdef HAVE_TSC const char *unit = "clocks"; #else const char *unit = "microSecs"; #endif std::cerr << std::dec << message << " : take " << cycles << " " << unit << ", loop= " << loop; if (loop) std::cerr << " clocks/loop= " << (cycles/loop) << "." << std::setfill('0') << std::setw(2) << (cycles*100/loop)-(cycles/loop)*100; std::cerr << std::endl; } osl::misc::CounterPair:: CounterPair(const char *file, const char *function, int line) : counter1(0), counter2(0), message(std::string(file)+":"+(function)+":"+boost::lexical_cast(line)) { } osl::misc::CounterPair::~CounterPair() { std::cerr << message << " " << counter1 << "/" << counter2; if(counter2!=0) std::cerr << " = " << (double)counter1/(double)counter2; std::cerr << std::endl; } osl::misc::MeasureTimeLock::~MeasureTimeLock () { timeval end; gettimeofday(&end, NULL); end.tv_usec -= start.tv_usec; if (end.tv_usec < 0) { end.tv_usec += 1000000; --end.tv_sec; } end.tv_sec -= start.tv_sec; os << message << "\t" << end.tv_sec << ":" << end.tv_usec << std::endl; } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/log/0000755000000000000000000000000012316770314015717 5ustar rootrootlibosl-0.8.0.orig/full/osl/misc/log/textPerformanceLog.h0000644000000000000000000000124512316770314021702 0ustar rootroot/* textPerformanceLog.h */ #ifndef OSL_TEXTPERFORMANCELOG_H #define OSL_TEXTPERFORMANCELOG_H #include "osl/misc/log/performanceLog.h" /** * mtdfstat, alphabetastat 用ã®è¨˜éŒ²ç”¨ (text) * */ namespace osl { namespace misc { namespace log { struct TextPerformanceLog : public PerformanceLog { TextPerformanceLog(); ~TextPerformanceLog(); void record(const char *name, Move correctMove, Move result, unsigned int nodes, unsigned int qnodes, double seconds, int depth); }; } } } // namespace osl #endif /* OSL_TEXTPERFORMANCELOG_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/misc/log/htmlPerformanceLog.cc0000644000000000000000000000256412316770314022025 0ustar rootroot/* htmlPerformanceLog.cc */ #include "osl/misc/log/htmlPerformanceLog.h" #include "osl/csa.h" osl::misc::log::HtmlPerformanceLog:: HtmlPerformanceLog(const char *filename, const char *title) : os(filename) { os << "" << title << "\n\n"; os << "\n"; os << "" << "\n"; } osl::misc::log::HtmlPerformanceLog::~HtmlPerformanceLog() { os << "
search resultcorrect move#nodessecondsdepth
\n"; os << "\n"; } void osl::misc::log::HtmlPerformanceLog:: record(const char *name, Move correctMove, Move result, unsigned int nodes, unsigned int qnodes, double seconds, int depth) { if (correctMove == result) os << ""; else os << ""; os << "" << name << ""; if (correctMove == result) os << "OK"; else { os << csa::show(result); } os << ""; os << csa::show(correctMove); os << "\n\t" << nodes + qnodes << "\n" << "\t" << seconds << "\n" << "\t" << depth << "\n" << std::flush; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/log/performanceLog.h0000644000000000000000000000116112316770314021032 0ustar rootroot/* performanceLog.h */ #ifndef OSL_PERFORMANCELOG_H #define OSL_PERFORMANCELOG_H #include "osl/basic_type.h" /** * mtdfstat, alphabetastat 用ã®è¨˜éŒ²ã®è¦ªã‚¯ãƒ©ã‚¹ * */ namespace osl { namespace misc { namespace log { struct PerformanceLog { virtual ~PerformanceLog() {} virtual void record(const char *name, Move correctMove, Move result, unsigned int nodes, unsigned int qnodes, double seconds, int depth) = 0; }; } } } // namespace osl #endif /* OSL_PERFORMANCELOG_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/misc/log/htmlPerformanceLog.h0000644000000000000000000000133112316770314021656 0ustar rootroot/* htmlPerformanceLog.h */ #ifndef OSL_HTMLPERFORMANCELOG_H #define OSL_HTMLPERFORMANCELOG_H #include "osl/misc/log/performanceLog.h" #include /** * mtdfstat, alphabetastat 用ã®è¨˜éŒ² */ namespace osl { namespace misc { namespace log { struct HtmlPerformanceLog : public PerformanceLog { std::ofstream os; HtmlPerformanceLog(const char *filename, const char *title); ~HtmlPerformanceLog(); void record(const char *name, Move correctMove, Move result, unsigned int nodes, unsigned int qnodes, double seconds, int depth); }; } } } #endif /* OSL_HTMLPERFORMANCELOG_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/misc/log/textPerformanceLog.cc0000644000000000000000000000165112316770314022041 0ustar rootroot/* textPerformanceLog.cc */ #include "osl/misc/log/textPerformanceLog.h" #include "osl/csa.h" #include osl::misc::log::TextPerformanceLog:: TextPerformanceLog() { } osl::misc::log::TextPerformanceLog::~TextPerformanceLog() { } void osl::misc::log::TextPerformanceLog:: record(const char *name, Move correctMove, Move result, unsigned int nodes, unsigned int qnodes, double seconds, int depth) { std::cout << name << "\t"; if (correctMove == result) std::cout << "OK"; else { std::cout << csa::show(result); } std::cout << "\t"; std::cout << csa::show(correctMove); std::cout << "\t" << nodes << "\t" << qnodes << "\t" << nodes + qnodes << "\t" << seconds << "\t" << depth << std::endl << std::flush; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/characterEncodingConvertWin32.h0000644000000000000000000000064612316770314023104 0ustar rootroot/* characterEncodingConvertWin32.h */ #ifndef OSL_CHARACTER_ENCODING_CONVERT_WIN32_H #define OSL_CHARACTER_ENCODING_CONVERT_WIN32_H #ifdef _WIN32 #include namespace osl { namespace misc { std::string eucToLang(const std::string& src); } using misc::eucToLang; } #endif #endif /* OSL_CHARACTER_ENCODING_CONVERT_WIN32_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/misc/characterEncodingConvertWin32.cc0000644000000000000000000000241712316770314023240 0ustar rootroot#include "osl/misc/characterEncodingConvertWin32.h" #ifdef _WIN32 #include #include #define CP_EUCJP 20932 //#define CP_EUCJP 51932 not supported by MultiByteToWideChar #define CP_SJIS 932 std::string osl::misc:: eucToLang(const std::string& src) { const int wlen = MultiByteToWideChar(CP_EUCJP, 0, src.c_str(), src.size(), NULL, 0); assert(wlen>0); wchar_t wbuf[wlen]; const int wret = MultiByteToWideChar(CP_EUCJP, 0, src.c_str(), src.size(), wbuf, wlen); if (!wret || wlen != wret) { return ""; } const int len = WideCharToMultiByte(CP_SJIS, 0, wbuf, wret, NULL, 0, NULL, NULL); assert(len>0); char buf[len]; const int ret = WideCharToMultiByte(CP_SJIS, 0, wbuf, wret, buf, len, NULL, NULL); if (!ret || len != ret) { return ""; } return std::string(buf, ret); } #endif // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/Makefile0000644000000000000000000000565412316770314015655 0ustar rootrootOSL_HOME = ../.. -include makefile.local -include $(OSL_HOME)/makefile.local include $(OSL_HOME)/makefile.conf OSL_HOME_FLAGS = -DOSL_HOME=\"$(shell dirname $(shell dirname `pwd`))\" CXXFLAGS += $(OSL_HOME_FLAGS) INCLUDES += -I.. -I../../std -I../../core ANNOTATE_SRC = analysesResult.cc analyzer.cc anno-facade.cc EU_SRC = effectUtil.cc pin.cc virtualPin.cc GP_SRC = \ alphaBetaPlayer.cc cuiClient.cc recordTracer.cc usiResponse.cc \ bookPlayer.cc gameManager.cc searchPlayer.cc usiState.cc \ computerPlayer.cc gameState.cc speculativeAllMoves.cc weightTracer.cc \ csaClient.cc gnuShogiClient.cc speculativeModel.cc winCountTracer.cc \ csaLogger.cc historyToTable.cc speculativeSearchPlayer.cc \ csaTime.cc openingBookTracer.cc timeKeeper.cc SEARCH_SRC = \ alphaBeta2.cc hashRejections.cc searchMonitor.cc \ alphaBeta2Parallel.cc historyTable.cc searchRecorder.cc \ alphaBeta3.cc killerMoveTable.cc searchState2.cc \ alphaBeta4.cc moveGenerator.cc searchTimer.cc \ analyzer/categoryMoveVector.cc moveScore.cc simpleHashRecord.cc \ analyzer/dotWriter.cc moveStackRejections.cc simpleHashTable.cc \ analyzer/logWriter.cc moveWithComment.cc sortCaptureMoves.cc \ analyzer/recordSet_.cc quiescenceGenerator.cc threatmateState.cc \ bigramKillerMove.cc quiescenceLog.cc timeControl.cc \ breakThreatmate.cc quiescenceRecord.cc usiReporter.cc \ dualThreatmateState.cc quiescenceSearch2.cc \ limitToCheckCount.cc usiProxy.cc interimReport.cc EVAL_SRC = \ endgame/attackDefense.cc endgame/attackKing.cc endgame/defenseKing.cc \ endgame/kingPieceTable.cc pieceEval.cc ppair/piecePairEvalBase.cc \ ppair/piecePairPieceTable.cc ppair/piecePairRawTable.cc progressEval.cc \ eval_mobilityTable.cc MG_SRC = \ addEffect8.cc attackToPinned.cc additionalLance.cc addEffect8Table.cc THREATMATE_SRC = kfendPredictor.cc mlPredictor.cc richPredictor.cc treePredictor.cc SRCS = \ $(patsubst %.cc,annotate/%.cc,$(ANNOTATE_SRC)) \ $(patsubst %.cc,effect_util/%.cc,$(EU_SRC)) \ $(patsubst %.cc,eval/%.cc,$(EVAL_SRC)) \ $(patsubst %.cc,move_generator/%.cc,$(MG_SRC)) \ $(patsubst %.cc,game_playing/%.cc,$(GP_SRC)) \ $(patsubst %.cc,record/%.cc,$(RECORD_SRC)) \ $(patsubst %.cc,search/%.cc,$(SEARCH_SRC)) \ $(patsubst %.cc,threatmate/%.cc,$(THREATMATE_SRC)) \ enter_king/simplePredictor.cc enter_king/enterKingUtil.cc \ c/facade.cc container/pieceValues.cc state/historyState.cc \ misc/characterEncodingConvertWin32.cc misc/perfmon.cc \ misc/log/htmlPerformanceLog.cc misc/log/textPerformanceLog.cc \ hash/hashRandom.cc OBJS = $(patsubst %.cc,%.o,$(SRCS)) DEPS = $(patsubst %.cc,.deps/%.cc.d,$(SRCS)) all: libosl_full.a light-clean: -rm -rf .deps -rm -f *.a clean: light-clean -rm $(OBJS) -include $(DEPS) libosl_full.a : $(OBJS) libosl-0.8.0.orig/full/osl/eval/0000755000000000000000000000000012316770314015132 5ustar rootrootlibosl-0.8.0.orig/full/osl/eval/endgame/0000755000000000000000000000000012316770314016532 5ustar rootrootlibosl-0.8.0.orig/full/osl/eval/endgame/attackDefense.cc0000644000000000000000000001263712316770314021613 0ustar rootroot/* attackDefense.cc */ #include "osl/eval/endgame/attackDefense.h" #include "osl/container/pieceValues.h" void osl::eval::endgame:: AttackDefense::setValues(const SimpleState& state, PieceValues& values) { values.fill(0); // 速度ã¯ç„¡è¦– const Piece king_black = state.kingPiece(BLACK); const Piece king_white = state.kingPiece(WHITE); for (int i=0; i(); const Piece white_king = new_state.kingPiece(); const Square to = last_move.to(); const Player player = new_state.turn(); if (last_move.isDrop()) { assert(last_move.ptype() != KING); const int inc = valueOf(black_king, white_king, last_move.ptypeO(), to); const int dec = valueOf(black_king, white_king, last_move.ptypeO(), Square::STAND()); addValue(player, inc - dec); return; } const Square from = last_move.from(); if (last_move.ptype() != KING) { const int inc = valueOf(black_king, white_king, last_move.ptypeO(), to); const int dec = valueOf(black_king, white_king, last_move.oldPtypeO(), from); addValue(player, inc - dec); if (last_move.capturePtype() != PTYPE_EMPTY) { const int inc_capture = valueOf(black_king, white_king, captured(last_move.capturePtypeO()), Square::STAND()); const int dec_capture = valueOf(black_king, white_king, last_move.capturePtypeO(), to); addValue(player, inc_capture); addValue(alt(player), -dec_capture); } return; } // KING reset(); for (int i=0; i(); const Piece white_king = state.kingPiece(); const Square to = move.to(); if (move.isDrop()) { const PtypeO ptypeO = move.ptypeO(); assert(getPtype(ptypeO) != KING); const int inc = valueOf(black_king, white_king, ptypeO, to); const int dec = valueOf(black_king, white_king, ptypeO, Square::STAND()); return value() + inc - dec; } const Square from = move.from(); const Piece old_piece = state.pieceOnBoard(from); const PtypeO new_ptypeo = move.ptypeO(); if (old_piece.ptype() == KING) { AttackDefense new_eval = *this; if (move.capturePtype() == PTYPE_EMPTY) new_eval.updateKingMove(state, from, to); else new_eval.updateKingMove(state, from, to, state.pieceOnBoard(to)); return new_eval.value(); } const int inc = valueOf(black_king, white_king, new_ptypeo, to); const int dec = valueOf(black_king, white_king, old_piece.ptypeO(), from); if (move.capturePtype() == PTYPE_EMPTY) return value() + inc - dec; const int inc_capture = valueOf(black_king, white_king, captured(move.capturePtypeO()), Square::STAND()); const int dec_capture = valueOf(black_king, white_king, move.capturePtypeO(), to); return value() + inc - dec + inc_capture - dec_capture; } void osl::eval::endgame:: AttackDefense::resetWeights(const int *w) { AttackKing::resetWeights(w); DefenseKing::resetWeights(w+KingPieceTable::dimension()); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/endgame/kingPieceTable.h0000644000000000000000000000354212316770314021555 0ustar rootroot/* kingPieceTable.h */ #ifndef ENDGAME_KINGPIECETABLE_H #define ENDGAME_KINGPIECETABLE_H #include "osl/container.h" namespace osl { namespace container { class PieceValues; } namespace eval { namespace endgame { class KingPieceTable; bool operator==(const KingPieceTable& l, KingPieceTable& r); /** * 玉ã¨ä»–ã®é§’ã®é–¢ä¿‚ã‚’ä¿æŒ */ class KingPieceTable { public: enum { EffectiveDimension = 81*2*82*PTYPE_SIZE }; protected: CArray2d data; KingPieceTable() { data.fill(0); } public: static int otherIndex(Square other, Ptype ptype) { return other.index()*PTYPE_SIZE + ptype; } static int kingIndex(Square king, Player defense) { return king.index()*2+playerToIndex(defense); } int& valueOf(Square king, Player defense, Square other, Ptype ptype) { return data[kingIndex(king,defense)][otherIndex(other,ptype)]; } int valueOf(Square king, Player defense, Square other, Ptype ptype) const { return data[kingIndex(king,defense)][otherIndex(other, ptype)]; } static int effectiveIndexOf(Square king, Player defense, Square other, Ptype ptype) { int base = (((king.x()-1)*9+king.y()-1)*2+playerToIndex(defense)); int s = other.isPieceStand() ? 0 : ((other.x()-1)*9+other.y()); return base*82*PTYPE_SIZE + s*PTYPE_SIZE + ptype; } void saveText(const char *filename) const; void loadText(const char *filename); void resetWeights(const int *w); void randomize(); void clear(); static int dimension() { return EffectiveDimension; } friend bool operator==(const KingPieceTable& l, KingPieceTable& r); }; } // namespace endgame } // namespace endgame } // namespace osl #endif /* ENDGAME_KINGPIECETABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/eval/endgame/defenseKing.h0000644000000000000000000000240512316770314021126 0ustar rootroot/** * defenseKing.h */ #ifndef EVAL_ENDGAME_DEFENSEKING_H #define EVAL_ENDGAME_DEFENSEKING_H #include "osl/eval/endgame/kingPieceTable.h" #include "osl/numEffectState.h" namespace osl { namespace eval { namespace endgame { /** * 玉ã®ä½ç½®*守備駒ã®ä½ç½®*ptype */ class DefenseKing { struct Table : public KingPieceTable { void init(); }; static Table table; public: static int valueOf(const Piece king, const Piece defender) { return valueOf(king, defender.ptypeO(), defender.square()); } static int valueOf(Piece king, PtypeO ptypeo, Square position) { assert(king.ptype() == KING); if (getOwner(ptypeo) != king.owner()) return 0; return table.valueOf(king.square(), king.owner(), position, getPtype(ptypeo)); } static void saveText(const char *filename) { table.saveText(filename); } static void loadText(const char *filename) { table.loadText(filename); } static void resetWeights(const int *w) { table.resetWeights(w); } static void init() { table.init(); } }; } // namespace endgame } // namespace endgame } // namespace osl #endif /* EVAL_ENDGAME_DEFENSEKING_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/eval/endgame/attackDefense.h0000644000000000000000000000514012316770314021444 0ustar rootroot/** * attackDefense.h */ #ifndef EVAL_ENDGAME_ATTACKtDEFENSE_H #define EVAL_ENDGAME_ATTACKtDEFENSE_H #include "osl/eval/endgame/attackKing.h" #include "osl/eval/endgame/defenseKing.h" #include "osl/eval/pieceEval.h" #include "osl/eval/evalTraits.h" namespace osl { namespace container { class PieceValues; } // namespace container namespace eval { namespace endgame { /** * max(AttackKing, DefenseKing). * ã†ã¾ãå‹•ãよã†ãªã‚‰çµ±åˆã—ãŸè¡¨ã‚’作る */ class AttackDefense { CArray values; void reset() { values.fill(0); } void addValue(Player owner, int value) { values[playerToIndex(owner)] += value; } void addValue(Piece king_black, Piece king_white, Piece target) { assert(king_black.ptype() == KING); assert(king_white.ptype() == KING); assert(king_black.owner() == BLACK); assert(king_white.owner() == WHITE); addValue(target.owner(), valueOf(king_black, king_white, target)); } public: explicit AttackDefense(const SimpleState&); void changeTurn() {} static bool initialized() { return true; } int value() const { return values[0] + values[1]; } int value(Player p) const { return values[playerToIndex(p)]; } void update(const SimpleState& new_state, Move last_move); int expect(const SimpleState& state, Move move) const; private: void updateKingMove(const SimpleState&, Square from, Square to); void updateKingMove(const SimpleState&, Square from, Square to, Piece target); public: static int infty() { return PieceEval::infty()*2; // 2倿œªæº€ã®ãƒœãƒ¼ãƒŠã‚¹ } static int valueOf(Piece black_king, Piece white_king, Piece target) { return valueOf(black_king, white_king, target.ptypeO(), target.square()); } static int valueOf(Piece black_king, Piece white_king, PtypeO ptypeo, Square position) { assert(black_king.owner() == BLACK); assert(white_king.owner() == WHITE); const Player player = getOwner(ptypeo); const Piece my_king = (player == BLACK) ? black_king : white_king; const Piece op_king = (player == BLACK) ? white_king : black_king; const int attack = AttackKing::valueOf(op_king, ptypeo, position); const int defense = DefenseKing::valueOf(my_king, ptypeo, position); return max(player, attack, defense); } static void setValues(const SimpleState&, container::PieceValues&); static void resetWeights(const int *w); }; } // namespace endgame } // namespace endgame } // namespace osl #endif /* EVAL_ENDGAME_ATTACKKING_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/endgame/defenseKing.cc0000644000000000000000000002235012316770314021265 0ustar rootroot/** * defenseKing.cc */ #include "osl/eval/endgame/defenseKing.h" #include "osl/eval/pieceEval.h" #include "osl/oslConfig.h" osl::eval::endgame::DefenseKing::Table osl::eval::endgame::DefenseKing::table; static osl::SetUpRegister _initializer([](){ osl::eval::endgame::DefenseKing::init(); }); // YSSã®è©•価値を真似 // http://www32.ocn.ne.jp/~yss/book.html#SEC3 // // 0 1 2 3 4 5 6 7 8 (Xè·é›¢) // +8 50 50 50 50 50 50 50 50 50 // +7 56 53 50 50 50 50 50 50 50 // +6 64 61 55 50 50 50 50 50 50 // +5 79 77 70 65 54 51 50 50 50 // +4 100 99 95 87 74 58 50 50 50 // +3 116 117 101 95 88 67 54 50 50 // +2 131 129 124 114 90 71 59 51 50 // +1 137 138 132 116 96 76 61 53 50 // 0 142 142 136 118 98 79 64 52 50 <--- 中心 // -1 132 132 129 109 95 75 60 51 50 // -2 121 120 105 97 84 66 54 50 50 // -3 95 93 89 75 68 58 51 50 50 // -4 79 76 69 60 53 50 50 50 50 // -5 64 61 55 51 50 50 50 50 50 // -6 56 52 50 50 50 50 50 50 50 // -7 50 50 50 50 50 50 50 50 50 // -8 50 50 50 50 50 50 50 50 50 namespace osl { namespace { const CArray yss_bonus = {{ // 桂,香ã¯ä¸€æ®µä¸‹ã’ã‚‹ãŸã‚,+9 ã‹ã‚‰ -9 ã¾ã§å–ã‚‹ 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 56, 53, 50, 50, 50, 50, 0, 0, 0, 64, 61, 55, 50, 50, 50, 0, 0, 0, 79, 77, 70, 65, 54, 51, 0, 0, 0, 100, 99, 95, 87, 74, 58, 0, 0, 0, 116, 117, 101, 95, 88, 67, 0, 0, 0, 131, 129, 124, 114, 90, 71, 0, 0, 0, 137, 138, 132, 116, 96, 76, 0, 0, 0, 142, 142, 136, 118, 98, 79, 0, 0, 0, 132, 132, 129, 109, 95, 75, 0, 0, 0, 121, 120, 105, 97, 84, 66, 0, 0, 0, 95, 93, 89, 75, 68, 58, 0, 0, 0, 79, 76, 69, 60, 53, 50, 0, 0, 0, 64, 61, 55, 51, 50, 50, 0, 0, 0, 56, 52, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, }}; /** 入玉用 */ const CArray yss_king_bonus = {{ 0, 0, 0, 150, 450, 900,1300,1550,1600 }}; inline int toEven(int value) { if (value % 2 == 0) return value; if (value > 0) return value - 1; return value + 1; } inline int multiply(int value, int bonus) { // http://www32.ocn.ne.jp/~yss/book.html#SEC3 // > 追記:2005å¹´01月22æ—¥ // > 自玉ã®è¿‘ãã®ç‚¹æ•°ã¯é«˜ã™ãŽã‚‹ã®ã§ã€ç¾åœ¨ã¯ï¼‹ã‚’3分ã®1ã®å€¤ã¾ã§ä¸‹ã’ã¦ã„ã¾ã™ if (bonus > 100) bonus = (bonus - 100)/3 + 100; // yss ã§ã¯æŒé§’ã®ä»˜åР価値ãŒ2割程度ã‚ã‚‹ãŸã‚1.2ã§å‰²ã‚‹ return toEven(value * bonus / 120); } inline void adhoc_adjust(int& value, double scale) { value = toEven(static_cast(value * scale)); } } // anonymous namespace } // namespace osl void osl::eval::endgame::DefenseKing:: Table::init() { // BLACKã®KINGã«å¯¾ã™ã‚‹BLACKã®ä¾¡å€¤ã‚’書ã,WHITEã®é§’ã®ä¾¡å€¤ã¯æœ€å¾Œã«å転ã•ã›ã‚‹ï¼Ž data.fill(0); for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king(king_x, king_y); for (int p=PTYPE_PIECE_MIN; p<=PTYPE_MAX; ++p) { const Ptype ptype = static_cast(p); assert(isPiece(ptype)); const Ptype basic_type = unpromote(ptype); const int ptype_value = Ptype_Eval_Table.value(newPtypeO(BLACK,ptype)); // æŒé§’ const int stand_bonus = (isMajorBasic(basic_type) ? Ptype_Eval_Table.value(newPtypeO(BLACK,PAWN)) : 0); valueOf(king, BLACK, Square::STAND(), ptype) = ptype_value + stand_bonus; if (ptype == KNIGHT || ptype == LANCE) { adhoc_adjust(valueOf(king, BLACK, Square::STAND(), ptype), 0.85); } // 盤上 if (basic_type == KING) { // 玉ã¯å…¥çŽ‰ã‚’è€ƒæ…® valueOf(king, BLACK, king, ptype) = ptype_value + yss_king_bonus[9-king_y]; continue; } for (int defense_x=1; defense_x<=9; ++defense_x) { const bool near_edge = (((defense_x < 3) && (defense_x < king_x)) || ((defense_x > 7) && (defense_x > king_x))); const int relative_x = abs(king_x - defense_x); for (int defense_y=1; defense_y<=9; ++defense_y) { const Square defender(defense_x, defense_y); // 馬以外ã®å¤§é§’ã¯0.9 if (isMajorBasic(basic_type) && ptype != PBISHOP) { int black_bonus; // 入玉後ã®å¤§é§’ã¯å¤§äº‹ if (king_y < 4) black_bonus = 105; else if (king_y == 4) black_bonus = 100; // 1段目ã¨2段目ã®çމã«å¯¾ã™ã‚‹2段目ã®é£›è»Šã¯ 0.95 ã‚ã’ã‚‹ else if (basic_type == ROOK && defense_y == 8 && king_y >= 8) black_bonus = 95; else black_bonus = 90; valueOf(king, BLACK, defender, ptype) = multiply(ptype_value, black_bonus); continue; } int relative_y_black_king = king_y - defense_y; if (ptype == KNIGHT || ptype == LANCE) { // 桂香ã¯ä¸€æ®µé ãã‹ã‚‰è©•価 relative_y_black_king++; } else if (ptype == PAWN) { // æ­©ã¯çމã®çœŸä¸Šã®æ®µã¨ãã®ä¸Šã®æ®µã®ãƒœãƒ¼ãƒŠã‚¹ã‚’交æ›ã™ã‚‹ if (relative_y_black_king == 1) { relative_y_black_king = 2; } else if (relative_y_black_king == 2) { relative_y_black_king = 1; } } int bonus_black_king = yss_bonus[relative_x + (-relative_y_black_king+9)*9]; // ç«¯ã®æ–¹ã«ã¯ãƒœãƒ¼ãƒŠã‚¹ã‚’ã‚ã’ãªã„ (自玉ã®è¿‘ãã®ç«¯æ­©ä»¥å¤– if (near_edge || ptype == LANCE) { if (!(ptype == PAWN && (defense_x == 1 || defense_x == 9) && defense_y < king_y)) bonus_black_king = std::min(100, bonus_black_king); } if (ptype == KNIGHT) { if ((defense_x == 2 || defense_x == 8) && (defense_y == 1 || defense_y == 9)) { } else { bonus_black_king = std::min(100, bonus_black_king); } } int black_defense = multiply(ptype_value,bonus_black_king); const bool near_center = abs(defense_x-king_x)==1 && (((king_x < 3) && (defense_x > king_x)) || ((king_x > 7) && (defense_x < king_x))); if(defense_x==king_x || near_center){ if(defense_y==king_y-1){ if(king_y==9 && (king_x==1 || king_x==9)) black_defense+=600; else if(defense_x!=king_x && king_y==8 && (king_x==2 || king_x==8)) black_defense+=200; else black_defense+=400; } } valueOf(king, BLACK, defender, ptype) = black_defense; } } } } } // 1ã¤ã—ã‹å‹•ã‘ãªã„é¦™ã¯æ­©ã¨åŒã˜ç‚¹æ•°ã« for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king(king_x, king_y); for (int x=1; x<=9; ++x) { const Square b(x,2); valueOf(king, BLACK, b, LANCE) = valueOf(king, BLACK, b, PAWN); adhoc_adjust(valueOf(king, BLACK, Square(x, 1), GOLD), 0.5); adhoc_adjust(valueOf(king, BLACK, Square(x, 1), SILVER), 0.5); adhoc_adjust(valueOf(king, BLACK, Square(x, 1), PSILVER), 0.5); } if (king_x < 6) { valueOf(king, BLACK, Square(9, 9), LANCE) = 0; valueOf(king, BLACK, Square(9, 8), LANCE) = 0; valueOf(king, BLACK, Square(9, 7), LANCE) = 0; valueOf(king, BLACK, Square(8, 9), KNIGHT) = 0; valueOf(king, BLACK, Square(9, 1), GOLD) = 0; valueOf(king, BLACK, Square(9, 1), SILVER) = 0; valueOf(king, BLACK, Square(9, 1), PSILVER) = 0; valueOf(king, BLACK, Square(8, 1), GOLD) = 0; valueOf(king, BLACK, Square(8, 1), SILVER) = 0; valueOf(king, BLACK, Square(8, 1), PSILVER) = 0; } if (king_x > 4) { valueOf(king, BLACK, Square(1, 9), LANCE) = 0; valueOf(king, BLACK, Square(1, 8), LANCE) = 0; valueOf(king, BLACK, Square(1, 7), LANCE) = 0; valueOf(king, BLACK, Square(2, 9), KNIGHT) = 0; valueOf(king, BLACK, Square(1, 1), GOLD) = 0; valueOf(king, BLACK, Square(1, 1), PSILVER) = 0; valueOf(king, BLACK, Square(1, 1), SILVER) = 0; valueOf(king, BLACK, Square(2, 1), GOLD) = 0; valueOf(king, BLACK, Square(2, 1), SILVER) = 0; valueOf(king, BLACK, Square(2, 1), PSILVER) = 0; } } } adhoc_adjust(valueOf(Square(1,1), BLACK, Square::STAND(), BISHOP), 0.95); adhoc_adjust(valueOf(Square(9,1), BLACK, Square::STAND(), BISHOP), 0.95); // BLACK/WHITE å転 for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king_b(king_x, king_y); const Square king_w = king_b.rotate180(); for (int p=PTYPE_PIECE_MIN; p<=PTYPE_MAX; ++p) { const Ptype ptype = static_cast(p); assert(isPiece(ptype)); // æŒé§’ valueOf(king_w, WHITE, Square::STAND(), ptype) = - valueOf(king_b, BLACK, Square::STAND(), ptype); // 盤上 for (int defense_x=1; defense_x<=9; ++defense_x) { for (int defense_y=1; defense_y<=9; ++defense_y) { const Square defense_b(defense_x, defense_y); // blackã¸ã®blackã®é˜²å¾¡ const Square defense_w = defense_b.rotate180(); valueOf(king_w, WHITE, defense_w, ptype) = - valueOf(king_b, BLACK, defense_b, ptype); } } } } } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/endgame/attackKing.cc0000644000000000000000000002754512316770314021136 0ustar rootroot/** * attackKing.cc */ #include "osl/eval/endgame/attackKing.h" #include "osl/eval/pieceEval.h" #include "osl/oslConfig.h" osl::eval::endgame::AttackKing::Table osl::eval::endgame::AttackKing::table; static osl::SetUpRegister _initializer([](){ osl::eval::endgame::AttackKing::init(); }); // YSSã®è©•価値を真似 // http://www32.ocn.ne.jp/~yss/book.html#SEC3 // // 先手ã®çމã«å¯¾ã™ã‚‹å¾Œæ‰‹ã®é§’ã®ç›¸å¯¾ä½ç½®ã«ã‚ˆã‚‹å¢—減割åˆã€‚X軸ã«ã¤ã„ã¦ã¯å¯¾ç§°ã§ã‚る。 // 0 1 2 3 4 5 6 7 8 (Xè·é›¢) // // +8 50 50 50 50 50 50 50 50 50 // +7 50 50 50 50 50 50 50 50 50 // +6 62 60 58 52 50 50 50 50 50 // +5 80 78 72 67 55 51 50 50 50 // +4 100 99 95 87 78 69 50 50 50 // +3 140 130 110 100 95 75 54 50 50 // +2 170 160 142 114 98 80 62 55 50 <--- 2段真上を最大ã¨ã™ã‚‹ã€‚ // +1 170 165 150 121 94 78 58 52 50 // 0 170 145 137 115 91 75 57 50 50 <--- 中心。左隅(0 0)ã«çŽ‹ãŒã„ã‚‹ã¨ã™ã‚‹ // -1 132 132 129 102 84 71 51 50 50 // -2 100 97 95 85 70 62 50 50 50 // -3 90 85 80 68 60 53 50 50 50 // -4 70 66 62 55 52 50 50 50 50 // -5 54 53 51 50 50 50 50 50 50 // -6 50 50 50 50 50 50 50 50 50 // -7 50 50 50 50 50 50 50 50 50 // -8 50 50 50 50 50 50 50 50 50 namespace osl { namespace { const CArray yss_bonus = {{ // 桂,香ã¯ä¸€æ®µä¸‹ã’ã‚‹ãŸã‚,+9 ã‹ã‚‰ -9 ã¾ã§å–ã‚‹ 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 62, 60, 58, 52, 50, 50, 0, 0, 0, 80, 78, 72, 67, 55, 51, 0, 0, 0, 100, 99, 95, 87, 78, 69, 0, 0, 0, 140, 130, 110, 100, 95, 75, 0, 0, 0, 170, 160, 142, 114, 98, 80, 0, 0, 0, 170, 165, 150, 121, 94, 78, 0, 0, 0, 170, 145, 137, 115, 91, 75, 0, 0, 0, 132, 132, 129, 102, 84, 71, 0, 0, 0, 100, 97, 95, 85, 70, 62, 0, 0, 0, 90, 85, 80, 68, 60, 53, 0, 0, 0, 70, 66, 62, 55, 52, 50, 0, 0, 0, 54, 53, 51, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, 50, 50, 50, 50, 50, 50, 0, 0, 0, }}; inline int toEven(int value) { if (value % 2 == 0) return value; if (value > 0) return value - 1; return value + 1; } inline int multiply(int value, int bonus) { // yss ã§ã¯æŒé§’ã®ä»˜åР価値ãŒ2割程度ã‚ã‚‹ãŸã‚1.2ã§å‰²ã‚‹ return toEven(value * bonus / 120); } inline void adhoc_adjust(int& value, double scale) { value = toEven(static_cast(value * scale)); } } // anonymous namespace } // namespace osl void osl::eval::endgame::AttackKing:: Table::adhoc_edge_king_1(const Player player, const Square king, const Square attack) { for (int ptype = PPAWN; ptype <= ROOK; ptype++) { if (ptype != KING) { adhoc_adjust(valueOf(king, player, attack, static_cast(ptype)), 1.25); } } } void osl::eval::endgame::AttackKing:: Table::adhoc_edge_king_2(const Player player, const Square king, const Square attack) { adhoc_adjust(valueOf(king, player, attack, GOLD), 1.25); adhoc_adjust(valueOf(king, player, attack, SILVER), 1.25); for (int ptype = PPAWN; ptype <= PSILVER; ptype++) { adhoc_adjust(valueOf(king, player, attack, static_cast(ptype)), 1.25); } } void osl::eval::endgame::AttackKing:: Table::init() { // WHITEã®KINGã«å¯¾ã™ã‚‹BLACKã®ä¾¡å€¤ã‚’書ã,最後ã«å転ã•ã›ã‚‹ï¼Ž data.fill(0); for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king(king_x, king_y); for (int p=PTYPE_PIECE_MIN; p<=PTYPE_MAX; ++p) { const Ptype ptype = static_cast(p); assert(isPiece(ptype)); const Ptype basic_type = unpromote(ptype); const int ptype_value = Ptype_Eval_Table.value(newPtypeO(BLACK,ptype)); // æŒé§’ const int stand_bonus = (isMajorBasic(basic_type) ? Ptype_Eval_Table.value(newPtypeO(BLACK,PAWN)) : 0); valueOf(king, WHITE, Square::STAND(), ptype) = +ptype_value + stand_bonus; if (ptype == KNIGHT || ptype == LANCE) adhoc_adjust(valueOf(king, WHITE, Square::STAND(), ptype), 0.85); if (ptype == GOLD || ptype == SILVER) adhoc_adjust(valueOf(king, WHITE, Square::STAND(), ptype), 1.1); // 盤上 for (int attack_x=1; attack_x<=9; ++attack_x) { const int relative_x = abs(king_x - attack_x); for (int attack_y=1; attack_y<=9; ++attack_y) { const Square attacker(attack_x, attack_y); if (basic_type == KING) { // 玉ã¯ãã®ã¾ã¾ valueOf(king, WHITE, attacker, ptype) = ptype_value; continue; } const int relative_y_white_king = (((ptype == KNIGHT)||(ptype == LANCE)) ? attack_y - king_y - 1 // 桂香ã¯ä¸€æ®µé ãã‹ã‚‰è©•価 : attack_y - king_y); const int bonus_white_king = yss_bonus[relative_x + (-relative_y_white_king+9)*9]; const int black_attack = multiply(ptype_value,bonus_white_king); if (isMajorBasic(basic_type)) { // å¤§é§’ã¯æ”»æ’ƒã«åˆ©ã„ã¦ã„れ㰠max ã‚’å–ã‚‹ const int relative_y = abs(king_y - attack_y); const int diff1 = king_x + king_y - (attack_x + attack_y); const int diff2 = king_x - king_y - (attack_x - attack_y); if ((basic_type == ROOK && relative_y <= 1) || (basic_type == BISHOP && ((-1 <= diff1 && diff1 <= 1) || (-1 <= diff2 && diff2 <= 1)))) { valueOf(king, WHITE, attacker, ptype) = EvalTraits::max(ptype_value, black_attack); // 玉ã¨åŒã˜ç­‹ã®æ–¹ã®ãƒœãƒ¼ãƒŠã‚¹ã‚’高ãã™ã‚‹ if (relative_y == 0) { adhoc_adjust(valueOf(king, WHITE, attacker, ptype), 0.98); } } else { // ãã®ä»–㯠90 ã« valueOf(king, WHITE, attacker, ptype) = multiply(ptype_value, 90); } continue; } //æˆã‚Œãªã„æ­©ã¨æ¡‚ã¯æ¸›ç‚¹ if ((ptype == PAWN && attack_y >= 5) || (ptype == KNIGHT && attack_y >= 6)) { int new_black_attack = black_attack; adhoc_adjust(new_black_attack, 0.95); valueOf(king, WHITE, attacker, ptype) = new_black_attack; } else valueOf(king, WHITE, attacker, ptype) = black_attack; } } } } } for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king(king_x, king_y); // 1ã¤ã—ã‹å‹•ã‘ãªã„é¦™ã¯æ­©ã¨åŒã˜ç‚¹æ•°ã« for (int x=1; x<=9; ++x) { const Square b(x,2); valueOf(king, WHITE, b, LANCE) = valueOf(king, WHITE, b, PAWN); } if (king_y <= 7) { adhoc_adjust(valueOf(king, WHITE, Square(king_x, king_y + 2), PAWN), 1.25); } // 1段目ã®é‡‘類ã¯ä¾¡å€¤ã‚’åŠåˆ†ã« for (int x=1; x<=9; ++x) { const Square b(x,1); if (x <= 2 || x >= 8) { adhoc_adjust(valueOf(king, WHITE, b, GOLD), 0.25); adhoc_adjust(valueOf(king, WHITE, b, PSILVER), 0.25); } else { adhoc_adjust(valueOf(king, WHITE, b, GOLD), 0.5); adhoc_adjust(valueOf(king, WHITE, b, PSILVER), 0.5); } adhoc_adjust(valueOf(king, WHITE, b, PKNIGHT), 0.5); adhoc_adjust(valueOf(king, WHITE, b, PLANCE), 0.5); adhoc_adjust(valueOf(king, WHITE, b, PPAWN), 0.5); } // 1段玉ã«å¯¾ã™ã‚‹3段目ã®é§’ã¯ä¾¡å€¤ã‚’1.25å€ã« if (king_y == 1) { for (int x = 1; x <= 9; ++x) { const Square three(x, 3); for (int ptype = PPAWN; ptype <= ROOK; ptype++) { if (ptype != KING && ptype != ROOK && ptype != PROOK) adhoc_adjust(valueOf(king, WHITE, three, static_cast(ptype)), 1.25); } } } if (king_y <= 2) { for (int x = std::max(king_x - 1, 2); x <= std::min(king_x + 1, 8); x++) { adhoc_adjust(valueOf(king, WHITE, Square(x, 4), PAWN), 1.25); } } // 端玉ã«å¯¾ã™ã‚‹ãƒœãƒ¼ãƒŠã‚¹ if (king_x == 1 || king_x == 9) { int next = king_x == 1 ? 2 : 8; adhoc_edge_king_1(WHITE, king, Square(next, king_y)); if (king_y < 9) { adhoc_edge_king_1(WHITE, king, Square(next, king_y + 1)); } if (king_y < 8) { // 3段目㯠1.25 * 1.25 å€ã•れるã‘ã©æ°—ã«ã—ãªã„ adhoc_edge_king_1(WHITE, king, Square(next, king_y + 2)); } } if (king_x < 6) { valueOf(king, WHITE, Square(9, 9), LANCE) = 0; valueOf(king, WHITE, Square(9, 8), LANCE) = 0; valueOf(king, WHITE, Square(9, 7), LANCE) = 0; valueOf(king, WHITE, Square(8, 9), KNIGHT) = 0; valueOf(king, WHITE, Square(9, 1), GOLD) = 0; valueOf(king, WHITE, Square(9, 1), SILVER) = 0; valueOf(king, WHITE, Square(9, 1), PSILVER) = 0; valueOf(king, WHITE, Square(8, 1), GOLD) = 0; valueOf(king, WHITE, Square(8, 1), SILVER) = 0; valueOf(king, WHITE, Square(8, 1), PSILVER) = 0; } if (king_x > 4) { valueOf(king, WHITE, Square(1, 9), LANCE) = 0; valueOf(king, WHITE, Square(1, 8), LANCE) = 0; valueOf(king, WHITE, Square(1, 7), LANCE) = 0; valueOf(king, WHITE, Square(2, 9), KNIGHT) = 0; valueOf(king, WHITE, Square(1, 1), GOLD) = 0; valueOf(king, WHITE, Square(1, 1), PSILVER) = 0; valueOf(king, WHITE, Square(1, 1), SILVER) = 0; valueOf(king, WHITE, Square(2, 1), GOLD) = 0; valueOf(king, WHITE, Square(2, 1), SILVER) = 0; valueOf(king, WHITE, Square(2, 1), PSILVER) = 0; } } } adhoc_edge_king_2(WHITE, Square(1, 1), Square(3, 2)); adhoc_edge_king_2(WHITE, Square(1, 2), Square(3, 3)); adhoc_edge_king_2(WHITE, Square(9, 1), Square(7, 2)); adhoc_edge_king_2(WHITE, Square(9, 2), Square(7, 3)); for (int x = 1; x <= 9; x++) { for (int y = 1; y <= 9; y++) { adhoc_adjust(valueOf(Square(1,1), WHITE, Square(x, y), GOLD), 1.05); adhoc_adjust(valueOf(Square(9,1), WHITE, Square(x, y), GOLD), 1.05); adhoc_adjust(valueOf(Square(1,1), WHITE, Square(x, y), SILVER), 1.05); adhoc_adjust(valueOf(Square(9,1), WHITE, Square(x, y), SILVER), 1.05); adhoc_adjust(valueOf(Square(1,1), WHITE, Square(x, y), BISHOP), 0.95); adhoc_adjust(valueOf(Square(1,1), WHITE, Square(x, y), PBISHOP), 0.95); adhoc_adjust(valueOf(Square(9,1), WHITE, Square(x, y), BISHOP), 0.95); adhoc_adjust(valueOf(Square(9,1), WHITE, Square(x, y), PBISHOP), 0.95); for (int ptype = PPAWN; ptype <= PSILVER; ptype++) { adhoc_adjust(valueOf(Square(1, 1), WHITE, Square(x,y), static_cast(ptype)), 1.05); adhoc_adjust(valueOf(Square(9, 1), WHITE, Square(x,y), static_cast(ptype)), 1.05); } } } adhoc_adjust(valueOf(Square(1,1), WHITE, Square::STAND(), BISHOP), 0.95); adhoc_adjust(valueOf(Square(9,1), WHITE, Square::STAND(), BISHOP), 0.95); // BLACK/WHITE å転 for (int king_x=1; king_x<=9; ++king_x) { for (int king_y=1; king_y<=9; ++king_y) { const Square king_b(king_x, king_y); const Square king_w = king_b.rotate180(); for (int p=PTYPE_PIECE_MIN; p<=PTYPE_MAX; ++p) { const Ptype ptype = static_cast(p); assert(isPiece(ptype)); // æŒé§’ valueOf(king_b, BLACK, Square::STAND(), ptype) = - valueOf(king_w, WHITE, Square::STAND(), ptype); // 盤上 for (int attack_x=1; attack_x<=9; ++attack_x) { for (int attack_y=1; attack_y<=9; ++attack_y) { const Square attack_b(attack_x, attack_y); // white ã¸ã®blackã®æ”»æ’ƒ const Square attack_w = attack_b.rotate180(); valueOf(king_b, BLACK, attack_w, ptype) = - valueOf(king_w, WHITE, attack_b, ptype); } } } } } } void osl::eval::endgame::AttackKing:: saveText(const char *filename) { table.saveText(filename); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/endgame/kingPieceTable.cc0000644000000000000000000000537012316770314021714 0ustar rootroot/** * kingPieceTable.cc */ #include "osl/eval/endgame/kingPieceTable.h" #include "osl/container/pieceValues.h" #include #include #if defined(_WIN32) # include #endif void osl::eval::endgame:: KingPieceTable::saveText(const char *filename) const { FILE *fp = fopen(filename, "w"); if (! fp) return; for (int x=1; x<=9; ++x) { for (int y=1; y<=9; ++y) { Square sq(x,y); for (int i=0; i<2; ++i) { for (int x2=0; x2<=9; ++x2) { for (int y2=(x2 == 0) ? 0 : 1; y2<=9; ++y2) { Square sq2(x2,y2); if (x2 == 0 && y2 == 0) sq2 = Square::STAND(); for (int j=0; j w; FILE *fp = fopen(filename, "r"); if (! fp) { std::cerr << "open failed " << filename << "\n"; return; } for (int i=0; i struct KingPieceValues { /** * å±€é¢ã®é§’ã®å€¤ã‚’求ã‚ã‚‹ */ static void setValues(const SimpleState&, PieceValues&); }; } // namespace endgame } // namespace eval } // namespace osl template void osl::eval::endgame:: KingPieceValues::setValues(const SimpleState& state, PieceValues& values) { values.fill(0); // 速度ã¯ç„¡è¦– const Piece king_black = state.kingPiece(BLACK); const Piece king_white = state.kingPiece(WHITE); for (int i=0; i class ProgressEvalGeneral { public: typedef OpeningEval opening_eval_t; typedef endgame::AttackDefense endgame_eval_t; typedef progress::Effect5x3WithBonus progress_t; typedef progress::Effect5x3d defense_t; private: opening_eval_t opening_eval; endgame_eval_t endgame_eval; progress_t current_progress; defense_t defense_effect; MinorPieceBonus minor_piece_bonus; // Records pinned pieces of a player, not the opponent's // (owner of pieces == player) mutable CArray pin_mask; CArray2d can_check_pieces; int progress_independent_bonus; int progress_dependent_bonus; int major_pieces; CArray attack_bonus; // index is king (i.e., defense) int rook_mobility, bishop_mobility, lance_mobility; enum{ INVALID=EvalTraits::MAX_VALUE+1, }; mutable int cache; static CArray capture_values; template void initializeCheckPieceDir(const NumEffectState &state, int count); template void initializeCheckPiece(const NumEffectState &state); static void setUpInternal(const char *filename=0); public: ProgressEvalGeneral(const NumEffectState& state); void changeTurn() {} static bool initialized() { return opening_eval_t::initialized(); } static bool setUp(const char *filename) { if (! opening_eval_t::setUp()) return false; setUpInternal(filename); return true; } static bool setUp() { if (! opening_eval_t::setUp()) return false; setUpInternal(); return true; } /** roundup 㯠2^n ã§ã‚ã‚‹ã“㨠*/ static const int ROUND_UP = 64; /** å±é™ºåº¦ãƒšãƒŠãƒ«ãƒ†ã‚£ã®16å€ */ static int attackDefenseBonusT16(Progress16 black, Progress16 white, Progress16 black_defense, Progress16 white_defense) { return (white.value() * 2 - white_defense.value() - black.value() * 2 + black_defense.value()) * 3200 / 2; } static int composeValue(int value_opening, int value_endgame, Progress16 progress16, Progress16 black, Progress16 white, Progress16 black_defense, Progress16 white_defense, int minor_piece_bonus, int progress_independent_bonus, int progress_dependent_bonus) { static_assert(((PtypeEvalTraits::val * 2 + PtypeEvalTraits::val) % 16) == 0, ""); static_assert((PtypeEvalTraits::val % 32) == 0, ""); assert(progress16.isValid()); assert(black.isValid()); assert(white.isValid()); /* value_opening * (16 - progress16) + value_endgame * progress16 + bonus * (white_progress - black_progress) * prorgress16 / 16 */ int result = value_opening*16 + progress16.value() * (value_endgame-value_opening + (attackDefenseBonusT16(black, white, black_defense, white_defense)) / 16); result += progress_independent_bonus; result += minor_piece_bonus; result += progress_dependent_bonus; result &= ~(ROUND_UP-1); assert(result % 2 == 0); return result; } const Progress16 progress16() const { return current_progress.progress16(); } const Progress16 progress16bonus(Player p) const { return current_progress.progress16bonus(p); } void invalidateCache(){ cache=INVALID; } int value() const { if(cache==INVALID) cache = composeValue( openingValue(), endgame_eval.value(), progress16(), current_progress.progress16bonus(BLACK), current_progress.progress16bonus(WHITE), defense_effect.progress16(BLACK), defense_effect.progress16(WHITE), minor_piece_bonus.value( progress16(), progress16bonus(BLACK), progress16bonus(WHITE)), progress_independent_bonus, progress_dependent_bonus); return cache; } const Progress32 progress32() const { return Progress32(current_progress.progress16(BLACK).value() + current_progress.progress16(WHITE).value()); } static void setValues(const SimpleState&, Progress16 progress16, container::PieceValues&); static void setValues(const SimpleState& s, container::PieceValues& o); int expect(const NumEffectState& state, Move move) const; Move suggestMove(const NumEffectState&) const { return Move(); } void update(const NumEffectState& new_state, Move last_move); template int calculateAttackBonusEach(const NumEffectState& state) const; template int calculateAttackBonusOne(const NumEffectState& state) const; int calculateKnightCheck(const NumEffectState& state) const; template int calculateKnightCheckEach(const NumEffectState& state) const; template int calculateEnterKingBonus(const NumEffectState& state) const ; template int calculateMiddleKingBonus(const NumEffectState& state) const; int calculateRookRankBonus(const NumEffectState& state) const; public: static int infty() { assert(endgame_eval_t::infty() <= opening_eval_t::infty()); // åºç›¤ã‚’使用 return composeValue(opening_eval_t::infty(), 0, Progress16(0), Progress16(0), Progress16(0), Progress16(0), Progress16(0), 0, 0, 0); } static int captureValue(PtypeO ptypeO) { return capture_values[ptypeOIndex(ptypeO)]; } static int seeScale() { return captureValue(newPtypeO(WHITE,PAWN)) / PieceEval::captureValue(newPtypeO(WHITE,PAWN)); } const PieceMask pins(Player player) const { return pin_mask[player]; } // for debug int minorPieceValue() const { return minor_piece_bonus.value(progress16(), progress16bonus(BLACK), progress16bonus(WHITE)); } int openingValue() const { return opening_eval.value(); } int endgameValue() const { return endgame_eval.value(); } ProgressDebugInfo debugInfo(const NumEffectState& state) const; // public for debugging purpose only // also updates pin_mask int calculatePinBonus(const NumEffectState& state) const; int calculateMobilityBonus() const; static int calculateMobilityBonusRook(const NumEffectState& state); static int calculateMobilityBonusBishop(const NumEffectState& state); static int calculateMobilityBonusLance(const NumEffectState& state); int calculateAttackRooks(const NumEffectState& state) const; int calculateAttackBonus(const NumEffectState& state) const; int calculateSilverPenalty(const NumEffectState& state) const; int calculateGoldPenalty(const NumEffectState& state) const; int attackDefenseBonus() const { return progress16().value() * attackDefenseBonusT16(current_progress.progress16bonus(BLACK), current_progress.progress16bonus(WHITE), defense_effect.progress16(BLACK), defense_effect.progress16(WHITE)) / 16; } int attackBonusScale(int val, Player attack) const { return val * current_progress.progress16(alt(attack)).value() / 16 * 4; } void debug() const {} enum { AdjustableDimension = PTYPE_SIZE + endgame::KingPieceTable::EffectiveDimension*2 }; static void resetWeights(const int *weight); }; typedef PiecePairPieceEval progress_eval_opening_t; class ProgressEval : public ProgressEvalGeneral { public: explicit ProgressEval(const NumEffectState& state) : ProgressEvalGeneral(state) { } ProgressEval() : ProgressEvalGeneral(NumEffectState()) { } static PtypeEvalTable Piece_Value; }; } // namespace eval using eval::ProgressEval; } // namespace osl #endif /* EVAL_PROGRESSEVAL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/progressEval.cc0000644000000000000000000007045312316770314020126 0ustar rootroot/* progressEval.cc */ #include "osl/eval/progressEval.h" #include "osl/container/pieceValues.h" #include "osl/numEffectState.tcc" #include "osl/effect_util/effectUtil.tcc" #include "osl/oslConfig.h" #include #include #include osl::eval::PtypeEvalTable osl::eval::ProgressEval::Piece_Value; static osl::SetUpRegister _initializer([](){ osl::eval::ProgressEval::Piece_Value.init(); }); static_assert((osl::eval::ProgressEval::ROUND_UP & (osl::eval::ProgressEval::ROUND_UP-1)) == 0, ""); #ifndef MINIMAL template osl::CArray osl::eval::ProgressEvalGeneral::capture_values; template int osl::eval:: ProgressEvalGeneral::expect(const NumEffectState& state, Move move) const { if (move.isPass()) return value(); progress_t new_progress = current_progress.expect(state, move); return composeValue(opening_eval.expect(state, move), endgame_eval.expect(state, move), progress16(), new_progress.progress16(BLACK), new_progress.progress16(WHITE), defense_effect.progress16(BLACK), defense_effect.progress16(WHITE), minor_piece_bonus.value(progress16(), progress16bonus(BLACK), progress16bonus(WHITE)), progress_independent_bonus, progress_dependent_bonus); } template void osl::eval:: ProgressEvalGeneral::setUpInternal(const char *filename_given) { // read weights if exists std::string filename; if (filename_given) filename = filename_given; else { filename = OslConfig::home(); filename += "/data/progresseval.txt"; } if (boost::filesystem::exists(filename.c_str())) { if (OslConfig::verbose()) std::cerr << "loading " << filename << "\n"; CArray w; FILE *fp = fopen(filename.c_str(), "r"); for (size_t i=0; i(i+PTYPEO_MIN); capture_values[i] = composeValue(opening_eval_t::captureValue(ptypeo), 0, Progress16(0), Progress16(0), Progress16(0), Progress16(0), Progress16(0), 0, 0, 0); } } template void osl::eval:: ProgressEvalGeneral::resetWeights(const int *w) { opening_eval_t::resetWeights(w); endgame_eval_t::resetWeights(w+PTYPE_SIZE); } template osl::eval:: ProgressEvalGeneral::ProgressEvalGeneral(const NumEffectState& state) : opening_eval(state), endgame_eval(state), current_progress(state), defense_effect(state), minor_piece_bonus(state), major_pieces(0), cache(INVALID) { for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { if (state.pieceOf(i).owner() == osl::BLACK) ++major_pieces; } for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { if (state.pieceOf(i).owner() == osl::BLACK) ++major_pieces; } can_check_pieces.fill(0); // knight and pawn are intentionally omitted initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); initializeCheckPiece(state); rook_mobility = calculateMobilityBonusRook(state); bishop_mobility = calculateMobilityBonusBishop(state); lance_mobility = calculateMobilityBonusLance(state); progress_independent_bonus = calculateMobilityBonus(); progress_independent_bonus += calculateAttackRooks(state); progress_independent_bonus += calculateSilverPenalty(state); progress_independent_bonus += calculateGoldPenalty(state); attack_bonus[BLACK] = calculateAttackBonusEach(state); attack_bonus[WHITE] = calculateAttackBonusEach(state); progress_dependent_bonus = attackBonusScale(attack_bonus[BLACK], WHITE); progress_dependent_bonus += attackBonusScale(attack_bonus[WHITE], BLACK); progress_dependent_bonus += calculatePinBonus(state); progress_independent_bonus += calculateKnightCheck(state); progress_independent_bonus += calculateRookRankBonus(state); progress_independent_bonus += calculateEnterKingBonus(state); progress_independent_bonus += calculateEnterKingBonus(state); progress_independent_bonus += calculateMiddleKingBonus(state); progress_independent_bonus += calculateMiddleKingBonus(state); assert(initialized()); } template template void osl::eval:: ProgressEvalGeneral::initializeCheckPiece( const NumEffectState &state) { if (state.hasPieceOnStand(P)) { int count = state.countPiecesOnStand(P, PTYPE); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); initializeCheckPieceDir(state, count); } } template template void osl::eval:: ProgressEvalGeneral::initializeCheckPieceDir( const NumEffectState &, int count) { if (PtypeTraits::moveMask & (DirectionTraits

::mask | DirectionTraits::mask)) can_check_pieces[P][Dir] = count; } template int osl::eval:: ProgressEvalGeneral::calculateMobilityBonusRook(const NumEffectState& state) { using namespace osl::mobility; int val=0; for(int i=PtypeTraits::indexMin; i::indexLimit;++i){ Piece p=state.pieceOf(i); if(p.isOnBoardByOwner()){ int vc= RookMobility::countVerticalAll(BLACK,state,p); int hc= RookMobility::countHorizontalAll(BLACK,state,p); if(p.isPromoted()){ val+=MobilityTable::prookVertical[vc]; val+=MobilityTable::prookHorizontal[hc]; } else{ val+=MobilityTable::rookVertical[vc]; val+=MobilityTable::rookHorizontal[hc]; } } else if(p.isOnBoardByOwner()){ int vc= RookMobility::countVerticalAll(WHITE,state,p); int hc= RookMobility::countHorizontalAll(WHITE,state,p); if(p.isPromoted()){ val-=MobilityTable::prookVertical[vc]; val-=MobilityTable::prookHorizontal[hc]; } else{ val-=MobilityTable::rookVertical[vc]; val-=MobilityTable::rookHorizontal[hc]; } } } return val; } template int osl::eval:: ProgressEvalGeneral::calculateMobilityBonusBishop(const NumEffectState& state) { using namespace osl::mobility; int val=0; for(int i=PtypeTraits::indexMin; i::indexLimit;++i){ Piece p=state.pieceOf(i); if(p.isOnBoardByOwner()){ int c= BishopMobility::countAll(BLACK,state,p); if(p.isPromoted()) val+=MobilityTable::pbishop[c]; else val+=MobilityTable::bishop[c]; } else if(p.isOnBoardByOwner()){ int c= BishopMobility::countAll(WHITE,state,p); if(p.isPromoted()) val-=MobilityTable::pbishop[c]; else val-=MobilityTable::bishop[c]; } } return val; } template int osl::eval:: ProgressEvalGeneral::calculateMobilityBonusLance(const NumEffectState& state) { using namespace osl::mobility; int val=0; for(int i=PtypeTraits::indexMin; i::indexLimit;++i){ Piece p=state.pieceOf(i); if(p.isOnBoardByOwner() && !p.isPromoted()){ int c= LanceMobility::countAll(BLACK,state,p); val+=MobilityTable::lance[c]; } else if(p.isOnBoardByOwner() && !p.isPromoted()){ int c= LanceMobility::countAll(WHITE,state,p); val-=MobilityTable::lance[c]; } } return val; } template inline int osl::eval:: ProgressEvalGeneral::calculateMobilityBonus() const { using namespace osl::mobility; int val=rook_mobility + bishop_mobility + lance_mobility; return val*128/100 * 12; } template void osl::eval:: ProgressEvalGeneral::update( const NumEffectState& new_state, Move last_move) { if (last_move.isPass()) return; const Ptype captured = last_move.capturePtype(); if (last_move.isDrop()) { const Ptype ptype = last_move.ptype(); if (ptype == ROOK) { --can_check_pieces[playerToIndex(last_move.player())][U]; --can_check_pieces[playerToIndex(last_move.player())][D]; --can_check_pieces[playerToIndex(last_move.player())][L]; --can_check_pieces[playerToIndex(last_move.player())][R]; } else if (ptype == BISHOP) { --can_check_pieces[playerToIndex(last_move.player())][UL]; --can_check_pieces[playerToIndex(last_move.player())][DL]; --can_check_pieces[playerToIndex(last_move.player())][UR]; --can_check_pieces[playerToIndex(last_move.player())][DR]; } if (ptype == GOLD) { --can_check_pieces[playerToIndex(last_move.player())][U]; --can_check_pieces[playerToIndex(last_move.player())][D]; --can_check_pieces[playerToIndex(last_move.player())][L]; --can_check_pieces[playerToIndex(last_move.player())][R]; --can_check_pieces[playerToIndex(last_move.player())][UL]; --can_check_pieces[playerToIndex(last_move.player())][UR]; } else if (ptype == SILVER) { --can_check_pieces[playerToIndex(last_move.player())][U]; --can_check_pieces[playerToIndex(last_move.player())][UL]; --can_check_pieces[playerToIndex(last_move.player())][DL]; --can_check_pieces[playerToIndex(last_move.player())][UR]; --can_check_pieces[playerToIndex(last_move.player())][DR]; } if (ptype == LANCE) { --can_check_pieces[playerToIndex(last_move.player())][U]; } } if (captured != PTYPE_EMPTY) { const Ptype captured_base = unpromote(captured); if (isMajor(captured_base)) { if (last_move.player() == BLACK) ++major_pieces; else --major_pieces; } if (captured_base == ROOK) { ++can_check_pieces[playerToIndex(last_move.player())][U]; ++can_check_pieces[playerToIndex(last_move.player())][D]; ++can_check_pieces[playerToIndex(last_move.player())][L]; ++can_check_pieces[playerToIndex(last_move.player())][R]; } else if (captured_base == BISHOP) { ++can_check_pieces[playerToIndex(last_move.player())][UL]; ++can_check_pieces[playerToIndex(last_move.player())][DL]; ++can_check_pieces[playerToIndex(last_move.player())][UR]; ++can_check_pieces[playerToIndex(last_move.player())][DR]; } if (captured_base == GOLD) { ++can_check_pieces[playerToIndex(last_move.player())][U]; ++can_check_pieces[playerToIndex(last_move.player())][D]; ++can_check_pieces[playerToIndex(last_move.player())][L]; ++can_check_pieces[playerToIndex(last_move.player())][R]; ++can_check_pieces[playerToIndex(last_move.player())][UL]; ++can_check_pieces[playerToIndex(last_move.player())][UR]; } else if (captured_base == SILVER) { ++can_check_pieces[playerToIndex(last_move.player())][U]; ++can_check_pieces[playerToIndex(last_move.player())][UL]; ++can_check_pieces[playerToIndex(last_move.player())][DL]; ++can_check_pieces[playerToIndex(last_move.player())][UR]; ++can_check_pieces[playerToIndex(last_move.player())][DR]; } if (captured_base == LANCE) { ++can_check_pieces[playerToIndex(last_move.player())][U]; } } opening_eval.update(new_state, last_move); endgame_eval.update(new_state, last_move); current_progress.update(new_state, last_move); defense_effect.update(new_state, last_move); minor_piece_bonus.update(new_state, last_move); if (new_state.longEffectChanged()) rook_mobility = calculateMobilityBonusRook(new_state); if (new_state.longEffectChanged()) bishop_mobility = calculateMobilityBonusBishop(new_state); if (new_state.longEffectChanged()) lance_mobility = calculateMobilityBonusLance(new_state); progress_independent_bonus = calculateMobilityBonus(); progress_independent_bonus += calculateAttackRooks(new_state); progress_independent_bonus += calculateSilverPenalty(new_state); progress_independent_bonus += calculateGoldPenalty(new_state); { bool capture_or_drop = last_move.isDrop() || last_move.capturePtype() != PTYPE_EMPTY; const Square kb = new_state.kingSquare(), kw = new_state.kingSquare(); BoardMask mask = new_state.changedEffects(); mask.set(last_move.from()); mask.set(last_move.to()); if ((capture_or_drop && new_state.turn() == BLACK) || mask.anyInRange(Board_Mask_Table3x3.mask(kb))) attack_bonus[BLACK] = calculateAttackBonusEach(new_state); if ((capture_or_drop && new_state.turn() == WHITE) || mask.anyInRange(Board_Mask_Table3x3.mask(kw))) attack_bonus[WHITE] = calculateAttackBonusEach(new_state); } progress_dependent_bonus = attackBonusScale(attack_bonus[BLACK], WHITE); progress_dependent_bonus += attackBonusScale(attack_bonus[WHITE], BLACK); progress_dependent_bonus += calculatePinBonus(new_state); progress_independent_bonus += calculateKnightCheck(new_state); progress_independent_bonus += calculateRookRankBonus(new_state); progress_independent_bonus += calculateEnterKingBonus(new_state); progress_independent_bonus += calculateEnterKingBonus(new_state); progress_independent_bonus += calculateMiddleKingBonus(new_state); progress_independent_bonus += calculateMiddleKingBonus(new_state); invalidateCache(); } template int osl::eval:: ProgressEvalGeneral::calculatePinBonus( const NumEffectState& state) const { const Piece black_king = state.kingPiece(); const Piece white_king = state.kingPiece(); int bonus = 0; PieceMask white_mask = pin_mask[WHITE] = state.pin(WHITE); PieceMask black_mask = pin_mask[BLACK] = state.pin(BLACK); while (white_mask.any()) { const Piece piece = state.pieceOf(white_mask.takeOneBit()); bonus -= endgame_eval.valueOf( black_king, white_king, piece) / 4; } while (black_mask.any()) { const Piece piece = state.pieceOf(black_mask.takeOneBit()); bonus -= endgame_eval.valueOf( black_king, white_king, piece) / 4; } return bonus * progress16().value() / 16; } template int osl::eval:: ProgressEvalGeneral::calculateAttackRooks( const NumEffectState& state) const { int rooks = 0; for(int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece rook = state.pieceOf(i); if (rook.isOnBoard() && rook.square().canPromote(rook.owner()) && state.kingPiece(alt(rook.owner())).square().canPromote(rook.owner())) { if (rook.owner() == BLACK) ++rooks; else --rooks; } } if (rooks == 2) return (PtypeEvalTraits::val + PtypeEvalTraits::val) * 16; else if (rooks == -2) return -(PtypeEvalTraits::val + PtypeEvalTraits::val) * 16; return 0; } template int osl::eval:: ProgressEvalGeneral::calculateAttackBonus( const NumEffectState& state) const { return attackBonusScale(calculateAttackBonusEach(state), BLACK) + attackBonusScale(calculateAttackBonusEach(state), WHITE); } template template int osl::eval:: ProgressEvalGeneral::calculateAttackBonusOne( const NumEffectState& state) const { constexpr Player defense = alt(Attack); const Square king = state.kingSquare(); const Square target = king + DirectionPlayerTraits::offset(); int result = 0; const Piece p = state.pieceAt(target); if (! p.isEdge() && (Dir != UUR || Attack != BLACK || p.isOnBoard())) { int effect_diff = (state.countEffect(Attack, target) - state.countEffect(alt(Attack), target)); if ((effect_diff >= 0 && p.isEmpty()) || (effect_diff >= 1 && !p.isEmpty() && p.owner() ==alt(Attack))) { if (Dir == UL || Dir == U || Dir == UR) result = PtypeEvalTraits::val * 3 * 16; else if (Dir == L || Dir == R) result = (PtypeEvalTraits::val * 1 + PtypeEvalTraits::val / 2) * 16; else result = PtypeEvalTraits::val * 1 * 16; if ((effect_diff > 0 && (target.canPromote() || state.hasEffectByPtype(Attack,target) || state.hasEffectByPtype(Attack,target) || state.hasEffectByPtype(Attack,target) || state.hasEffectByPtype(Attack,target))) || (p.isEmpty() && can_check_pieces[Attack][Dir] > 0)) result += PtypeEvalTraits::val * 16; } } if (Attack == BLACK) return result; else return -result; } // P is attacking player template template int osl::eval:: ProgressEvalGeneral::calculateAttackBonusEach( const NumEffectState& state) const { int result = 0; result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); result += calculateAttackBonusOne(state); return result; } template int osl::eval:: ProgressEvalGeneral::calculateSilverPenalty( const NumEffectState &state) const { int result = 0; const int bonus = PtypeEvalTraits::val / 4 * 16; for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece silver = state.pieceOf(i); if (!silver.isOnBoard() || silver.isPromoted()) continue; if (silver.square().y() >= 4 && silver.square().y() <= 6) { Square dl = Board_Table.nextSquare(silver.owner(), silver.square(), DL); Square dr = Board_Table.nextSquare(silver.owner(), silver.square(), DR); if ((!dl.isOnBoard() || state.pieceAt(dl).isOnBoardByOwner(silver.owner()) || state.hasEffectAt(alt(silver.owner()), dl)) && (!dr.isOnBoard() || state.pieceAt(dr).isOnBoardByOwner(silver.owner()) || state.hasEffectAt(alt(silver.owner()), dr))) { if (silver.owner() == BLACK) result -= bonus; else result += bonus; } } } return result; } template int osl::eval:: ProgressEvalGeneral::calculateGoldPenalty( const NumEffectState &state) const { int result = 0; const int bonus = PtypeEvalTraits::val / 4 * 16; for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece gold = state.pieceOf(i); if (!gold.isOnBoard()) continue; if (gold.square().y() >= 4 && gold.square().y() <= 6) { Square d = Board_Table.nextSquare(gold.owner(), gold.square(), D); if ((state.pieceAt(d).isOnBoardByOwner(gold.owner()) || state.hasEffectAt(alt(gold.owner()), d))) { if (gold.owner() == BLACK) result -= bonus; else result += bonus; } } } return result; } template int osl::eval:: ProgressEvalGeneral::calculateKnightCheck( const NumEffectState& state) const { return calculateKnightCheckEach(state) + calculateKnightCheckEach(state); } // P is attacking player template template int osl::eval:: ProgressEvalGeneral::calculateKnightCheckEach( const NumEffectState& state) const { const int bonus = (P == BLACK ? 1 : -1) * (PtypeEvalTraits::val * 3 + PtypeEvalTraits::val / 2) * 16; const Square king = state.kingSquare(); const Square up = king + DirectionPlayerTraits::offset(); if (!state.hasEffectAt(king) && ! state.pieceAt(up).isEdge()) { const Square ur = up + DirectionPlayerTraits::offset(); if (! state.pieceAt(ur).isEdge() && state.pieceAt(ur).isEmpty() && !state.hasEffectAt(ur) && (state.hasPieceOnStand(P) || state.hasEffectByPtype(P, ur))) { if (state.hasPieceOnStand(P)) return bonus; else return bonus / 2; } const Square ul = up + DirectionPlayerTraits::offset(); if (! state.pieceAt(ul).isEdge() && state.pieceAt(ul).isEmpty() && !state.hasEffectAt(ul) && (state.hasPieceOnStand(P) || state.hasEffectByPtype(P, ul))) { if (state.hasPieceOnStand(P)) return bonus; else return bonus / 2; } } return 0; } // P is defense player template template int osl::eval:: ProgressEvalGeneral::calculateEnterKingBonus( const NumEffectState& state) const { const Square king = state.kingSquare

(); if ((P == BLACK && king.y() > 4) || (P == WHITE && king.y() < 6)) { return 0; } // If not the last rank, check one rank above if ((P == BLACK && king.y() >= 2) || (P == WHITE && king.y() <= 8)) { const int y = P == BLACK ? king.y() - 1 : king.y() + 1; const int min_x = std::max(1, king.x() - 1); const int max_x = std::min(9, king.x() + 1); bool found_opening = false; for (int x = min_x; x <= max_x; ++x) { Square pos(x, y); Piece piece = state.pieceAt(pos); if (piece.isEmpty()) { if (!state.hasEffectAt(pos)) found_opening = true; else if (state.countEffect(P, pos) <= state.countEffect(alt(P), pos)) return 0; } else if (piece.owner() == alt(P)) { return 0; } else if (piece.owner() == P) { if (state.countEffect(P, pos) < state.countEffect(alt(P), pos)) return 0; } else abort(); } if (!found_opening) return 0; } return PtypeEvalTraits::val * 16 * sign(P) * 4; } // P is defense player template template int osl::eval:: ProgressEvalGeneral::calculateMiddleKingBonus( const NumEffectState& state) const { const Square king = state.kingSquare

(); if ((P == BLACK && king.y() >= 6 && major_pieces == 4) || (P == WHITE && king.y() <= 4 && major_pieces == 0)) { return PtypeEvalTraits::val * 2 * 16 * sign(P); } return 0; } template int osl::eval:: ProgressEvalGeneral::calculateRookRankBonus( const NumEffectState& state) const { int bonus = 0; for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece rook = state.pieceOf(i); const Player owner = rook.owner(); const int target_y = owner == BLACK ? 3 : 7; const int inbetween_y = owner == BLACK ? 4 : 6; if (rook.isOnBoard() && !rook.square().canPromote(owner)) { const Piece rank5 = state.pieceAt(Square(rook.square().x(), 5)); const Piece rank4 = state.pieceAt(Square(rook.square().x(), inbetween_y)); const Square rank3_pos(rook.square().x(), target_y); if (state.hasEffectByPtype( owner, Square(rook.square().x(), inbetween_y)) && !rank5.isOnBoardByOwner(alt(owner)) && !state.pieceAt(rank3_pos).isOnBoardByOwner(owner) && state.countEffect(alt(owner), Square(rook.square().x(), target_y)) <= 1 && state.countEffect(owner, Square(rook.square().x(), inbetween_y)) >= state.countEffect(alt(owner), Square(rook.square().x(), inbetween_y))) { if (rook.owner() == BLACK) bonus += PtypeEvalTraits::val * 2 * 16; else bonus -= PtypeEvalTraits::val * 2 * 16; } else if (((rank5.isOnBoardByOwner(owner) && rank5.ptype() == PAWN && state.hasEffectByPiece(rook, rank5.square())) || (rank4.isOnBoardByOwner(owner) && rank4.ptype() == PAWN && state.hasEffectByPiece(rook, rank4.square()))) && !state.hasEffectAt(alt(owner), rank3_pos) && state.countEffect(alt(owner), Square(rook.square().x(), inbetween_y)) <= 1) { if (rook.owner() == BLACK) bonus += PtypeEvalTraits::val * 2 * 16; else bonus -= PtypeEvalTraits::val * 2 * 16; } else if (state.hasEffectByPiece(rook, rank3_pos) && !state.hasEffectAt(alt(owner), rank3_pos) && !state.isPawnMaskSet(owner, rook.square().x())) { if (rook.owner() == BLACK) bonus += PtypeEvalTraits::val * 16; else bonus -= PtypeEvalTraits::val * 16; } } } return bonus; } template void osl::eval:: ProgressEvalGeneral::setValues(const SimpleState& state, Progress16 progress16, PieceValues& out) { PieceValues opening, endgame; const NumEffectState nstate(state); const progress_t progress(nstate); const defense_t defense_effect(nstate); const MinorPieceBonus minor_piece_bonus(state); opening_eval_t::setValues(state, opening); endgame_eval_t::setValues(state, endgame); for (int i=0; i void osl::eval:: ProgressEvalGeneral::setValues(const SimpleState& state, PieceValues& out) { const NumEffectState nstate(state); const progress_t progress(nstate); setValues(state, progress.progress16(), out); } template osl::eval::ProgressDebugInfo osl::eval:: ProgressEvalGeneral::debugInfo(const NumEffectState& state) const { ProgressDebugInfo debug_info; debug_info.eval = value(); debug_info.opening = openingValue(); debug_info.endgame = endgameValue(); debug_info.progress = current_progress.progress16().value(); debug_info.progress_bonus = attackDefenseBonus(); debug_info.progress_independent_bonus = progress_independent_bonus; debug_info.progress_dependent_bonus = progress_dependent_bonus; debug_info.minor_piece_bonus = minorPieceValue(); debug_info.black_danger = current_progress.progress16bonus(BLACK).value(); debug_info.white_danger = current_progress.progress16bonus(WHITE).value(); debug_info.black_defense = defense_effect.progress16(BLACK).value(); debug_info.white_defense = defense_effect.progress16(WHITE).value(); debug_info.mobility_bonus = calculateMobilityBonus(); debug_info.two_rook_bonus = calculateAttackRooks(state); debug_info.knight_check_bonus = calculateKnightCheck(state); debug_info.rook_rank_bonus = calculateRookRankBonus(state); debug_info.enter_king_bonus = calculateEnterKingBonus(state) + calculateEnterKingBonus(state); debug_info.middle_king_bonus = calculateMiddleKingBonus(state) + calculateMiddleKingBonus(state); debug_info.silver_penalty = calculateSilverPenalty(state); debug_info.gold_penalty = calculateGoldPenalty(state); debug_info.king8_attack_bonus = calculateAttackBonus(state); debug_info.pin_bonus = calculatePinBonus(state); debug_info.minor_piece_bonus_info = minor_piece_bonus.debugInfo(progress16(), progress16bonus(BLACK), progress16bonus(WHITE)); return debug_info; } namespace osl { namespace eval { template class ProgressEvalGeneral; } #ifndef DFPNSTATONE template void EffectUtil::findThreat(const NumEffectState& state, Square position, PtypeO ptypeo, PieceVector& out); #endif } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/eval/pieceEval.h0000644000000000000000000001015612316770314017203 0ustar rootroot/* pieceEval.h */ #ifndef OSL_PIECEEVAL_H #define OSL_PIECEEVAL_H #include "osl/eval/ptypeEval.h" #include "osl/progress.h" #include "osl/numEffectState.h" #include namespace osl { namespace eval { /** * é§’ã®ä¾¡å€¤ãƒ™ãƒ¼ã‚¹ã®è©•価関数. * å¿…ãšå¶æ•° * 先手有利 +, 後手有利 - * æ­© PtypeEvalTraits::val 点 */ class PieceEval { int val; public: explicit PieceEval(const NumEffectState& state); explicit PieceEval(int v) : val(v) {} PieceEval(); static bool initialized() { return true; } void changeTurn() {} int value() const { assert(isConsistentValueForNormalState(val)); return val; } static int infty() { return 57984; } /** * move ã«ã‚ˆã‚‹å–り返ã—値ã®å¤‰åŒ– (SOMA) * * - move 後ã®ãƒžã‚¹ã ã‘考ãˆã‚‹ * - 基本ã¯ä¾¡å€¤ã®å°ã•ã„é †ã«èª¿ã¹ã‚‹ * - 順番ã«é–¢ã—ã¦ï¼ŒPROMOTE ã®æœ‰ç„¡ã¯è€ƒãˆã¦ã„ãªã„ * - ç¾åœ¨ï¼Œé£›è»Šã‚„香ã®åˆ©ãã¯move ã®å¾Œã‚ã«ã‚ã‚‹ã‚‚ã®ã—ã‹ä¼¸ã³ãªã„ * - ?? é§’ãŒå‘³æ–¹ã®é§’を飛ã³è¶Šãˆã‚‹æ‰‹ã‚‚考ãˆã‚‹ * - 数値ã®ä¾¡å€¤ã¯ Player ã«ã¨ã£ã¦ï¼Ž * - 王手ãªã©ã¯æ°—ã«ã—ãªã„ */ template static int computeDiffAfterMove(const NumEffectState& state,Move move); static int computeDiffAfterMove(const NumEffectState& state,Move move) { assert(state.turn() == move.player()); if (state.turn() == BLACK) return computeDiffAfterMove(state,move); else return computeDiffAfterMove(state,move); } /** * 実ç¾ç¢ºçŽ‡æŽ¢ç´¢ç”¨å–り返ã—値 * * ç¾åœ¨ã®å±€é¢ã®è©•価値㨠move 後ã®å±€é¢ã®å·®åˆ†(PãŒå¾—ã™ã‚‹å ´åˆãŒæ­£ã¨ãª * るよã†ç¬¦å·ã‚’補正)ã‚’è¿”ã™ï¼Ž */ template static int computeDiffAfterMoveForRP(const NumEffectState& state,Move move) { assert(move.player()==P); const int diff = computeDiffAfterMove

(state,move); return (P==BLACK) ? diff : -diff; } static int computeDiffAfterMoveForRP(const NumEffectState& state, Move move) { if (move.player()==BLACK) return computeDiffAfterMoveForRP(state,move); else return computeDiffAfterMoveForRP(state,move); } private: void addVal(int d) { val+=d; } public: const Move suggestMove(const NumEffectState&) const { return Move(); } /** state ã§moveを指ã—ãŸå¾Œã®è©•価値を予測 */ int expect(const NumEffectState& /*state*/, Move move) const { if (move.isPass() || move.isDrop()) return value(); const PtypeO ptypeO=move.ptypeO(); const PtypeO captured=move.capturePtypeOSafe(); int result = val + Ptype_Eval_Table.value(ptypeO) - Ptype_Eval_Table.value(move.oldPtypeO()); if (getPtype(captured) != PTYPE_EMPTY) result += Ptype_Eval_Table.value(osl::captured(captured)) - Ptype_Eval_Table.value(captured); return result; } const Progress32 progress32() const { return Progress32(0); } const Progress16 progress16() const { return Progress16(0); } static int seeScale() { return 1; } /** * QuiescenceSearch ã®æžåˆˆã§ä½¿ç”¨ */ static int captureValue(PtypeO ptypeO) { return Ptype_Eval_Table.captureValue(ptypeO); } static int value(PtypeO ptypeO) { return Ptype_Eval_Table.value(ptypeO); } void update(const NumEffectState& /*new_state*/, Move last_move) { if (last_move.isPass() || last_move.isDrop()) return; addVal(Ptype_Eval_Table.value(last_move.ptypeO()) - Ptype_Eval_Table.value(last_move.oldPtypeO())); if (last_move.capturePtype() != PTYPE_EMPTY) { const PtypeO capture_ptypeo = last_move.capturePtypeO(); addVal(Ptype_Eval_Table.value(captured(capture_ptypeo)) - Ptype_Eval_Table.value(capture_ptypeo)); } } static PtypeEvalTable Piece_Value; }; } // namespace eval using eval::PieceEval; } // namespace osl #endif /* OSL_PIECEEVAL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/evalCompareLarger.h0000644000000000000000000000147012316770314020700 0ustar rootroot/* evalCompareLarger.h */ #ifndef _EVAL_COMPARE_LARGER_H #define _EVAL_COMPARE_LARGER_H #include "osl/eval/evalTraits.h" namespace osl { namespace eval { /** * 評価ã®é«˜ã„é †ã«ä¸¦ã¹ã‚‹æ¯”較 */ template struct EvalCompareLarger { bool operator()(int l, int r) const { return EvalTraits

::betterThan(l, r); } }; /** * 評価ã®é«˜ã„é †ã«ä¸¦ã¹ã‚‹æ¯”較 */ struct EvalCompareLargerNT { const Player player; EvalCompareLargerNT(Player p) : player(p) { } bool operator()(int l, int r) const { return betterThan(player, l, r); } }; } // namespace eval } // namespace osl #endif /* _EVAL_COMPARE_LARGER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/0000755000000000000000000000000012316770314016245 5ustar rootrootlibosl-0.8.0.orig/full/osl/eval/ppair/piecePairEvalBase.cc0000644000000000000000000000034312316770314022060 0ustar rootroot/* piecePairEvalBase.cc */ #include "osl/eval/ppair/piecePairEval.h" /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairIndex.h0000644000000000000000000001141012316770314021304 0ustar rootroot/* piecePairIndex.h */ #ifndef EVAL_PIECEPAIRINDEX_H #define EVAL_PIECEPAIRINDEX_H #include "osl/numEffectState.h" #include "osl/bits/squareCompressor.h" namespace osl { namespace eval { namespace ppair { /** * PiecePairEvalTable ã®æ·»å­—計算. * キャッシュã®ãƒ’ット率を上ã’ã‚‹ãŸã‚ã«ï¼Œr2246ã‹ã‚‰è¨ˆç®—を変更ã™ã‚‹ï¼Ž * r2246以é™ã§ã¯ç‰‡æ–¹ã‚ã‚‹ã„ã¯ä¸¡æ–¹ãŒSquare::STAND()ã®å ´åˆã¯ * tableã®ä¸­èº«ãŒ0ã§ã‚ã‚‹ã¨ã—ã¦ï¼Œå·®åˆ†è¨ˆç®—ã®å¯¾è±¡ã‹ã‚‰å¤–ã™ï¼Ž */ struct PiecePairIndex { static const unsigned int maxSquareIndex = 82; static const unsigned int maxPtypeOIndex = PTYPEO_SIZE; static const unsigned int maxPieceIndex = maxSquareIndex*maxPtypeOIndex; static const unsigned int maxPairIndex = maxPieceIndex*maxPieceIndex; static unsigned int selfIndexOf(unsigned int i) { return indexOf(i, i); } static unsigned int indexOf(unsigned int i1, unsigned int i2) { assert(i1 < maxPieceIndex); assert(i2 < maxPieceIndex); return i1*maxPieceIndex + i2; } static unsigned int canonicalIndexOf(unsigned int i1, unsigned int i2) { if (i1 > i2) std::swap(i1,i2); return indexOf(i1,i2); } /** é€†å¤‰æ› */ static void meltIndex(size_t index, size_t& i1, size_t& i2) { i1 = index / maxPieceIndex; i2 = index % maxPieceIndex; } static unsigned int positionIndexOf(Square pos) { unsigned int result = SquareCompressor::compress(pos); assert(result < maxSquareIndex); return result; } static unsigned int ptypeOIndexOf(PtypeO ptypeo) { return ptypeo - PTYPEO_MIN; } static unsigned int indexOf(Square pos, PtypeO ptypeo) { const int result = maxSquareIndex*ptypeOIndexOf(ptypeo) + positionIndexOf(pos); return result; } /** é€†å¤‰æ› */ static void meltIndex(size_t index, Square& pos, PtypeO& ptypeo) { ptypeo = static_cast(static_cast(index / maxSquareIndex)+PTYPEO_MIN); pos = SquareCompressor::melt(index % maxSquareIndex); } static unsigned int indexOf(Piece piece) { return indexOf(piece.square(), piece.ptypeO()); } static unsigned int indexOf(Piece p1, Piece p2) { return indexOf(indexOf(p1), indexOf(p2)); } static unsigned int indexOfPieceNum(const SimpleState& s, int id) { return indexOf(s.pieceOf(id)); } /** å…¨ã¦ã®é–¢ä¿‚ã«ã¤ã„ã¦fを実行ã™ã‚‹ï¼Žé‡è¤‡ã™ã‚‹é–¢ä¿‚ã¯è¨ªã‚Œãªã„ */ template static void forEachRelation(F f); }; } // namespace ppair using ppair::PiecePairIndex; } // namespace eval } // namespace osl template void osl::eval::ppair:: PiecePairIndex::forEachRelation(F f) { for (int x=1; x<=9; ++x) { for (int y=1; y<=9; ++y) { const Square pos1(x,y); for (int ptype=PPAWN; ptype<=PTYPE_MAX; ++ptype) { const Ptype p1 = static_cast(ptype); const unsigned int i1 = indexOf(pos1, newPtypeO(BLACK, p1)); const unsigned int i1w = indexOf(pos1, newPtypeO(WHITE, p1)); f(indexOf(i1,i1)); f(indexOf(i1w,i1w)); for (int x2=x; x2<=9; ++x2) { for (int y2=((x2 == x) ? y+1 : 1); y2<=9; ++y2) { const Square pos2(x2,y2); for (int ptype2=PPAWN; ptype2<=PTYPE_MAX; ++ptype2) { const Ptype p2 = static_cast(ptype2); const unsigned int i2 = indexOf(pos2, newPtypeO(BLACK, p2)); const unsigned int i2w = indexOf(pos2, newPtypeO(WHITE, p2)); f(indexOf(i1, i2)); f(indexOf(i1, i2w)); f(indexOf(i1w, i2)); f(indexOf(i1w, i2w)); } } } for (int ptype2=KING; ptype2<=PTYPE_MAX; ++ptype2) { const Ptype p2 = static_cast(ptype2); const unsigned int i2 = indexOf(Square::STAND(), newPtypeO(BLACK, p2)); const unsigned int i2w = indexOf(Square::STAND(), newPtypeO(WHITE, p2)); f(indexOf(i1, i2)); f(indexOf(i1, i2w)); f(indexOf(i1w, i2)); f(indexOf(i1w, i2w)); } } // ptype } // x } // y // æŒé§’åŒå£«ã¯æœ€å¾Œã« for (int ptype=KING; ptype<=PTYPE_MAX; ++ptype) { const Ptype p1 = static_cast(ptype); const unsigned int i1 = indexOf(Square::STAND(), newPtypeO(BLACK, p1)); const unsigned int i1w = indexOf(Square::STAND(), newPtypeO(WHITE, p1)); f(indexOf(i1, i1)); f(indexOf(i1, i1w)); f(indexOf(i1w, i1w)); for (int ptype2=ptype+1; ptype2<=PTYPE_MAX; ++ptype2) { const Ptype p2 = static_cast(ptype2); const unsigned int i2 = indexOf(Square::STAND(), newPtypeO(BLACK, p2)); const unsigned int i2w = indexOf(Square::STAND(), newPtypeO(WHITE, p2)); f(indexOf(i1, i2)); f(indexOf(i1, i2w)); f(indexOf(i1w, i2)); f(indexOf(i1w, i2w)); } } } #endif /* EVAL_PIECEPAIRINDEX_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairWithStand.h0000644000000000000000000000620712316770314022152 0ustar rootroot/* piecePairWithStand.h */ #ifndef EVAL_PPAIR_PIECEPAIRWITHSTAND_H #define EVAL_PPAIR_PIECEPAIRWITHSTAND_H #include "osl/eval/ppair/piecePairEval.h" #include "osl/eval/pieceEval.h" namespace osl { namespace eval { namespace ppair { /** * æŒé§’ã®ç‚¹æ•°ã¯è¡¨ä»¥å¤–ã§ç®¡ç†ã™ã‚‹ãƒ•レームワーク. * * (æŒé§’ã®ç‚¹æ•°ã‚’è¡¨ã«æ›¸ã込むã¨ï¼ŒåŒã˜ç¨®é¡žã®é§’を複数もã£ã¦ã„ã‚‹ã¨å• * 題ãŒèµ·ã“ã‚‹ãŸã‚) * => ãã®å¾Œç›¤ä¸Šã®é§’ã‚‚ç®¡ç† (点数を変更å¯èƒ½ã«ã™ã‚‹ãŸã‚) */ template class PiecePairWithStand : public PiecePairEval,Table> { public: static int standBonus(PtypeO ptypeo) { assert(isBasic(getPtype(ptypeo))); if (isMajorBasic(getPtype(ptypeo))) return Table::Piece_Value.value(newPtypeO(getOwner(ptypeo), PAWN)); return 0; } static int standBonus(const SimpleState& state); typedef PiecePairEval, Table> base_t; explicit PiecePairWithStand(const SimpleState& state); protected: ~PiecePairWithStand() {} public: static int diffAfterDropMove(const SimpleState& state,Square to,PtypeO ptypeo) { const int bonus = standBonus(ptypeo); return base_t::diffAfterDropMove(state,to,ptypeo) - bonus; } static int diffAfterSimpleMove(const SimpleState& state, Square from, Square to, int promote_mask) { int diff = base_t::diffAfterSimpleMove(state, from, to, promote_mask); if (promote_mask) { const Piece old_piece=state.pieceAt(from); const PtypeO newPtypeO = promoteWithMask(old_piece.ptypeO(), promote_mask); diff += Table::Piece_Value.promoteValue(newPtypeO); } return diff; } static int diffAfterCaptureMove(const SimpleState& state, Square from, Square to, PtypeO victim,int promote_mask) { const PtypeO captured = osl::captured(victim); int bonus = standBonus(captured); if (promote_mask) { const Piece old_piece=state.pieceAt(from); const PtypeO newPtypeO = promoteWithMask(old_piece.ptypeO(), promote_mask); bonus += Table::Piece_Value.promoteValue(newPtypeO); } return base_t::diffAfterCaptureMove(state,from,to,victim,promote_mask) + Table::Piece_Value.captureValue(victim) + bonus; } static int diffWithUpdate(const SimpleState& new_state, Move last_move) { int diff = base_t::diffWithUpdate(new_state, last_move); if (last_move.isDrop()) { const int bonus = standBonus(last_move.ptypeO()); return diff - bonus; } if (last_move.isPromotion()) diff += Table::Piece_Value.promoteValue(last_move.ptypeO()); if (last_move.capturePtype() != PTYPE_EMPTY) { const PtypeO captured = last_move.capturePtypeO(); const int bonus = standBonus(osl::captured(captured)); diff += Table::Piece_Value.captureValue(captured) + bonus; } return diff; } static void setValues(const SimpleState&, container::PieceValues&); }; } // namespace ppair } // namespace eval } // namespace osl #endif /* EVAL_PPAIR_PIECEPAIRWITHSTAND_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairEval.h0000644000000000000000000001412612316770314021133 0ustar rootroot/* piecePairEval.h */ #ifndef _PIECE_PAIR_EVAL_H #define _PIECE_PAIR_EVAL_H #include "osl/eval/ppair/piecePairIndex.h" #include "osl/eval/pieceEval.h" #include "osl/eval/evalTraits.h" #include namespace osl { namespace container { class PieceValues; } // container namespace eval { namespace ppair { /** * PiecePairEval ã®ï¼Œtemplate parameterã«ä¾å­˜ã—ãªã„部分㮠* 共通ã®å®Ÿè£…. */ class PiecePairEvalBase { protected: int val; PiecePairEvalBase() : val(0) { } ~PiecePairEvalBase() { } public: /** roundup 㯠2^n ã§ã‚ã‚‹ã“㨠*/ static const int ROUND_UP = 2; static int roundUp(int v) { return v & (~(ROUND_UP-1)); } int value() const { return roundUp(val); } int rawValue() const { return val; } static int infty() { // ProgressEval ã§è¶³ã—ã¦ã‚‚overflowã—ãªã„値ã«ã™ã‚‹ // PieceEval::infty() + 100*40*39/2 return 150000; } static int captureValue(PtypeO ptypeo) { return PieceEval::captureValue(ptypeo); } }; template class PiecePairEvalTableBase : public PiecePairEvalBase { protected: // å¿…ãšç¶™æ‰¿ã—ã¦ä½¿ã† explicit PiecePairEvalTableBase(const SimpleState& state); ~PiecePairEvalTableBase() {} public: /** * 駒㌠old_index ã‹ã‚‰ new_index ã«å‹•ã„ãŸã¨ãã®å€¤ã®å·®åˆ† * @param state å‹•ãå‰ã®å±€é¢ * @param old_index é§’+移動元 * @param new_index é§’+移動先 */ static int adjustPairs(const SimpleState& state, unsigned int new_index); static int adjustPairs(const SimpleState& state, unsigned int old_index, unsigned int new_index); static int adjustPairs(const SimpleState& state, unsigned int old_index, unsigned int old_index2, unsigned int new_index); static int diffAfterSimpleMove(const SimpleState& state, Square from, Square to, int promote_mask) { const Piece old_piece=state.pieceAt(from); const PtypeO newPtypeO = promoteWithMask(old_piece.ptypeO(), promote_mask); const unsigned int old_index = PiecePairIndex::indexOf(old_piece); const unsigned int new_index = PiecePairIndex::indexOf(to, newPtypeO); return adjustPairs(state, old_index, new_index); } static int diffAfterDropMove(const SimpleState& state,Square to,PtypeO ptypeo) { const unsigned int new_index = PiecePairIndex::indexOf(to, ptypeo); return adjustPairs(state, new_index); } static int diffAfterCaptureMove(const SimpleState& state, Square from, Square to, PtypeO victim,int promote_mask) { const Piece old_piece=state.pieceAt(from); const PtypeO newPtypeO = promoteWithMask(old_piece.ptypeO(), promote_mask); const unsigned int old_index = PiecePairIndex::indexOf(old_piece); const unsigned int new_index = PiecePairIndex::indexOf(to, newPtypeO); const unsigned int indexVictim = PiecePairIndex::indexOf(to, victim); return adjustPairs(state, old_index, indexVictim, new_index); } /** ã“ã®æ™‚ state 㯠move ã—ãŸå¾Œ */ static int adjustPairsAfterMove(const SimpleState& state, unsigned int new_index); static int adjustPairsAfterMove(const SimpleState& state, unsigned int old_index, unsigned int new_index); static int adjustPairsAfterMove(const SimpleState& state, unsigned int old_index, unsigned int old_index2, unsigned int new_index); static int diffWithUpdate(const SimpleState& new_state, Move last_move) { const unsigned int new_index = PiecePairIndex::indexOf(last_move.to(), last_move.ptypeO()); if (last_move.isDrop()) return adjustPairsAfterMove(new_state, new_index); const unsigned int old_index = PiecePairIndex::indexOf(last_move.from(), last_move.oldPtypeO()); if (last_move.capturePtype() == PTYPE_EMPTY) return adjustPairsAfterMove(new_state, old_index, new_index); const unsigned int index_victim = PiecePairIndex::indexOf(last_move.to(), last_move.capturePtypeO()); return adjustPairsAfterMove(new_state, old_index, index_victim, new_index); } /** * 関係ã®å€¤ã‚’Piece 毎ã®ä¾¡å€¤ã«å¤‰æ›ã™ã‚‹. * - é§’Aã®ä¾¡å€¤ã¯ r(A,A) + \sum_B(r(A+B)/2) * - 但ã—,A,Bã®ã©ã¡ã‚‰ã‹(ã®ã¿)çŽ‰ã®æ™‚ã«ã¯ï¼Œçމã§ãªã„æ–¹ã«é–¢ä¿‚ã®ç‚¹æ•°ã‚’集ã‚ã‚‹ */ static void setValues(const SimpleState&, container::PieceValues&); private: static bool& initializationFlag(); public: static bool initialized() { return initializationFlag(); } // read only static bool setUp(const char *filename); static bool setUp(); }; /** * é§’ã®ãƒšã‚¢ã®çµ±è¨ˆæƒ…報を元ã«ã—ãŸè©•価関数ã®å…±é€šéƒ¨åˆ†. * - å¿…ãšå¶æ•° * - 先手有利 +, 後手有利 - * @param Table PiecePairTable ã®ã©ã‚Œã‹ã®instatiationを想定 */ template class PiecePairEval : public PiecePairEvalTableBase { protected: // å¿…ãšç¶™æ‰¿ã—ã¦ä½¿ã† explicit PiecePairEval(const SimpleState& state); public: typedef PiecePairEvalTableBase
base_t; void changeTurn() {} /** ã“ã®æ™‚ state 㯠move ã™ã‚‹å‰ */ int expect(const SimpleState& state, Move m) const; /** ã“ã®æ™‚ state 㯠move ã—ãŸå¾Œ */ void update(const SimpleState& new_state, Move last_move) { base_t::val += Eval::diffWithUpdate(new_state, last_move); } static int diffWithMove(const SimpleState& state, Move move) { // TRICK: Eval::diffXXX ã¨ã™ã‚‹ã“ã¨ã§subclassã«ã‚ˆã‚‹overrideã‚’å¯èƒ½ã«ã™ã‚‹ const Square from=move.from(); const Square to=move.to(); if (from.isPieceStand()) return Eval::diffAfterDropMove(state, to, move.ptypeO()); const Ptype ptypeCaptured=move.capturePtype(); if (ptypeCaptured != PTYPE_EMPTY) return Eval::diffAfterCaptureMove(state, from, to, newPtypeO(alt(move.player()), ptypeCaptured), move.promoteMask()); return Eval::diffAfterSimpleMove(state, from,to,move.promoteMask()); } }; } // namespace ppair } // namespace eval } // namespace osl #endif /* _PIECE_PAIR_EVAL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairWithStand.tcc0000644000000000000000000000276412316770314022500 0ustar rootroot/* piecePairWithStand.tcc */ #ifndef EVAL_PPAIR_PIECEPAIRWITHSTAND_TCC #define EVAL_PPAIR_PIECEPAIRWITHSTAND_TCC #include "osl/eval/ppair/piecePairWithStand.h" #include "osl/container/pieceValues.h" template void osl::eval::ppair::PiecePairWithStand
:: setValues(const SimpleState& state, container::PieceValues& values) { base_t::setValues(state, values); // 速度ã¯ç„¡è¦– for (int i=0; i int osl::eval::ppair::PiecePairWithStand
:: standBonus(const SimpleState& state) { int result = 0; for (int i=0; i osl::eval::ppair::PiecePairWithStand
:: PiecePairWithStand(const SimpleState& state) : base_t(state) { for (int i=0; i #ifdef PIECE_PAIR_EXTRA_DEBUG # define piece_pair_assert(x) assert(x) #else # define piece_pair_assert(x) #endif #endif /* EVAL_PPAIR_PIECEPAIRASSERT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairEval.tcc0000644000000000000000000001626412316770314021462 0ustar rootroot/* piecePairEval.tcc */ #ifndef EVAL_PIECE_PAIR_EVAL_TCC #define EVAL_PIECE_PAIR_EVAL_TCC #include "osl/eval/ppair/piecePairEval.h" #include "osl/eval/ppair/piecePairAssert.h" #include "osl/container/pieceValues.h" #include "osl/bits/pieceTable.h" #include "osl/oslConfig.h" template osl::eval::ppair:: PiecePairEvalTableBase
::PiecePairEvalTableBase(const SimpleState& state) { for (int i=0; i bool& osl::eval::ppair:: PiecePairEvalTableBase
::initializationFlag() { static bool flag = false; return flag; } template bool osl::eval::ppair:: PiecePairEvalTableBase
::setUp(const char *filename) { bool& result = initializationFlag(); result = Table::Table.setUp(filename); return result; } template bool osl::eval::ppair:: PiecePairEvalTableBase
::setUp() { std::string filename = OslConfig::home(); filename += "/data/sibling-attack.pair"; return setUp(filename.c_str()); } template int osl::eval::ppair::PiecePairEvalTableBase
:: adjustPairs(const SimpleState& state, unsigned int new_index) { int diff = 0; for (int i=0; i int osl::eval::ppair::PiecePairEvalTableBase
:: adjustPairs(const SimpleState& state, unsigned int old_index, unsigned int new_index) { int diff = 0; for (int i=0; i int osl::eval::ppair::PiecePairEvalTableBase
:: adjustPairs(const SimpleState& state, unsigned int old_index, unsigned int old_index2, unsigned int new_index) { int diff = 0; for (int i=0;i int osl::eval::ppair::PiecePairEvalTableBase
:: adjustPairsAfterMove(const SimpleState& state, unsigned int new_index) { int diff = 0; for (int i=0; i int osl::eval::ppair::PiecePairEvalTableBase
:: adjustPairsAfterMove(const SimpleState& state, unsigned int old_index, unsigned int new_index) { int diff = 0; for (int i=0; i int osl::eval::ppair::PiecePairEvalTableBase
:: adjustPairsAfterMove(const SimpleState& state, unsigned int old_index, unsigned int old_index2, unsigned int new_index) { int diff = 0; for (int i=0;i void osl::eval::ppair::PiecePairEvalTableBase
:: setValues(const SimpleState& state, container::PieceValues& values) { values.fill(0); // 速度ã¯ç„¡è¦– for (int i=0; i osl::eval::ppair:: PiecePairEval::PiecePairEval(const SimpleState& state) : PiecePairEvalTableBase
(state) { } template int osl::eval::ppair::PiecePairEval:: expect(const SimpleState& state, Move m) const { const Ptype ptype = m.ptype(); const Square to = m.to(); const Player player = state.turn(); if (m.isDrop()) { piece_pair_assert(state.pieceAt(to) == Piece::EMPTY()); return this->roundUp(this->val + Eval::diffAfterDropMove(state, to, newPtypeO(player, ptype))); } const Square from = m.from(); piece_pair_assert(state.pieceAt(from) != Piece::EMPTY()); if (m.capturePtype() == PTYPE_EMPTY) { piece_pair_assert(state.pieceAt(to) == Piece::EMPTY()); return this->roundUp(this->val + Eval::diffAfterSimpleMove(state, from, to, m.promoteMask())); } piece_pair_assert(state.pieceAt(to) != Piece::EMPTY()); return this->roundUp(this->val + Eval::diffAfterCaptureMove(state, from, to, m.capturePtypeO(), m.promoteMask())); } #endif /* EVAL_PIECE_PAIR_EVAL_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairRawTable.cc0000644000000000000000000000756712316770314022116 0ustar rootroot/* piecePairRawTable.cc */ #include "osl/eval/ppair/piecePairRawEval.h" #include "osl/eval/ppair/piecePairEval.tcc" #include "osl/oslConfig.h" #include #ifdef __MINGW32__ # include #endif #include #include #include #include osl::eval::ppair::PiecePairRawTable osl::eval::ppair::PiecePairRawTable::Table; namespace osl { namespace eval { namespace ppair { static_assert(PiecePairIndex::maxPtypeOIndex == 32, ""); // roundup ㌠2^n ã‹ã¤ 2 以上ã§ã‚ã‚‹ã“ã¨ã®ç¢ºèª static_assert((PiecePairEvalBase::ROUND_UP & (PiecePairEvalBase::ROUND_UP-1)) == 0, ""); static_assert(PiecePairEvalBase::ROUND_UP >= 2, ""); template class PiecePairEvalTableBase; template class PiecePairEval; } // namespace ppair } // namespace eval } // namespace osl osl::eval::ppair:: PiecePairRawTable::PiecePairRawTable() { } osl::eval::ppair:: PiecePairRawTable::~PiecePairRawTable() { } void osl::eval::ppair:: PiecePairRawTable::writeInBinaryFile(const char *filename) const { std::ofstream os(filename); std::vector buffer(82*PTYPEO_SIZE*82*PTYPEO_SIZE); for(int i=0;i<82;i++){ Square pos0=SquareCompressor::melt(i); for(int j=0;j<82;j++){ Square pos1=SquareCompressor::melt(j); for(int k=0;k(k+PTYPEO_MIN)); int index1=PiecePairIndex::indexOf(pos1,static_cast(l+PTYPEO_MIN)); int index=PiecePairIndex::indexOf(index0,index1); buffer[(i*32+k)*82*32+(j*32+l)]=values[index]; } } } os.write(reinterpret_cast(&*buffer.begin()),buffer.size()); } bool osl::eval::ppair:: PiecePairRawTable:: loadFromBinaryFile(const char *filename) const { if (OslConfig::verbose()) std::cerr << "PiecePairRawTable loading... " << filename << "\n"; #ifdef __MINGW32__ namespace bf = boost::filesystem; bf::path filename_path(filename); bf::ifstream is(filename_path, std::ios_base::in | std::ios_base::binary); is.exceptions(std::ios_base::badbit | std::ios_base::failbit); // Workaround a bug of MINGW. std::vector temp_buffer(82*PTYPEO_SIZE); is.rdbuf()->pubsetbuf(reinterpret_cast(&*temp_buffer.begin()), temp_buffer.size()); #else std::ifstream is(filename); #endif std::vector buffer(82*PTYPEO_SIZE*82*PTYPEO_SIZE); is.read(reinterpret_cast(&*buffer.begin()), buffer.size()); for(int i=0;i<82;i++){ Square pos0=SquareCompressor::melt(i); for(int j=0;j<82;j++){ Square pos1=SquareCompressor::melt(j); for(int k=0;k(k+PTYPEO_MIN)); int index1=PiecePairIndex::indexOf(pos1,static_cast(l+PTYPEO_MIN)); int index=PiecePairIndex::indexOf(index0,index1); if(!pos0.isPieceStand() && !pos1.isPieceStand()) values[index]=buffer[(i*32+k)*82*32+(j*32+l)]; else values[index]=0; } } } if (! is) return false; if (OslConfig::verbose()) std::cerr << "done.\n"; return true; } bool osl::eval::ppair:: PiecePairRawTable:: setUp(const char *filename) const { static std::string filename_memory; if (! filename_memory.empty()) { if (filename_memory != filename) { std::cerr << "PiecePairRawTable: don't load " << filename << ", since " << filename_memory << " already loaded \n"; return false; } return true; } filename_memory = filename; return loadFromBinaryFile(filename); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairPieceTable.cc0000644000000000000000000001142212316770314022373 0ustar rootroot/* piecePairPieceTable.cc */ #include "osl/eval/ppair/piecePairPieceEval.h" #include "osl/eval/ppair/piecePairRawEval.h" #include "osl/eval/ppair/piecePairEval.tcc" #include "osl/eval/ppair/piecePairWithStand.tcc" #include "osl/eval/pieceEval.h" osl::eval::ppair::PiecePairPieceTable osl::eval::ppair::PiecePairPieceTable::Table; osl::eval::PtypeEvalTable osl::eval::ppair::PiecePairPieceTable::Piece_Value; static osl::SetUpRegister _initializer([](){ // The parent, PtypeEvalTable's constructor has initialized before main. // However, due to the initialization order problem outside tables.cc // the initilized value may be zero. osl::eval::ppair::PiecePairPieceTable::Piece_Value.init(); }); namespace osl { namespace eval { namespace ppair { template class PiecePairEvalTableBase; template class PiecePairEval,PiecePairPieceTable>; template class PiecePairWithStand; } // namespace ppair } // namespace eval } // namespace osl osl::eval::ppair:: PiecePairPieceTable::~PiecePairPieceTable() { } bool osl::eval::ppair:: PiecePairPieceTable:: setUp(const char *filename) const { if (! PiecePairRawEval::setUp(filename)) return false; for (unsigned int i=0; i(p); if (! isPiece(ptypeo)) continue; const unsigned int index = indexOf(position, ptypeo); values[indexOf(index, index)] += Ptype_Eval_Table.value(ptypeo); } } } // for gold, silver static const CArray gold_silver = {{ GOLD, SILVER }}; for (size_t i=0; i(p); if (! isPiece(ptypeo)) continue; const unsigned int index = indexOf(position, ptypeo); values[indexOf(index, index)] -= Ptype_Eval_Table.value(ptypeo); } } } return true; } void osl::eval::ppair:: PiecePairPieceEval::resetWeights(const int *w) { CArray values; std::copy(w, w+(int)PTYPE_SIZE, values.begin()); PiecePairPieceTable::Piece_Value.reset(values); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairRawEval.h0000644000000000000000000000327312316770314021606 0ustar rootroot/* piecePairRawEval.h */ #ifndef EVAL_PPAIR_PIECEPAIRRAWEVAL_H #define EVAL_PPAIR_PIECEPAIRRAWEVAL_H #include "osl/eval/ppair/piecePairEval.h" #include "osl/eval/ppair/piecePairTable.h" namespace osl { namespace eval { namespace ppair { class PiecePairRawTable : public PiecePairTable { public: PiecePairRawTable(); ~PiecePairRawTable(); /** * 一度ã ã‘読ã¿è¾¼ã‚€ * @return successful load */ bool setUp(const char *filename) const; /** * ãƒã‚¤ãƒŠãƒªãƒ•ァイルã‹ã‚‰èª­ã¿è¾¼ã‚€. * r2246以é™ã§ã¯ãƒ•ァイルイメージã¨ãƒ¡ãƒ¢ãƒªã‚¤ãƒ¡ãƒ¼ã‚¸ã¨ã¯ï¼ŒPiecePairIndex * ãŒé•ã†ã®ã§ï¼Œå¤‰æ›ãŒå¿…è¦. * @return successful load */ bool loadFromBinaryFile(const char *filename) const; /** * ãƒã‚¤ãƒŠãƒªãƒ•ã‚¡ã‚¤ãƒ«ã«æ›¸ã出ã™. * r2246以é™ã§ã¯ãƒ•ァイルイメージã¨ãƒ¡ãƒ¢ãƒªã‚¤ãƒ¡ãƒ¼ã‚¸ã¨ã¯ï¼ŒPiecePairIndex * ãŒé•ã†ã®ã§ï¼Œå¤‰æ›ãŒå¿…è¦. * @return successful load */ void writeInBinaryFile(const char *filename) const; /** user must initialize this before use */ static PiecePairRawTable Table; }; /** * 関係ã®ä¾¡å€¤ã¯[-127,127]点ã®è©•価関数. */ class PiecePairRawEval : public PiecePairEval { public: typedef PiecePairEval base_t; explicit PiecePairRawEval(const SimpleState& state) : base_t(state) { } }; } // namespace ppair using ppair::PiecePairRawTable; using ppair::PiecePairRawEval; } // namespace eval } // namespace osl #endif /* EVAL_PPAIR_PIECEPAIRRAWEVAL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairPieceEval.h0000644000000000000000000000254612316770314022104 0ustar rootroot/* piecePairPieceEval.h */ #ifndef EVAL_PPAIR_PIECEPAIRPIECEEVAL_H #define EVAL_PPAIR_PIECEPAIRPIECEEVAL_H #include "osl/eval/ppair/piecePairWithStand.h" #include "osl/eval/ppair/piecePairTable.h" namespace osl { namespace eval { namespace ppair { class PiecePairPieceTable : public PiecePairTable { public: ~PiecePairPieceTable(); /** * @return successful load * @param filename PiecePairRawTable 用ã®ãƒ•ァイル */ bool setUp(const char *filename) const; /** user must initialize this before use */ static PiecePairPieceTable Table; static PtypeEvalTable Piece_Value; }; /** * 評価関数: PiecePairRawEval + PieceEval ã®ç‚¹æ•°ã‚’加ãˆãŸã‚‚ã® */ class PiecePairPieceEval : public PiecePairWithStand { public: typedef PiecePairWithStand base_t; explicit PiecePairPieceEval(const SimpleState& state) : base_t(state) { } static int adjustableDimension() { return PTYPE_SIZE; } static void resetWeights(const int *w); }; } // namespace ppair using ppair::PiecePairPieceTable; using ppair::PiecePairPieceEval; } // namespace eval } // namespace osl #endif /* EVAL_PPAIR_PIECEPAIRPIECEEVAL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/eval/ppair/piecePairTable.h0000644000000000000000000000301712316770314021270 0ustar rootroot/* piecePairTable.h */ #ifndef EVAL_PPAIR_PIECEPAIRTABLE_H #define EVAL_PPAIR_PIECEPAIRTABLE_H #include "osl/eval/ppair/piecePairIndex.h" namespace osl { namespace eval { namespace ppair { /** * é§’ã®é–¢ä¿‚毎ã®è©•価値を格ç´ã—ãŸè¡¨. * [Square*(Player*Ptype==PtypeO)] ^2 * * @param T signed 㪠char, int ãªã©ãŒæƒ³å®šã•れã¦ã„ã‚‹ */ template class PiecePairTable : public PiecePairIndex { public: typedef T value_type; protected: /** * const object ã«å¯¾ã—ã¦ï¼Œãƒ‡ãƒ¼ã‚¿ã®å¤‰æ›´ã¯ä¸å¯ï¼Œèª­ã¿è¾¼ã¿ã¯è¨±å¯ã™ã‚‹ãŸã‚ã« * mutable ã«ã™ã‚‹ï¼Ž */ mutable CArray values; PiecePairTable() { values.fill(); } ~PiecePairTable() {} public: int value(unsigned int i) const { return values[i]; } value_type& valueOf(unsigned int i1, unsigned int i2) { const unsigned int index = indexOf(i1,i2); return values[index]; } value_type& valueOf(Piece p1, Piece p2) { const unsigned int index = indexOf(p1,p2); return values[index]; } int valueOf(unsigned int i1, unsigned int i2) const { const unsigned int index = indexOf(i1,i2); return values[index]; } int valueOf(Piece p1, Piece p2) const { const unsigned int index = indexOf(p1,p2); return values[index]; } }; } // namespace ppair } // namespace eval } // namespace osl #endif /* EVAL_PPAIR_PIECEPAIRTABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/minorPieceBonus.h0000644000000000000000000001646012316770314020413 0ustar rootroot/* minorPieceBonus.h */ #ifndef EVAL_MINORPIECEBONUS_H #define EVAL_MINORPIECEBONUS_H #include "osl/eval/pieceEval.h" #include "osl/progress.h" namespace osl { namespace eval { struct MinorPieceDebugInfo { int pawn_bonus, lance_bonus, knight_bonus, gold_bonus; }; /** * 歩切れãªã©ã®è©•価 */ class MinorPieceBonus { CArray pawn_on_stand; CArray lance_on_stand; CArray knight_on_stand; CArray pawns; CArray golds; private: int pawnBonus(Progress16 progress16) const { const int black_pawn = pawn_on_stand[BLACK]; const int white_pawn = pawn_on_stand[WHITE]; const int black_pawn_total = pawns[BLACK]; const int white_pawn_total = pawns[WHITE]; int result = 0; if (black_pawn > 1) { result -= (black_pawn - 1) * progress16.value() * PtypeEvalTraits::val / 32; } else if (black_pawn == 0 && black_pawn_total < white_pawn_total) { result -= PtypeEvalTraits::val / 2; } if (black_pawn >= 9) { result -= (black_pawn - 8) * progress16.value() * PtypeEvalTraits::val / 8; } if (white_pawn > 1) { result += (white_pawn - 1) * progress16.value() * PtypeEvalTraits::val / 32; } else if (white_pawn == 0 && white_pawn_total < black_pawn_total) { result += PtypeEvalTraits::val / 2; } if (white_pawn >= 9) { result += (white_pawn - 8) * progress16.value() * PtypeEvalTraits::val / 8; } return result; } int lanceBonus(Progress16 progress16) const { const int black_lance = lance_on_stand[BLACK]; const int white_lance = lance_on_stand[WHITE]; int result = 0; if (black_lance > 1) { result -= (black_lance - 1) * progress16.value() * PtypeEvalTraits::val / 32; } if (black_lance > 2) { result -= (black_lance - 2) * progress16.value() * PtypeEvalTraits::val / 24; } if (white_lance > 1) { result += (white_lance - 1) * progress16.value() * PtypeEvalTraits::val / 32; } if (white_lance > 2) { result += (white_lance - 2) * progress16.value() * PtypeEvalTraits::val / 24; } return result; } int knightBonus(Progress16 progress16) const { const int black_knight = knight_on_stand[BLACK]; const int white_knight = knight_on_stand[WHITE]; int result = 0; if (black_knight > 1) { result -= (black_knight - 1) * progress16.value() * PtypeEvalTraits::val / 32; } if (black_knight > 2) { result -= (black_knight - 2) * progress16.value() * PtypeEvalTraits::val / 8; } if (white_knight > 1) { result += (white_knight - 1) * progress16.value() * PtypeEvalTraits::val / 32; } if (white_knight > 2) { result += (white_knight - 2) * progress16.value() * PtypeEvalTraits::val / 8; } return result; } int goldBonus(Progress16 black, Progress16 white) const { const int black_gold = golds[BLACK]; const int white_gold = golds[WHITE]; if (black_gold >= 3) { return white.value() * PtypeEvalTraits::val * (black_gold - 2); } else if (white_gold >= 3) { return -black.value() * PtypeEvalTraits::val * (white_gold - 2); } return 0; } public: MinorPieceBonus(const SimpleState& state) { pawn_on_stand[BLACK] = state.countPiecesOnStand(BLACK, PAWN); pawn_on_stand[WHITE] = state.countPiecesOnStand(WHITE, PAWN); lance_on_stand[BLACK] = state.countPiecesOnStand(BLACK, LANCE); lance_on_stand[WHITE] = state.countPiecesOnStand(WHITE, LANCE); knight_on_stand[BLACK] = state.countPiecesOnStand(BLACK, KNIGHT); knight_on_stand[WHITE] = state.countPiecesOnStand(WHITE, KNIGHT); pawns[BLACK] = 0; pawns[WHITE] = 0; golds[BLACK] = 0; golds[WHITE] = 0; for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; i++) { const Piece pawn = state.pieceOf(i); if (pawn.owner() == BLACK) pawns[BLACK]++; else pawns[WHITE]++; } for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; i++) { const Piece gold = state.pieceOf(i); golds[gold.owner()]++; } } int value(Progress16 progress16, Progress16 black, Progress16 white) const { return pawnBonus(progress16) + lanceBonus(progress16) + knightBonus(progress16) + goldBonus(black, white); } void update(const SimpleState& /*new_state*/, Move last_move) { const Player player = last_move.player(); const Ptype ptype = last_move.ptype(); if (last_move.isDrop()) { if (ptype == PAWN) { pawn_on_stand[player]--; assert(pawn_on_stand[BLACK] >= 0); assert(pawn_on_stand[WHITE] >= 0); } if (ptype == LANCE) { lance_on_stand[player]--; } if (ptype == KNIGHT) { knight_on_stand[player]--; } return; } const Ptype captured = last_move.capturePtype(); if (captured != PTYPE_EMPTY) { switch (unpromote(captured)) { case PAWN: pawn_on_stand[player]++; pawns[player]++; pawns[alt(player)]--; assert(pawns[BLACK] + pawns[WHITE] == 18); assert(pawn_on_stand[BLACK] >= 0); assert(pawn_on_stand[WHITE] >= 0); break; case LANCE: lance_on_stand[player]++; break; case KNIGHT: knight_on_stand[player]++; break; case GOLD: golds[player]++; golds[alt(player)]--; assert(golds[BLACK] + golds[WHITE] == 4); break; default: ; } } } int expect(const SimpleState& state, Move move, Progress16 progress16, Progress16 black, Progress16 white) const { MinorPieceBonus new_eval = *this; if (move.isDrop()){ const Ptype ptype = move.ptype(); if (ptype == PAWN) { new_eval.pawn_on_stand[state.turn()]--; assert(new_eval.pawn_on_stand[BLACK] >= 0); assert(new_eval.pawn_on_stand[WHITE] >= 0); } else if (ptype == LANCE) { new_eval.lance_on_stand[state.turn()]--; } else if (ptype == KNIGHT) { new_eval.knight_on_stand[state.turn()]--; } return new_eval.value(progress16, black, white); } Ptype ptype = move.capturePtype(); if (ptype != PTYPE_EMPTY) { if (unpromote(ptype) == PAWN) { new_eval.pawn_on_stand[state.turn()]++; new_eval.pawns[state.turn()]++; new_eval.pawns[alt(state.turn())]--; assert(new_eval.pawns[BLACK] + new_eval.pawns[WHITE] == 18); assert(new_eval.pawn_on_stand[BLACK] >= 0); assert(new_eval.pawn_on_stand[WHITE] >= 0); } else if (unpromote(ptype) == LANCE) { new_eval.lance_on_stand[state.turn()]++; } else if (unpromote(ptype) == KNIGHT) { new_eval.knight_on_stand[state.turn()]++; } else if (unpromote(ptype) == GOLD) { new_eval.golds[state.turn()]++; new_eval.golds[alt(state.turn())]--; assert(new_eval.golds[BLACK] + new_eval.golds[WHITE] == 4); } } return new_eval.value(progress16, black, white); } MinorPieceDebugInfo debugInfo(Progress16 progress16, Progress16 black, Progress16 white) const { MinorPieceDebugInfo debug_info; debug_info.pawn_bonus = pawnBonus(progress16); debug_info.lance_bonus = lanceBonus(progress16); debug_info.knight_bonus = knightBonus(progress16); debug_info.gold_bonus = goldBonus(black, white); return debug_info; } }; } // namespace eval } // namespace osl #endif /* EVAL_MINORPIECEBONUS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/eval/eval_mobilityTable.cc0000644000000000000000000000153012316770314021247 0ustar rootroot/* eval_mobilityTable.cc */ #include "osl/eval/mobilityTable.h" namespace osl { const CArray eval::MobilityTable::rookVertical = { { -61,-43,-22,-9,-2,9,12,17,17, } }; const CArray eval::MobilityTable::rookHorizontal={{ -72,-47,-18,4,10,28,21,27,27, }}; const CArray eval::MobilityTable::prookVertical={{ -45,-26,-17,-13,-1,1,10,8,8, }}; const CArray eval::MobilityTable::prookHorizontal={{ -35,-23,-16,-10,-4,4,11,12,12, }}; const CArray eval::MobilityTable::bishop={{ -60,-30,-6,2,4,8,10,12, 12,13,15,17,19,21,23,25,27 }}; const CArray eval::MobilityTable::pbishop={{ -39,-30,-9,-6,-2,2,0,5, 13,15,17,19,21,23,25,27,29 }}; const CArray eval::MobilityTable::lance={{ -10,-7,2,6,18,25,27,24,24 }}; } libosl-0.8.0.orig/full/osl/eval/ml/0000755000000000000000000000000012316770314015542 5ustar rootrootlibosl-0.8.0.orig/full/osl/eval/pieceEval.cc0000644000000000000000000000300612316770314017335 0ustar rootroot#include "osl/eval/pieceEval.h" #include "osl/eval/pieceEval.tcc" #include "osl/eval/evalTraits.h" #include "osl/numEffectState.tcc" #include "osl/effect_util/effectUtil.tcc" #include "osl/bits/pieceTable.h" #include "osl/oslConfig.h" osl::eval::PtypeEvalTable osl::eval::PieceEval::Piece_Value; static osl::SetUpRegister _initializer([](){ osl::eval::PieceEval::Piece_Value.init(); }); namespace osl { // explicit template instantiation template int PieceEval::computeDiffAfterMove (const NumEffectState&, Move); template int PieceEval::computeDiffAfterMove (const NumEffectState&, Move); #ifndef DFPNSTATONE #ifndef MINIMAL template void EffectUtil::findThreat(const NumEffectState& state, Square position, PtypeO ptypeo, PieceVector& out); #endif #endif } osl::PieceEval::PieceEval(const NumEffectState& state) { int ret=0; for (int num=0;num namespace osl { namespace eval { /** * 評価関数ã®interface (人間用) */ class EvaluationFunction { public: int getVal() const; }; /** * EvaluationFunction ã®åˆ¶ç´„. * http://www.boost.org/libs/concept_check/concept_check.htm */ template struct Concept { /** * 制約. * ä»–ã«ï¼Œ ApplyMoveOfTurn ã§ãã‚‹å¿…è¦ãŒã‚る. */ void constraints() { const int value = eval.value(); boost::ignore_unused_variable_warning(value); const int infty = T::infty(); boost::ignore_unused_variable_warning(infty); const int capture_val = T::captureValue(ptypeo); boost::ignore_unused_variable_warning(capture_val); } T eval; PtypeO ptypeo; }; } // namespace move_action } // namespace osl #endif /* EVAL_CONCEPT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/pieceEval.tcc0000644000000000000000000001720112316770314017523 0ustar rootroot/* pieceEval.tcc */ #ifndef OSL_PIECEEVAL_TCC #define OSL_PIECEEVAL_TCC #include "osl/move_generator/effect_action.h" #include "osl/move_classifier/kingOpenMove.h" #include "osl/eval/pieceEval.h" #include "osl/eval/see.h" namespace osl { namespace eval { /** * å®‰å…¨ãªæŒ‡æ‰‹ã‚’é¸ã¶. * å˜ç´”ãªç´ æŠœãã¯è€ƒæ…®ã™ã‚‹ãŒæ­£ç¢ºã§ã¯ãªã„ * @param P 指手を指ã™ãƒ—レイヤ */ template struct SelectSafePieces { static void select(const NumEffectState& state, Square target, const PtypeOSquareVector& src, PtypeOSquareVector& out) { for (size_t i=0; i:: isMember(state,ptype,from,target))) { out.push_back(src[i]); } } } /** * @param exceptFor ã“ã“ã‹ã‚‰ã®åˆ©ãã¯é™¤å¤– */ static void select(const NumEffectState& state, Square target, const PtypeOSquareVector& src, PtypeOSquareVector& out, Square except_for) { for (size_t i=0; i:: isMember(state,ptype,from,target,except_for))) { out.push_back(src[i]); } } } }; struct TakeBackValue { /** effectTo ã«åˆ©ãã®ã‚ã‚‹é§’ã‚’å…¨ã¦é›†ã‚ã‚‹ */ template static void findEffectPieces(const NumEffectState& state, Square effect_to, PtypeOSquareVector& my_pieces, PtypeOSquareVector& op_pieces) { typedef effect_action::StorePtypeOSquare store_t; store_t op_pieces_store(&op_pieces, effect_to); state.template forEachEffect (effect_to, op_pieces_store); if (! op_pieces.empty()) { store_t my_pieces_store(&my_pieces, effect_to); state.template forEachEffect(effect_to, my_pieces_store); } } /** move 後㫠move.to() ã«åˆ©ãã®ã‚ã‚‹é§’ã‚’å…¨ã¦é›†ã‚ã‚‹ */ template static void findEffectPiecesAfterMove(const NumEffectState& state, Move move, PtypeOSquareVector& my_pieces, PtypeOSquareVector& op_pieces) { using namespace effect_action; const Square from=move.from(); const Square to=move.to(); const Player Opponent = alt(P); StorePtypeOSquare my_pieces_store(&my_pieces, to); StorePtypeOSquare op_pieces_store(&op_pieces, to); { // moveã®çµæžœç›®çš„ã®ãƒžã‚¹ã®åˆ©ããŒå¤‰ã‚ã‚‹ã®ã‚’調節 /** ã“ã®éƒ¨åˆ†ã¯ effectã®ç¨®é¡žã«ã‚ˆã£ã¦ã¯é«˜é€Ÿã«æ±‚ã¾ã‚‹ã‹ã‚‚ã—れãªã„ */ /** offsetã‹ã‚‰shortを求ã‚ã‚‹ */ /** knight moveã¯0ã«ã—ãŸã„ãŒï¼ŒBoard_Tableã«ã¯å¯¾å¿œã™ã‚‹ã‚‚ã®ã¯ãªã„ */ Offset shortOffset=Board_Table.getShortOffsetNotKnight(Offset32(to,from)); // knightã®å ´åˆã¯å¤‰ã‚らãªã„ if (! shortOffset.zero()){ Piece p; for (Square pos=from-shortOffset; (p=state.pieceAt(pos)).isEmpty(); pos-=shortOffset) ; if (p.isOnBoardByOwner

()){ // 利ãã‚り const int moveMask=Ptype_Table.getMoveMask(p.ptype()); Direction dir=Board_Table.getLongDirection

(Offset32(to,from)); if ((moveMask&dirToMask(dir))!=0){ my_pieces_store.store(p); } } else if (p.isOnBoardByOwner()){ // 利ãã‚り const int moveMask=Ptype_Table.getMoveMask(p.ptype()); Direction dir=Board_Table.getLongDirection

(Offset32(from,to)); if ((moveMask&dirToMask(dir))!=0){ op_pieces_store.store(p); } } } } state.template forEachEffect (to, op_pieces_store); if (! op_pieces.empty()) { const Piece movePiece=state.pieceAt(from); state.template forEachEffectNotBy (to, movePiece,my_pieces_store); } } /** * PtypeOSquareVector ã‚’ã‚‚ã¨ã«å–り返ã—値を計算ã™ã‚‹ * * FIXME: 利ãã‚’å»¶ã°ã™ã‚³ãƒ¼ãƒ‰ã‚’入れるå‰ã« PtypeOSquareVector ã‚’ * PtypeO,Square ã®ãƒ™ã‚¯ã‚¿ã«å¤‰æ›´ã™ã‚‹å¿…è¦ãŒã‚る. * computeDiffAfterMoveMulti ãªã©ã§é§’ã‚’å‹•ã‹ã•ãšã«ï¼Œ * move 後ã®å–りåˆã„を考ãˆã¦ã„る時ã«ï¼Œpiece.square() ãŒå¿…ãšã—ã‚‚ * å–りåˆã„ã®ãŸã‚ã®position ã§ã¯ãªã„ãŸã‚. * * @param P alt(P) ã‹ã‚‰ã®å–り返㗠* @param target ã“ã“ã«é–¢ã™ã‚‹å–り返㗠* @param ptypeo target ã«ã‚ã‚‹ã¨æƒ³å®šã•れる駒 */ template static int computeValue(Square target, PtypeO ptypeO, const PtypeOSquareVector& my_pieces, const PtypeOSquareVector& op_pieces) { int val = 0; CArray vals; const Player Opponent = alt(P); size_t i; for (i=0;i() || op_pieces[i].second.canPromote()); if (promotable) { ptypeO=promote(ptypeO); val+=Ptype_Eval_Table.promoteValue(ptypeO); } } vals[i*2+1]=val; // myMove if (i>=my_pieces.size()){ break; } val+=Ptype_Eval_Table.captureValue(ptypeO); { ptypeO=my_pieces[i].first; const bool promotable = canPromote(ptypeO) && (target.canPromote

() || my_pieces[i].second.canPromote

()); if (promotable) { ptypeO=promote(ptypeO); val+=Ptype_Eval_Table.promoteValue(ptypeO); } } } for (int j=i-1;j>=0;j--) { val=EvalTraits

::max(val,vals[j*2+1]); val=EvalTraits::max(val,vals[j*2]); } return val; } }; /** P ㌠PTYPE ã®é§’ã‚’å–ã£ãŸæ™‚ã®å€¤ */ template inline int captureVal(Player P) { // unpromote(PTYPE) ã‚’å®šæ•°ã§æ±‚ã‚られれã°å³å€¤ã«å‡ºæ¥ã‚‹ return Ptype_Eval_Table.captureValue(newPtypeO(alt(P),PTYPE)); } } // namespace eval } // namespace osl template int osl::PieceEval:: computeDiffAfterMove(const NumEffectState& state, Move move) { assert(P == state.turn()); assert(state.isAlmostValidMove(move)); /** move.to() ã«åˆ©ãã®ã‚る駒を集ã‚ã‚‹ */ PtypeOSquareVector my_pieces,op_pieces; /** * moveã®çµæžœ, å»¶ã³ã‚‹åйããŒã‚ã‚‹ã‹ */ const Square from=move.from(); const Square to=move.to(); int val=0; /** * ç¾çжã§è‡ªåˆ†ã‚’除ãã™ã¹ã¦ã®é§’ */ if (from.isPieceStand()) // drop moveã¯ç°¡å˜ { TakeBackValue::findEffectPieces

(state, to, my_pieces, op_pieces); } else { val+=Ptype_Eval_Table.diffWithMove(state,move); TakeBackValue:: findEffectPiecesAfterMove

(state, move, my_pieces, op_pieces); } if (op_pieces.empty()) return val; PtypeOSquareVector my_safe_pieces, op_safe_pieces; if (from.isPieceStand()) { SelectSafePieces

:: select(state, to, my_pieces, my_safe_pieces); SelectSafePieces:: select(state, to, op_pieces, op_safe_pieces); } else { SelectSafePieces

:: select(state, to, my_pieces, my_safe_pieces, from); SelectSafePieces:: select(state, to, op_pieces, op_safe_pieces, from); } my_safe_pieces.sort(); op_safe_pieces.sort(); return val + TakeBackValue:: computeValue

(to, move.ptypeO(), my_safe_pieces, op_safe_pieces); } #endif /* OSL_PIECEEVAL_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/eval/mobilityTable.h0000644000000000000000000000117412316770314020106 0ustar rootroot/* mobilityTable.h */ #ifndef EVAL_MOBILITYTABLE_H #define EVAL_MOBILITYTABLE_H #include "osl/container.h" namespace osl { namespace eval { class MobilityTable { public: static const CArray rookVertical; static const CArray rookHorizontal; static const CArray prookVertical; static const CArray prookHorizontal; static const CArray bishop; static const CArray pbishop; static const CArray lance; }; } } #endif /* EVAL_MOBILITYTABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/0000755000000000000000000000000012316770314015665 5ustar rootrootlibosl-0.8.0.orig/full/osl/ntesuki/ntesukiMoveList.h0000644000000000000000000000314412316770314021205 0ustar rootroot/* ntesukiMoveList.h */ #ifndef _NTESUKI_MOVELIST_H #define _NTESUKI_MOVELIST_H #include "osl/ntesuki/ntesukiMove.h" #include "osl/ntesuki/ntesukiExceptions.h" #include "osl/state/numEffectState.h" #include "osl/container/moveVector.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/check_.h" #include "osl/stl/slist.h" #include #include #include #include namespace osl { namespace ntesuki { // TODO: 自作ã™ã¹ã typedef slist NtesukiMoveListBase; /** * ntesuki 探索ã§ä½¿ã†æŒ‡æ‰‹ã®ãƒªã‚¹ãƒˆ */ class NtesukiMoveList : public NtesukiMoveListBase { public: NtesukiMoveList(); NtesukiMoveList(const NumEffectState& state, const osl::MoveVector& mv); /** * é‡è¤‡ã‚’ã—ãªã„よã†ã«æ‰‹ã‚’追加ã™ã‚‹ãƒ¡ã‚½ãƒƒãƒ‰. * @c move ãŒã‚ã‚‹ã‹ã©ã†ã‹æœã—,ã‚ã£ãŸå ´åˆã«ã¯ * æ—¢ã«ã‚ã‚‹ move ã¸ã®å‚ç…§ã‚’è¿”ã™. * ãªã‹ã£ãŸå ´åˆã«ã¯ @c move ã¨åŒã˜ osl::Move ã‚’æŒã¤ã‚ˆã†ãª * NtesukiMove を追加ã™ã‚‹. * 勿•—ã«é–¢ä¿‚ã™ã‚‹ flags ã‚„ record ç­‰ã®æƒ…å ±ã¯ä¿æŒã—ãªã„ã®ã§æ³¨æ„. * 通常ã®è¿½åŠ ã®å ´åˆã«ã¯ push_front を用ã„ã‚‹ã“ã¨. */ NtesukiMove* add(const NtesukiMove& move); const NtesukiMove& find(const NtesukiMove& move) const; }; std::ostream& operator<<(std::ostream&, const NtesukiMoveList&); } // namespace ntesukimate } // namespace osl #endif /* _NTESUKI_MOVELIST_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMoveList.cc0000644000000000000000000000363612316770314021351 0ustar rootroot/* ntesukiList.cc */ #include "osl/ntesuki/ntesukiMoveList.h" #include osl::ntesuki::NtesukiMoveList:: NtesukiMoveList() { } osl::ntesuki::NtesukiMoveList:: NtesukiMoveList(const NumEffectState& state, const osl::MoveVector& mv) { ntesuki_assert(empty()); if (!state.kingSquare(alt(state.turn())).isOnBoard()) { for (size_t i = 0; i < mv.size(); ++i) { NtesukiMove move(mv[i]); push_front(move); } } else { for (size_t i = 0; i < mv.size(); ++i) { NtesukiMove move(mv[i]); if (move_classifier::PlayerMoveAdaptor::isMember(state, mv[i])) { move.setCheck(); } push_front(move); } } } /* * é‡è¤‡ã‚’ã—ãªã„よã†ã«æ‰‹ã‚’追加ã™ã‚‹ãƒ¡ã‚½ãƒƒãƒ‰. * @c move ãŒã‚ã‚‹ã‹ã©ã†ã‹æœã—,ã‚ã£ãŸå ´åˆã«ã¯ * æ—¢ã«ã‚ã‚‹ move ã¸ã®å‚ç…§ã‚’è¿”ã™. * ãªã‹ã£ãŸå ´åˆã«ã¯ @c move ã¨åŒã˜ osl::Move ã‚’æŒã¤ã‚ˆã†ãª * NtesukiMove を追加ã™ã‚‹. * 勿•—ã«é–¢ä¿‚ã™ã‚‹ flags ã‚„ record ç­‰ã®æƒ…å ±ã¯ä¿æŒã—ãªã„ã®ã§æ³¨æ„. * 通常ã®è¿½åŠ ã®å ´åˆã«ã¯ push_front を用ã„ã‚‹ã“ã¨. */ const osl::ntesuki::NtesukiMove& osl::ntesuki::NtesukiMoveList:: find(const NtesukiMove& move) const { const_iterator it; for (it = begin(); it != end(); it++) { if(it->getMove() == move.getMove()) { return *it; } } return *it; } osl::ntesuki::NtesukiMove* osl::ntesuki::NtesukiMoveList:: add(const NtesukiMove& move) { for (iterator it = begin(); it != end(); it++) { if(it->getMove() == move.getMove()) { return &(*it); } } push_front(NtesukiMove(move.getMove())); if (move.isCheck()) { front().setCheck(); } return &(front()); } std::ostream& osl::ntesuki:: operator<<(std::ostream& os, const NtesukiMoveList& l) { for (NtesukiMoveList::const_iterator p=l.begin(); p!=l.end(); ++p) { os << (*p) << " "; } return os << "\n"; } libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSimulationSearcher.h0000644000000000000000000001044712316770314023250 0ustar rootroot/* ntesukiSimulationSearcher.h */ #ifndef __NTESUKI_SIMULATION_SEARCHER_H #define __NTESUKI_SIMULATION_SEARCHER_H #include "osl/ntesuki/ntesukiTable.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "ntesukiExceptions.h" typedef osl::state::NumEffectState state_t; namespace osl { namespace ntesuki { class NtesukiSimulationSearcher { /** ç¾åœ¨ã¾ã§ã«ä½•ノード読んã ã‹ */ unsigned int node_count; /** 経éŽã‚’ã©ã“ã¾ã§è¡¨ç¤ºã™ã‚‹ã‹ */ bool verbose; /** Simulation çµæžœã®çµ±è¨ˆ */ unsigned int proof_count; unsigned int proof_success_count; unsigned int light_proof_success_count; unsigned int disproof_count; unsigned int disproof_success_count; public: bool debug; private: NtesukiResult result; state_t& state; NtesukiMoveGenerator *mg; PathEncoding& path; NtesukiTable& table; NtesukiRecord::ISScheme isscheme; /* * helpers */ template class AttackHelperProof; template class DefenseHelperProof; template class AttackHelperDisproof; template class DefenseHelperDisproof; /* Utilities */ template bool isSafeMove(const Move move, int pass_left); template Move adjustMove(Move candidate) const { assert(candidate.isValid()); if (! candidate.isDrop()) { const Piece p=state.pieceOnBoard(candidate.to()); candidate=setCapture(candidate,p); } return candidate; } /** * Proof 攻撃ã«é–¢ã™ã‚‹è¨ˆç®— */ template void attackForProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /** * Disproof 防御ã«é–¢ã™ã‚‹è¨ˆç®— */ template void defenseForProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /** * Disproof 攻撃ã«é–¢ã™ã‚‹è¨ˆç®— */ template void attackForDisproof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /** * Disproof 防御ã«é–¢ã™ã‚‹è¨ˆç®— */ template void defenseForDisproof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); public: NtesukiSimulationSearcher(state_t& state, NtesukiMoveGenerator *mg, PathEncoding& path, NtesukiTable& table, NtesukiRecord::ISScheme isscheme, bool verbose = false); ~NtesukiSimulationSearcher(); /** * Start simulation to proof, P as Attacker. * @return true, if checkmate is proven */ template bool startFromAttackProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /** * Start simulation to proof, P as Defender. * @return true, if checkmate is proven */ template bool startFromDefenseProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /** * Start simulation to disproof, P as Attacker. * @return true, if nocheckmate is proven */ template bool startFromAttackDisproof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /** * Start simulation to disproof, P as Defender. * @return true, if nocheckmate is proven */ template bool startFromDefenseDisproof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); unsigned int nodeCount() const { return node_count; } }; } //ntesuki } //osl #endif /* _NTESUKI_SIMULATION_SEARCHER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSearcher.h0000644000000000000000000002124412316770314021200 0ustar rootroot/* ntesukiSearcher.h */ #ifndef _NTESUKI_SEACHER_H #define _NTESUKI_SEACHER_H #include "osl/state/numEffectState.h" #include "osl/ntesuki/ntesukiTable.h" #include "osl/ntesuki/ntesukiRecord.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/ntesuki/ntesukiExceptions.h" #include "osl/container/moveVector.h" #include "osl/ntesuki/ntesukiSimulationSearcher.h" #include namespace osl { namespace ntesuki { class NtesukiSearcher { public: typedef NumEffectState State; private: State& state; /** 手生æˆå™¨. */ NtesukiMoveGenerator *mg; /** トランスãƒã‚¸ã‚·ãƒ§ãƒ³ãƒ†ãƒ¼ãƒ–ル. */ NtesukiTable table; /** シミュレーション探索器. */ NtesukiSimulationSearcher simulator; /** ç¾åœ¨ã¾ã§ã«ä½•ノード読んã ã‹. */ unsigned int node_count; /** 最大何ノードã¾ã§èª­ã‚€ã‹. */ unsigned int read_node_limit; /** 経éŽã‚’ã©ã“ã¾ã§è¡¨ç¤ºã™ã‚‹ã‹. */ bool verbose; /** 探索を途中ã§å¼·åˆ¶çš„ã«çµ‚了ã•ã›ã‚‹ãŸã‚ã® flag. */ volatile int *stop_flag; /** ルートã‹ã‚‰ç¾åœ¨æŽ¢ç´¢ä¸­ã®ãƒŽãƒ¼ãƒ‰ã¾ã§ã® path ã® hash値. */ PathEncoding path; /** ルートã‹ã‚‰ç¾åœ¨æŽ¢ç´¢ä¸­ã®ãƒŽãƒ¼ãƒ‰ã¾ã§ã® move. */ typedef std::vector moves_t; moves_t moves_played; /** ルートã‹ã‚‰ç¾åœ¨æŽ¢ç´¢ä¸­ã®ãƒŽãƒ¼ãƒ‰ã¾ã§ã®å±€é¢. */ typedef std::vector nodes_t; nodes_t nodes_played; /** λオーダ */ unsigned int max_pass; public: /** * 探索ã®ãµã‚‹ã¾ã„を制御ã™ã‚‹å¤‰æ•°. */ static bool delay_non_pass; static bool ptt_invalid_defense; static bool delay_interpose; static bool delay_nopromote; static bool delay_non_attack; static bool read_attack_only; static bool ptt_non_attack; static bool ptt_siblings_fail; static bool ptt_siblings_success; static bool ptt_uncle; static bool ptt_aunt; static unsigned int dynamic_widening_width; private: /** Iterative widening ã® scheme */ NtesukiRecord::IWScheme iwscheme; /** Player selection ã® scheme */ NtesukiRecord::PSScheme psscheme; /** Inversion searching ã® scheme */ NtesukiRecord::ISScheme isscheme; /** è©°ã‚ã‚ãªæ‰‹ã«é–¢ã™ã‚‹ cost */ int tsumero_cost; /** è©°ã‚ã‚ãªæ‰‹ã«é–¢ã™ã‚‹è¨¼æ˜Žæ•°ã®äºˆæ¸¬å€¤ */ int tsumero_estimate; /** GC ã®éš›ã«ãƒ†ãƒ¼ãƒ–ル ã‚’ã©ã“ã¾ã§å°ã•ãã™ã‚‹ã‹ */ double gc_ratio; template class AttackHelper; template class DefenseHelper; template class CallSimulationAttack; template class CallSimulationDefense; template class CallSimulationDefenseDisproof; /* statistic information */ unsigned int blockByAttackBack; unsigned int blockByPass; unsigned int attack_node_count; unsigned int attack_node_under_attack_count; unsigned int attack_node_moves_count; unsigned int defense_node_count; unsigned int defense_node_under_attack_count; unsigned int defense_node_moves_count; unsigned int pass_count, pass_success_count; unsigned int pass_attack_count, pass_attack_success_count; unsigned int sibling_defense_count, sibling_defense_success_count; unsigned int sibling_attack_count, sibling_attack_success_count; unsigned int isshogi_defense_count, isshogi_defense_success_count; unsigned int isshogi_attack_count, isshogi_attack_success_count; unsigned int immediate_win, immediate_lose; unsigned int attack_back_count; unsigned int proof_without_inversion_count, proof_AND_count, disproof_by_inversion_count; public: static const int NtesukiNotFound = -1; static const int ReadLimitReached = -2; static const int TableLimitReached = -3; private: static const unsigned int INITIAL_PROOF_LIMIT = ProofDisproof::PROOF_LIMIT / 4; static const unsigned int INITIAL_DISPROOF_LIMIT = ProofDisproof::DISPROOF_LIMIT / 4; /** * 攻撃å´ã®å‡¦ç† */ template NtesukiResult attack(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proofLimit, unsigned int disproofLimit, int pass_left, const Move last_move); template void attackWithOrder(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proofLimit, unsigned int disproofLimit, int pass_left, const Move last_move); template NtesukiMove* selectMoveAttack(NtesukiRecord* record, unsigned int& best_proof, unsigned int& sum_disproof, unsigned int& second_proof, unsigned int& best_disproof, unsigned int& step_cost, NtesukiMoveList& moves, const int pass_left); /** * 防御ã«é–¢ã™ã‚‹è¨ˆç®— */ template NtesukiResult defense(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proofLimit, unsigned int disproofLimit, int pass_left, const Move last_move); template void defenseWithPlayer(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proofLimit, unsigned int disproofLimit, int pass_left, const Move last_move); template NtesukiMove* selectMoveDefense(NtesukiRecord* record, unsigned int& best_disproof, unsigned int& sum_proof, unsigned int& second_disproof, unsigned int& best_proof, unsigned int& step_cost, NtesukiMoveList& moves, const int pass_left, const Move last_move); /** * å—ã‘æ‰‹ç•ªã§ï¼Œã‚る手㌠Success ã ã¨ã‚ã‹ã£ãŸå ´åˆï¼Œ * ä»–ã®æ‰‹ã‚‚åŒæ§˜ã« Success ã«ãªã‚‰ãªã„ã‹ Simulaition ã§èª¿ã¹ã‚‹. * ç¾åœ¨ $\lambda^n$ 探索中ã®å ´åˆã«ã¯ï¼ŒåŽŸå‰‡ $\lambda^(n-1)$ move ã®å ´åˆã«ã¯èª¿ã¹ãªã„. * * e.g. 必至探索中ã«ã¯çŽ‹æ‰‹ã¯èª¿ã¹ãªã„. */ template void simulateSiblingsSuccess(NtesukiRecord *record, NtesukiRecord *record_best, int pass_left, unsigned int& success_count, unsigned int& total_count); /** * æ”»ã‚æ‰‹ç•ªã§ï¼Œã‚る手㌠Fail ã ã¨ã‚ã‹ã£ãŸå ´åˆï¼Œ * ä»–ã®æ‰‹ã‚‚åŒæ§˜ã« Fail ã«ãªã‚‰ãªã„ã‹ Simulaition ã§èª¿ã¹ã‚‹. */ template void simulateSiblingsFail(NtesukiRecord *record, NtesukiRecord *record_best, int pass_left, unsigned int& success_count, unsigned int& total_count); /** * æ”»ã‚ã«ãªã£ã¦ã„ãªã„手を除ã. */ template void handleNonAttack(NtesukiRecord *record, int pass_left); /** * é “æ­»ãŒãªã„ã‹èª¿ã¹ã‚‹. */ template void handleTonshi(NtesukiRecord *record, int pass_left, const Move last_move); /** * ç„¡é§„åˆå€™è£œãŒæœ¬å½“ã«ç„¡é§„åˆãŒèª¿ã¹ã‚‹. */ template void handleInterpose(NtesukiRecord *record, int pass_left); public: /* ====================== * 外ã‹ã‚‰å‘¼ã°ã‚Œã‚‹é–¢æ•° */ NtesukiSearcher(State& state, NtesukiMoveGenerator *mg, unsigned int table_limit, volatile int *stop_flag, bool verbose, int maxPass = NtesukiRecord::SIZE, NtesukiRecord::IWScheme iwscheme = NtesukiRecord::pn_iw, NtesukiRecord::PSScheme psscheme = NtesukiRecord::no_ps, NtesukiRecord::ISScheme isscheme = NtesukiRecord::no_is, int tsumero_cost = 0, int tsumero_estimate = 0, double gc_ratio = 0.33); ~NtesukiSearcher(); template int search(); int searchSlow(Player attacker, int rnl = 160000) { read_node_limit = rnl; if (attacker == BLACK) return search(); else return search(); } NtesukiTable& getTable(); int getNodeCount() const { return node_count; } bool exceedReadNodeLimit() const {return node_count > read_node_limit;} }; } //ntesuki } //osl #endif /* _NTESUKI_SEACHER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSimulationSearcher.cc0000644000000000000000000000574712316770314023415 0ustar rootroot#include "osl/ntesuki/ntesukiSimulationSearcherProof.tcc" #include "osl/ntesuki/ntesukiSimulationSearcherDisproof.tcc" #include "osl/ntesuki/ntesukiMoveGenerator.h" typedef NumEffectState state_t; /* Constructor/ Destructor */ osl::ntesuki::NtesukiSimulationSearcher:: NtesukiSimulationSearcher(state_t& state, NtesukiMoveGenerator *mg, PathEncoding& path, NtesukiTable& table, NtesukiRecord::ISScheme isscheme, bool verbose) : node_count(0), verbose(verbose), proof_count(0), proof_success_count(0), light_proof_success_count(0), disproof_count(0), disproof_success_count(0), debug(false), state(state), mg(mg), path(path), table(table), isscheme(isscheme) { } osl::ntesuki::NtesukiSimulationSearcher:: ~NtesukiSimulationSearcher() { if (verbose) std::cerr << "~NtesukiSimulationSeacher:\t(" << node_count << ")\tproof(" << light_proof_success_count << "/" << proof_success_count << "/" << proof_count << ")\tdisproof(" << disproof_success_count << "/" << disproof_count << ")" << std::endl; } template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromAttackProof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromAttackProof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromDefenseProof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromDefenseProof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromAttackDisproof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromAttackDisproof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromDefenseDisproof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); template bool osl::ntesuki::NtesukiSimulationSearcher:: startFromDefenseDisproof(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int passLeft, const Move last_move); /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMoveGeneratorAttack.cc0000644000000000000000000002255512316770314023515 0ustar rootroot/* ntesukiMoveGenerator.cc */ #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/state/numEffectState.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/effect_util/neighboring25Direct.h" #include "osl/move_classifier/canAttackInNMoves.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/safeMove.h" #include "osl/move_classifier/check.h" #include "osl/move_generator/escape.h" #include "osl/move_generator/legalMoves.h" #include "osl/move_generator/addEffect.h" #include "osl/move_generator/addEffect.tcc" #include "osl/move_generator/addEffect8.h" #include "osl/move_generator/kingWalk.h" #include "osl/move_generator/drop.h" #include "osl/move_generator/dropAroundKing8.h" #include "osl/move_generator/openKingRoad.h" #include "osl/move_generator/capture.h" #include "osl/move_generator/capture.tcc" #include "osl/move_generator/captureEffectToAroundKing8.h" #include "osl/move_action/store.h" #include "osl/move_action/safeFilter.h" #include /* * n 手ã™ã探索ã§ç”¨ã„ã‚‹ move generator. */ namespace osl { namespace ntesuki { /* ---------------------------------------------------------------------- * Utility * ---------------------------------------------------------------------- */ static bool hasEffectByBigPieces (const NumEffectState& state, const Player player, const Square pos) { #if OSL_WORDSIZE == 64 const PieceMask bigPieceMask (container::PieceMaskBase( PieceMask::numToMask (PtypeTraits::indexMin) | PieceMask::numToMask (PtypeTraits::indexMin + 1) | PieceMask::numToMask (PtypeTraits::indexMin) | PieceMask::numToMask (PtypeTraits::indexMin + 1))); const PieceMask pieceMask = (state.piecesOnBoard (player) & state.effectAt (pos) & bigPieceMask); return pieceMask.any(); #elif OSL_WORDSIZE == 32 // TODO: 多分ã“ã®ã‚³ãƒ¼ãƒ‰ã§64bit 環境ã¨å…±é€šã«ã§ãã‚‹ã¨æ€ã†ã‚“ã ã‘ã© // 締切ã¾ã§ã¯ãã®ã¾ã¾ã« PieceMask bigPieceMask; bigPieceMask.set(PtypeTraits::indexMin); bigPieceMask.set(PtypeTraits::indexMin + 1); bigPieceMask.set(PtypeTraits::indexMin); bigPieceMask.set(PtypeTraits::indexMin + 1); const PieceMask pieceMask = (state.piecesOnBoard (player) & state.effectAt (pos) & bigPieceMask); return pieceMask.any(); #endif } template static void getCheckMoves (const NumEffectState& state, MoveVector& moves) { using namespace move_classifier; const Square targetKing = state.kingSquare::opponent>(); move_action::Store store(moves); move_action::SafeFilter store_safe(state, store); move_generator::AddEffect::generate(state, targetKing, store_safe); } template struct CaptureHelper { CaptureHelper(const NumEffectState& state, move_action::Store& action) : state(state), action(action) { } void operator()(Piece p) { move_generator::GenerateCapture::generate(P,state, p.square(), action); } private: const NumEffectState& state; move_action::Store& action; }; template static void capture(const NumEffectState& state, move_action::Store action) { CaptureHelper

captureHelper(state, action); state.forEachOnBoard::opponent, T, CaptureHelper

>(captureHelper); } /* ---------------------------------------------------------------------- * ATTACK * ---------------------------------------------------------------------- */ /* GetAllAttackMoves */ GetAllAttackMoves::GetAllAttackMoves(bool verbose) : NtesukiAttackMoveGenerator(verbose) {} GetAllAttackMoves::~GetAllAttackMoves() {} template void GetAllAttackMoves:: generate(const NumEffectState& state, NtesukiMoveList& moves) { MoveVector move_candidates; LegalMoves::generate(state, move_candidates); moves = NtesukiMoveList(state, move_candidates); } template void GetAllAttackMoves::generate(const NumEffectState& state, NtesukiMoveList& moves); template void GetAllAttackMoves::generate(const NumEffectState& state, NtesukiMoveList& moves); /* GetAttackMoves */ GetAttackMoves::GetAttackMoves(bool verbose) : NtesukiAttackMoveGenerator(verbose) {} GetAttackMoves::~GetAttackMoves() {} template void GetAttackMoves:: generate(const NumEffectState& state, NtesukiMoveList& moves) { #if 0 const Square pos = state.template kingSquare

(); const bool check = state.hasEffectAt(PlayerTraits

::opponent, pos); if (check) { MoveVector move_candidates; GenerateEscapeKing::generate(state, move_candidates); moves = NtesukiMoveList(state, move_candidates); return; } MoveVector check_candidates; getCheckMoves

(state, check_candidates); MoveVector move_candidates; move_action::Store store(move_candidates); move_generator::AddEffect8

::generate(state, store); capture(state, store); capture(state, store); capture(state, store); capture(state, store); capture(state, store); capture(state, store); //shold we generate pawn? size_t deleted = 0; for (size_t i = 0; i < move_candidates.size(); ++i) { const Move m = move_candidates[i]; if (check_candidates.isMember(move_candidates[i]) || (m.from() != Square::STAND() && !move_classifier::SafeMove

::isMember(state, m.ptype(), m.from(), m.to()))) { ++deleted; move_candidates[i] = Move::INVALID(); } } for (size_t i = 0; i < move_candidates.size(); ++i) { if (move_candidates[i] == Move::INVALID()) continue; { ntesuki_assert(!move_classifier:: PlayerMoveAdaptor:: isMember(state, move_candidates[i]) || (std::cerr << std::endl << state << check_candidates << std::endl << move_candidates << std::endl, 0)); } moves.push_front(NtesukiMove(move_candidates[i], NtesukiMove::NONE)); } for (size_t i = 0; i < check_candidates.size(); ++i) { moves.push_front(NtesukiMove(check_candidates[i], NtesukiMove::CHECK_FLAG)); } #else MoveVector all_moves; MoveVector move_candidates; LegalMoves::generate(state, all_moves); const Square opKingSquare = state.kingSquare (alt(state.turn ())); for (unsigned int i=0; i(const NumEffectState& state, NtesukiMoveList& moves); template void GetAttackMoves::generate(const NumEffectState& state, NtesukiMoveList& moves); /* GetMultipleAttackMoves */ GetMultipleAttackMoves::GetMultipleAttackMoves(bool verbose) : NtesukiAttackMoveGenerator(verbose) {} GetMultipleAttackMoves::~GetMultipleAttackMoves() {} template void GetMultipleAttackMoves:: generate(const NumEffectState& state, NtesukiMoveList& moves) { assert (state.turn() == P); MoveVector all_moves; MoveVector move_candidates; LegalMoves::generate(state, all_moves); const Square opKingSquare = state.kingSquare (alt(state.turn ())); for (unsigned int i=0; i(const NumEffectState& state, NtesukiMoveList& moves); template void GetMultipleAttackMoves::generate(const NumEffectState& state, NtesukiMoveList& moves); }//ntesuki }//osl // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiResult.h0000644000000000000000000000076612316770314020730 0ustar rootroot#ifndef _ID_NTESUKI_RESULT_H #define _ID_NTESUKI_RESULT_H #include "osl/checkmate/proofDisproof.h" #include #include using namespace osl::checkmate; namespace osl{ namespace ntesuki{ /** * n 手ã™ãを探索ã—ãŸçµæžœã‚’ä¿å­˜ã—ã¦ãŠããŸã‚ã®åž‹. * ç¾åœ¨ã§ã¯ checkmate ã® ProofDisProof */ typedef ProofDisproof NtesukiResult; } } #endif /* _ID_NTESUKI_RESULT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMoveGenerator.cc0000644000000000000000000002367412316770314022370 0ustar rootroot/* ntesukiMoveGenerator.cc */ #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/ntesuki/ntesukiRecord.h" #include "osl/state/numEffectState.h" #include "osl/effect_util/neighboring8Effect.h" #include "osl/effect_util/neighboring25Direct.h" #include "osl/move_generator/escape_.h" #include "osl/move_generator/addEffect_.h" #include "osl/move_classifier/canAttackInNMoves.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/safeMove.h" #include "osl/move_generator/allMoves.h" #include "osl/move_action/store.h" #include "osl/move_action/safeFilter.h" #include "osl/effect_util/effectUtil.h" #include #ifdef NDEBUG # include "osl/move_generator/escape_.tcc" # include "osl/move_generator/capture_.tcc" #endif #include "osl/move_action/store.h" namespace osl { namespace ntesuki { } } /* * n 手ã™ã探索ã§ç”¨ã„ã‚‹ move generator. */ namespace osl { namespace ntesuki { /* ---------------------------------------------------------------------- * Utility * ---------------------------------------------------------------------- */ inline bool hasEffectByBigPieces (const NumEffectState& state, const Player player, const Square pos) { #if OSL_WORDSIZE == 64 const PieceMask bigPieceMask (container::PieceMaskBase( PieceMask::numToMask (PtypeTraits::indexMin) | PieceMask::numToMask (PtypeTraits::indexMin + 1) | PieceMask::numToMask (PtypeTraits::indexMin) | PieceMask::numToMask (PtypeTraits::indexMin + 1))); const PieceMask pieceMask = (state.piecesOnBoard (player) & state.effectAt (pos) & bigPieceMask); return pieceMask.any(); #elif OSL_WORDSIZE == 32 // TODO: 多分ã“ã®ã‚³ãƒ¼ãƒ‰ã§64bit 環境ã¨å…±é€šã«ã§ãã‚‹ã¨æ€ã†ã‚“ã ã‘ã© // 締切ã¾ã§ã¯ãã®ã¾ã¾ã« PieceMask bigPieceMask; bigPieceMask.set(PtypeTraits::indexMin); bigPieceMask.set(PtypeTraits::indexMin + 1); bigPieceMask.set(PtypeTraits::indexMin); bigPieceMask.set(PtypeTraits::indexMin + 1); const PieceMask pieceMask = (state.piecesOnBoard (player) & state.effectAt (pos) & bigPieceMask); return pieceMask.any(); #endif } template struct CaptureHelper { CaptureHelper(const NumEffectState& state, move_action::Store& action) : state(state), action(action) { } void operator()(Piece p) { move_generator::GenerateCapture::generate(P,state, p.square(), action); } private: const NumEffectState& state; move_action::Store& action; }; template static void capture(const NumEffectState& state, move_action::Store action) { CaptureHelper

captureHelper(state, action); state.forEachOnBoard::opponent, T, CaptureHelper

>(captureHelper); } /* NtesukiMoveGenerator */ NtesukiMoveGenerator::NtesukiMoveGenerator(bool verbose) :verbose(verbose) {} NtesukiMoveGenerator::~NtesukiMoveGenerator() {} template static void generate_all_moves(const NumEffectState& state, MoveVector& moves) { if (state.inCheck(T)) { // 王手ãŒã‹ã‹ã£ã¦ã„る時ã¯é˜²ã手ã®ã¿ã‚’ç”Ÿæˆ GenerateEscapeKing::generate(state, moves); } else { MoveVector all_moves; // ãã†ã§ãªã‘れã°å…¨ã¦ã®æ‰‹ã‚’ç”Ÿæˆ GenerateAllMoves::generate(T, state, all_moves); // ã“ã®æŒ‡æ‰‹ã¯ï¼Œçމã®ç´ æŠœããŒã‚ã£ãŸã‚Šï¼Œæ‰“æ­©è©°ã®å¯èƒ½æ€§ãŒã‚ã‚‹ã®ã§ // 確èªãŒå¿…è¦ using namespace osl::move_classifier; for (unsigned int i=0; i::isMember(state, m)) { moves.push_back(m); } } } } template void NtesukiMoveGenerator:: generateWithRzone(const NumEffectState& state, NtesukiRecord *record, int pass_left, NtesukiMoveList& moves) { /* æ”»ã‚æ–¹ã®æ‰‹ç•ªã§ï¼Œ rzone を使ã£ã¦ã®æ‰‹ç”Ÿæˆ. */ ntesuki_assert(record->turn() == T); const Player O = PlayerTraits::opponent; const Square targetKing = state.kingSquare(); if (state.inCheck(T)) { /* 自玉ã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã¯ï¼Œå…¨åˆæ³•æ‰‹ã‚’ç”Ÿæˆ */ MoveVector move_candidates; GenerateEscapeKing::generate(state, move_candidates); moves = NtesukiMoveList(state, move_candidates); setOrder(state, moves); } else if (pass_left == 0) { /* è©°ã¿æŽ¢ç´¢ã®å ´åˆã«ã¯ï¼ŒçŽ‹æ‰‹ã®ã¿ç”Ÿæˆ */ MoveVector move_candidates; { move_action::Store store(move_candidates); move_action::SafeFilter store_safe(state, store); move_generator::AddEffect::generate(state, targetKing, store_safe); } moves = NtesukiMoveList(state, move_candidates); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { /* 大駒ã®ãŸã æ¨ã¦ã¯é…らã›ã‚‹ */ const Move m = move_it->getMove(); const Square to = m.to(); const Piece atTo = state.pieceOnBoard(to); if (m.isDrop() && isMajor(m.ptype()) && state.countEffect2(O, to) == 1) { move_it->setOrder(1); } else { move_it->setOrder(0); } } moves.push_front(NtesukiMove(Move::PASS(T))); moves.front().setOrder(0); } else if (!record->rzone_move_generation) { return generate(state, moves); } else { int rzone_order = pass_left - 1; Rzone rzone_cur = record->rzone()[rzone_order]; ntesuki_assert(rzone_cur.any()); /* å–ã‚‹æ‰‹ã‚’ç”Ÿæˆ */ MoveVector captures; { move_action::Store store(captures); capture(state, store); capture(state, store); capture(state, store); capture(state, store); capture(state, store); capture(state, store); } for (size_t i = 0; i < captures.size(); ++i) { const Move m = captures[i]; if (move_classifier::SafeMove::isMember(state, m.ptype(), m.from(), m.to())) { moves.add(m); } } /* 玉ãŒé€ƒã’ãã†ãªä½ç½®ã«åˆ©ãã‚’ã¤ã‘ã‚‹æ‰‹ã‚’ç”Ÿæˆ */ for (int x = 1; x <=9; ++x) { for (int y = 1; y <=9; ++y) { bool close_to_target = false; const Square pos(x,y); if (NtesukiRecord::use_9rzone == true) { for (int dx = -1; dx <=1; dx++) { for (int dy = -1; dy <=1; dy++) { int xx = x + dx; int yy = y + dy; if (xx > 0 && xx < 10 && yy > 0 && yy < 10) { ntesuki_assert(xx >= 1 && xx <= 9); ntesuki_assert(yy >= 1 && yy <= 9); const Square pos2(xx,yy); close_to_target |= rzone_cur.test(pos2); } } } } else { close_to_target = rzone_cur.test(pos); } if (close_to_target) { MoveVector king_blocks; { move_action::Store store2(king_blocks); move_action::SafeFilter store_safe(state, store2); move_generator::AddEffect::generate(state, pos, store_safe); } for (size_t i = 0; i < king_blocks.size(); ++i) { const Move m = king_blocks[i]; moves.add(m); } } } } setOrder(state, moves); moves.push_front(NtesukiMove(Move::PASS(T))); moves.front().setOrder(0); } } template void NtesukiMoveGenerator:: generate(const NumEffectState& state, NtesukiMoveList& moves) { MoveVector all_moves; generate_all_moves(state, all_moves); moves = NtesukiMoveList(state, all_moves); setOrder(state, moves); if (!state.inCheck(T)) { moves.push_front(NtesukiMove(Move::PASS(T))); moves.front().setOrder(0); } }//generate template void NtesukiMoveGenerator:: setOrder(const NumEffectState& state, NtesukiMoveList& moves) { const Square opKingSquare = state.kingSquare (alt(state.turn ())); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { if (!opKingSquare.isOnBoard()) { move_it->setOrder(3); continue; } const Move m = move_it->getMove(); const Square from = m.from(); const Square to = m.to(); const Piece atTo = state.pieceOnBoard (to); /* order == 0 : 王手 */ if (move_it->isCheck()) { move_it->setOrder(0); } /* order == 1 : 王ã®è¿‘å‚ã¸ã®åˆ©ã, 大駒ã®é“, å°é§’以外をå–ã‚‹ */ else if (Neighboring8Effect::hasEffect(state, m.ptypeO(), to, opKingSquare)) { move_it->setOrder(1); } else if (hasEffectByBigPieces (state, state.turn (), from)) { move_it->setOrder(1); } else if ((atTo.isPiece()) && (atTo.owner() == alt (state.turn ()))&& (atTo.ptype() != PAWN)) { move_it->setOrder(1); } /* order == 2 : 王ã®25è¿‘å‚,å°é§’ã‚’å–ã‚‹ */ else if (Neighboring25Direct::hasEffect(state, m.ptypeO(), to, opKingSquare)) { move_it->setOrder(2); } else if ((atTo.isPiece()) && (atTo.owner() == alt (state.turn ()))) { move_it->setOrder(2); } /* order > 2 : ãã‚Œä»¥å¤–ã®æ‰‹ */ else { move_it->setOrder(3); } } } template void NtesukiMoveGenerator::generate(const NumEffectState& state, NtesukiMoveList& moves); template void NtesukiMoveGenerator::generate(const NumEffectState& state, NtesukiMoveList& moves); template void NtesukiMoveGenerator::generateWithRzone(const NumEffectState& state, NtesukiRecord* record, int pass_left, NtesukiMoveList& moves); template void NtesukiMoveGenerator::generateWithRzone(const NumEffectState& state, NtesukiRecord* record, int pass_left, NtesukiMoveList& moves); }//ntesuki }//osl // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiExceptions.h0000644000000000000000000000174412316770314021570 0ustar rootroot/* ntesukiExceptions */ #ifndef OSL_NTESUKI_EXCEPTIONS #define OSL_NTESUKI_EXCEPTIONS #include #include #ifndef NDEBUG # define ntesuki_assert(assertion)\ if (!(assertion))\ throw DfpnError("assertion failed", __FILE__, __LINE__); #else #define ntesuki_assert(assertion) #endif #ifndef NDEBUG #define TRY_DFPN \ try\ {\ #define CATCH_DFPN \ }\ catch (DfpnError err)\ {\ ntesuki_assert(false);\ } #else #define TRY_DFPN #define CATCH_DFPN #endif namespace osl { namespace ntesuki { /** * Throwed when something wrong happend with the df-pn search. */ struct DfpnError : std::runtime_error { DfpnError(const char *message, const char *filename, int linenum) : std::runtime_error(message) { std::cerr << message << "\n\tin " << filename << " line " << linenum << "\n"; } }; }// ntesuki }//osl #endif /* OSL_NTESUKI_EXCEPTIONS */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiTable.h0000644000000000000000000001745312316770314020502 0ustar rootroot#ifndef _PD_NTESUKI_TABLE_H #define _PD_NTESUKI_TABLE_H #include "osl/ntesuki/ntesukiRecord.h" #include "osl/ntesuki/ntesukiMove.h" #include "osl/misc/carray.h" #include "osl/stl/hash_set.h" #include "osl/pathEncoding.h" #include "osl/hash/hashKey.h" #include "osl/stl/hash_map.h" #include "osl/stl/slist.h" #include #include namespace osl { namespace stl { template <> struct hash{ unsigned long operator()(const Square& p) const { return p.uintValue(); } }; } namespace ntesuki { /** * An exception thrown when the table is full. */ struct TableFull : std::runtime_error { TableFull() : std::runtime_error("table full") { } }; /** * An exception thrown when forEcachRecordFromRoot is called * althogh the root state is not set. */ struct RootStateNotSet : std::runtime_error { RootStateNotSet () : std::runtime_error("root node not set") { } }; /** * A table to hold ntesukiRecord. */ class NtesukiTable { private: typedef hash_map ntesuki_hash_map; public: class Table : public ntesuki_hash_map { public: unsigned int capacity, default_gc_size; bool verbose, no_gc, gc_request; unsigned int numEntry, numCacheHit, gcCount; NtesukiRecord *root; boost::scoped_ptr rootState; static int largeGCCount; Table(unsigned int capacity, unsigned int default_gc_size, bool verbose); ~Table(); /** * @c key ã«å¯¾å¿œã™ã‚‹ Record ã‚’ Table ã‹ã‚‰æŽ¢ã™. * ã‚‚ã—登録ã•れã¦ã„ãªã‹ã£ãŸã‚‰æ–°ãŸã«ç™»éŒ²ã™ã‚‹. * @param key å±€é¢ã® Hash値 * @return 対応ã™ã‚‹ NtesukiRecord ã¸ã®ãƒã‚¤ãƒ³ã‚¿. * (外部ã‹ã‚‰ delete ç­‰ã—ã¦ã¯ãªã‚‰ãªã„) */ NtesukiRecord *allocate(const HashKey& key, const PieceStand& white_stand, signed short distance); /** * 表を探ã™ï¼Žæ–°ãŸã«ç™»éŒ²ã™ã‚‹äº‹ã¯ãªã„ * @return 存在ã—ãªã‘れã°0 * ãã†ã§ãªã‘れã°å†…部ã§ç¢ºä¿ã—ãŸå ´æ‰€ã¸ã®ãƒã‚¤ãƒ³ã‚¿ * (é–“é•ã£ã¦ã‚‚ delete ã—ãªã„ã“ã¨) */ NtesukiRecord *find(const HashKey& key); /** * 表ã«ç™»éŒ²ã•れãŸè¦ç´ ã‚’削除ã™ã‚‹. */ void erase(const HashKey key); /** * テーブルã«ç™»éŒ²ã•れãŸå„ record ã‚’ F ã§å‡¦ç†ã™ã‚‹. */ template void forEachRecord(F& f); template void forEachRecordFrom(F&, NumEffectState&, NtesukiRecord *); template void forEachRecordFromRoot(F& f); /** * Collect garbage, until the size of the table reduces to * @c gc_size */ void collectGarbage(unsigned int gc_size); }; private: boost::scoped_ptr

table; bool verbose; public: typedef NtesukiRecord record_t; struct HashPathEncoding { unsigned long operator()(PathEncoding const& pe) const { return pe.getPath(); } }; typedef hash_set PathSet; std::vector depths; /** * @param capacity 表ã«ä¿æŒã™ã‚‹æœ€å¤§å±€é¢ */ NtesukiTable(unsigned int capacity, unsigned int default_gc_size=0, bool verbose=false); ~NtesukiTable(); void clear() { table->clear(); } Table::const_iterator begin() const { return table->begin(); } Table::const_iterator end() const { return table->end(); } /** * テーブルをã²ã. ã‚‚ã—è¦ç´ ãŒè¦‹ã¤ã‹ã‚‰ãªã‹ã£ãŸå ´åˆï¼Œ * テーブルã®å¤§ãã•を増やã—ã¦è‰¯ã„ã®ãªã‚‰ï¼Œ * æ–°ã—ã„è¦ç´ ã‚’ allocate ã™ã‚‹. */ NtesukiRecord *allocateRoot(const HashKey& key, const PieceStand& white_stand, signed short distance, const NumEffectState* root_state = NULL) { table->root = table->allocate(key, white_stand, distance); if (root_state) { table->rootState.reset(new NumEffectState(*root_state)); } return table->root; } NtesukiRecord *allocateWithMove(NtesukiRecord* record, const NtesukiMove& move) { /* 毎回 white stand を計算ã—ã¦ã„ã‚‹ã®ã¯ç„¡é§„ */ PieceStand white_stand = record->white_stand; const Move m = move.getMove(); if (!move.isPass() && m.player()) { if (m.isDrop()) { white_stand.sub(m.ptype()); } else if (m.capturePtype() != PTYPE_EMPTY) { white_stand.add(unpromote(m.capturePtype())); } } unsigned short child_distance = record->distance + 1; NtesukiRecord *child = table->allocate(record->key.newHashWithMove(m), white_stand, child_distance); if (child) { child->distance = std::min(child->distance, child_distance); child->checkNewParent(record); } return child; } /** * テーブルã®å¤§ãã•を変化ã•ã›ãšã« find ã™ã‚‹. */ NtesukiRecord *find(const HashKey& key) { return table->find(key); } const NtesukiRecord *find(const HashKey& key) const { return table->find(key); } /** * 表ã«ç™»éŒ²ã•れãŸè¦ç´ ã‚’削除ã™ã‚‹. */ void erase(const HashKey key) { table->erase(key); } /** * 表を整ç†ã™ã‚‹. */ void collectGarbage(unsigned int gc_size) { table->collectGarbage(gc_size); } /** * 与ãˆã‚‰ã‚ŒãŸ @param move ã«æ ¼ç´ã•れã¦ã„る手を返ãã†ã¨ã™ã‚‹. * ãªã‹ã£ãŸã‚‰ãƒ†ãƒ¼ãƒ–ルã‹ã‚‰å¼•ã. */ NtesukiRecord *findWithMove(NtesukiRecord *record, const NtesukiMove& move) { /* テーブルを調ã¹ï¼Œã‚ã£ãŸã‚‰ move ã«ç™»éŒ²ã—ã¦ãŠã * * (関係ãªã„ã¨ã“ã‚ã‹ã‚‰æŒã£ã¦ã㟠move ã ã¨ * record ã«ãªã„ piece ã‚’ drop ã™ã‚‹å¯èƒ½æ€§ãŒ) */ if (move.isNormal() && move.isDrop()) { const Ptype drop_type = unpromote(move.getMove().ptype()); const PieceStand ps = record->getPieceStandSlow(move.getMove() .player()); if (ps.get(drop_type) == 0) { return NULL; } } NtesukiRecord *child = table->find(record->key.newHashWithMove(move.getMove())); if (child) { child->checkNewParent(record); } return child; } NtesukiRecord *findWithMoveConst(const NtesukiRecord *record, const NtesukiMove& move) { /* テーブルを調ã¹ï¼Œã‚ã£ãŸã‚‰ move ã«ç™»éŒ²ã—ã¦ãŠã * * (関係ãªã„ã¨ã“ã‚ã‹ã‚‰æŒã£ã¦ã㟠move ã ã¨ * record ã«ãªã„ piece ã‚’ drop ã™ã‚‹å¯èƒ½æ€§ãŒ) */ if (move.isNormal() && move.isDrop()) { const Ptype drop_type = unpromote(move.getMove().ptype()); const PieceStand ps = record->getPieceStandSlow(move.getMove() .player()); if (ps.get(drop_type) == 0) { return NULL; } } return table->find(record->key.newHashWithMove(move.getMove())); } /** * テーブルã«ç™»éŒ²ã•れãŸå„ record ã‚’ F ã§å‡¦ç†ã™ã‚‹. */ template void forEachRecord(F& f) { table->forEachRecord(f); } /** * テーブルを root node ã‹ã‚‰é †ç•ªã«èª¿ã¹ã‚‹. */ template void forEachRecordFromRoot(F& f) { table->forEachRecordFromRoot(f); } /** * テーブルã«ç™»éŒ²ã•れ㟠record ã®æ•°. */ unsigned int size() const { return table->numEntry;/* not size() */ } unsigned int capacity() const { return table->capacity; } void lockGC() { table->no_gc = true; } void unlockGC() { table->no_gc = false; if (table->gc_request && (table->default_gc_size > 0)) { table->collectGarbage(table->default_gc_size); table->gc_request = false; } } bool isVerbose() const; }; } //ntesuki }// osl #endif /* _PD_NTESUKI_TABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMove.tcc0000644000000000000000000000361512316770314020676 0ustar rootroot/* ntesukiMove.tcc */ #include "osl/ntesuki/ntesukiMove.h" #include "osl/ntesuki/ntesukiRecord.h" template void osl::ntesuki::NtesukiMove:: setImmediateCheckmate() { if (P == osl::BLACK) flags |= (IS_SUCCESS_BLACK_MASK | IMMEDIATE_CHECKMATE); else flags |= (IS_SUCCESS_WHITE_MASK | IMMEDIATE_CHECKMATE); }; /* private functions to check FLAGS for success/fail */ template int osl::ntesuki::NtesukiMove:: is_success_flag(int pass_left) const { ntesuki_assert(pass_left >= 0 && pass_left <= 3); if (P == osl::BLACK) return 1 << (IS_SUCCESS_BLACK_SHIFT + pass_left); if (P == osl::WHITE) return 1 << (IS_SUCCESS_WHITE_SHIFT + pass_left); } template int osl::ntesuki::NtesukiMove:: is_fail_flag(int pass_left) const { ntesuki_assert(pass_left >= 0 && pass_left <= 3); if (P == osl::BLACK) return 1 << (IS_FAIL_BLACK_SHIFT + pass_left); else return 1 << (IS_FAIL_WHITE_SHIFT + pass_left); } template void osl::ntesuki::NtesukiMove:: setCheckmateSuccess(int pass_left) { ntesuki_assert(!(flags & is_success_flag

(pass_left))); ntesuki_assert(!(flags & is_fail_flag

(pass_left))); flags |= is_success_flag

(pass_left); }; template bool osl::ntesuki::NtesukiMove:: isCheckmateSuccess(int pass_left) const { return (flags & is_success_flag

(pass_left)) == is_success_flag

(pass_left); } template void osl::ntesuki::NtesukiMove:: setCheckmateFail(int pass_left) { ntesuki_assert(!(flags & is_fail_flag

(pass_left))); ntesuki_assert(!(flags & is_success_flag

(pass_left))); flags |= is_fail_flag

(pass_left); }; template bool osl::ntesuki::NtesukiMove:: isCheckmateFail(int pass_left) const { return (flags & is_fail_flag

(pass_left)) == is_fail_flag

(pass_left); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/oracleProverLight.tcc0000644000000000000000000002024512316770314022016 0ustar rootroot/* oracleProverLight.tcc */ #include "osl/ntesuki/oracleProverLight.h" #include "osl/ntesuki/ntesukiRecord.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/checkmate/fixedDepthSearcher.h" #include "osl/checkmate/fixedDepthSearcher.tcc" #include "osl/move_classifier/safeMove.h" #include "osl/apply_move/applyMoveWithPath.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/effect_util/effectUtil.h" #ifdef NDEBUG # include "osl/ntesuki/ntesukiMove.tcc" # include "osl/ntesuki/ntesukiRecord.tcc" //# include "osl/move_generator/escape.tcc" #endif using namespace osl; using namespace osl::ntesuki; /* Helper classes */ template class OracleProverLight:: AttackHelper { Searcher* searcher; const NtesukiRecord *record_orig; unsigned int pass_left; public: bool result; AttackHelper(Searcher* searcher, const NtesukiRecord* record_orig, unsigned int pass_left) : searcher(searcher), record_orig(record_orig), pass_left(pass_left) {} void operator()(Square p) { const Player O = PlayerTraits

::opponent; result = (*searcher).template defense(record_orig, pass_left); } }; template class OracleProverLight:: DefenseHelper { Searcher* searcher; const NtesukiRecord *record_orig; unsigned int pass_left; public: bool result; DefenseHelper(Searcher* searcher, const NtesukiRecord* record_orig, unsigned int pass_left) : searcher(searcher), record_orig(record_orig), pass_left(pass_left) {} void operator()(Square p) { const Player O = PlayerTraits

::opponent; result = (*searcher).template attack(record_orig, pass_left); } }; /* Utility */ /* Still cannot see if is safe move */ template static bool is_safe_move(const osl::ntesuki::OracleProverLight::state_t state, const osl::Move& m, int pass_left) { if (!m.isValid()) return false; if (!state.isValidMove(m, false)) return false; if (m.isDrop()) return true; return move_classifier::SafeMove

::isMember(state, m.ptype(), m.from(), m.to()); } /* adjust the captuer ptype of a move */ template static osl::Move adjustMove(const osl::ntesuki::OracleProverLight::state_t state, osl::Move candidate) { if (! candidate.isDrop()) { const osl::Piece p = state.pieceOnBoard(candidate.to()); candidate=setCapture(candidate,p); } return candidate; } /* The worker */ /* attack */ template bool OracleProverLight:: attack(const NtesukiRecord* record_orig, const unsigned int pass_left) { const Player attacker = P; ntesuki_assert(P == state.turn()); if (!record_orig || !record_orig->getValue(pass_left) .isCheckmateSuccess() || !record_orig->getBestMove(pass_left).isValid()) { return false; } Move check_move; FixedDepthSearcher fixed_searcher(state); if (!state.inCheck(P) && fixed_searcher.hasCheckmateMove

(NtesukiRecord::fixed_search_depth, check_move).isCheckmateSuccess()) { /* Immediate Checkmate */ return true; } /* Simulation 元㌠immediate checkmate ãªã‚‰ã“ã®å…ˆã¯ simulate ã§ããªã„ */ const NtesukiMove best_move_orig = record_orig->getBestMove(pass_left); if (best_move_orig.isImmediateCheckmate()) { return false; } /* n ãŒå°‘ãªã„ã¨ãã®çµæžœã‚’å‚ç…§ */ if ((pass_left > 0) && record_orig->getValue(pass_left - 1).isCheckmateSuccess()) { return attack

(record_orig, pass_left - 1); } const Move move = adjustMove

(state, best_move_orig.move()); /* invalid move ã¨ãªã£ã¦ã—ã¾ã£ãŸ */ if (!is_safe_move

(state, move, pass_left)) { return false; } const bool move_is_check = (move_classifier::PlayerMoveAdaptor:: isMember(state, move)); /* å³è©°æŽ¢ç´¢ä¸­ã¯çŽ‹æ‰‹ã®ã¿èª­ã‚€ */ if(0 == pass_left && !move_is_check) { return false; } /* 以å‰ã¯ check ã ã£ãŸã®ãŒä»Šã¯é•ã£ã¦ã—ã¾ã£ãŸãƒ»ãã®é€† */ if (best_move_orig.isCheck() != move_is_check) { return false; } /* 以å‰ã® bestMove を実行 */ const NtesukiRecord* record_child_orig = table.findWithMoveConst(record_orig, best_move_orig); if (!record_child_orig) { //ntesuki_assert (record_orig->isBySimulation()); return false; } //ntesuki_assert(record_child_orig); AttackHelper helper(this, record_child_orig, pass_left); TRY_DFPN; ApplyMoveWithPath

::doUndoMove(state, path, move, helper); CATCH_DFPN; return helper.result; } /* defense */ template bool OracleProverLight:: defense(const NtesukiRecord* record_orig, const unsigned int pass_left) { const Player attacker = PlayerTraits

::opponent; ntesuki_assert(P == state.turn()); if (!record_orig || !record_orig->getValue(pass_left) .isCheckmateSuccess()) { return false; } /* 攻撃å´ã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ãªã„ã‹èª¿ã¹ã‚‹ */ if (state.inCheck(attacker)) { return false; } /* ç¾åœ¨çŽ‹æ‰‹ã«ãªã£ã¦ã„ã‚‹ã‹ã©ã†ã‹ */ if ((pass_left == 0) && !state.inCheck(P)) { return false; } /* n ãŒå°‘ãªã„ã¨ãã®çµæžœã‚’å‚ç…§ */ if (pass_left > 0 && record_orig->getValue(pass_left - 1).isCheckmateSuccess()) { return defense

(record_orig, pass_left - 1); } /* 手ã®ç”Ÿæˆ */ NtesukiMoveList moves; mg->generateSlow(P, state, moves); if (moves.empty()) return true; /* å—ã‘る手ã®å®Ÿè¡Œ */ for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { NtesukiMove& move = *move_it; if (isscheme != NtesukiRecord::normal_is && isscheme != NtesukiRecord::delay_is && move.isCheck() && pass_left > 0) continue; ntesuki_assert(move.isPass() || move.isNormal()); const NtesukiRecord *record_child_orig = table.findWithMoveConst(record_orig, move); if (!record_child_orig || !record_child_orig->getValue(pass_left).isCheckmateSuccess()) { return false; } int pass_left_child = pass_left; if (move.isPass()) --pass_left_child; DefenseHelper helper(this, record_child_orig, pass_left_child); TRY_DFPN; ApplyMoveWithPath

::doUndoMoveOrPass(state, path, move.move(), helper); CATCH_DFPN; if (false == helper.result) return false; } return true; } /* Publice interface */ template bool OracleProverLight:: startFromAttack(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left) { const Player attacker = P; if (!record || !record_orig) return false; if (!record->getPieceStand().isSuperiorOrEqualTo (record_orig->getPDPieces(pass_left))) { return false; } ntesuki_assert(record_orig->getValue(pass_left).isCheckmateSuccess()); if (attack

(record_orig, pass_left)) { #ifndef NDEBUG const NtesukiMove m = (record_orig->getBestMove(pass_left)); ntesuki_assert(m.isValid()); ntesuki_assert(!m.isImmediateCheckmate()); #endif TRY_DFPN; const PieceStand ps = record->getPieceStand(); record->setResult(pass_left, ProofDisproof::Checkmate(), record_orig->getBestMove(pass_left), true, &ps); CATCH_DFPN; return true; } return false; } template bool OracleProverLight:: startFromDefense(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left) { const Player attacker = PlayerTraits

::opponent; if (!record || !record_orig) return false; if (!record->getPieceStand().isSuperiorOrEqualTo (record_orig->getPDPieces(pass_left))) { return false; } ntesuki_assert(record_orig->getValue(pass_left).isCheckmateSuccess()); if (defense

(record_orig, pass_left)) { TRY_DFPN; const PieceStand ps = record->getPieceStand(); record->setResult(pass_left, ProofDisproof::Checkmate(), record_orig->getBestMove(pass_left), true, &ps); CATCH_DFPN; return true; } return false; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/rzone.h0000644000000000000000000000426212316770314017177 0ustar rootroot/* rzone.h */ #ifndef _NTESUKI_RZONE_H #define _NTESUKI_RZONE_H #include "osl/state/numEffectState.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/ntesuki/ntesukiExceptions.h" #include "osl/container/moveVector.h" #include #include #include using namespace osl::state; namespace osl { namespace ntesuki { class Rzone { typedef std::bitset<0x100> mask_t; mask_t mask; public: /** state ã®çމã®ä½ç½®ãŒ mask ã•れ㟠rzone. */ Rzone (NumEffectState state, Player p) { const Square pos = state.kingSquare(p); if (!pos.isOnBoard()) return; unsigned int index = pos.index(); ntesuki_assert(index < Square::indexMax()); mask.set(index); } Rzone() {} Rzone (const Square pos) { unsigned int index = pos.index(); ntesuki_assert(index < Square::indexMax()); mask.set(index); } /** rzone ãŒä¸€ç®‡æ‰€ã§ã‚‚ set ã•れã¦ã„ã‚‹ã‹èª¿ã¹ã‚‹. */ bool any() const { return mask.any(); } /** pos ã« rzone ㌠set ã•れã¦ã„ã‚‹ã‹èª¿ã¹ã‚‹. */ bool test(Square pos) const { return mask.test(pos.index()); } /** rzone ã®æ¯”較. */ bool operator==(const Rzone rhs) const { return mask == rhs.mask; } /** rzone ã®å’Œ. */ Rzone operator+(const Rzone rhs) const { mask_t m = mask | rhs.mask; return Rzone(m); } /** rzone ã®å·®. */ Rzone operator-(const Rzone rhs) const { ntesuki_assert((rhs.mask & mask) == rhs.mask); mask_t m = (rhs.mask ^ mask) & mask; return Rzone(m); } /** rzone ã®æ›´æ–°, 差を返ã™. */ Rzone update(const Rzone rhs) { mask_t mask_orig = mask; mask |= rhs.mask; mask_t mask_diff = (mask_orig ^ mask) & mask; return Rzone(mask_diff); } /** rzone ã®å‡ºåŠ›. */ friend std::ostream& operator<<(std::ostream& os, const Rzone& rzone) { return os << rzone.mask; } private: Rzone(mask_t _mask) : mask(_mask) {} }; } //ntesuki } //osl #endif /* _NTESUKI_SEACHER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/readme.h0000644000000000000000000000033712316770314017276 0ustar rootroot/* readme.h */ #ifndef _README_H #define _README_H namespace osl { /** * ntesuki */ namespace ntesuki { } } #endif /* _README_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSimulationSearcherDisproof.tcc0000644000000000000000000002634512316770314025304 0ustar rootroot/* ntesukiSimulationDisproof.tcc */ #include "osl/ntesuki/ntesukiSimulationSearcher.h" #include "osl/state/hashEffectState.h" #include "osl/ntesuki/ntesukiRecord.h" #include "osl/ntesuki/ntesukiExceptions.h" #include "osl/container/moveVector.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/apply_move/applyMoveWithPath.h" #ifndef NDEBUG #define RETURN \ TRY_DFPN;\ ntesuki_assert(result.isFinal());\ CATCH_DFPN; \ return #else #define RETURN return #endif using namespace osl; using namespace osl::ntesuki; template class NtesukiSimulationSearcher:: AttackHelperDisproof { Searcher* searcher; NtesukiRecord* record; const NtesukiRecord* record_orig; unsigned int pass_left; const Move last_move; public: AttackHelperDisproof(Searcher* searcher, NtesukiRecord* record, const NtesukiRecord* record_orig, unsigned int pass_left, const Move last_move) : searcher(searcher), record(record), record_orig(record_orig), pass_left(pass_left), last_move(last_move) {} void operator()(Square p) { (*searcher).template defenseForDisproof::opponent> (record, record_orig, pass_left, last_move); } }; template class NtesukiSimulationSearcher:: DefenseHelperDisproof { Searcher* searcher; NtesukiRecord* record; const NtesukiRecord* record_orig; unsigned int pass_left; const Move last_move; public: DefenseHelperDisproof(Searcher* searcher, NtesukiRecord* record, const NtesukiRecord* record_orig, unsigned int pass_left, const Move last_move) : searcher(searcher), record(record), record_orig(record_orig), pass_left(pass_left), last_move(last_move) {} void operator()(Square p) { (*searcher).template attackForDisproof::opponent> (record, record_orig, pass_left, last_move); } }; /*====================================================================== * Disproof *====================================================================== */ template void NtesukiSimulationSearcher:: attackForDisproof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left, const Move last_move) { const Player attacker = P; ++node_count; ntesuki_assert(P == state.turn()); ntesuki_assert(record); ntesuki_assert(record->getBestMove(pass_left).isInvalid()); ntesuki_assert(record_orig); const bool invalid_defense = state.inCheck(PlayerTraits

::opponent); if (invalid_defense) { result = ProofDisproof::Checkmate(); RETURN; } ntesuki_assert (!record->isVisited()); NtesukiRecord::VisitLock visitLock(record); if (record->setUpNode

()) { result = record->getValueWithPath(pass_left, path); if (result.isFinal()) { /* result by fixed depth searcher */ RETURN; } } /* n ãŒå°‘ãªã„ã¨ãã®çµæžœã‚’確定 */ if (pass_left > 0) { result = record->getValueWithPath(pass_left - 1, path); if (!result.isFinal()) { NtesukiRecord::UnVisitLock unVisitLock(record); attackForDisproof

(record, record_orig, pass_left - 1, last_move); } if (!result.isCheckmateFail()) { RETURN; } ntesuki_assert(result.isCheckmateFail()); } /* æ”»ã‚æ‰‹ã®ç”Ÿæˆ */ NtesukiMoveList moves; record->generateMoves

(moves, pass_left, false); /* æ”»ã‚る手ã®å®Ÿè¡Œ */ bool has_loop = false; bool disproof_failed = false; for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { NtesukiMove& move = *move_it; if (move.isPass()) continue; if (move.isCheckmateFail(pass_left)) continue; if (!move.isCheck() && 0 == pass_left) continue; /* DANGEROUS this time pawn checkmate might be avoidable */ if (move.isNoPromote()) continue; NtesukiRecord *record_child = table.allocateWithMove(record, move); if (record_child == 0) { result = ProofDisproof::Checkmate(); RETURN; } ntesuki_assert(record_child); if(record_child->isVisited()) { //move.setCheckmateFail(pass_left); has_loop = true; continue; } PathEncoding path_child(path, move.getMove()); result = record_child->getValueWithPath(pass_left, path_child); if(result.isUnknown()) { const NtesukiRecord* record_child_orig = table.findWithMoveConst(record_orig, move); if (!record_child_orig || !record_child_orig->getValue(pass_left).isCheckmateFail()) { /* a move that used not to be a check became a check, or * might have been a loop */ result = ProofDisproof::Checkmate(); RETURN; } AttackHelperDisproof helper(this, record_child, record_child_orig, pass_left, move.getMove()); TRY_DFPN; ApplyMoveWithPath

::doUndoMove(state, path, move.getMove(), helper); CATCH_DFPN; if (record->getValueWithPath(pass_left, path).isFinal()) { result = record->getValueWithPath(pass_left, path); RETURN; } } if (result.isCheckmateSuccess()) { disproof_failed = true; continue; } else if (result == ProofDisproof::LoopDetection()) { has_loop = true; } ntesuki_assert(result.isCheckmateFail()); move.setCheckmateFail(pass_left); } if (disproof_failed) { result = ProofDisproof::Checkmate(); RETURN; } if (has_loop) { record->setLoopWithPath(pass_left, path); result = ProofDisproof::LoopDetection(); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; } else { result = ProofDisproof::NoCheckmate(); TRY_DFPN; record->setResult(pass_left, result, NtesukiMove::INVALID(), true); CATCH_DFPN; } RETURN; } template void NtesukiSimulationSearcher:: defenseForDisproof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left, const Move last_move) { const Player attacker = PlayerTraits

::opponent; ++node_count; ntesuki_assert(P == state.turn()); ntesuki_assert(state.inCheck(P) || (pass_left > 0)); ntesuki_assert(record); ntesuki_assert(record->getBestMove(pass_left).isInvalid()); ntesuki_assert(record_orig); ntesuki_assert(!record->isVisited()); ntesuki_assert(record_orig->getValue(pass_left). isCheckmateFail()); NtesukiRecord::VisitLock visitLock(record); if (record->setUpNode

()) { result = record->getValueWithPath(pass_left, path); if (result.isFinal()) { /* result by fixed depth searcher */ RETURN; } } #ifndef NDEBUG /* 攻撃å´ã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ãªã„ã‹èª¿ã¹ã‚‹ */ ntesuki_assert(!state.inCheck(attacker)); #endif /* 以å‰ã® bestMove を実行 */ const NtesukiMove best_move = record_orig->getBestMove(pass_left); if (best_move.isInvalid()) { /* is by fixed depth searcher */ result = ProofDisproof::Checkmate(); RETURN; } const NtesukiRecord *record_child_orig = table.findWithMoveConst(record_orig, best_move); if (!record_child_orig || !record_child_orig->getValue(pass_left).isCheckmateFail()) { /* fixed depth searcher ç­‰ã§ã® disproof */ result = ProofDisproof::Checkmate(); RETURN; } ntesuki_assert(record_child_orig); if (!best_move.isPass() && !state.template isAlmostValidMove(best_move.getMove())) { result = ProofDisproof::Checkmate(); RETURN; } NtesukiRecord *record_child = table.allocateWithMove(record, best_move); if (record_child == 0) { result = ProofDisproof::Checkmate(); RETURN; } ntesuki_assert(record_child); int pass_left_child = pass_left; if (best_move.isPass()) --pass_left_child; if (record_child->isVisited()) { TRY_DFPN; result = ProofDisproof::LoopDetection(); record->setLoopWithPath(pass_left, path); record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; RETURN; } else if (!record_child_orig->getValue(pass_left_child).isCheckmateFail()) { result = ProofDisproof::Checkmate(); RETURN; } const PathEncoding path_child(path, best_move.getMove()); result = record_child->getValueWithPath(pass_left_child, path_child); if (result.isUnknown()) { DefenseHelperDisproof helper(this, record_child, record_child_orig, pass_left_child, best_move.getMove()); TRY_DFPN; ApplyMoveWithPath

::doUndoMoveOrPass(state, path, best_move.getMove(), helper); CATCH_DFPN; if (record->getValueWithPath(pass_left, path).isFinal()) { result = record->getValueWithPath(pass_left, path); RETURN; } } if (result == ProofDisproof::LoopDetection()) { TRY_DFPN; record->setLoopWithPath(pass_left, path); record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; RETURN; } else if (result.isCheckmateFail()) { NtesukiMove move(best_move.getMove()); TRY_DFPN; move.setCheckmateFail(pass_left); record->setResult(pass_left, result, move, true); CATCH_DFPN; RETURN; } else { /* best_move is invalid : some rare casese, including * - the original state was invalid(attacker was under check) */ // ntesuki_assert(record_orig->getValue(pass_left) // == ProofDisproof::AttackBack()); result = ProofDisproof::Checkmate(); RETURN; } } /* Start simulation to disproof, P as Attacker. * @return true, if nocheckmate is proven */ template bool NtesukiSimulationSearcher:: startFromAttackDisproof(NtesukiRecord *record, const NtesukiRecord *record_orig, const unsigned int pass_left, const Move last_move) { ++disproof_count; const Player attacker = P; ntesuki_assert(record_orig); if (!record_orig->getValue(pass_left).isCheckmateFail()) return false; TRY_DFPN; attackForDisproof

(record, record_orig, pass_left, last_move); CATCH_DFPN; if (result.isCheckmateFail()) { ++disproof_success_count; return true; } return false; } /* Start simulation to disproof, P as Defender. * @return true, if nocheckmate is proven */ template bool NtesukiSimulationSearcher:: startFromDefenseDisproof(NtesukiRecord *record, const NtesukiRecord *record_orig, const unsigned int pass_left, const Move last_move) { ntesuki_assert (P == state.turn()); ++disproof_count; const Player attacker = PlayerTraits

::opponent; ntesuki_assert(record_orig); if (!record_orig->getValue(pass_left).isCheckmateFail()) return false; TRY_DFPN; defenseForDisproof

(record, record_orig, pass_left, last_move); CATCH_DFPN; if (result.isCheckmateFail()) { ++disproof_success_count; return true; } return false; } #undef RETURN // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMove.h0000644000000000000000000001202112316770314020343 0ustar rootroot/* ntesukiMove.h */ #ifndef _NTESUKIMOVE_H #define _NTESUKIMOVE_H #include "osl/move.h" #include "osl/ntesuki/ntesukiExceptions.h" namespace osl { namespace ntesuki { /** * Move ã« ntesuki 探索ã«é–¢ã™ã‚‹æƒ…報を加ãˆãŸã‚‚ã® * * - flag ã«ãƒŽãƒ¼ãƒ‰ã®çŠ¶æ…‹ã‚’ä¿æŒã™ã‚‹ã‚ˆã†ã«ã—㟠*/ class NtesukiMove { enum Flags { NONE = 0, /* 2^0 */ CHECK_FLAG = 1, /** If this move is a check move. */ /* 2^1 */ PAWN_DROP_CHECKMATE_FLAG = 2, /** If this move is a pawn drop checkmate foul. */ /* 2^2 */ /* 4 not used */ /* 2^3 */ IMMEDIATE_CHECKMATE = 8, /** If this move is an immidiate checkmate. */ /* 2^4 */ TO_OLDER_CHILD = 16, /** If the distance of the parent is larger than the child */ /* 2^5 */ NOPROMOTE = 32, /** A promotable PAWN,ROOK,BISHOP move without promotion */ /* 2^6 */ INTERPOSE = 64, /** Aigoma */ /* 2^7 */ ATTACK_FLAG = 128, /** Attack move candidate */ /* 2^8 */ BY_SIMULATION = 256, /** Value of the node after this move determined by simulation */ /* 2^9 */ LAME_LONG = 512, /* 2^10 */ /* 2^11 */ /* 2^12 */ /* 2^13 */ /* 2^14 */ /* 2^15 */ WHITE_SHIFT = 4, IS_SUCCESS_SHIFT = 16, /** This move leads to checkmate success. */ /* 16-19 BLACK SUCCESS */ IS_SUCCESS_BLACK_SHIFT = IS_SUCCESS_SHIFT, /* 20-23 WHITE SUCCESS */ IS_SUCCESS_WHITE_SHIFT = IS_SUCCESS_SHIFT + WHITE_SHIFT, IS_SUCCESS_BLACK_BASE = 1 << IS_SUCCESS_BLACK_SHIFT, IS_SUCCESS_WHITE_BASE = 1 << IS_SUCCESS_WHITE_SHIFT, IS_SUCCESS_BLACK_MASK = 0xf * IS_SUCCESS_BLACK_BASE, IS_SUCCESS_WHITE_MASK = 0xf * IS_SUCCESS_WHITE_BASE, IS_FAIL_SHIFT = 24, /** This move leads to checkmate fail. */ /* 24-27 BLACK FAIL */ IS_FAIL_BLACK_SHIFT = IS_FAIL_SHIFT, /* 28-31 WHITE FAIL */ IS_FAIL_WHITE_SHIFT = IS_FAIL_SHIFT + WHITE_SHIFT, IS_FAIL_BLACK_BASE = 1 << IS_FAIL_SHIFT, IS_FAIL_WHITE_BASE = 1 << (IS_FAIL_SHIFT + WHITE_SHIFT), IS_FAIL_BLACK_MASK = 0xf * IS_FAIL_BLACK_BASE, IS_FAIL_WHITE_MASK = 0xfLL * IS_FAIL_WHITE_BASE, }; static std::string FlagsStr[]; template int is_success_flag(int pass_left) const; template int is_fail_flag(int pass_left) const; osl::Move move; int flags; int order; public: unsigned short h_a_proof, h_a_disproof; // 4 byte unsigned short h_d_proof, h_d_disproof; // 4 byte public: NtesukiMove(); NtesukiMove(osl::Move m); NtesukiMove(osl::Move m, Flags f); NtesukiMove(const NtesukiMove&); ~NtesukiMove(); NtesukiMove operator=(const NtesukiMove&); /* static methods */ static NtesukiMove INVALID(); /* about the state of the node */ /* if it is a check move */ void setCheck(); bool isCheck() const; /* if it is a check move */ void setOrder(int o); int getOrder() const; /* interpose */ void setInterpose(); bool isInterpose() const; /* long move with no specific meaning */ void setLameLong(); bool isLameLong() const; /* by simulation */ void setBySimulation(); bool isBySimulation() const; /* nopromote */ void setNoPromote(); bool isNoPromote() const; /* if it is a move to an child with less depth */ void setToOld(); bool isToOld() const; /* if it is a immidiate checkmate move */ template void setImmediateCheckmate(); bool isImmediateCheckmate() const; /* if it is a success/fail move */ template void setCheckmateSuccess(int pass_left); template bool isCheckmateSuccess(int pass_left) const; bool isCheckmateSuccessSlow(Player P, int pass_left) const; template void setCheckmateFail(int pass_left); template bool isCheckmateFail(int pass_left) const; bool isCheckmateFailSlow(Player P, int pass_left) const; /* if it is a pawn drop checkmate move */ void setPawnDropCheckmate(); bool isPawnDropCheckmate() const; /* estimates used before the node after the move is expanded */ void setHEstimates(unsigned short p_a, unsigned short d_a, unsigned short p_d, unsigned short d_d); void setCEstimates(unsigned short p, unsigned short d); /* about the move itself */ bool isValid() const; bool isInvalid() const; bool isNormal() const; bool isPass() const; bool isDrop() const; Square to() const; Ptype ptype() const; Move getMove() const; /* equality, only the equality of the move is checked * (the flags are not considered) */ bool operator==(const NtesukiMove& rhs) const; bool operator!=(const NtesukiMove& rhs) const; /* output to stream */ void flagsToStream(std::ostream& os) const; friend std::ostream& operator<<(std::ostream& os, const NtesukiMove& move); }; }// ntesuki }// osl #endif /* _NTESUKIMOVE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiRecord.h0000644000000000000000000004515712316770314020673 0ustar rootroot#ifndef _NTESUKI_NTESUKI_RECORD_H #define _NTESUKI_NTESUKI_RECORD_H #include "osl/ntesuki/ntesukiResult.h" #include "osl/ntesuki/ntesukiMove.h" #include "osl/ntesuki/ntesukiMoveList.h" #include "osl/ntesuki/rzone.h" #include "osl/ntesuki/ntesukiExceptions.h" #include "osl/checkmate/checkAssert.h" #include "osl/misc/carray.h" #include "osl/state/hashEffectState.h" #include "osl/container/moveVector.h" #include "osl/pathEncoding.h" #include namespace osl { namespace ntesuki { class NtesukiRecord; class PathEncodingList : public slist { }; class NtesukiMoveGenerator; class NtesukiTable; /** * ã‚ã‚‹å±€é¢ã«ã¤ã„ã¦ï¼Œãã®å±€é¢ã‚’ n手ã™ãã§æŽ¢ç´¢ã—ãŸå ´åˆã® * çµæžœã‚’ä¿æŒã—ã¦ãŠãクラス. */ class NtesukiRecord { public: typedef slist RecordList; typedef slist RecordPList; /** * å„é…列ã®ã‚µã‚¤ã‚º. SIZE - 1 手ã™ãã¾ã§èª¿ã¹ã‚‰ã‚Œã‚‹. */ static const unsigned int SIZE = 2; enum IWScheme { no_iw = 0, strict_iw = 1, pn_iw = 2 }; enum PSScheme { no_ps = 0, pn_ps = 1 }; enum ISScheme { no_is = 0, tonshi_is = 1, delay_is = 2, normal_is = 3 }; /** * 探索関係ã®è‰²ã€…ãªæƒ…å ±. */ static unsigned int fixed_search_depth; static unsigned int inversion_cost; static bool use_dominance; static int pass_count; static bool max_for_split; static bool use_rzone_move_generation; static bool delay_lame_long; static bool use_9rzone; static NumEffectState *state; static NtesukiMoveGenerator *mg; static NtesukiTable *table; /* DAG関係ã®çµ±è¨ˆæƒ…å ± */ static unsigned int split_count /** 分æµç‚¹ãŒã„ãã¤ã‚ã‚‹ã‹. */, confluence_count /** åˆæµç‚¹ãŒã„ãã¤ã‚ã‚‹ã‹. */; /* Visit Lock */ class VisitLock; class UnVisitLock; /** å„ãƒ—ãƒ¬ã‚¤ãƒ¤ã®æŒé§’ */ PieceStand black_stand, white_stand; /** root ã‹ã‚‰ã®æœ€çŸ­ path ã®è·é›¢ */ unsigned short distance; /** å±€é¢ã® HashKey */ HashKey key; /** 盤é¢ãƒ»æ‰‹ç•ªãŒåŒã˜ã§ï¼ŒæŒé§’ã ã‘é•ã†å±€é¢ã®ãƒªã‚¹ãƒˆ */ RecordList *same_board_list; /** 親局é¢ã®ãƒªã‚¹ãƒˆ */ RecordPList parents; int rev_refcount;/* å­ã‹ã‚‰è¦ªã¸ã® reference ã® count */ /** * コンストラクタ. */ NtesukiRecord(signed short distance, const HashKey& key, const PieceStand& white_stand, RecordList* same_board_list); ~NtesukiRecord() { } /** 手番 */ Player turn() const { return key.turn(); } /** simulation ã«ã‚ˆã£ã¦å€¤ãŒæ±ºã¾ã£ãŸã‹ */ bool isBySimulation() const { return by_simulation; } /** * ã“ã®å±€é¢ã§ã®ãƒ—ãƒ¬ã‚¤ãƒ¤ã®æŒé§’. * - @const P プレイヤ */ template const PieceStand& getPieceStand() const { return piece_stand

(); } const PieceStand& getPieceStandSlow(Player P) const { if (P == BLACK) { return piece_stand(); } else { return piece_stand(); } } /** * 証明駒を計算ã™ã‚‹. * - @const A 攻撃å´ã®ãƒ—レイヤ */ template PieceStand calcProofPiecesOr(int pass_left, const NtesukiMove& m); template PieceStand calcProofPiecesAnd(int pass_left); /** * 証明駒を設定ã™ã‚‹. * - @const A 攻撃å´ã®ãƒ—レイヤ */ template void setProofPieces(int pass_left, const NtesukiResult& r, const NtesukiMove& m, const PieceStand* ps); /** * å証駒を設定ã™ã‚‹. * - @const A 攻撃å´ã®ãƒ—レイヤ */ template void setDisproofPieces(int pass_left, const NtesukiResult& r, const NtesukiMove& m, const PieceStand* ps); /** * 探索ã®çµæžœã‚’æ ¼ç´ã™ã‚‹ * - @const A 攻撃å´ã®ãƒ—レイヤ */ template void setResult(int i, const NtesukiResult& r, const NtesukiMove& m, bool bs, const PieceStand* ps = NULL); /** ã“ã®ãƒŽãƒ¼ãƒ‰ã® NtesukiResult ã®å€¤ã‚’調ã¹ã‚‹ * - @const A 攻撃å´ã®ãƒ—レイヤ */ template const NtesukiResult getValue(int i) const; template const NtesukiResult getValueWithPath(int i, const PathEncoding path) const; template const NtesukiResult getValueOr(int i, const PathEncoding path, IWScheme iwscheme) const; template const NtesukiResult getValueAnd(int i, const PathEncoding path, IWScheme iwscheme, PSScheme psscheme) const; const NtesukiResult getValueSlow(const Player attacker, int i) const; const NtesukiResult getValueOfTurn(int i) const; const NtesukiResult valueBeforeFinal() const; /* å‹ã¡ã‹èª¿ã¹ã‚‹. * å‹ã¡ã ã£ãŸã‚‰ pass_left を, * ãれ以外ã ã£ãŸã‚‰ SIZE ã‚’è¿”ã™. */ int isWin(const Player attacker) const { int o = 0; for (; o < (int)SIZE; o++) { if (getValueSlow(attacker, o).isCheckmateSuccess()) { break; } } return o; } /** * 登録ã•れã¦ã‚‹æœ€å–„手を返ã™. */ template const NtesukiMove& getBestMove(int i) const; const NtesukiMove& getBestMoveSlow(Player attacker, int i) const; /** * Loop ã«ãªã£ã¦ã„ã‚‹ã‹ãƒã‚§ãƒƒã‚¯. */ bool isVisited() const { return visited; } bool isFinal() {return final; } void setVisited() { assert (!visited); visited = true; } void resetVisited() { assert (visited); visited = false; } /** * Fixed Depth Searcher ã«ã‚ˆã£ã¦å€¤ãŒè¨­å®šã•れãŸã‹. */ template bool isByFixed() const; bool isByFixedSlow(Player attacker) const; /** * ã“ã®ãƒŽãƒ¼ãƒ‰ãŒ n手ã™ãã«ãªã£ã¦ã„ã‚‹ã‹. */ template bool isNtesuki(int pass_left) const; template void setNtesuki(int pass_left); /** * ã“ã®ãƒŽãƒ¼ãƒ‰ã§è¦ªã‹ã‚‰æ¥ãŸ oracle を試ã—ãŸã‹ */ template bool hasTriedPropagatedOracle(int pass_left) const; template void triedPropagatedOracle(int pass_left); /** * 証明駒を得る */ template PieceStand getPDPieces(int pass_left) const; PieceStand getPDPiecesSlow(Player attacker, int pass_left) const; template void setPDPieces(int pass_left, const PieceStand p); /** * ç„¡é§„åˆã„を読むã¹ãã‹. */ bool readInterpose(int pass_left) const { return read_interpose[pass_left]; } void setReadInterpose(int pass_left) { read_interpose[pass_left] = true; } /** * defense ã®éš›ã«çŽ‹æ‰‹ã‚’èª­ã‚€ã¹ãã‹. */ bool readCheckDefense(int pass_left) const { return read_check_defense[pass_left]; } void setReadCheckDefense(int pass_left) { read_check_defense[pass_left] = true; } /** * attack ã®éš›ã«ï¼Œãƒ’ューリスティックã«åˆ¤åˆ¥ã•ã‚ŒãŸæ”»æ’ƒæ‰‹ä»¥å¤–も読むã‹. */ bool readNonAttack(int pass_left) const { return read_non_attack[pass_left]; } void setReadNonAttack(int pass_left) { read_non_attack[pass_left] = true; } /** * old child を読むã¹ãã‹. */ template bool useOld(int pass_left) const; template void setUseOld(int pass_left, bool value); /** * ã“ã® path ã§ loop ã«ãªã‚‹ã‹ï¼Ž */ template bool isLoopWithPath(int pass_left, const PathEncoding& path) const; template void setLoopWithPath(int pass_left, const PathEncoding& path); template bool hasLoop(int pass_left) const { return !loop_path_list()[pass_left].empty(); } /** * Fixed Depth Searcher を呼ã¶ç­‰. */ template bool setUpNode(); /* 王手ã®ã‹ã‹ã£ã¦ã„ãªã„å±€é¢. */ template void setUpAttackNode(); /* 王手ã®ã‹ã‹ã£ã¦ã„ã‚‹å±€é¢. */ template void setUpDefenseNode(); /* å­ãƒŽãƒ¼ãƒ‰ã‹ã‚‰ã®æƒ…報を使ã£ã¦ç¾åœ¨ã®æƒ…報を更新ã™ã‚‹. */ void updateWithChild(NtesukiRecord* child, int pass_left); /** * 手ã®ç”Ÿæˆ. */ template void generateMoves(NtesukiMoveList& moves, int pass_left, bool all_moves); bool operator==(const NtesukiRecord& record) { return key == record.key; } /* GC 関係 */ unsigned int getChildCount() const { return child_count; } void addChildCount(unsigned int i) { child_count += i; } unsigned int getReadCount() const { return read_count; } unsigned int getWrittenCount() const { return written_count; } /* DAG 対策関係 */ private: bool isNewParent(const NtesukiRecord* p) const { for (RecordPList::const_iterator it = parents.begin(); it != parents.end(); ++it) { if (*it == p) return false; } return true; } void find_split(NtesukiRecord *rhs, RecordPList& lvisited, RecordPList& rvisited) { if (find_split_right(rhs, lvisited, rvisited)) { return; } #if 1 if (parents.empty()) { return; } /* 最åˆã®ä¸€ã¤ã®è¦ªã ã‘見る */ RecordPList::iterator lp = parents.begin(); if (std::find(lvisited.begin(), lvisited.end(), *lp) != lvisited.end()) { return; } lvisited.push_front(*lp); (*lp)->find_split(rhs, lvisited, rvisited); lvisited.pop_front(); #else for (RecordPList::iterator lp = parents.begin(); lp != parents.end(); ++lp) { if (std::find(lvisited.begin(), lvisited.end(), *lp) == lvisited.end()) { lvisited.push_front(*lp); (*lp)->find_split(rhs, lvisited, rvisited); lvisited.pop_front(); } } #endif } /* find_split 一ã¤ã§ã‚„ã‚ã†ã¨ã™ã‚‹ã¨ï¼Œ O(n^2) ã§æ¸ˆã‚€ã¨ã“ã‚ã‚‚ O(2^n) ã‹ã‹ã‚‹ã®ã§æ³¨æ„ */ bool find_split_right(NtesukiRecord *rhs, RecordPList& lvisited, RecordPList& rvisited) { if (this == rhs) { if (!is_split) { ++split_count; is_split = true; } return true; } #if 1 if (rhs->parents.empty()) { return false; } /* 最åˆã®ä¸€ã¤ã®è¦ªã ã‘見る */ RecordPList::iterator rp = rhs->parents.begin(); if (std::find(rvisited.begin(), rvisited.end(), *rp) != rvisited.end()) { return false; } rvisited.push_front(*rp); bool result = find_split_right(*rp, lvisited, rvisited); rvisited.pop_front(); return result; #else bool result = false; for (RecordPList::iterator rp = rhs->parents.begin(); rp != rhs->parents.end(); ++rp) { if (std::find(rvisited.begin(), rvisited.end(), *rp) == rvisited.end()) { rvisited.push_front(*rp); result |= find_split_right(*rp, lvisited, rvisited); rvisited.pop_front(); } } return result; #endif } void addNewParent(NtesukiRecord* p) { ntesuki_assert(isNewParent(p)); parents.push_front(p); p->rev_refcount++; } public: void checkNewParent(NtesukiRecord *p) { if (parents.empty()) { /* allocate ã•れãŸã°ã‹ã‚Šãªã‚‰ï¼Œ parent ã‚’ add ã—ã¦çµ‚了 */ addNewParent(p); } else if (isNewParent(p)) { ++confluence_count; if (max_for_split) { /* DAG ã®åˆ†æµæŽ¥ç‚¹(?)を探㙠*/ RecordPList lvisited, rvisited; lvisited.push_front(this); rvisited.push_front(p); find_split(p, lvisited, rvisited); } addNewParent(p); } } private: typedef CArray values_t; typedef CArray moves_t; typedef CArray nodesread_t; typedef CArray pdpieces_t; typedef CArray flags_t; typedef CArray pell_t; typedef CArray rzones_t; values_t values_black, values_white; moves_t best_move_black, best_move_white; pdpieces_t pd_pieces_black, pd_pieces_white; /** åŒä¸€ã®å±€é¢ã§ï¼ŒLoop ã«ãªã£ã¦ã„ã‚‹ã‚‚ã®ã® Path */ pell_t loop_path_list_black, loop_path_list_white; mutable unsigned int child_count, read_count, written_count; NtesukiResult value_before_final;/** setResult ã§ final ãªå€¤ã‚’設定ã•れる直å‰ã® result */ bool visited; bool by_simulation; bool by_fixed_black, by_fixed_white; bool already_set_up; bool final; public: bool is_split; /** DAG ã®åˆ†æµç‚¹ */ bool do_oracle_attack; /* AND節点ã«ã¤ã„ã¦ï¼Œè¦ªç¯€ç‚¹ãŒ pass_left = 0 ã§ disproof * ã•れãŸå ´åˆï¼Œã“ã®ç¯€ç‚¹ã‹ã‚‰ãƒ‘スã§åˆ°é”ã§ãる節点ã«ã¤ã„ã¦ï¼Œ * simulation ã‚’ã™ã‚‹. */ bool do_oracle_aunt; /* OR 節点ã§ï¼Œrzone を使用ã—ãŸæ‰‹ç”Ÿæˆã‚’ã™ã‚‹ */ bool rzone_move_generation; private: flags_t read_interpose;/* å—ã‘æ–¹ã§ã®ã¿ä½¿ã‚れる */ flags_t read_check_defense;/* å—ã‘æ–¹ã§ã®ã¿ä½¿ã‚れる */ flags_t read_non_attack;/* æ”»ã‚æ–¹ã§ã®ã¿ä½¿ã‚れる */ flags_t is_ntesuki_black, is_ntesuki_white; flags_t propagated_oracle_black, propagated_oracle_white; flags_t use_old_black, use_old_white; rzones_t rzone_black, rzone_white; NtesukiRecord(); template bool& by_fixed() { if (P == BLACK) return by_fixed_black; else return by_fixed_white; } template const bool& by_fixed() const { if (P == BLACK) return by_fixed_black; else return by_fixed_white; } template PieceStand& piece_stand() { if (P == BLACK) return black_stand; else return white_stand; } template const PieceStand& piece_stand() const { if (P == BLACK) return black_stand; else return white_stand; } template values_t& values() { if (P == BLACK) return values_black; else return values_white; } template const values_t& values() const { if (P == BLACK) return values_black; else return values_white; } template moves_t& best_move() { if (P == BLACK) return best_move_black; else return best_move_white; } template const moves_t& best_move() const { if (P == BLACK) return best_move_black; else return best_move_white; } template pdpieces_t& pdpieces() { if (P == BLACK) return pd_pieces_black; else return pd_pieces_white; } template const pdpieces_t& pdpieces() const { if (P == BLACK) return pd_pieces_black; else return pd_pieces_white; } template flags_t& is_ntesuki() { if (P == BLACK) return is_ntesuki_black; else return is_ntesuki_white; } template const flags_t& is_ntesuki() const { if (P == BLACK) return is_ntesuki_black; else return is_ntesuki_white; } template flags_t& propagated_oracle() { if (P == BLACK) return propagated_oracle_black; else return propagated_oracle_white; } template const flags_t propagated_oracle() const { if (P == BLACK) return propagated_oracle_black; else return propagated_oracle_white; } template flags_t& use_old() { if (P == BLACK) return use_old_black; else return use_old_white; } template const flags_t use_old() const { if (P == BLACK) return use_old_black; else return use_old_white; } template pell_t& loop_path_list() { if (P == BLACK) return loop_path_list_black; else return loop_path_list_white; } template const pell_t& loop_path_list() const { if (P == BLACK) return loop_path_list_black; else return loop_path_list_white; } public: template rzones_t& rzone() { if (P == BLACK) return rzone_black; else return rzone_white; } private: template void setFinal(int i, const NtesukiResult& r, const NtesukiMove& m, const PieceStand* ps); /** * Dominace ã®ä¼æ’­ç”¨. */ void lookup_same_board_list(); template void propagate_proof(int pass_left); template void propagate_disproof(int pass_left); public: template bool isDominatedByProofPieces(const NtesukiRecord* record, int pass_left) const; template bool isDominatedByDisproofPieces(const NtesukiRecord* record, int pass_left) const; template bool isBetterFor(NtesukiRecord* record); }; std::ostream& operator<<(std::ostream&, const osl::ntesuki::NtesukiRecord&); std::ostream& operator<<(std::ostream&, const osl::ntesuki::NtesukiRecord::IWScheme&); std::istream& operator>>(std::istream&, osl::ntesuki::NtesukiRecord::IWScheme&); std::ostream& operator<<(std::ostream&, const osl::ntesuki::NtesukiRecord::PSScheme&); std::istream& operator>>(std::istream&, osl::ntesuki::NtesukiRecord::PSScheme&); std::ostream& operator<<(std::ostream&, const osl::ntesuki::NtesukiRecord::ISScheme&); std::istream& operator>>(std::istream&, osl::ntesuki::NtesukiRecord::ISScheme&); class NtesukiRecord::VisitLock { NtesukiRecord* record; public: VisitLock(NtesukiRecord* record) : record(record) { assert(!record->isVisited()); record->setVisited(); } ~VisitLock() { assert(record->isVisited()); record->resetVisited(); } }; class NtesukiRecord::UnVisitLock { NtesukiRecord* record; public: UnVisitLock(NtesukiRecord* record) : record(record) { assert(record->isVisited()); record->resetVisited(); } ~UnVisitLock() { assert(!record->isVisited()); record->setVisited(); } }; }//ntesuki }//osl #endif /* _NTESUKI_NTESUKI_RECORD_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiRecord.tcc0000644000000000000000000006327512316770314021216 0ustar rootroot#include "ntesukiRecord.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/ntesuki/ntesukiTable.h" #include "osl/checkmate/fixedDepthSearcher.h" #include "osl/checkmate/fixedDepthSearcher.tcc" #include "osl/checkmate/libertyEstimator.h" #include "osl/threatmate/richPredictor.h" #include "osl/threatmate/kfendPredictor.h" #include "osl/effect_util/effectUtil.h" #include "osl/checkmate/pawnCheckmateMoves.h" #include "osl/effect_util/unblockableCheck.h" #include "osl/pieceStand.h" template void osl::ntesuki::NtesukiRecord:: propagate_proof(int pass_left) { for (RecordList::iterator it = same_board_list->begin(); it != same_board_list->end(); it++) { if (&(*it) == this) { continue; } if (it->isDominatedByProofPieces

(this, pass_left)) { if (!it->getValue

(pass_left).isFinal()) { PieceStand ps = getPDPieces

(pass_left); TRY_DFPN; it->setResult

(pass_left, getValue

(pass_left), getBestMove

(pass_left), false, &ps); CATCH_DFPN; } else { if (!it->getValue

(pass_left).isCheckmateSuccess()) { #ifdef DEBUG std::cerr << <"for " < P << "\tat pass_left:" << pass_left << "\tcontradiction occured\n" << *it << *this; ntesuki_assert(pass_left >0 || it->getValue

(pass_left) == ProofDisproof::LoopDetection() || getValue

(pass_left) == ProofDisproof::LoopDetection()); #endif } } } } } template void osl::ntesuki::NtesukiRecord:: propagate_disproof(int pass_left) { for (RecordList::iterator it = same_board_list->begin(); it != same_board_list->end(); it++) { if (&(*it) == this) { continue; } if (it->isDominatedByDisproofPieces

(this, pass_left)) { if (!it->getValue

(pass_left).isFinal()) { PieceStand ps = getPDPieces

(pass_left); TRY_DFPN; it->setResult

(pass_left, getValue

(pass_left), getBestMove

(pass_left), false, &ps); CATCH_DFPN; } else { if (!it->getValue

(pass_left).isCheckmateFail()) { #ifdef DEBUG std::cerr << <"for " < P << "\tat pass_left:" << pass_left << "\tcontradiction occured\n" << *it << *this; ntesuki_assert(it->getValue

(pass_left) == ProofDisproof::LoopDetection() || getValue

(pass_left) == ProofDisproof::LoopDetection()); #endif } } } } } namespace osl { namespace ntesuki { template Ptype getCheapestDrop(Player turn, const NumEffectState& state) { if (state.hasPieceOnStand(turn, PAWN)) return PAWN; if (state.hasPieceOnStand(turn, LANCE)) return LANCE; if (state.hasPieceOnStand(turn, KNIGHT)) return KNIGHT; if (state.hasPieceOnStand(turn, SILVER)) return SILVER; if (state.hasPieceOnStand(turn, GOLD)) return GOLD; if (state.hasPieceOnStand(turn, BISHOP)) return BISHOP; if (state.hasPieceOnStand(turn, ROOK)) return ROOK; return PTYPE_EMPTY; } template Ptype getSecondCheapestDrop(Player turn, const NumEffectState& state, Ptype cheapest) { if (cheapest == PAWN) { if (state.hasPieceOnStand(turn, LANCE)) return LANCE; if (state.hasPieceOnStand(turn, KNIGHT)) return KNIGHT; if (state.hasPieceOnStand(turn, SILVER)) return SILVER; if (state.hasPieceOnStand(turn, GOLD)) return GOLD; if (state.hasPieceOnStand(turn, BISHOP)) return BISHOP; if (state.hasPieceOnStand(turn, ROOK)) return ROOK; } return PTYPE_EMPTY; } } } /* ãƒŽãƒ¼ãƒ‰ã®æº–å‚™ * - æ·±ã•固定 checkmate searcher を呼ã³å‡ºã™ */ template bool osl::ntesuki::NtesukiRecord:: setUpNode() { ntesuki_assert(state->turn() == turn()); #ifndef NDEBUG const Player O = PlayerTraits::opponent; #endif const bool under_attack = state->inCheck(T); ntesuki_assert(!state->inCheck(O)); if (already_set_up) { return false; } already_set_up = true; /* é»’ãŒæ”»ã‚ã‚‹ã¨ãã® Rzone ã¯ç™½ã®çމã®ä½ç½® */ rzone()[0] = Rzone(*state, WHITE); rzone()[1] = rzone()[0]; /* ç™½ãŒæ”»ã‚ã‚‹ã¨ãã® Rzone ã¯é»’ã®çމã®ä½ç½® */ rzone()[0] = Rzone(*state, BLACK); rzone()[1] = rzone()[0]; if (!under_attack) { setUpAttackNode(); } else { setUpDefenseNode(); } return true; } template void osl::ntesuki::NtesukiRecord:: setUpAttackNode() { const Player O = PlayerTraits::opponent; /* 王手ãŒã‹ã‹ã£ã¦ã„ãªã„ã¨ãã¯ï¼Œç›¸æ‰‹ã®æ‰‹ç•ªã®å³è©°ã¯å¤±æ•—ã—ã¦ã„ã‚‹. */ NtesukiMove pass(Move::PASS(T)); values()[0] = ProofDisproof::NoCheckmate(); best_move()[0] = pass; if (!values()[0].isFinal() && state->template kingSquare().isOnBoard()) { /* æ·±ã•固定 checkmate searcher を呼ã³å‡ºã™ */ FixedDepthSearcher fixed_searcher(*state); PieceStand proof_pieces; Move check_move; const NtesukiResult result_fixed = fixed_searcher.hasCheckmateMove(fixed_search_depth, check_move, proof_pieces); if (result_fixed.isCheckmateSuccess()) { NtesukiMove best_move(check_move); best_move.setCheck(); best_move.setImmediateCheckmate(); TRY_DFPN; setResult(0, result_fixed, best_move, false, &proof_pieces); CATCH_DFPN; } else if (result_fixed.isCheckmateFail()) { PieceStand disproof_pieces = getPieceStand(); TRY_DFPN; setResult(0, result_fixed, NtesukiMove::INVALID(), false, &disproof_pieces); CATCH_DFPN; } else { TRY_DFPN; setResult(0, result_fixed, NtesukiMove::INVALID(), false); if (!values()[1].isFinal()) { setResult(1, ProofDisproof(1, result_fixed.disproof()), NtesukiMove::INVALID(), false); } CATCH_DFPN; } } } template void osl::ntesuki::NtesukiRecord:: setUpDefenseNode() { const Player O = PlayerTraits::opponent; /* 王手ãŒã‹ã‹ã£ã¦ã„ã‚‹ã®ã§è‡ªå‹•çš„ã«ç›¸æ‰‹ã‹ã‚‰ã® n 手ã™ããŒã‹ã‹ã£ã¦ã„ã‚‹. */ for (size_t i = 0; i < SIZE; ++i) { setNtesuki(i); } /* ã‚‚ã—自玉ãŒç›¤é¢ä¸Šã«ã‚ã‚‹ã®ãªã‚‰, fixed depth searcher を呼ã³å‡ºã™ */ if (!values()[0].isFinal() && state->template kingSquare().isOnBoard()) { /* æ·±ã•固定 checkmate searcher を呼ã³å‡ºã™ */ FixedDepthSearcher fixed_searcher(*state); PieceStand proof_pieces; //when called with Move::INVALID() as last move, PawnDropCheckmate is not checked for // the last move const NtesukiResult result_fixed = fixed_searcher.hasEscapeMove(Move::INVALID(), fixed_search_depth, proof_pieces); if (result_fixed.isCheckmateSuccess()) { TRY_DFPN; setResult(0, result_fixed, NtesukiMove::INVALID(), false, &proof_pieces); CATCH_DFPN; } else if (result_fixed.isCheckmateFail()) { PieceStand disproof_pieces = getPieceStand(); NtesukiMove best_move = NtesukiMove::INVALID(); /* might want to know the true best move, or mark best move as immediateCheckmate */ TRY_DFPN; setResult(0, result_fixed, best_move, false, &disproof_pieces); CATCH_DFPN; } else { TRY_DFPN; setResult(0, result_fixed, NtesukiMove::INVALID(), false); if (!values()[1].isFinal()) { setResult(1, ProofDisproof(1, result_fixed.disproof()), NtesukiMove::INVALID(), false); } CATCH_DFPN; } } } /* 手生æˆã‚’行ㆠ*/ template void osl::ntesuki::NtesukiRecord:: generateMoves(NtesukiMoveList& move_list, int pass_left, bool all_moves) { const Player O = PlayerTraits

::opponent; if (all_moves) { mg->generateSlow(P, *state, move_list); } else { mg->generateWithRzoneSlow(P, *state, this, pass_left, move_list); } const Ptype cheapest = getCheapestDrop(P, *state); const Ptype secondCheapest = getSecondCheapestDrop(P, *state, cheapest); for (NtesukiMoveList::iterator move_it = move_list.begin(); move_it != move_list.end(); move_it++) { const Move move = move_it->getMove(); if (move_it->isPass()) { unsigned int p_a = 1, d_a = 1, p_d = 1, d_d = 1; move_it->setHEstimates(p_a, d_a, p_d, d_d); continue; } unsigned int p_a = 1, d_a = 1, p_d = 1, d_d = 1; #if 0 if (state->template kingSquare().isOnBoard()) { checkmate::LibertyEstimator::attackH(P, *state, move_it->getMove(), p_a, d_a); } if (state->template kingSquare

().isOnBoard()) { checkmate::LibertyEstimator::defenseH(P, *state, move_it->getMove(), p_d, d_d); } #endif move_it->setHEstimates(p_a, d_a, p_d, d_d); const Square from = move.from(); const Square to = move.to(); const Ptype ptype = move.ptype(); /* é§’ã®ãŸã æ¨ã¦(ç„¡é§„åˆã‚’å«ã‚€)を記録 */ if (state->hasEffectAt(O, to)) { if (from.isPieceStand()) { if ((ptype != cheapest) && (ptype != secondCheapest)) { move_it->setInterpose(); } else if((! state->hasEffectAt(P, to)) // 自分ã®åˆ©ããŒãªã„ && (! state->hasMultipleEffectAt(O, to)))// 焦点ã§ã‚‚ãªã„ { move_it->setInterpose(); } } else if ((ptype != KING) && (move.capturePtype() == PTYPE_EMPTY) && (! state->hasMultipleEffectAt(P, to))) { move_it->setInterpose(); } } /* ç„¡é§„ãªé ã„利ã */ if (delay_lame_long && from.isPieceStand() && (isMajor(ptype) || ptype == LANCE) && (! state->hasMultipleEffectAt(P, to))) { const Square opKingSquare = state->template kingSquare(); const Square myKingSquare = state->template kingSquare

(); bool close_to_king = false; if (opKingSquare.isOnBoard()) { int distance = (opKingSquare.x() - to.x()) * (opKingSquare.x() - to.x()) + (opKingSquare.y() - to.y()) * (opKingSquare.y() - to.y()); if (distance < 19) { close_to_king = true; } } if (myKingSquare.isOnBoard()) { int distance = (myKingSquare.x() - to.x()) * (myKingSquare.x() - to.x()) + (myKingSquare.y() - to.y()) * (myKingSquare.y() - to.y()); if (distance < 19) { close_to_king = true; } } if (!close_to_king) { move_it->setLameLong(); ntesuki_assert(move_it->isLameLong()); } } /* 䏿ˆã‚’記録 */ if (from.isOnBoard() && PawnCheckmateMoves::effectiveOnlyIfPawnCheckmate

(ptype, from, to)) { move_it->setNoPromote(); } } } struct DifferentMove { const osl::ntesuki::NtesukiMove* move; DifferentMove(const osl::ntesuki::NtesukiMove* move) :move(move) {} bool operator()(const osl::ntesuki::NtesukiMove& m) { return m.getMove() != move->getMove(); } }; template osl::PieceStand osl::ntesuki::NtesukiRecord:: calcProofPiecesOr(int pass_left, const osl::ntesuki::NtesukiMove& move) { ntesuki_assert(turn() == P); PieceStand proof_pieces; const NtesukiRecord* record_child = table->findWithMove(this, move); ntesuki_assert(record_child); proof_pieces = record_child->getPDPieces

(pass_left); if (move.isDrop()) { proof_pieces.add(move.ptype()); } else if (move.getMove().capturePtype() != PTYPE_EMPTY) { proof_pieces.trySub(unpromote(move.getMove().capturePtype())); } return proof_pieces; } template osl::PieceStand osl::ntesuki::NtesukiRecord:: calcProofPiecesAnd(int pass_left) { ntesuki_assert(state->turn() == turn()); const Player O = PlayerTraits

::opponent; ntesuki_assert(turn() != P); PieceStand proof_pieces; NtesukiMoveList moves; mg->generate(*state, moves); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { const NtesukiMove& move = *move_it; const NtesukiRecord* record_child = table->findWithMove(this, move); if (!record_child) { if (move.isCheck() || (0 == pass_left && (!move.isCheck() || move.isNoPromote()))) { continue; } else { return piece_stand

(); } } else if (!record_child->getValue

(pass_left).isCheckmateSuccess()) { continue; } PieceStand proof_pieces_child = record_child->getPDPieces

(pass_left); proof_pieces = proof_pieces.max(proof_pieces_child); } /* monopolized pieces */ ntesuki_assert(state); if (! effect_util::UnblockableCheck::isMember(O, *state)) { for (unsigned int i=0; ihasPieceOnStand(O, ptype)) { const int diff = state->countPiecesOnStand(P, ptype) - proof_pieces.get(ptype); ntesuki_assert(diff >= 0); if (diff) proof_pieces.add(ptype, diff); } } } return proof_pieces; } template void osl::ntesuki::NtesukiRecord:: setProofPieces(int pass_left, const NtesukiResult& r, const NtesukiMove& best_move, const PieceStand* ps) { const Player D = PlayerTraits::opponent; PieceStand proof_pieces; if (ps) { /* Immediate checkmate or dominance or oracel prover light */ proof_pieces = *ps; } else if (best_move.isPass()) { const NtesukiRecord* record_pass = table->findWithMove(this, best_move); ntesuki_assert(record_pass); proof_pieces = record_pass->getPDPieces(pass_left - 1); } else if (best_move.isValid()) { proof_pieces = calcProofPiecesOr(pass_left, best_move); } else { /* set_proof_tree_AND */ proof_pieces = calcProofPiecesAnd(pass_left); } ntesuki_assert(piece_stand().template hasMoreThan(proof_pieces)); for (unsigned int j = pass_left; j < SIZE; j++) { setPDPieces(j, proof_pieces); setPDPieces(j, proof_pieces);//for attack back } } template void osl::ntesuki::NtesukiRecord:: setDisproofPieces(int pass_left, const NtesukiResult& r, const NtesukiMove& m, const PieceStand* ps) { const Player O = PlayerTraits

::opponent; PieceStand disproof_pieces; if (ps) { /* Immediate checkmate or dominance */ disproof_pieces = *ps; } else if (m.isPass()) { const NtesukiRecord* record_pass = table->findWithMove(this, m); ntesuki_assert(record_pass); disproof_pieces = record_pass->getPDPieces

(pass_left - 1); } else if (m.isValid()) { /* set_disproof_tree_OR */ ntesuki_assert(turn() != P); const NtesukiRecord* record_child = table->findWithMove(this, m); ntesuki_assert(record_child); disproof_pieces = record_child->getPDPieces

(pass_left); if (m.isDrop()) { disproof_pieces.add(m.ptype()); } else if (m.getMove().capturePtype() != PTYPE_EMPTY) { disproof_pieces.trySub(unpromote(m.getMove().capturePtype())); } } else { /* set_disproof_tree_AND */ ntesuki_assert(turn() == P); NtesukiMoveList moves; generateMoves

(moves, 0, true); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { const NtesukiRecord* record_child = table->findWithMove(this, *move_it); if (!record_child) { if (move_it->isPass() || (0 == pass_left && (!move_it->isCheck() || move_it->isNoPromote()))) { continue; } else { setPDPieces

(pass_left, piece_stand()); return; } } PieceStand disproof_pieces_child = record_child->getPDPieces

(pass_left); disproof_pieces = disproof_pieces.max(disproof_pieces_child); } /* monopolized pieces */ ntesuki_assert(state); ntesuki_assert(state->turn() == turn()); //if (! effect_util::UnblockableCheck::isMember(P, *state)) if (true) { for (unsigned int i=0; ihasPieceOnStand(P, ptype)) { const int diff = state->countPiecesOnStand(O, ptype) - disproof_pieces.get(ptype); ntesuki_assert(diff >= 0); if (diff) disproof_pieces.add(ptype, diff); } } } } #ifndef NDEBUG ntesuki_assert(piece_stand().isSuperiorOrEqualTo(disproof_pieces)) #endif setPDPieces

(pass_left, disproof_pieces); } template void osl::ntesuki::NtesukiRecord:: setFinal(int pass_left, const NtesukiResult& r, const NtesukiMove& m, const PieceStand* ps) { if (r.isCheckmateSuccess() && pass_count) { final = true; } const Player O = PlayerTraits

::opponent; if (r.isCheckmateSuccess()) { TRY_DFPN; setProofPieces

(pass_left, r, m, ps); CATCH_DFPN; for (unsigned int j = pass_left; j < SIZE; j++) { values

()[j] = r; best_move

()[j] = m; if (!values()[j].isCheckmateFail()) { ntesuki_assert(!values()[j].isCheckmateSuccess()); values ()[j] = ProofDisproof::AttackBack(); best_move()[j] = m; } } if (use_dominance) { propagate_proof

(pass_left); } #ifdef COLLECT_GARBAGE //collect garbage if (turn() == P) { DifferentMove different_move(best_move

()[pass_left]); moves.remove_if(different_move); } #endif } else //fail { ntesuki_assert(r.isCheckmateFail()); setDisproofPieces

(pass_left, r, m, ps); values

()[pass_left] = r; best_move

()[pass_left] = m; if (pass_left != 0 && !values

()[pass_left - 1].isCheckmateFail() ) { setFinal

(pass_left - 1, r, m, ps); } if (use_dominance) { propagate_disproof

(pass_left); } #ifdef COLLECT_GARBAGE //collect garbage if (turn() != P) { for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { bool not_best_move = true; for (size_t i = 0; i < SIZE; i++) { if (&(*move_it) != best_move()[pass_left]) not_best_move = false; } if (not_best_move) { move_it->clearRecord(); } } } #endif } } /* set result * also propagate values to deeper threats if checkmate success * P is the attacker */ template void osl::ntesuki::NtesukiRecord:: setResult(int i, //i tesuki const NtesukiResult& r, //pn/dn of this node at i const NtesukiMove& m, //best move bool bs, //by simulation const PieceStand* ps //when set by fixed depth searcher ) { ++written_count; /* TODO something that should dissapear, * as this is a result of a loop gaining/losing pieces */ ntesuki_assert(!values

()[i].isFinal()); ntesuki_assert(best_move

()[i].isInvalid()); by_simulation = bs; if (r.isFinal()) { value_before_final = values

()[i];//remember the last pdp for latter use setFinal

(i, r, m, ps); } else { values

()[i] = r; /* Dominance between lambda order */ int order = 0; for (; order < i; order++) { if (values

()[order].disproof() > r.disproof()) { values

()[order] = ProofDisproof(values

()[order].proof(), r.disproof()); } } ++order; for (; order < (int)SIZE; order++) { /* L^order ㌠AttackBackç­‰ã§æ—¢ã« disproof ã•れã¦ã„ã‚‹å ´åˆ */ if (values

()[order].isCheckmateFail()) continue; if (values

()[order].disproof() < r.disproof()) { values

()[order] = ProofDisproof(values

()[order].proof(), r.disproof()); } } } #ifndef NDEBUG if (by_simulation) ntesuki_assert(r.isFinal()); if (m.isValid()) { ntesuki_assert(r.isFinal()); } if (key.turn() == P && values

()[i].isCheckmateSuccess()) { ntesuki_assert(m.isValid()); } else if (key.turn() != P && values

()[i].isCheckmateFail()) { /* ntesuki_assert(m); */ } #endif } /* See if this is dominated by the proof pieces for record */ template bool osl::ntesuki::NtesukiRecord:: isDominatedByProofPieces(const NtesukiRecord* record, int pass_left) const { if (!record->getValue

(pass_left).isCheckmateSuccess()) return false; const PieceStand& my_stand = piece_stand

(); const PieceStand& other_pp = record->getPDPieces

(pass_left); return my_stand.isSuperiorOrEqualTo(other_pp); } /* See if this is dominated by the disproof pieces for record */ template bool osl::ntesuki::NtesukiRecord:: isDominatedByDisproofPieces(const NtesukiRecord* record, int pass_left) const { const Player O = PlayerTraits

::opponent; if (!record->getValue

(pass_left).isCheckmateFail()) return false; const PieceStand& my_stand = piece_stand(); const PieceStand& other_dp = record->getPDPieces

(pass_left); return my_stand.isSuperiorOrEqualTo(other_dp); } /* See if this dominated by record */ template bool osl::ntesuki::NtesukiRecord:: isBetterFor(NtesukiRecord* record) { const PieceStand& mystand = key.getPieceStand(); const PieceStand& opstand = record->key.getPieceStand(); if (mystand == opstand) return false; return mystand.hasMoreThan

(opstand); } /* ============================================================================= * accessors */ template bool osl::ntesuki::NtesukiRecord:: useOld(int pass_left) const { return use_old()[pass_left]; } template void osl::ntesuki::NtesukiRecord:: setUseOld(int pass_left, bool value) { use_old()[pass_left] = value; } template bool osl::ntesuki::NtesukiRecord:: isLoopWithPath(int pass_left, const PathEncoding& path) const { typedef osl::ntesuki::PathEncodingList list_t; const list_t& list = loop_path_list

()[pass_left]; for (list_t::const_iterator it = list.begin(); it != list.end(); it++) { if (*it == path) { return true; } } return false; } template void osl::ntesuki::NtesukiRecord:: setLoopWithPath(int pass_left, const PathEncoding& path) { typedef osl::ntesuki::PathEncodingList list_t; list_t& list = loop_path_list

()[pass_left]; list.push_front(path); } template const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: getValue(int i) const { ++read_count; return values

()[i]; } template const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: getValueWithPath(int i, const PathEncoding path) const { ++read_count; if (values

()[i].isFinal()) return values

()[i]; if (isLoopWithPath

(i, path)) { return ProofDisproof::LoopDetection(); } return values

()[i]; } template const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: getValueOr(int max_pass_left, const PathEncoding path, IWScheme iwscheme) const { ++read_count; if (values

()[max_pass_left].isFinal()) return values

()[max_pass_left]; if (isLoopWithPath

(max_pass_left, path)) { return ProofDisproof::LoopDetection(); } NtesukiResult ret = values

()[max_pass_left]; if (iwscheme == pn_iw) { unsigned int min_proof = ret.proof(); for (int pass_left = 0; pass_left < max_pass_left; ++pass_left) { if (isLoopWithPath

(pass_left, path)) continue; const NtesukiResult result = values

()[pass_left]; ntesuki_assert(result.disproof() <= ret.disproof()); min_proof = std::min(min_proof, result.proof()); } ret = NtesukiResult(min_proof, ret.disproof()); } else if (iwscheme == strict_iw) { for (int pass_left = 0; pass_left < max_pass_left; ++pass_left) { if (isLoopWithPath

(pass_left, path)) continue; const NtesukiResult result = values

()[pass_left]; if (!result.isCheckmateFail()) { ret = result; break; } } } return ret; } template const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: getValueAnd(int max_pass_left, const PathEncoding path, IWScheme iwscheme, PSScheme psscheme) const { ++read_count; if (values

()[max_pass_left].isFinal()) return values

()[max_pass_left]; if (isLoopWithPath

(max_pass_left, path)) { return ProofDisproof::LoopDetection(); } NtesukiResult ret = values

()[max_pass_left]; if (psscheme && max_pass_left != 0) { /* max_pass_left - 1 ã¾ã§æ•µã® PN を見ã¦ï¼Œ * ã“ã¡ã‚‰ã® DN よりå°ã•ã‹ã£ãŸã‚‰å…ˆã«èª­ã‚€. */ const Player O = PlayerTraits

::opponent; const NtesukiResult result_opponent = getValueOr(max_pass_left - 1, path, iwscheme); if (!result_opponent.isFinal() && result_opponent.proof() + inversion_cost < ret.disproof()) { ret = ProofDisproof(result_opponent.disproof(), //最もå˜ç´”ãªãƒ¢ãƒ‡ãƒ«ã§ã¯ ret.proof() result_opponent.proof() + inversion_cost); } } return ret; } template const osl::ntesuki::NtesukiMove& osl::ntesuki::NtesukiRecord:: getBestMove(int i) const { return best_move

()[i]; } template bool osl::ntesuki::NtesukiRecord:: isNtesuki(int pass_left) const { return is_ntesuki

()[pass_left]; } template void osl::ntesuki::NtesukiRecord:: setNtesuki(int pass_left) { //ntesuki_assert(false == is_ntesuki

()[pass_left]); is_ntesuki

()[pass_left] = true; } template bool osl::ntesuki::NtesukiRecord:: hasTriedPropagatedOracle(int pass_left) const { return propagated_oracle

()[pass_left]; } template void osl::ntesuki::NtesukiRecord:: triedPropagatedOracle(int pass_left) { assert(false == propagated_oracle

()[pass_left]); propagated_oracle

()[pass_left] = true; } template bool osl::ntesuki::NtesukiRecord:: isByFixed() const { return by_fixed

(); } template osl::PieceStand osl::ntesuki::NtesukiRecord:: getPDPieces(int pass_left) const { return pdpieces

()[pass_left]; } template void osl::ntesuki::NtesukiRecord:: setPDPieces(int pass_left, const PieceStand p) { pdpieces

()[pass_left] = p; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/oracleProverLight.cc0000644000000000000000000000221712316770314021631 0ustar rootroot#include "osl/ntesuki/oracleProverLight.h" #include "osl/ntesuki/oracleProverLight.tcc" #include "osl/ntesuki/ntesukiMoveGenerator.h" typedef NumEffectState state_t; osl::ntesuki::OracleProverLight:: OracleProverLight(state_t& s, gen_t *g, PathEncoding p, table_t& t, NtesukiRecord::ISScheme ischeme); template bool osl::ntesuki::OracleProverLight:: startFromAttack(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int pass_left); template bool osl::ntesuki::OracleProverLight:: startFromAttack(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int pass_left); template bool osl::ntesuki::OracleProverLight:: startFromDefense(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int pass_left); template bool osl::ntesuki::OracleProverLight:: startFromDefense(NtesukiRecord *record, const NtesukiRecord* record_orig, const unsigned int pass_left); /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiTable.tcc0000644000000000000000000000430712316770314021016 0ustar rootroot/* ntesukiTable.tcc */ #include "osl/ntesuki/ntesukiTable.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/apply_move/applyMoveWithPath.h" #include using namespace osl; using namespace osl::ntesuki; template class DoUndoMoveHelper { Search* searcher; F& func; NumEffectState& state; NtesukiRecord *child; public: DoUndoMoveHelper(Search* searcher, F& func, NumEffectState& state, NtesukiRecord *child) : searcher(searcher), state(state), child(child) { } void operator()(Square last_to) { (*searcher).template forEachRecordFrom(func, state, child); } }; template void osl::ntesuki::NtesukiTable::Table:: forEachRecord(F& func) { for (iterator it = begin(); it != end(); ++it) { for (NtesukiRecord::RecordList::iterator p = it->second.begin(); p != it->second.end(); ++p) { NtesukiRecord *r = &(*p); func(r); } } } template void osl::ntesuki::NtesukiTable::Table:: forEachRecordFrom(F& func, NumEffectState& state, NtesukiRecord *record) { NtesukiMoveGenerator mg; NtesukiMoveList all_moves; mg.generateSlow(state.turn(), state, all_moves); func.enter(record); std::vector moves; std::copy(all_moves.begin(), all_moves.end(), std::back_insert_iterator >(moves)); typename F::Compare c; std::sort(moves.begin(), moves.end(), c); for (std::vector::const_iterator it = moves.begin(); it != moves.end(); ++it) { const NtesukiMove& m = *it; NtesukiRecord *child = find(record->key.newHashWithMove(m.getMove())); if (child) { if (func.withChildMove(m, child)) { DoUndoMoveHelper helper(func, state, child); ApplyMoveOfTurn::doUndoMove(state, m.getMove(), helper); } } else { func.noChildMove(m); } } func.exit(); } template void osl::ntesuki::NtesukiTable::Table:: forEachRecordFromRoot(F& func) { if (rootState.get() == NULL) { throw RootStateNotSet(); } NumEffectState state(*rootState); forEachRecordFrom(func, state, root); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiRecord.cc0000644000000000000000000003032712316770314021022 0ustar rootroot#include "osl/ntesuki/ntesukiRecord.h" #include "osl/ntesuki/ntesukiRecord.tcc" #include "osl/player.h" #include #include unsigned int osl::ntesuki::NtesukiRecord:: fixed_search_depth = 0; unsigned int osl::ntesuki::NtesukiRecord:: inversion_cost = 0; bool osl::ntesuki::NtesukiRecord:: use_dominance = false; osl::ntesuki::NtesukiTable * osl::ntesuki::NtesukiRecord::table = NULL; osl::NumEffectState * osl::ntesuki::NtesukiRecord::state = NULL; osl::ntesuki::NtesukiMoveGenerator * osl::ntesuki::NtesukiRecord::mg = NULL; int osl::ntesuki::NtesukiRecord:: pass_count = 0; bool osl::ntesuki::NtesukiRecord:: max_for_split = false; bool osl::ntesuki::NtesukiRecord:: use_rzone_move_generation= false; bool osl::ntesuki::NtesukiRecord:: delay_lame_long = false; bool osl::ntesuki::NtesukiRecord:: use_9rzone = false; unsigned int osl::ntesuki::NtesukiRecord:: split_count = 0; unsigned int osl::ntesuki::NtesukiRecord:: confluence_count = 0; /* constructor */ osl::ntesuki::NtesukiRecord:: NtesukiRecord(signed short distance, const HashKey& key, const PieceStand& white_stand, RecordList* same_board_list) : black_stand(key.getPieceStand()), white_stand(white_stand), distance(distance), key(key), same_board_list(same_board_list), rev_refcount(0), child_count(0), read_count(0), written_count(0), visited(false), by_simulation(false), by_fixed_black(false), by_fixed_white(false), already_set_up(false), final(false), is_split(false), do_oracle_attack(true), do_oracle_aunt(true), rzone_move_generation(use_rzone_move_generation) { std::fill(values_black.begin(), values_black.end(), ProofDisproof(1, 1)); std::fill(values_white.begin(), values_white.end(), ProofDisproof(1, 1)); std::fill(read_interpose.begin(), read_interpose.end(), false); std::fill(read_check_defense.begin(), read_check_defense.end(), false); std::fill(read_non_attack.begin(), read_non_attack.end(), false); std::fill(is_ntesuki_black.begin(), is_ntesuki_black.end(), false); std::fill(is_ntesuki_white.begin(), is_ntesuki_white.end(), false); std::fill(propagated_oracle_black.begin(), propagated_oracle_black.end(), false); std::fill(propagated_oracle_white.begin(), propagated_oracle_white.end(), false); std::fill(use_old_black.begin(), use_old_black.end(), false); std::fill(use_old_white.begin(), use_old_white.end(), false); if (use_dominance) { lookup_same_board_list(); } } void osl::ntesuki::NtesukiRecord:: updateWithChild(osl::ntesuki::NtesukiRecord* child, int pass_left) { for (unsigned int i = pass_left; i < SIZE; i++) { rzone()[i].update(child->rzone()[i]); rzone()[i].update(child->rzone()[i]); } } void osl::ntesuki::NtesukiRecord:: lookup_same_board_list() { for (RecordList::iterator it = same_board_list->begin(); it != same_board_list->end(); it++) { if (&(*it) == this) continue; for (size_t pass_left = 0; pass_left < SIZE; pass_left++) { if (isDominatedByProofPieces(&(*it), pass_left)) { PieceStand ps = it->getPDPieces(pass_left); TRY_DFPN; setResult(pass_left, it->getValue(pass_left), it->getBestMove(pass_left), false, &ps); CATCH_DFPN; return; } else if (isDominatedByProofPieces(&(*it), pass_left)) { PieceStand ps = it->getPDPieces(pass_left); TRY_DFPN; setResult(pass_left, it->getValue(pass_left), it->getBestMove(pass_left), false, &ps); CATCH_DFPN; return; } } for (int pass_left = (int)SIZE - 1; pass_left >= 0; pass_left--) { if (isDominatedByDisproofPieces(&(*it), pass_left)) { PieceStand ps = it->getPDPieces(pass_left); TRY_DFPN; setResult(pass_left, it->getValue(pass_left), it->getBestMove(pass_left), false, &ps); CATCH_DFPN; return; } else if (isDominatedByDisproofPieces(&(*it), pass_left)) { PieceStand ps = it->getPDPieces(pass_left); const NtesukiMove& best_move = it->getBestMove(pass_left); TRY_DFPN; setResult(pass_left, it->getValue(pass_left), best_move, false, &ps); CATCH_DFPN; return; } } } } /* ============================================================================= * 'slow' accessors */ const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: getValueSlow(const Player player, int i) const { if (BLACK == player) return values()[i]; else return values()[i]; } const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: getValueOfTurn(int i) const { return getValueSlow(turn(), i); } const osl::ntesuki::NtesukiResult osl::ntesuki::NtesukiRecord:: valueBeforeFinal() const { return value_before_final; } const osl::ntesuki::NtesukiMove& osl::ntesuki::NtesukiRecord:: getBestMoveSlow(Player P, int i) const { if (BLACK == P) return getBestMove(i); else return getBestMove(i); } bool osl::ntesuki::NtesukiRecord:: isByFixedSlow(Player P) const { if (P == BLACK) return isByFixed(); else return isByFixed(); } osl::PieceStand osl::ntesuki::NtesukiRecord:: getPDPiecesSlow(Player p, int pass_left) const { if (p == BLACK) return pdpieces()[pass_left]; else return pdpieces()[pass_left]; } /* ============================================================================= * explicit instantiation */ namespace osl { namespace ntesuki { template void NtesukiRecord:: setResult(int i, const NtesukiResult& r, const NtesukiMove& m, bool bs, const PieceStand* ps); template void NtesukiRecord:: setResult(int i, const NtesukiResult& r, const NtesukiMove& m, bool bs, const PieceStand* ps); template bool NtesukiRecord:: setUpNode(); template bool NtesukiRecord:: setUpNode(); template void NtesukiRecord:: generateMoves(NtesukiMoveList& moves, int pass_left, bool all_moves); template void NtesukiRecord:: generateMoves(NtesukiMoveList& moves, int pass_left, bool all_moves); template bool NtesukiRecord:: isNtesuki(int pass_left) const; template bool NtesukiRecord:: isNtesuki(int pass_left) const; template void NtesukiRecord:: setNtesuki(int pass_left); template void NtesukiRecord:: setNtesuki(int pass_left); template bool NtesukiRecord:: hasTriedPropagatedOracle(int pass_left) const; template bool NtesukiRecord:: hasTriedPropagatedOracle(int pass_left) const; template void NtesukiRecord:: triedPropagatedOracle(int pass_left); template void NtesukiRecord:: triedPropagatedOracle(int pass_left); template bool NtesukiRecord:: useOld(int pass_left) const; template bool NtesukiRecord:: useOld(int pass_left) const; template void NtesukiRecord:: setUseOld(int pass_left, bool b); template void NtesukiRecord:: setUseOld(int pass_left, bool b); template PieceStand NtesukiRecord:: getPDPieces(int pass_left) const; template PieceStand NtesukiRecord:: getPDPieces(int pass_left) const; template void NtesukiRecord:: setPDPieces(int pass_left, const PieceStand p); template void NtesukiRecord:: setPDPieces(int pass_left, const PieceStand p); template bool NtesukiRecord:: isLoopWithPath(int pass_left, const PathEncoding& path) const; template bool NtesukiRecord:: isLoopWithPath(int pass_left, const PathEncoding& path) const; template void NtesukiRecord:: setLoopWithPath(int pass_left, const PathEncoding& path); template void NtesukiRecord:: setLoopWithPath(int pass_left, const PathEncoding& path); template const NtesukiResult NtesukiRecord:: getValueWithPath(int max_pass_left, const PathEncoding path) const; template const NtesukiResult NtesukiRecord:: getValueWithPath(int max_pass_left, const PathEncoding pat) const; template const NtesukiResult NtesukiRecord:: getValueOr(int max_pass_left, const PathEncoding path, IWScheme iwscheme) const; template const NtesukiResult NtesukiRecord:: getValueOr(int max_pass_left, const PathEncoding pat, IWScheme iwscheme) const; template const NtesukiResult NtesukiRecord:: getValueAnd(int max_pass_left, const PathEncoding pat, IWScheme iwscheme, PSScheme psscheme) const; template const NtesukiResult NtesukiRecord:: getValueAnd(int max_pass_left, const PathEncoding pat, IWScheme iwscheme, PSScheme psscheme) const; std::ostream& operator<<(std::ostream& os, const NtesukiRecord& record) { os << "player:\t" << record.key.turn() << "\n" << "visited:\t" << record.isVisited() << "\n" << "distance:\t" << record.distance << "\n" << "subtree:\t" << record.getChildCount() << "\n" << record.key << "\nBS" << record.black_stand << "\nWS" << record.white_stand << "\n"; for(size_t i = 0; i < NtesukiRecord::SIZE; ++i) { os << i << " B\tmove(" << record.getBestMove(i) << ")\t" << record.getValue(i) << "\tdom(" << record.getPDPieces(i) << "\n" << i << " W\tmove(" << record.getBestMove(i) << ")\t" << record.getValue(i) << "\tdom(" << record.getPDPieces(i) << "\n"; } return os; } std::ostream& operator<<(std::ostream& os, const NtesukiRecord::IWScheme& s) { switch (s) { case NtesukiRecord::no_iw: os << "no_widening"; break; case NtesukiRecord::strict_iw: os << "iterative_widening"; break; case NtesukiRecord::pn_iw: os << "pnbased_widening"; break; default: throw std::runtime_error("cannot parse string"); } return os; } std::istream& operator>>(std::istream& is, NtesukiRecord::IWScheme& s) { std::string token; is >> token; switch (token[0]) { case 'n': s = NtesukiRecord::no_iw; break; case 'i': s = NtesukiRecord::strict_iw; break; case 'p': s = NtesukiRecord::pn_iw; break; default: throw std::runtime_error("cannot parse string"); } return is; } std::ostream& operator<<(std::ostream& os, const NtesukiRecord::PSScheme& s) { switch (s) { case NtesukiRecord::no_ps: os << "single_lambda"; break; case NtesukiRecord::pn_ps: os << "dual_lambda"; break; default: throw std::runtime_error("cannot parse string"); } return os; } std::istream& operator>>(std::istream& is, NtesukiRecord::PSScheme& s) { std::string token; is >> token; switch (token[0]) { case 'n': case 's': s = NtesukiRecord::no_ps; break; case 'p': case 'd': s = NtesukiRecord::pn_ps; break; default: throw std::runtime_error("cannot parse string"); } return is; } std::ostream& operator<<(std::ostream& os, const NtesukiRecord::ISScheme& s) { switch (s) { case NtesukiRecord::no_is: os << "katagyoku"; break; case NtesukiRecord::tonshi_is: os << "tonshi-only"; break; case NtesukiRecord::delay_is: os << "delay-inversion"; break; case NtesukiRecord::normal_is: os << "full-inversion"; break; default: throw std::runtime_error("cannot parse string"); } return os; } std::istream& operator>>(std::istream& is, NtesukiRecord::ISScheme& s) { std::string token; is >> token; switch (token[0]) { case 'n': s = NtesukiRecord::no_is; break; case 't': s = NtesukiRecord::tonshi_is; break; case 'd': s = NtesukiRecord::delay_is; break; case 'f': s = NtesukiRecord::normal_is; break; default: throw std::runtime_error("cannot parse string"); } return is; } } } libosl-0.8.0.orig/full/osl/ntesuki/oracleProverLight.h0000644000000000000000000000330212316770314021467 0ustar rootroot/* oracleProverLight.h */ #ifndef _NTESUKI_ORACLE_PROVER_LIGHT_H #define _NTESUKI_ORACLE_PROVER_LIGHT_H #include "osl/ntesuki/ntesukiTable.h" #include "osl/state/numEffectState.h" #include "osl/hash/hashKey.h" #include "osl/player.h" #include "osl/pathEncoding.h" namespace osl { namespace ntesuki { class OracleProverLight { public: typedef NtesukiTable table_t; typedef NumEffectState state_t; typedef NtesukiMoveGenerator gen_t; private: state_t& state; gen_t *mg; PathEncoding path; table_t& table; NtesukiRecord::ISScheme isscheme; int fixed_search_depth; template class AttackHelper; template class DefenseHelper; public: explicit OracleProverLight(state_t& s, gen_t *g, PathEncoding p, table_t& t, NtesukiRecord::ISScheme isscheme = NtesukiRecord::no_is) : state(s), mg(g), path(p), table(t), isscheme(isscheme) { } template bool startFromAttack(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left); template bool startFromDefense(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left); private: template bool attack(const NtesukiRecord *oracle, const unsigned int pass_left); template bool defense(const NtesukiRecord *oracle, const unsigned int pass_left); }; } // namespace ntesuki } // namespace osl #endif /* _NTESUKI_ORACLE_PROVER_LIGHT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSearcher.tcc0000644000000000000000000016267012316770314021533 0ustar rootroot/* ntesukiSearcher.tcc */ #include "osl/ntesuki/ntesukiSearcher.h" #include "osl/ntesuki/ntesukiMove.h" #include "osl/ntesuki/ntesukiMoveList.h" #include "osl/ntesuki/ntesukiSimulationSearcher.h" #include "osl/apply_move/applyMoveWithPath.h" #include "osl/effect_util/effectUtil.h" // for release, inline the following templates as well #ifdef NDEBUG # include "osl/ntesuki/ntesukiMove.tcc" # include "osl/ntesuki/ntesukiRecord.tcc" #endif #include "osl/record/csaRecord.h" #include #include #include using namespace osl; using namespace osl::ntesuki; /* 409600 nodes at root node for MTDF * (/ 40960 8) => 5120 * cf. 1600 for brinkmate searcher */ const int READ_ATTACK_BACK_LIMIT = 5120; #ifndef NDEBUG #define RETURN(val) \ if (record->getValueWithPath(pass_left, path).proof() == 0)\ ntesuki_assert(record->getValueWithPath(pass_left, path).disproof() > ProofDisproof::DISPROOF_LIMIT);\ if (record->getValueWithPath(pass_left, path).disproof() == 0)\ ntesuki_assert(record->getValueWithPath(pass_left, path).proof() > ProofDisproof::PROOF_LIMIT);\ ntesuki_assert(val.isFinal() == record->getValueWithPath(pass_left, path).isFinal());\ return val #else #define RETURN(val) return val #endif #define RETURN_ON_STOP \ if (node_count > read_node_limit || *stop_flag)\ return /* =================== * misc */ static unsigned int addWithSaturation(unsigned int limit, unsigned int l, unsigned int r) { if (limit < l) return limit; const unsigned int sum = l+r; if (limit < sum) return limit; // guard against overflow if (sum < l) return limit; ntesuki_assert(r <= sum); return sum; } struct PlayMoveLock { std::vector& mlist; PlayMoveLock(std::vector& l, const osl::Move& m) : mlist(l) { mlist.push_back(m); } ~PlayMoveLock() { mlist.pop_back(); } }; struct LockGC { osl::ntesuki::NtesukiTable& table; LockGC(osl::ntesuki::NtesukiTable& t) : table(t) { table.lockGC(); } ~LockGC() { table.unlockGC(); } }; /* =================== * Attack helper */ template class osl::ntesuki::NtesukiSearcher:: AttackHelper { unsigned int proof_limit, disproof_limit, pass_left; Search* searcher; NtesukiResult& result; NtesukiRecord* record; const NtesukiRecord* oracle_attack; const NtesukiRecord* oracle_defense; const Move last_move; public: AttackHelper(Search* searcher, NtesukiResult& result, NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proof_limit, unsigned int disproof_limit, unsigned int pass_left, const Move last_move) : proof_limit(proof_limit), disproof_limit(disproof_limit), pass_left(pass_left), searcher(searcher), result(result), record(record), oracle_attack(oracle_attack), oracle_defense(oracle_defense), last_move(last_move) { } void operator()(Square last_to) { result = (*searcher).template defense::opponent> (record, oracle_attack, oracle_defense, proof_limit, disproof_limit, pass_left, last_move); } }; // AttackHelper /* =================== * Call Simulation Attack */ template class osl::ntesuki::NtesukiSearcher:: CallSimulationAttack { Search &simulator; NtesukiTable& table; NtesukiRecord *record; const NtesukiRecord *record_orig; unsigned int pass_left; bool& simulation_result; const Move last_move; public: CallSimulationAttack(Search& simulator, NtesukiTable& table, NtesukiRecord *record, const NtesukiRecord *record_orig, unsigned int pass_left, bool& simulation_result, const Move last_move) : simulator(simulator), table(table), record(record), record_orig(record_orig), pass_left(pass_left), simulation_result(simulation_result), last_move(last_move) { } void operator()(Square last_to) { LockGC glock(table); simulation_result = simulator.template startFromDefenseDisproof::opponent> (record, record_orig, pass_left, last_move); } }; // Call Simulation Attack /* =================== * Defense helper */ template class osl::ntesuki::NtesukiSearcher:: DefenseHelper { unsigned int proof_limit, disproof_limit, pass_left; Search* searcher; NtesukiResult& result; NtesukiRecord* record; const NtesukiRecord* oracle_attack; const NtesukiRecord* oracle_defense; const Move last_move; public: DefenseHelper(Search* searcher, NtesukiResult& result, NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proof_limit, unsigned int disproof_limit, unsigned int pass_left, const Move last_move) : proof_limit(proof_limit), disproof_limit(disproof_limit), pass_left(pass_left), searcher(searcher), result(result), record(record), oracle_attack(oracle_attack), oracle_defense(oracle_defense), last_move(last_move) { } void operator()(Square p) { (*searcher).template attack::opponent> (record, oracle_attack, oracle_defense, proof_limit, disproof_limit, pass_left, last_move); } };// DefenseHelper /* =================== * Call Simulation Defense */ template class osl::ntesuki::NtesukiSearcher:: CallSimulationDefense { Search &simulator; NtesukiTable &table; NtesukiRecord *record; const NtesukiRecord *record_orig; unsigned int pass_left; bool& simulation_result; const Move last_move; public: CallSimulationDefense(Search& simulator, NtesukiTable& table, NtesukiRecord *record, const NtesukiRecord *record_orig, unsigned int pass_left, bool& simulation_result, const Move last_move) : simulator(simulator), table(table), record(record), record_orig(record_orig), pass_left(pass_left), simulation_result(simulation_result), last_move(last_move) { } void operator()(Square last_to) { LockGC glock(table); simulation_result = simulator.template startFromAttackProof::opponent> (record, record_orig, pass_left, last_move); } }; // Call Simulation Defense /* =================== * Call Simulation Defense Disproof */ template class osl::ntesuki::NtesukiSearcher:: CallSimulationDefenseDisproof { Search &simulator; NtesukiTable &table; NtesukiRecord *record; const NtesukiRecord *record_orig; unsigned int pass_left; bool& simulation_result; const Move last_move; public: CallSimulationDefenseDisproof(Search& simulator, NtesukiTable& table, NtesukiRecord *record, const NtesukiRecord *record_orig, unsigned int pass_left, bool& simulation_result, const Move last_move) : simulator(simulator), table(table), record(record), record_orig(record_orig), pass_left(pass_left), simulation_result(simulation_result), last_move(last_move) { } void operator()(Square last_to) { LockGC glock(table); simulation_result = simulator.template startFromAttackDisproof::opponent> (record, record_orig, pass_left, last_move); } }; // Call Simulation Defense Disproof template void osl::ntesuki::NtesukiSearcher:: simulateSiblingsFail(NtesukiRecord *record, NtesukiRecord *record_best, int pass_left, unsigned int& success_count, unsigned int& total_count) { LockGC glock(table); const Player A = T; if (!record_best) return; ntesuki_assert(record_best); NtesukiMoveList moves; mg->generate(state, moves); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { NtesukiMove& move = *move_it; NtesukiRecord *record_child = table.allocateWithMove(record, move); if (record_child == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_child); if (record_child == record_best) continue; if (record_child->isVisited()) continue; if (move.isCheckmateFail(pass_left)) continue; const PathEncoding path_child(path, move.getMove()); const NtesukiResult result_child = record_child->getValueWithPath(pass_left, path_child); if (result_child.isFinal()) { continue; } bool simulation_result; total_count++; CallSimulationAttack helper(simulator, table, record_child, record_best, pass_left, simulation_result, move.getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, move.getMove(), helper); CATCH_DFPN; RETURN_ON_STOP; if (simulation_result) { success_count++; ntesuki_assert(record_child->getValueWithPath(pass_left, path_child).isCheckmateFail()); TRY_DFPN; move.setBySimulation(); move.setCheckmateFail(pass_left); CATCH_DFPN; } } } /* =================== * Count the increase of child nodes */ class CountChildLock { public: CountChildLock(NtesukiRecord* r, const NtesukiTable& t) : record(r), table(t) { size_start = table.size(); } ~CountChildLock() { record->addChildCount(table.size() - size_start); } private: osl::ntesuki::NtesukiRecord* record; const osl::ntesuki::NtesukiTable& table; unsigned int size_start; }; /* =================== * Attack */ template NtesukiResult osl::ntesuki::NtesukiSearcher:: attack(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proof_limit, unsigned int disproof_limit, const int pass_left, const Move last_move) { CountChildLock cclock(record, table); const Player A = T; #ifndef NDEBUG const Player D = PlayerTraits::opponent; #endif ntesuki_assert(T == state.turn()); ntesuki_assert(!state.inCheck(D)); ntesuki_assert(proof_limit < ProofDisproof::PROOF_LIMIT); ntesuki_assert(disproof_limit < ProofDisproof::DISPROOF_LIMIT); ntesuki_assert(record->getValueOr(pass_left, path, iwscheme).proof() < proof_limit); ntesuki_assert(record->getValueOr(pass_left, path, iwscheme).disproof() < disproof_limit); RETURN_ON_STOP (record->getValueOr(pass_left, path, iwscheme)); ntesuki_assert(record->getValueOr(pass_left, path, iwscheme).proof() < proof_limit); ntesuki_assert(record->getValueOr(pass_left, path, iwscheme).disproof() < disproof_limit); ntesuki_assert(record->getBestMove(pass_left).isInvalid()); ntesuki_assert(proof_limit > 0); ntesuki_assert(disproof_limit > 0); /* ノードã®åˆæœŸåŒ–. å¿…è¦ãªã‚‰ FixedDepthSearcher も呼ã°ã‚Œã‚‹ï¼Ž */ TRY_DFPN; if (record->setUpNode()) { const NtesukiResult result_cur = record->getValueWithPath(pass_left, path); if (result_cur.isCheckmateSuccess()) { /* By fixed searcher */ ++immediate_win; RETURN (result_cur); } else if (result_cur.isCheckmateFail() && pass_left == 0) { RETURN (result_cur); } } CATCH_DFPN; /* Iterative Wideningc Scheme ã«å¿œã˜ã¦æŽ¢ç´¢ */ NtesukiResult result_cur = record->getValueOr(pass_left, path, iwscheme); while ((result_cur.proof() < proof_limit) && (result_cur.disproof() < disproof_limit)) { if (iwscheme == NtesukiRecord::no_iw) { /* Order ã¯å¤‰ãˆãªã„ */ TRY_DFPN; attackWithOrder(record, NULL, NULL, proof_limit, disproof_limit, pass_left, last_move); CATCH_DFPN; RETURN_ON_STOP (result_cur); }// no_iw else if (iwscheme == NtesukiRecord::strict_iw) { /* å¿…ãšå°ã•ã„æ–¹ã‹ã‚‰æŽ¢ç´¢ */ for (int pass_left_child = 0; pass_left_child <= pass_left; pass_left_child++) { NtesukiResult result_st = record->getValueWithPath(pass_left_child, path); if (!result_st.isCheckmateFail()) { ntesuki_assert(result_st.proof() < proof_limit); ntesuki_assert(result_st.disproof() < disproof_limit); TRY_DFPN; attackWithOrder(record, NULL, NULL, proof_limit, disproof_limit, pass_left_child, last_move); CATCH_DFPN; RETURN_ON_STOP (result_cur); break; } } }// strict_iw else if (iwscheme == NtesukiRecord::pn_iw) { /* proof number ã®å°ã•ã„æ–¹ã‹ã‚‰æŽ¢ç´¢ */ unsigned int p_min = ProofDisproof::BigProofNumber, p_2nd = ProofDisproof::BigProofNumber; int pass_left_best = -1; for (int pass_left_child = 0; pass_left_child <= pass_left; pass_left_child++) { NtesukiResult result_st = record->getValueWithPath(pass_left_child, path); if (result_st.isCheckmateFail()) continue; const unsigned int proof = result_st.proof(); if (proof < p_min) { pass_left_best = pass_left_child; p_2nd = p_min; p_min = proof; } else if (proof < p_2nd) { p_2nd = proof; } } unsigned int proof_limit_child = std::min(proof_limit, p_2nd + 1); unsigned int disproof_limit_child = disproof_limit; TRY_DFPN; attackWithOrder(record, NULL, NULL, proof_limit_child, disproof_limit_child, pass_left_best, last_move); CATCH_DFPN; RETURN_ON_STOP (result_cur); }// pn_iw result_cur = record->getValueOr(pass_left, path, iwscheme); } return result_cur; } template void osl::ntesuki::NtesukiSearcher:: attackWithOrder(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proof_limit, unsigned int disproof_limit, const int pass_left, const Move last_move) { ++node_count; const Player A = T; #ifndef NDEBUG const Player D = PlayerTraits::opponent; #endif ntesuki_assert(T == state.turn()); ntesuki_assert(!state.inCheck(D)); ntesuki_assert(proof_limit < ProofDisproof::PROOF_LIMIT); ntesuki_assert(disproof_limit < ProofDisproof::DISPROOF_LIMIT); RETURN_ON_STOP; const bool under_attack = state.inCheck(T); ntesuki_assert (record->getValueWithPath(pass_left, path).proof() < proof_limit); ntesuki_assert (record->getValueWithPath(pass_left, path).disproof() < disproof_limit); ntesuki_assert(record->getBestMove(pass_left).isInvalid()); NtesukiRecord::VisitLock visitLock(record); ntesuki_assert(proof_limit > 0); ntesuki_assert(disproof_limit > 0); NtesukiMoveList moves; /* 手ã®ç”Ÿæˆ */ TRY_DFPN; record->generateMoves(moves, pass_left, false); CATCH_DFPN; /* collect statistic information */ ++attack_node_count; if (under_attack) { ++attack_node_under_attack_count; } attack_node_moves_count += moves.size(); /* æ”»ã‚æ‰‹ãŒãªããªã‚‹â†’失敗 */ if (moves.empty()) { if (pass_left != 0 && record->rzone_move_generation) { /* ã¾ã æœªç”Ÿæˆã®æ‰‹ãŒã‚ã‚‹ */ NtesukiResult r = record->getValueWithPath(pass_left - 1, path); if (r.isCheckmateFail()) { /* rzone ã¯ã“ã‚Œä»¥ä¸Šã¯æ‹¡å¤§ã—ãªã„ */ record->rzone_move_generation = false; TRY_DFPN; record->setResult(pass_left, ProofDisproof(1,1), NtesukiMove::INVALID(), false); CATCH_DFPN; } else { /* rzone ãŒå¢—ãˆã‚‹ã¾ã§ï¼Œã‚ˆã‚Šä½Žã„ order ã§ã®æŽ¢ç´¢ã‚’優先ã•ã›ã‚‹ */ TRY_DFPN; record->setResult(pass_left, ProofDisproof(r.proof() + 2, r.disproof() + 2), NtesukiMove::INVALID(), false); CATCH_DFPN; } return; } TRY_DFPN; /* åŒçމå•題ãªã‚‰ D ã® NoEscape ã ãŒï¼Œ * 片玉å•題ã§ï¼Œå…¨åˆæ³•手を生æˆã—ãªã„å ´åˆ(pass_left==0 ã®å ´åˆãªã©)ã§ã¯ * ãŸã ã® NoCheckmate */ record->setResult(pass_left, ProofDisproof::NoCheckmate(), NtesukiMove::INVALID(), false); CATCH_DFPN; return; } ntesuki_assert(!moves.empty()); ntesuki_assert(record->getValueWithPath(pass_left, path).proof() != 0); ntesuki_assert(record->getValueWithPath(pass_left, path).disproof() != 0); /* æ”»ã‚る手ã®å®Ÿè¡Œ */ for (;;) { ntesuki_assert(record->getValueWithPath(pass_left, path).proof() != 0); ntesuki_assert(record->getValueWithPath(pass_left, path).disproof() != 0); unsigned int best_proof = ProofDisproof::BigProofNumber, best_disproof = 0, second_proof = ProofDisproof::BigProofNumber, sum_disproof = 0; unsigned int step_cost = 1; NtesukiMove* best_move = selectMoveAttack(record, best_proof, sum_disproof, second_proof, best_disproof, step_cost, moves, pass_left); if (best_move == NULL) { if (pass_left != 0 && record->rzone_move_generation) { /* ã¾ã æœªç”Ÿæˆã®æ‰‹ãŒã‚ã‚‹ */ NtesukiResult r = record->getValueWithPath(pass_left - 1, path); if (r.isCheckmateFail()) { /* rzone ã¯ã“ã‚Œä»¥ä¸Šã¯æ‹¡å¤§ã—ãªã„ */ record->rzone_move_generation = false; TRY_DFPN; record->setResult(pass_left, ProofDisproof(1,1), NtesukiMove::INVALID(), false); CATCH_DFPN; } else { /* rzone ãŒå¢—ãˆã‚‹ã¾ã§ï¼Œã‚ˆã‚Šä½Žã„ order ã§ã®æŽ¢ç´¢ã‚’優先ã•ã›ã‚‹ */ TRY_DFPN; record->setResult(pass_left, ProofDisproof(r.proof() + 2, r.disproof() + 2), NtesukiMove::INVALID(), false); CATCH_DFPN; } } else { ntesuki_assert(record->getValueWithPath(pass_left, path).disproof() == 0); } return; } else if (best_move->isCheckmateSuccess(pass_left)) { return; } /* ã“ã®ãƒŽãƒ¼ãƒ‰ã®è¨¼æ˜Žæ•°ãƒ»å証数を設定ã™ã‚‹ */ const NtesukiResult result_cur(best_proof, sum_disproof); record->setResult(pass_left, result_cur, NtesukiMove::INVALID(), false); /* 他を読む */ if ((proof_limit <= best_proof) || (disproof_limit <= sum_disproof)) { ntesuki_assert(!result_cur.isFinal()); return; } /* 手を試㙠*/ unsigned int proof_child = std::min(proof_limit, second_proof + step_cost); ntesuki_assert(disproof_limit > sum_disproof);// disproof_child unsigned int disproof_child = addWithSaturation(ProofDisproof::DISPROOF_LIMIT, disproof_limit, best_disproof) - sum_disproof; NtesukiRecord *record_child = table.allocateWithMove(record, *best_move); if (record_child == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_child); const PathEncoding path_child(path, best_move->getMove()); NtesukiResult result_child = record_child->getValueWithPath(pass_left, path_child); if (!result_child.isFinal()) { if (best_move->isCheck()) { oracle_attack = NULL; } if (ptt_aunt && pass_left != 0 && record->getValueWithPath(pass_left - 1, path).isCheckmateFail()) { oracle_defense = record; } AttackHelper helper(this, result_child, record_child, oracle_attack, oracle_defense, proof_child, disproof_child, pass_left, best_move->getMove()); PlayMoveLock pml(moves_played, best_move->getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, best_move->getMove(), helper); CATCH_DFPN; record->updateWithChild(record_child, pass_left); RETURN_ON_STOP; const NtesukiResult result_cur = record->getValueWithPath(pass_left, path_child); if (result_cur.isFinal()) { return; } } if (result_child.isPawnDropFoul(best_move->getMove())) { best_move->setPawnDropCheckmate(); best_move->setCheckmateFail(pass_left); } else if (result_child.isCheckmateSuccess()) { best_move->setCheckmateSuccess(pass_left); TRY_DFPN; record->setResult(pass_left, ProofDisproof::Checkmate(), *best_move, false); CATCH_DFPN; return; } else if (result_child.isCheckmateFail()) { if (result_child != ProofDisproof::LoopDetection()) { best_move->setCheckmateFail(pass_left); } if (result_child == ProofDisproof::PawnCheckmate()) { best_move->setPawnDropCheckmate(); } if (ptt_siblings_fail && !best_move->isCheck() && result_child != ProofDisproof::LoopDetection()) { TRY_DFPN; simulateSiblingsFail(record, record_child, pass_left, sibling_attack_success_count, sibling_attack_count); CATCH_DFPN; } } }//for(;;) } /* dynamic widening */ typedef std::pair top_pdp_t; static bool sorter(const top_pdp_t& lhs, const top_pdp_t& rhs) { if (lhs.first == rhs.first) { //return rhs.second > rhs.second; return rhs.second < rhs.second; } else { return lhs.first > rhs.first; } } template osl::ntesuki::NtesukiMove * osl::ntesuki::NtesukiSearcher:: selectMoveAttack(NtesukiRecord* record, unsigned int& best_proof, unsigned int& sum_disproof, unsigned int& second_proof, unsigned int& best_disproof, unsigned int& step_cost, NtesukiMoveList& moves, const int pass_left) { const Player A = T; bool read_nopromote = false; re_select_move_attack: NtesukiMove *best_move = NULL; bool loop = false; bool pawn_checkmate = false; unsigned short min_child_age = SHRT_MAX; int average_cost = 0; int average_cost_count = 0; /* reset values */ best_proof = ProofDisproof::BigProofNumber; best_disproof = 0; second_proof = ProofDisproof::BigProofNumber; sum_disproof = 0; /* dynamic Widening */ std::list pdps; /* 手をé¸ã¶ */ for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); ++move_it) { NtesukiMove& move = *move_it; pawn_checkmate |= move.isPawnDropCheckmate(); if (move.isPass()) { continue; } if (!move.isCheck() && 0 == pass_left) { continue; } if (move.isCheckmateFail(pass_left)) { continue; } if (delay_nopromote && !read_nopromote && move.isNoPromote()) { continue; } if (delay_non_attack && !record->readNonAttack(pass_left) && ((move.getOrder() > pass_left) || move.isLameLong()) ) { continue; } unsigned int proof = move.h_a_proof; unsigned int disproof = move.h_a_disproof; if (tsumero_estimate && !move.isCheck()) { proof = tsumero_estimate; disproof = 1; } average_cost += proof; average_cost_count++; NtesukiRecord *record_child = table.findWithMove(record, move); if (record_child) { if (record_child->isVisited()) { /* ループ発見 */ /* defender ã®æ–¹ã‹ã‚‰ã®çŽ‹æ‰‹åƒæ—¥æ‰‹ã®å¯èƒ½æ€§ã‚¢ãƒª */ loop = true; continue; } const PathEncoding path_child(path, move.getMove()); NtesukiResult result_child; TRY_DFPN; result_child = record_child->getValueAnd(pass_left, path_child, iwscheme, psscheme); CATCH_DFPN; proof = result_child.proof(); disproof = result_child.disproof(); if (0 == disproof)/* ä¸è©°ã¿ */ { if (result_child == ProofDisproof::LoopDetection()) { loop = true; continue; } if (record_child->getValueWithPath(pass_left, path_child) == ProofDisproof::PawnCheckmate()) { move.setPawnDropCheckmate(); pawn_checkmate = true; } ntesuki_assert(proof >= ProofDisproof::PROOF_LIMIT); move.setCheckmateFail(pass_left); /* should do ptt_siblings_fail */ continue; } else if (0 == proof)/* è©°ã¿ */ { /* 打歩詰ã‚ã ã‘ãƒã‚§ãƒƒã‚¯ */ if (record_child->getValueWithPath(pass_left, path_child). isPawnDropFoul(move.getMove())) { move.setPawnDropCheckmate(); move.setCheckmateFail(pass_left); pawn_checkmate = true; continue; } /* é–“é•ã„ãªãå‹ã¡æ‰‹ */ ntesuki_assert(disproof >= ProofDisproof::DISPROOF_LIMIT); move.setCheckmateSuccess(pass_left); TRY_DFPN; record->setResult(pass_left, ProofDisproof::Checkmate(), move, false); CATCH_DFPN; return &move; } min_child_age = std::min(record_child->distance, min_child_age); if (record_child->distance <= record->distance) { if (!record->useOld(pass_left)) { continue; } } /* the assertion: * use_old == (record_child->distance <= record->distance) * does not hold, as the distance gets updated to youngest. */ } /* Proof Disproof ã®èª¿æ•´ã¯ã“ã“ã§ */ if (!move.isCheck()) { ntesuki_assert(pass_left > 0); proof += tsumero_cost; disproof += tsumero_cost; } if (!record->useOld(pass_left) && !(NtesukiRecord::max_for_split && record->is_split)) { sum_disproof = addWithSaturation(ProofDisproof::DISPROOF_LIMIT, disproof, sum_disproof); } else { sum_disproof = std::max(disproof, sum_disproof); } /* best move ã®è¨­å®š */ if (proof < best_proof) { best_move = &move; second_proof = best_proof; best_proof = proof; best_disproof = disproof; } else if (proof < second_proof) { second_proof = proof; } /* dynamic widening: è‰¯ã„æ‰‹ã®é¸å®š */ if (dynamic_widening_width > 0) { if (pdps.size() < dynamic_widening_width) { pdps.push_back(top_pdp_t(proof, disproof)); //Sorter sorter; pdps.sort(sorter); } else { if (pdps.back().first > proof) { pdps.pop_back(); pdps.push_back(top_pdp_t(proof, disproof)); }// back().proof == proof ã ã£ãŸå ´åˆã¯ï¼Ÿ pdps.sort(sorter); } } } /* dynamic widening: è‰¯ã„æ‰‹ã®é›†è¨ˆ */ if ((dynamic_widening_width > 0 && dynamic_widening_width < moves.size()) && (!record->useOld(pass_left) && !(NtesukiRecord::max_for_split && record->is_split))) { sum_disproof = 0; for (std::list::const_iterator it = pdps.begin(); it != pdps.end(); ++it) { sum_disproof += it->second; } } /* é¸ã‚“ã æ‰‹ã‚’åŸå‘³ã™ã‚‹ */ if (best_move == NULL) { if (false == record->useOld(pass_left)) { if (SHRT_MAX != min_child_age) { record->setUseOld(pass_left, true); ntesuki_assert(min_child_age <= record->distance); record->distance = min_child_age; goto re_select_move_attack; } } if (!record->readNonAttack(pass_left)) { if (!read_attack_only) { record->setReadNonAttack(pass_left); if (ptt_non_attack && pass_left != 0) { TRY_DFPN; handleNonAttack(record, pass_left); CATCH_DFPN; RETURN_ON_STOP NULL; } record->setUseOld(pass_left, false); goto re_select_move_attack; } } if (delay_nopromote && !read_nopromote && (pass_left > 0 || pawn_checkmate)) { read_nopromote = true; record->setUseOld(pass_left, false); goto re_select_move_attack; } ntesuki_assert(best_proof == ProofDisproof::BigProofNumber); if (pass_left != 0 && record->rzone_move_generation) { /* ã¾ã æœªç”Ÿæˆã®æ‰‹ãŒã‚ã‚‹ */ return NULL; } /* 本当㫠disproof ã•れã¦ã—ã¾ã£ãŸ */ if (pawn_checkmate)/* 打歩詰ã‚ãŒã‚ã£ãŸ */ { if (delay_nopromote) assert(read_nopromote); TRY_DFPN; record->setResult(pass_left, ProofDisproof::PawnCheckmate(), NtesukiMove::INVALID(), false); CATCH_DFPN; return NULL; } // pawn checkmate and loop?? else if (loop) /* ループãŒã‚ã£ãŸ */ { record->setLoopWithPath(pass_left, path); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; return NULL; } else /* å…¨ã¦ã®æ‰‹ãŒæ™®é€šã«å証ã•れ㟠*/ { TRY_DFPN; record->setResult(pass_left, ProofDisproof::NoCheckmate(), NtesukiMove::INVALID(), false); CATCH_DFPN; return NULL; } } ntesuki_assert(best_proof != 0); ntesuki_assert(sum_disproof != 0); ntesuki_assert(best_proof < ProofDisproof::PROOF_LIMIT); ntesuki_assert(sum_disproof < ProofDisproof::DISPROOF_LIMIT); if (record->useOld(pass_left)) { ntesuki_assert(min_child_age != SHRT_MAX); record->distance = min_child_age; } average_cost /= average_cost_count; step_cost = std::max(average_cost, 1); return best_move; } template void osl::ntesuki::NtesukiSearcher:: handleNonAttack(NtesukiRecord* record, int pass_left) { const Player A = T; ntesuki_assert(T == state.turn()); NtesukiMoveList moves; mg->generate(state, moves); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); ++move_it) { NtesukiRecord *record_best = table.findWithMove(record, *move_it); const PathEncoding path_best(path, move_it->getMove()); if (!record_best || !record_best->getValueWithPath(pass_left, path_best).isCheckmateFail()) continue; /* record_best is checkmate fail */ for (NtesukiMoveList::iterator move_it2 = moves.begin(); move_it2 != moves.end(); ++move_it2) { if (move_it2->isPass()) { continue; } if (*move_it2 == *move_it) { continue; } if (move_it2->isCheckmateFail(pass_left)) { continue; } NtesukiRecord *record_child = table.allocateWithMove(record, *move_it2); if (record_child == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_child); const PathEncoding path_child(path, move_it->getMove()); if(record_child->getValueWithPath(pass_left, path_child).isFinal()) { continue; } if (record_child->isVisited()) { TRY_DFPN; move_it2->setCheckmateFail(pass_left); record->setLoopWithPath(pass_left, path_child); CATCH_DFPN; continue; } bool simulation_result; CallSimulationAttack helper(simulator, table, record_child, record_best, pass_left, simulation_result, move_it2->getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, move_it2->getMove(), helper); CATCH_DFPN; RETURN_ON_STOP; if (simulation_result) { move_it2->setBySimulation(); move_it2->setCheckmateFail(pass_left); } } } } /* =================== * defense */ template NtesukiResult osl::ntesuki::NtesukiSearcher:: defense(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proof_limit, unsigned int disproof_limit, int pass_left, const Move last_move) { const Player A = PlayerTraits::opponent; const Player D = T; CountChildLock cclock(record, table); ntesuki_assert(T == state.turn()); ntesuki_assert(proof_limit < ProofDisproof::PROOF_LIMIT); ntesuki_assert(disproof_limit < ProofDisproof::DISPROOF_LIMIT); ntesuki_assert (record->getValueAnd(pass_left, path, iwscheme, psscheme).proof() < proof_limit); ntesuki_assert (record->getValueAnd(pass_left, path, iwscheme, psscheme).disproof() < disproof_limit); ntesuki_assert(state.inCheck(T) || (pass_left > 0)); ntesuki_assert(!state.inCheck(A)); ++node_count; RETURN_ON_STOP (record->getValueAnd(pass_left, path, iwscheme, psscheme)); ntesuki_assert(record); ntesuki_assert(!record->getValueWithPath(pass_left, path).isFinal()); ntesuki_assert(record->getBestMove(pass_left).isInvalid()); NtesukiRecord::VisitLock visitLock(record); /* ノードã®åˆæœŸåŒ–. å¿…è¦ãªã‚‰ FixedDepthSearcher も呼ã°ã‚Œã‚‹ï¼Ž */ TRY_DFPN; if (record->setUpNode()) { const NtesukiResult r = record->getValueWithPath(pass_left, path); if (r.isCheckmateFail()) { /* By fixed searcher */ ++immediate_lose; RETURN (r); } else if (r.isFinal()) { RETURN (r); } } CATCH_DFPN; /* Player Selection Scheme ã«å¿œã˜ã¦æŽ¢ç´¢ */ NtesukiResult result_cur = record->getValueAnd(pass_left, path, iwscheme, psscheme); while ((result_cur.proof() < proof_limit) && (result_cur.disproof() < disproof_limit)) { bool read_attack_first = false; if (psscheme) { /* Dual Lambda 探索を行ã†: * pn_D(n-1) < dn_A(n) ãªã‚‰ order を下ã’ã¦ï¼Œæ”»å®ˆã‚’入れæ›ãˆã‚‹. ãŸã ã—, * pn_D(n-1) : å—ã‘æ–¹ã® order n-1 ã«ãŠã‘る証明数 * dn_A(n) : æ”»ã‚æ–¹ã® order n ã«ãŠã‘ã‚‹å証数 */ if (pass_left > 0) { const NtesukiResult result_attacker = record->getValueWithPath(pass_left, path); const NtesukiResult result_defender = record->getValueOr(pass_left - 1, path, iwscheme); if (result_defender.proof() < result_attacker.disproof()) { read_attack_first = true; } } } if (read_attack_first) { NtesukiRecord::UnVisitLock unVisitLock(record); TRY_DFPN; attack(record, NULL, NULL, disproof_limit, proof_limit, pass_left - 1, last_move); CATCH_DFPN; RETURN_ON_STOP (result_cur); } else { TRY_DFPN; defenseWithPlayer(record, oracle_attack, oracle_defense, proof_limit, disproof_limit, pass_left, last_move); CATCH_DFPN; RETURN_ON_STOP (result_cur); } result_cur = record->getValueAnd(pass_left, path, iwscheme, psscheme); } return result_cur; } template void osl::ntesuki::NtesukiSearcher:: defenseWithPlayer(NtesukiRecord* record, const NtesukiRecord* oracle_attack, const NtesukiRecord* oracle_defense, unsigned int proof_limit, unsigned int disproof_limit, int pass_left, const Move last_move) { const Player A = PlayerTraits::opponent; const bool under_attack = state.inCheck(T); /* å—ã‘æ‰‹ã®ç”Ÿæˆ */ NtesukiMoveList moves; TRY_DFPN; record->generateMoves(moves, pass_left, true); CATCH_DFPN; if (moves.empty()) { TRY_DFPN; record->setResult(0, ProofDisproof::NoEscape(), NtesukiMove::INVALID(), false); CATCH_DFPN; return; } /* collect statistic information */ ++defense_node_count; if (under_attack) { ++defense_node_under_attack_count; } defense_node_moves_count += moves.size(); ntesuki_assert(!moves.empty()); ntesuki_assert(record->getValueWithPath(pass_left, path).isUnknown()); /* Pass ã® disproof simulation. */ if (!under_attack && record->do_oracle_aunt && oracle_defense) { record->do_oracle_aunt = false; NtesukiMove pass(Move::PASS(T)); NtesukiRecord *record_pass = table.allocateWithMove(record, pass); if (record_pass == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_pass); if (record_pass->isVisited()) { /* ループ発見 */ record->setLoopWithPath(pass_left, path); assert(record->isLoopWithPath(pass_left, path)); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; return; } ntesuki_assert(record_pass); const PathEncoding path_pass(path, pass.getMove()); const NtesukiResult result_pass = record_pass->getValueWithPath(pass_left - 1, path_pass); if (!result_pass.isFinal()) { bool simulation_result; CallSimulationDefenseDisproof helper(simulator, table, record_pass, oracle_defense, pass_left - 1, simulation_result, pass.getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, pass.getMove(), helper); CATCH_DFPN; return; if (simulation_result) { ntesuki_assert(record_pass->getValueWithPath(pass_left - 1, path_pass).isCheckmateFail()); pass.setBySimulation(); pass.setCheckmateFail(pass_left); } } } /* IS 将棋㮠simulation */ if (record->do_oracle_attack && oracle_attack) { record->do_oracle_attack = false; ntesuki_assert(ptt_uncle && !under_attack); // 本æ¥ã¯ pass_left >= 1 ã‹ NtesukiMove pass(Move::PASS(T)); NtesukiRecord *record_pass = table.allocateWithMove(record, pass); if (record_pass == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_pass); if (record_pass->isVisited()) { /* ループ発見 */ record->setLoopWithPath(pass_left, path); assert(record->isLoopWithPath(pass_left, path)); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; return; } ntesuki_assert(record_pass); const PathEncoding path_pass(path, pass.getMove()); const NtesukiResult result_pass = record_pass->getValueWithPath(pass_left - 1, path_pass); if (!result_pass.isFinal()) { ++isshogi_attack_count; bool simulation_result; CallSimulationDefense helper(simulator, table, record_pass, oracle_attack, pass_left - 1, simulation_result, pass.getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, pass.getMove(), helper); CATCH_DFPN; return; if (simulation_result) { ++isshogi_attack_success_count; ntesuki_assert(record_pass->getValueWithPath(pass_left - 1, path_pass).isCheckmateSuccess()); pass.setBySimulation(); pass.setCheckmateSuccess(pass_left); record->setNtesuki(pass_left); if (ptt_invalid_defense) { TRY_DFPN; simulateSiblingsSuccess(record, record_pass, pass_left, pass_success_count, pass_count); CATCH_DFPN; return; } } } } for (;;) { unsigned int best_disproof = ProofDisproof::BigProofNumber, sum_proof = 0, second_disproof = ProofDisproof::BigProofNumber, best_proof = 0; unsigned int step_cost = 1; NtesukiMove *best_move = NULL; best_move = selectMoveDefense(record, best_disproof, sum_proof, second_disproof, best_proof, step_cost, moves, pass_left, last_move); RETURN_ON_STOP; if (NULL == best_move) { ntesuki_assert(record->getValueWithPath(pass_left, path). isCheckmateSuccess()); return; } else if (best_disproof == 0) { ntesuki_assert(best_move->isCheckmateFail(pass_left) || record->isLoopWithPath(pass_left, path)); return; } #ifndef NDEBUG { //XXXXXXX NtesukiRecord* best_child = table.findWithMove(record, *best_move); if (best_child) { const PathEncoding path_child(path, best_move->getMove()); int pass_left_child = pass_left; if (best_move->isPass()) --pass_left_child; const NtesukiResult r = best_child->getValueOr(pass_left_child, path_child,iwscheme); ntesuki_assert(r.disproof() == best_disproof); ntesuki_assert(r.proof() <= sum_proof); } } //XXXXXXX #endif /* ã“ã®ãƒŽãƒ¼ãƒ‰ã®è¨¼æ˜Žæ•°ãƒ»å証数を設定ã™ã‚‹ */ const NtesukiResult result_cur = ProofDisproof(sum_proof, best_disproof); record->setResult(pass_left, result_cur, NtesukiMove::INVALID(), false); /* 他を読む */ if ((disproof_limit <= best_disproof) || (proof_limit <= sum_proof)) { ntesuki_assert(!result_cur.isFinal()); return; } unsigned int proof_child = addWithSaturation(ProofDisproof::DISPROOF_LIMIT, proof_limit, best_proof) - sum_proof; unsigned int disproof_child = std::min(disproof_limit, second_disproof + step_cost); /* 手を試㙠*/ int pass_left_child = pass_left; if (best_move->isPass()) { --pass_left_child; } NtesukiRecord *record_child = table.allocateWithMove(record, *best_move); if (record_child == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_child); const PathEncoding path_child(path, best_move->getMove()); ntesuki_assert(pass_left_child >= 0); NtesukiResult result_child = record_child->getValueOr(pass_left_child, path_child, iwscheme); if (!result_child.isFinal()) { if (best_move->isCheck()) { if (ptt_uncle && !under_attack && delay_non_pass) { NtesukiMove& pass = moves.front(); ntesuki_assert(pass.isPass()); oracle_attack = table.findWithMove(record, pass); ntesuki_assert(oracle_attack); } } if (result_child.proof() >= proof_child) { std::cerr << *record_child << result_child << "<- result \n" << proof_child << "/" << disproof_child << "<- limit\n" << *best_move << "\n" << sum_proof << "/" << best_disproof << " <- cur\n"; } DefenseHelper helper(this, result_child, record_child, oracle_attack, oracle_defense, proof_child, disproof_child, pass_left_child, best_move->getMove()); PlayMoveLock pml(moves_played, best_move->getMove()); if (best_move->isPass()) { NtesukiRecord::pass_count++; } TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, best_move->getMove(), helper); CATCH_DFPN; if (best_move->isPass()) { NtesukiRecord::pass_count--; } record->updateWithChild(record_child, pass_left); RETURN_ON_STOP; if (record->getValueWithPath(pass_left, path).isFinal()) { return; } } /* çµæžœã‚’åŸå‘³ã™ã‚‹ */ if (result_child.isCheckmateFail()) { if (result_child == ProofDisproof::AttackBack()) { ++disproof_by_inversion_count; } if (result_child == ProofDisproof::LoopDetection()) { record->setLoopWithPath(pass_left, path); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; return; } best_move->setCheckmateFail(pass_left); TRY_DFPN; record->setResult(pass_left, result_child, *best_move, false); CATCH_DFPN; return; } else if (result_child.isCheckmateSuccess()) { best_move->setCheckmateSuccess(pass_left); NtesukiRecord *best_record = table.findWithMove(record, *best_move); if ((ptt_invalid_defense && best_move->isPass()) || (ptt_siblings_success && !best_move->isCheck()) ) { TRY_DFPN; simulateSiblingsSuccess(record, best_record, pass_left, sibling_defense_success_count, sibling_defense_count); CATCH_DFPN; RETURN_ON_STOP; } } }//for(;;) } template osl::ntesuki::NtesukiMove* osl::ntesuki::NtesukiSearcher:: selectMoveDefense(NtesukiRecord* record, unsigned int& best_disproof, unsigned int& sum_proof, unsigned int& second_disproof, unsigned int& best_proof, unsigned int& step_cost, NtesukiMoveList& moves, const int pass_left, const Move last_move) { const Player A = PlayerTraits::opponent; const bool under_attack = state.inCheck(T); bool read_interpose = record->readInterpose(pass_left); /* GCã«ã‚ˆã£ã¦æƒ…å ±ãŒã‹ã‚ã£ã¦ã„ã‚‹å¯èƒ½æ€§ãŒ * bool read_non_pass = record->isNtesuki(pass_left);*/ bool read_non_pass = under_attack; if (pass_left > 0 && !under_attack) { NtesukiMove pass(Move::PASS(T)); NtesukiRecord *record_pass = table.findWithMove(record, pass); if (record_pass) { const PathEncoding path_child(path, pass.getMove()); read_non_pass = record_pass->getValueWithPath(pass_left - 1, path_child).isCheckmateSuccess(); } } if (under_attack) ntesuki_assert(read_non_pass); bool read_check_defense = record->readCheckDefense(pass_left); if (isscheme == NtesukiRecord::normal_is) { read_check_defense = true; } re_select_move_defense: unsigned short min_child_age = SHRT_MAX; NtesukiMove *best_move = NULL; int average_cost = 0; int average_cost_count = 0; /* reset values */ best_disproof = ProofDisproof::BigProofNumber; sum_proof = 0; second_disproof = ProofDisproof::BigProofNumber; best_proof = 0; /* dynamic Widening */ std::list pdps; /* 手をé¸ã¶ */ for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); ++move_it) { NtesukiMove& move = *move_it; if (move.isCheckmateSuccess(pass_left)) { continue; } ntesuki_assert(!move.isCheckmateFail(pass_left)); if (delay_non_pass && !read_non_pass && !move.isPass()) { continue; } if (delay_interpose && (move.isInterpose() || move.isLameLong()) && !read_interpose) { continue; } if (move.isCheck() && !under_attack && !read_check_defense) { continue; } unsigned int proof = move.h_d_proof; unsigned int disproof = move.h_d_disproof; average_cost += disproof; average_cost_count++; NtesukiRecord *record_child = table.findWithMove(record, move); if (record_child) { int pass_left_child = pass_left; if (move.isPass()) --pass_left_child; const PathEncoding path_child(path, move.getMove()); NtesukiResult result_child; TRY_DFPN; result_child = record_child->getValueOr(pass_left_child, path_child, iwscheme); CATCH_DFPN; if (record_child->isVisited()) { /* ループ発見 */ record->setLoopWithPath(pass_left, path); ntesuki_assert(record->isLoopWithPath(pass_left, path)); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; best_disproof = 0; return &move; } proof = result_child.proof(); disproof = result_child.disproof(); if (result_child.isCheckmateSuccess())//証明 { ntesuki_assert(disproof >= ProofDisproof::DISPROOF_LIMIT); move.setCheckmateSuccess(pass_left); if (move.isPass()) { /* æ—¢ã«ãƒ‘スã®å¾ŒãŒè¨¼æ˜Žã•れã¦ã„㟠*/ record->setNtesuki(pass_left); if (ptt_invalid_defense) { TRY_DFPN; simulateSiblingsSuccess(record, record_child, pass_left, pass_success_count, pass_count); CATCH_DFPN; RETURN_ON_STOP(NULL); goto re_select_move_defense; } } if (ptt_siblings_success && !move.isCheck()) { TRY_DFPN; simulateSiblingsSuccess(record, record_child, pass_left, sibling_defense_success_count, sibling_defense_count); CATCH_DFPN; RETURN_ON_STOP(NULL); //re search as simulation is done. goto re_select_move_defense; } continue; } else if (result_child.isCheckmateFail())//å証 { if (move.isCheck() && read_check_defense) { ++disproof_by_inversion_count; } if (result_child == ProofDisproof::LoopDetection()) { record->setLoopWithPath(pass_left, path); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; best_disproof = 0; return &move; } ntesuki_assert(proof >= ProofDisproof::PROOF_LIMIT); move.setCheckmateFail(pass_left); TRY_DFPN; record->setResult(pass_left, result_child, move, false); CATCH_DFPN; best_disproof = 0; return &move; } min_child_age = std::min(min_child_age, record_child->distance); if ((record_child->distance <= record->distance) && !move.isPass()) { if (!record->useOld(pass_left)) { continue; } } }/* has record */ /* Proof Disproof ã®èª¿æ•´ã¯ã“ã“ã§ã™ã‚‹ */ if (record->useOld(pass_left)) { sum_proof = std::max(proof, sum_proof); } else if (NtesukiRecord::max_for_split && record->is_split) { sum_proof = std::max(proof, sum_proof); } else { sum_proof = addWithSaturation(ProofDisproof::PROOF_LIMIT, proof, sum_proof); } if (disproof < best_disproof) { best_move = &move; second_disproof = best_disproof; best_disproof = disproof; best_proof = proof; } else if (disproof < second_disproof) { second_disproof = disproof; } /* dynamic widening: è‰¯ã„æ‰‹ã®é¸å®š */ if (dynamic_widening_width > 0) { if (pdps.size() < dynamic_widening_width) { pdps.push_back(top_pdp_t(disproof, proof)); pdps.sort(sorter); } else { if (pdps.back().first > disproof) { pdps.pop_back(); pdps.push_back(top_pdp_t(disproof, proof)); }// back().disproof == disproof ã ã£ãŸå ´åˆã¯ï¼Ÿ pdps.sort(sorter); } } }/* foreach move */ /* dynamic widening: è‰¯ã„æ‰‹ã®é›†è¨ˆ */ if (dynamic_widening_width > 0 && dynamic_widening_width < moves.size()) { sum_proof = 0; for (std::list::const_iterator it = pdps.begin(); it != pdps.end(); ++it) { sum_proof += it->second; } } /* é¸ã‚“ã æ‰‹ã‚’åŸå‘³ã™ã‚‹ */ if (NULL == best_move) { ntesuki_assert(sum_proof == 0); /* パスã ã‘å…ˆã«èª­ã‚€ enhancement */ if (delay_non_pass && read_non_pass == false) { ntesuki_assert(!under_attack); read_non_pass = true; record->setUseOld(pass_left, false); record->setNtesuki(pass_left); if (ptt_invalid_defense) { NtesukiMove move_pass = moves.front(); ntesuki_assert(move_pass.isPass()); NtesukiRecord *record_pass = table.findWithMove(record, move_pass); const PathEncoding path_child(path, move_pass.getMove()); ntesuki_assert(record_pass->getValueWithPath(pass_left - 1, path_child).isCheckmateSuccess()); TRY_DFPN; simulateSiblingsSuccess(record, record_pass, pass_left, pass_success_count, pass_count); CATCH_DFPN; RETURN_ON_STOP(NULL); } goto re_select_move_defense; } /* delay non pass */ if (!record->useOld(pass_left)) { if (SHRT_MAX != min_child_age) { record->setUseOld(pass_left, true); ntesuki_assert(min_child_age <= record->distance); record->distance = min_child_age; goto re_select_move_defense; } } if (delay_interpose && read_interpose == false) { read_interpose = true; record->setUseOld(pass_left, false); record->setReadInterpose(pass_left); TRY_DFPN; handleInterpose(record, pass_left); CATCH_DFPN; RETURN_ON_STOP NULL; goto re_select_move_defense; } /* é€†çŽ‹æ‰‹ã®æ‰±ã„ */ switch(isscheme) { case NtesukiRecord::no_is: ntesuki_assert(read_check_defense == false); break; case NtesukiRecord::tonshi_is: handleTonshi(record, pass_left, last_move); RETURN_ON_STOP NULL; break; case NtesukiRecord::delay_is: if (read_check_defense == false) { ++proof_without_inversion_count; read_check_defense = true; record->setReadCheckDefense(pass_left); goto re_select_move_defense; } break; case NtesukiRecord::normal_is: ntesuki_assert(read_check_defense == true); break; } /* å…¨ã¦ã®æ‰‹ãŒæ™®é€šã«è¨¼æ˜Žã•れ㟠*/ TRY_DFPN; record->setResult(pass_left, ProofDisproof::Checkmate(), NtesukiMove::INVALID(), false); CATCH_DFPN; return NULL; } ntesuki_assert(best_move); ntesuki_assert(sum_proof != 0); ntesuki_assert(best_disproof != 0); if (record->useOld(pass_left)) { ntesuki_assert(min_child_age != SHRT_MAX); record->distance = min_child_age; } average_cost /= average_cost_count; step_cost = std::max(average_cost, 1); return best_move; } template void osl::ntesuki::NtesukiSearcher:: handleTonshi(NtesukiRecord *record, int pass_left, const Move last_move) { const Player A = PlayerTraits::opponent; const Player D = T; if (pass_left > 0) { NtesukiResult result_defender = record->getValueWithPath(pass_left - 1, path); if (!result_defender.isFinal()) { /* to make sure not to come back here */ record->setResult(pass_left, ProofDisproof::Bottom(), NtesukiMove::INVALID(), false); const unsigned int read_node_limit_orig = read_node_limit; int ratio = 1; if ((record->distance / 2) == 0) ratio = 8; else if ((record->distance / 2) == 1) ratio = 2; read_node_limit = node_count + READ_ATTACK_BACK_LIMIT * ratio; NtesukiRecord::UnVisitLock unVisitLock(record); TRY_DFPN; result_defender = attack(record, NULL, NULL, INITIAL_PROOF_LIMIT, INITIAL_PROOF_LIMIT, pass_left - 1, last_move); CATCH_DFPN; if (result_defender.isCheckmateSuccess()) { ++attack_back_count; } read_node_limit = read_node_limit_orig; RETURN_ON_STOP; } if (result_defender.isFinal()) { return; } } } template void osl::ntesuki::NtesukiSearcher:: simulateSiblingsSuccess(NtesukiRecord *record, NtesukiRecord *record_best, int pass_left, unsigned int& success_count, unsigned int& total_count) { LockGC glock(table); const Player A = PlayerTraits::opponent; if (!record_best) return; ntesuki_assert(record_best); ntesuki_assert(record_best->getValue(pass_left).isCheckmateSuccess()); NtesukiMoveList moves; mg->generate(state, moves); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); ++move_it) { NtesukiMove& move = *move_it; NtesukiRecord *record_child = table.allocateWithMove(record, move); if (record_child == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_child); if (record_child == record_best) continue; if (record_child->isVisited()) continue; ntesuki_assert(record_child); const PathEncoding path_child(path, move.getMove()); const NtesukiResult result_child = record_child->getValueWithPath(pass_left, path_child); if (result_child.isFinal()) { continue; } bool simulation_result; total_count++; CallSimulationDefense helper(simulator, table, record_child, record_best, pass_left, simulation_result, move.getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, move.getMove(), helper); CATCH_DFPN; RETURN_ON_STOP; if (simulation_result) { success_count++; ntesuki_assert(record_child->getValueWithPath(pass_left, path_child).isCheckmateSuccess()); move.setBySimulation(); move.setCheckmateSuccess(pass_left); } } } template void osl::ntesuki::NtesukiSearcher:: handleInterpose(NtesukiRecord* record, int pass_left) { const Player A = PlayerTraits::opponent; ntesuki_assert(T == state.turn()); NtesukiMoveList moves; mg->generate(state, moves); for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); ++move_it) { if (move_it->isInterpose() && !move_it->isCheckmateSuccess(pass_left)) { NtesukiRecord *record_child = table.allocateWithMove(record, *move_it); if (record_child == 0) { *stop_flag = TableLimitReached; return; } ntesuki_assert(record_child); const PathEncoding path_child(path, move_it->getMove()); if(record_child->getValueWithPath(pass_left, path_child).isFinal()) { continue; } ntesuki_assert(record_child->getBestMove(pass_left).isInvalid()); NtesukiMoveList::iterator best_it = moves.begin(); for (; best_it != moves.end(); ++best_it) { if (best_it->to() == move_it->to() && best_it->isCheckmateSuccess(pass_left)) break; } if (best_it == moves.end()) { continue; } const NtesukiRecord* record_best = table.findWithMove(record, *best_it); ntesuki_assert(record_best); bool simulation_result; CallSimulationDefense helper(simulator, table, record_child, record_best, pass_left, simulation_result, move_it->getMove()); TRY_DFPN; ApplyMoveWithPath::doUndoMoveOrPass(state, path, move_it->getMove(), helper); CATCH_DFPN; RETURN_ON_STOP; if (simulation_result) { move_it->setBySimulation(); move_it->setCheckmateSuccess(pass_left); } else if (record_child->getValue(pass_left).isCheckmateFail()) { break; } } } } /* 外ã‹ã‚‰å‘¼ã°ã‚Œã‚‹é–¢æ•°. */ template int osl::ntesuki::NtesukiSearcher:: search() { NtesukiRecord::pass_count = 0; const Player D = PlayerTraits::opponent; //const HashKey key = HashKey::calcHash(state); const HashKey key(state); NtesukiRecord *record = table.allocateRoot(key, PieceStand(WHITE, state), 0, &state); ntesuki_assert(record); NtesukiResult result; if (A == state.turn()) { const Player T = A; result = attack(record, NULL, NULL, INITIAL_PROOF_LIMIT, INITIAL_DISPROOF_LIMIT, max_pass - 1, Move::INVALID()); } else//A != turn { const Player T = D; if (0 == (max_pass - 1) && !state.inCheck(D)) { if (verbose) std::cerr << "No Check" << std::endl; return NtesukiNotFound; } else { result = defense(record, NULL, NULL, INITIAL_PROOF_LIMIT, INITIAL_DISPROOF_LIMIT, max_pass - 1, Move::INVALID()); } } if (node_count > read_node_limit || *stop_flag) { if (verbose) std::cerr << "Limit Reached\t" << result << std::endl; return ReadLimitReached; } else { if (verbose) std::cerr << "result:\t" << result << std::endl; if (result.isCheckmateSuccess()) { for (unsigned int i = 0; i < max_pass; ++i) { if (record->getValue(i).isCheckmateSuccess()) { return i; } } } } ntesuki_assert(result.isCheckmateFail()); return NtesukiNotFound; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/move_generator/0000755000000000000000000000000012316770314020701 5ustar rootrootlibosl-0.8.0.orig/full/osl/ntesuki/move_generator/addEffect8Defense.h0000644000000000000000000000350512316770314024304 0ustar rootroot#ifndef _GENERATE_ADD_EFFECT8_DEFENSE_H #define _GENERATE_ADD_EFFECT8_DEFENSE_H #include "osl/move_generator/pieceOnBoard.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/move_action/store.h" #include "osl/centering3x3.h" #include "osl/state/numEffectState.h" namespace osl { namespace move_generator { /** * 玉㮠8è¿‘å‚ã«åˆ©ãã‚’ã¤ã‘ã‚‹æ‰‹ã‚’ç”Ÿæˆ * - 玉自身ãŒå‹•ãæ‰‹ã‚‚ç”Ÿæˆ * - 自殺手ã¯ç”Ÿæˆã—ãªã„ */ template struct AddEffect8Defense { static void generateTo(const NumEffectState& state, Square p, move_action::Store& action) { if (!p.isOnBoard()) return; GenerateAddEffectWithEffect::generate(P, state, p, action); } static void generate(const NumEffectState& state, MoveVector& moves) { const Square king = state.template kingSquare

(); const Square center = Centering3x3::adjustCenter(king); { move_action::Store action(moves); generateTo(state, center, action); generateTo(state, center + Board_Table.getOffsetForBlack(UL), action); generateTo(state, center + Board_Table.getOffsetForBlack(U), action); generateTo(state, center + Board_Table.getOffsetForBlack(UR), action); generateTo(state, center + Board_Table.getOffsetForBlack(L), action); generateTo(state, center + Board_Table.getOffsetForBlack(R), action); generateTo(state, center + Board_Table.getOffsetForBlack(DL), action); generateTo(state, center + Board_Table.getOffsetForBlack(D), action); generateTo(state, center + Board_Table.getOffsetForBlack(DR), action); } moves.unique(); } }; } } // namespace osl #endif /* _GENERATE_ADD_EFFECT8_DEFENSE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/move_generator/captureEffectToAroundKing8.h0000644000000000000000000000435612316770314026217 0ustar rootroot#ifndef _GENERATE_CAPTURE_EFFECT_TO_AROUND_KING8_H #define _GENERATE_CAPTURE_EFFECT_TO_AROUND_KING8_H #include "osl/move_generator/pieceOnBoard.h" #include "osl/move_action/captureFrom.h" #include "osl/move_action/store.h" #include "osl/centering3x3.h" #include "osl/state/numEffectState.h" #include "osl/container/moveVector.h" namespace osl { namespace move_generator { /** * Capture pieces that has effect to squares around King and to the King. * - TODO should be Capture Effecto To Around King 9? * - Using centering3x3, i.e. if the King is on the edge, * the area is move towards the center of the board. */ template struct CaptureEffectToAroundKing8 { template static void generateTo(const NumEffectState& state, Square p, Action& action) { typedef move_action::CaptureFrom capture_action; capture_action capture(state, action); if (p.isEdge()) return; assert(p.isOnBoard()); state.template forEachEffect::opponent, capture_action>(p, capture); } static void generate(const NumEffectState& state, MoveVector& moves) { const Square position_king = Centering3x3::adjustCenter(state.template kingSquare

()); { move_action::Store action(moves); generateTo(state, position_king, action); generateTo(state, position_king + Board_Table.getOffsetForBlack(UL), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(U), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(UR), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(L), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(R), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(DL), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(D), action); generateTo(state, position_king + Board_Table.getOffsetForBlack(DR), action); } moves.unique(); } }; } } // namespace osl #endif /* _GENERATE_CAPTURE_EFFECT_TO_AROUND_KING8_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSimulationSearcherProof.tcc0000644000000000000000000003732312316770314024602 0ustar rootroot/* ntesukiSimulationProof.tcc */ #include "osl/ntesuki/ntesukiSimulationSearcher.h" #include "osl/ntesuki/oracleProverLight.h" #include "osl/ntesuki/ntesukiExceptions.h" #include "osl/ntesuki/ntesukiRecord.h" #include "osl/container/moveVector.h" #include "osl/move_classifier/safeMove.h" #include "osl/apply_move/applyMoveWithPath.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/effect_util/effectUtil.h" #ifdef NDEBUG # include "osl/ntesuki/ntesukiMove.tcc" # include "osl/ntesuki/ntesukiRecord.tcc" //# include "osl/move_generator/escape.tcc" #endif using namespace osl; using namespace osl::ntesuki; #ifndef RETURN #ifndef NDEBUG #define RETURN \ ntesuki_assert(result.isCheckmateSuccess() ==\ record->getValueWithPath(pass_left, path).isCheckmateSuccess());\ if (record->getValueWithPath(pass_left, path).proof() == 0)\ ntesuki_assert(record->getValueWithPath(pass_left, path).disproof() > ProofDisproof::DISPROOF_LIMIT);\ if (record->getValueWithPath(pass_left, path).disproof() == 0)\ ntesuki_assert(record->getValueWithPath(pass_left, path).proof() > ProofDisproof::PROOF_LIMIT);\ return #else #define RETURN return #endif #endif /* Helper classes */ template class NtesukiSimulationSearcher:: AttackHelperProof { Searcher* searcher; NtesukiRecord *record; const NtesukiRecord *record_orig; unsigned int pass_left; const Move last_move; public: AttackHelperProof(Searcher* searcher, NtesukiRecord* record, const NtesukiRecord* record_orig, unsigned int pass_left, const Move last_move) : searcher(searcher), record(record), record_orig(record_orig), pass_left(pass_left), last_move(last_move) {} void operator()(Square p) { (*searcher).template defenseForProof::opponent> (record, record_orig, pass_left, last_move); } }; template class NtesukiSimulationSearcher:: DefenseHelperProof { Searcher* searcher; NtesukiRecord *record; const NtesukiRecord *record_orig; unsigned int pass_left; const Move last_move; public: DefenseHelperProof(Searcher* searcher, NtesukiRecord* record, const NtesukiRecord* record_orig, unsigned int pass_left, const Move last_move) : searcher(searcher), record(record), record_orig(record_orig), pass_left(pass_left), last_move(last_move) {} void operator()(Square p) { (*searcher).template attackForProof::opponent> (record, record_orig, pass_left, last_move); } }; /* =================== * Count the increase of child nodes */ class CountChildLock { public: CountChildLock(NtesukiRecord* r, const NtesukiTable& t) : record(r), table(t) { size_start = table.size(); } ~CountChildLock() { record->addChildCount(table.size() - size_start); } private: osl::ntesuki::NtesukiRecord* record; const osl::ntesuki::NtesukiTable& table; unsigned int size_start; }; /*====================================================================== * Proof *====================================================================== */ /** * Still cannot see if is safe move */ template bool NtesukiSimulationSearcher:: isSafeMove(const Move move, int pass_left) { if (!state.isValidMove(move, false)) return false; if (move.isDrop()) return true; return move_classifier::SafeMove

::isMember(state, move.ptype(), move.from(), move.to()); } template void NtesukiSimulationSearcher:: attackForProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left, const Move last_move) { CountChildLock cclock(record, table); const Player A = P; #ifndef NDEBUG const Player O = PlayerTraits

::opponent; #endif ++node_count; ntesuki_assert(P == state.turn()); ntesuki_assert(record); ntesuki_assert(!record->getValueWithPath(pass_left, path).isFinal()); ntesuki_assert(record->getBestMove(pass_left).isInvalid()); ntesuki_assert(record_orig); ntesuki_assert(record_orig->getValueWithPath(pass_left, path).isCheckmateSuccess()); ntesuki_assert(record_orig->getBestMove(pass_left).isValid()); ntesuki_assert(!state.inCheck(O)); if (record->isVisited()) { result = ProofDisproof::LoopDetection(); RETURN; } /* æ·±ã•固定 checkmate searcher を呼ã³å‡ºã™ */ if (record->setUpNode

()) { const NtesukiResult result_cur = record->getValueWithPath(pass_left, path); if (result_cur.isCheckmateSuccess()) { /* Immediate Checkmate */ result = ProofDisproof::Checkmate(); RETURN; } else if (result_cur.isFinal()) { result = result_cur; RETURN; } } /* Simulation 元㌠immediate checkmate ãªã‚‰ã“ã®å…ˆã¯ simulate ã§ããªã„ */ const NtesukiMove best_move_orig = record_orig->getBestMove(pass_left); if (best_move_orig.isImmediateCheckmate()) { result = ProofDisproof::NoCheckmate(); RETURN; } NtesukiRecord::VisitLock visitLock(record); /* n ãŒå°‘ãªã„ã¨ãã®çµæžœã‚’å‚ç…§ */ if ((pass_left > 0) && record_orig->getValueWithPath(pass_left - 1, path) .isCheckmateSuccess()) { if (record->getValueWithPath(pass_left - 1, path) .isCheckmateFail()) { result = ProofDisproof::NoCheckmate(); RETURN; } ntesuki_assert(!record->getValueWithPath(pass_left - 1, path) .isFinal()); NtesukiRecord::UnVisitLock unVisitLock(record); TRY_DFPN; attackForProof

(record, record_orig, pass_left - 1, last_move); CATCH_DFPN; RETURN; } const Move move = adjustMove

(best_move_orig.getMove()); /* invalid move ã¨ãªã£ã¦ã—ã¾ã£ãŸ */ if (!move.isValid() || !isSafeMove

(move, pass_left)) { result = ProofDisproof::NoCheckmate(); RETURN; } const bool move_is_check = (move_classifier::PlayerMoveAdaptor:: isMember(state, move)); if (0 == pass_left && !move_is_check) { result = ProofDisproof::NoCheckmate(); RETURN; } if (move_is_check != best_move_orig.isCheck()) { result = ProofDisproof::NoCheckmate(); RETURN; } /* 以å‰ã® bestMove を実行 */ NtesukiRecord *record_child = table.allocateWithMove(record, move); if (record_child == 0) { result = ProofDisproof::NoCheckmate(); RETURN; } const NtesukiRecord* record_child_orig = table.findWithMoveConst(record_orig, best_move_orig); if (!record_child_orig) { result = ProofDisproof::NoCheckmate(); RETURN; } result = record_child->getValueWithPath(pass_left, path); if (result.isUnknown()) { AttackHelperProof helper(this, record_child, record_child_orig, pass_left, move); TRY_DFPN; ApplyMoveWithPath

::doUndoMove(state, path, move, helper); if (record->getValueWithPath(pass_left, path).isFinal()) { result = record->getValueWithPath(pass_left, path); RETURN; } CATCH_DFPN; } if (result.isPawnDropFoul(move)) { result = ProofDisproof::PawnCheckmate(); RETURN; } else if (result.isCheckmateSuccess()) { result = ProofDisproof::Checkmate(); NtesukiMove best_move(move); TRY_DFPN; best_move.setCheckmateSuccess(pass_left); record->setResult(pass_left, result, best_move, true); CATCH_DFPN; RETURN; } else if (result == ProofDisproof::LoopDetection()) { result = ProofDisproof::NoCheckmate(); } ntesuki_assert(result.isCheckmateFail()); RETURN; } template void NtesukiSimulationSearcher:: defenseForProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left, const Move last_move) { CountChildLock cclock(record, table); const Player A = PlayerTraits

::opponent; const Player O = PlayerTraits

::opponent; ++node_count; ntesuki_assert(P == state.turn()); ntesuki_assert(record); if (!record_orig) { result = ProofDisproof::NoCheckmate(); return; } if (state.inCheck(O)) { //the previous move was a drop move that did not resolve a check result = ProofDisproof::NoCheckmate(); return; } /* æ·±ã•固定 checkmate searcher を呼ã³å‡ºã™ */ if (record->setUpNode

()) { result = record->getValueWithPath(pass_left, path); if (result.isFinal()) { return; } } /* å…ƒã®ã‚·ãƒŠãƒªã‚ªãŒé–“é•ã£ã¦ã„ã‚‹ */ if (!record_orig->getValueWithPath(pass_left, path).isCheckmateSuccess()) { result = ProofDisproof::NoCheckmate(); return; } if (record->isVisited()) { result = ProofDisproof::LoopDetection(); RETURN; } NtesukiRecord::VisitLock visitLock(record); /* 攻撃å´ã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ãªã„ã‹èª¿ã¹ã‚‹ */ const bool invalidAttack = state.inCheck(PlayerTraits

::opponent); if (invalidAttack) { result = ProofDisproof::AttackBack(); RETURN; } /* n ãŒå°‘ãªã„ã¨ãã®çµæžœã‚’å‚ç…§ */ if (pass_left > 0 && record_orig->getValueWithPath(pass_left - 1, path) .isCheckmateSuccess()) { result = (record->getValueWithPath(pass_left - 1, path)); if(result.isCheckmateFail()) { RETURN; } ntesuki_assert(!record->getValueWithPath(pass_left - 1, path) .isFinal()); NtesukiRecord::UnVisitLock unVisitLock(record); TRY_DFPN; defenseForProof

(record, record_orig, pass_left - 1, last_move); CATCH_DFPN; RETURN; } /* * å—ã‘る手ã®å®Ÿè¡Œ */ /* * 守りå´ã®æ‰‹ã‚’生æˆã™ã‚‹ * - 王手ãŒã‹ã‹ã£ã¦ã„ã‚‹ã‹èª¿ã¹ã‚‹(王手ãŒã‹ã‹ã£ã¦ã„ãŸå ´åˆã«ã¯é€ƒã’る手を生æˆã™ã‚‹) * - ãã†ã§ãªã„ãªã‚‰ï¼Œé€šå¸¸ã®æ‰‹ç”Ÿæˆã‚’行ㆠ*/ NtesukiMoveList moves; record->generateMoves

(moves, 0, true); result = ProofDisproof::Checkmate(); if (moves.empty()) { result = ProofDisproof::NoEscape(); TRY_DFPN; record->setResult(pass_left, result, NtesukiMove::INVALID(), false); CATCH_DFPN; RETURN; } bool some_moves_not_generated = false; for (NtesukiMoveList::iterator move_it = moves.begin(); move_it != moves.end(); move_it++) { NtesukiMove& move = *move_it; if (move.isCheckmateSuccess(pass_left)) continue; /* 逆王手ã¯èª­ã‚“ã§ã„ãªã„å¯èƒ½æ€§ãŒã‚ã‚‹ */ if (isscheme != NtesukiRecord::normal_is && isscheme != NtesukiRecord::delay_is && move.isCheck() && pass_left > 0) continue; /* シミュレーション元ã®å­ã‚’探㙠*/ const NtesukiRecord* record_child_orig = table.findWithMoveConst(record_orig, move); if (!record_child_orig || !record_child_orig->getValue(pass_left).isCheckmateSuccess()) { some_moves_not_generated = true; continue; } NtesukiRecord *record_child = table.allocateWithMove(record, move); if (record_child == 0) { result = ProofDisproof::NoCheckmate(); RETURN; } if(record_child->isVisited()) { result = ProofDisproof::LoopDetection(); record->setLoopWithPath(pass_left, path); TRY_DFPN; record->setResult(pass_left, NtesukiResult(1, 1), NtesukiMove::INVALID(), false); CATCH_DFPN; RETURN; } int pass_left_child = pass_left; if (move.isPass()) --pass_left_child; const PathEncoding path_child(path, move.getMove()); result = record_child->getValueWithPath(pass_left_child, path_child); if (result.isUnknown()) { DefenseHelperProof helper(this, record_child, record_child_orig, pass_left_child, move.getMove()); TRY_DFPN; ApplyMoveWithPath

::doUndoMoveOrPass(state, path, move.getMove(), helper); CATCH_DFPN; if (record->getValueWithPath(pass_left, path).isFinal()) { result = record->getValueWithPath(pass_left, path); RETURN; } } if (result.isCheckmateFail()) { RETURN; } } ntesuki_assert(result.isCheckmateSuccess()); if (some_moves_not_generated) { result = ProofDisproof::NoCheckmate(); } else { TRY_DFPN; record->setResult(pass_left, result, NtesukiMove::INVALID(), true); CATCH_DFPN; } RETURN; } /* Public interface */ template bool NtesukiSimulationSearcher:: startFromAttackProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left, const Move last_move) { assert(P == state.turn()); const Player A = P; ntesuki_assert(record); if (!record_orig) { return false; } if (!record_orig->getValueWithPath(pass_left, path).isCheckmateSuccess()) { return false; } if (!record->isDominatedByProofPieces(record_orig, pass_left)) { return false; } TRY_DFPN; if (record->setUpNode

()) { if (record->getValueWithPath(pass_left, path).isCheckmateSuccess()) { /* Immediate Checkmate */ result = ProofDisproof::Checkmate(); return true; } else if (record->getValueWithPath(pass_left, path).isCheckmateFail()) { result = ProofDisproof::NoCheckmate(); return false; } } CATCH_DFPN; TRY_DFPN; const NtesukiMove m = (record_orig->getBestMove(pass_left)); if (m.isImmediateCheckmate()) return false; CATCH_DFPN; ++proof_count; TRY_DFPN; OracleProverLight light(state, mg, path, table,isscheme); if (light.startFromAttack

(record, record_orig, pass_left)) { ++proof_success_count; ++light_proof_success_count; ntesuki_assert(record->getValueWithPath(pass_left, path) .isCheckmateSuccess()); return true; } else if (record->getValueWithPath(pass_left, path).isCheckmateFail()) { result = ProofDisproof::NoCheckmate(); return false; } CATCH_DFPN; TRY_DFPN; attackForProof

(record, record_orig, pass_left, last_move); CATCH_DFPN; if (result.isCheckmateSuccess()) { ++proof_success_count; return true; } return false; } template bool NtesukiSimulationSearcher:: startFromDefenseProof(NtesukiRecord* record, const NtesukiRecord* record_orig, const unsigned int pass_left, const Move last_move) { assert(P == state.turn()); const Player A = PlayerTraits

::opponent; ntesuki_assert(record); if (!record_orig || !record_orig->getValueWithPath(pass_left, path). isCheckmateSuccess()) { return false; } if (!record->isDominatedByProofPieces(record_orig, pass_left)) { return false; } if (record->setUpNode

()) { if (record->getValueWithPath(pass_left, path).isCheckmateSuccess()) { /* Immediate Checkmate */ result = ProofDisproof::Checkmate(); return true; } else if (record->getValueWithPath(pass_left, path).isCheckmateFail()) { result = ProofDisproof::NoCheckmate(); return false; } } const NtesukiMove m = (record_orig->getBestMove(pass_left)); if (m.isImmediateCheckmate()) return false; ++proof_count; OracleProverLight light(state, mg, path, table, isscheme); TRY_DFPN; if (light.startFromDefense

(record, record_orig, pass_left)) { ++proof_success_count; ++light_proof_success_count; ntesuki_assert(record->getValueWithPath(pass_left, path). isCheckmateSuccess()); return true; } else if (record->getValueWithPath(pass_left, path).isCheckmateFail()) { result = ProofDisproof::NoCheckmate(); return false; } CATCH_DFPN; TRY_DFPN; defenseForProof

(record, record_orig, pass_left, last_move); CATCH_DFPN; if (result.isCheckmateSuccess()) { ++proof_success_count; return true; } return false; } #undef RETURN // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMoveGeneratorDefense.cc0000644000000000000000000001153112316770314023647 0ustar rootroot/* ntesukiMoveGenerator.cc */ #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/state/numEffectState.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/move_generator/escape.h" #include "osl/move_classifier/canAttackInNMoves.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/safeMove.h" #include "osl/move_classifier/check.h" #include "osl/move_generator/legalMoves.h" #include "osl/move_generator/addEffect.h" #include "osl/move_generator/drop.h" #include "osl/move_generator/addEffect8.h" #include "osl/move_generator/kingWalk.h" #include "osl/move_generator/openKingRoad.h" #include "osl/move_generator/dropAroundKing8.h" #include "osl/move_generator/captureEffectToAroundKing8.h" #include "osl/move_generator/addEffect8Defense.h" #include "osl/move_action/store.h" #include /* * n 手ã™ã探索ã§ç”¨ã„ã‚‹ move generator. */ namespace osl { namespace ntesuki { /* ---------------------------------------------------------------------- * DEFENSE * ---------------------------------------------------------------------- */ /* GetAllDefenseMoves */ GetAllDefenseMoves::GetAllDefenseMoves(bool verbose) : NtesukiDefenseMoveGenerator(verbose) {} GetAllDefenseMoves::~GetAllDefenseMoves() {} template void GetAllDefenseMoves:: generate(const NumEffectState& state, NtesukiMoveList& moves, const Square& last_to) { assert (state.turn() == P); MoveVector move_candidates; LegalMoves::generate(state, move_candidates); moves = NtesukiMoveList(state, move_candidates); } template void GetAllDefenseMoves::generate(const NumEffectState& state, NtesukiMoveList& moves, const Square& last_to); template void GetAllDefenseMoves::generate(const NumEffectState& state, NtesukiMoveList& moves, const Square& last_to); /* GetDefenseMoves * - 実装済㿠* -- 玉を動ã‹ã™ * -- 玉ã®ã¾ã‚り 8è¿‘å‚ã«é§’を打㤠* -- 玉ã®é€ƒã’é“を空ã‘ã‚‹ * -- 玉ã®ã¾ã‚り8è¿‘å‚ã«åˆ©ãã‚’ã¤ã‘ã¦ã„ã‚‹é§’(ã‚’å–ã‚‹ * -- 玉ã®ã¾ã‚り 8è¿‘å‚ã«(守りã®)利ãã‚’ã¤ã‘ã‚‹ã«ã‚ˆã‚‹ defense * -- ç›´å‰ã«å‹•ã„ãŸé§’ã‚’å–る手 * - 未実装 * -- 玉ã®ã¾ã‚り 8è¿‘å‚ã®é§’ã‚’å–ã‚‹ * -- 最後ã«å‹•ã‹ã—ãŸå¤§é§’ã‹ã‚‰å…«è¿‘å‚ã¸åˆ©ããŒã‚ã‚‹å ´åˆã€ * ãã®åˆ©ãã®é€”中ã®ãƒžã‚¹ã§ã€è‡ªåˆ†ãŒåˆ©ããŒã‚ã‚‹ã¨ã“ã‚ã«é§’を打㤠* - 相手ã‹ã‚‰ã®åæ’ƒã®ã†ã¡ * -- é§’ã‚’å–りã¤ã¤çŽ‹æ‰‹(特ã«éŠ€ãŒãªã„ã¨ãã®éŠ€å–りã®ã‚ˆã†ãªæ‰‹) */ GetDefenseMoves::GetDefenseMoves(bool verbose) : NtesukiDefenseMoveGenerator(verbose) {} GetDefenseMoves::~GetDefenseMoves(){} template void GetDefenseMoves:: generate(const NumEffectState& state, NtesukiMoveList& moves, const Square& last_to) { MoveVector move_candidates; const Square pos = state.template kingSquare

(); const bool check = state.hasEffectAt(PlayerTraits

::opponent, pos); if (check) { GenerateEscapeKing::generate(state, move_candidates); moves = NtesukiMoveList(state, move_candidates); return; } typedef move_action::Store action_t; assert (state.turn() == P); move_action::Store store_candidates(move_candidates); move_generator::KingWalk

:: generate(static_cast(state), store_candidates); move_generator::OpenKingRoad

:: generate(static_cast(state), store_candidates); move_generator::CaptureEffectToAroundKing8

:: generate(state, store_candidates); move_generator::GenerateCapture:: generate(state.turn(), state, last_to, store_candidates); //these are non drop moves that could be 'non safe moves' MoveVector move_safe; using namespace osl::move_classifier; for (unsigned int i = 0; i < move_candidates.size(); ++i) { const Move m = move_candidates[i]; if (PlayerMoveAdaptor::isMember(state, m)) { move_safe.push_back(m); } } move_action::Store store_safe(move_safe); move_generator::AddEffect8Defense

:: generate(state, store_safe); //drop moves that are always safe move_generator::DropAroundKing8

:: generate(static_cast(state), store_safe); move_safe.unique(); moves = NtesukiMoveList(state, move_safe); } template void GetDefenseMoves::generate(const NumEffectState& state, NtesukiMoveList& moves, const Square& last_to); template void GetDefenseMoves::generate(const NumEffectState& state, NtesukiMoveList& moves, const Square& last_to); }//ntesuki }//osl // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiSearcher.cc0000644000000000000000000001334312316770314021337 0ustar rootroot#include "osl/ntesuki/ntesukiSearcher.tcc" #include bool osl::ntesuki::NtesukiSearcher:: delay_non_pass = false; bool osl::ntesuki::NtesukiSearcher:: ptt_invalid_defense = false; bool osl::ntesuki::NtesukiSearcher:: delay_interpose = false; bool osl::ntesuki::NtesukiSearcher:: delay_nopromote = false; bool osl::ntesuki::NtesukiSearcher:: delay_non_attack = false; bool osl::ntesuki::NtesukiSearcher:: read_attack_only = false; bool osl::ntesuki::NtesukiSearcher:: ptt_non_attack = false; bool osl::ntesuki::NtesukiSearcher:: ptt_siblings_fail = false; bool osl::ntesuki::NtesukiSearcher:: ptt_siblings_success = false; bool osl::ntesuki::NtesukiSearcher:: ptt_uncle = false; bool osl::ntesuki::NtesukiSearcher:: ptt_aunt = false; unsigned int osl::ntesuki::NtesukiSearcher:: dynamic_widening_width = 0; /* =================== * Constructor / Destructor */ osl::ntesuki::NtesukiSearcher:: NtesukiSearcher(State& state, NtesukiMoveGenerator *mg, unsigned int table_limit, volatile int *stop_flag, bool verbose, int max_pass, NtesukiRecord::IWScheme iwscheme, NtesukiRecord::PSScheme psscheme, NtesukiRecord::ISScheme isscheme, int tsumero_cost, int tsumero_estimate, double gc_ratio) : state(state), mg(mg), table(table_limit, static_cast(table_limit * gc_ratio), verbose), simulator(state, mg, path, table, isscheme, verbose), node_count(0), verbose(verbose), stop_flag(stop_flag), path(state.turn()), /* control on search */ max_pass(max_pass), iwscheme(iwscheme), psscheme(psscheme), isscheme(isscheme), tsumero_cost(tsumero_cost), tsumero_estimate(tsumero_estimate), gc_ratio(gc_ratio), /* statistical information */ blockByAttackBack(0), blockByPass(0), attack_node_count(0), attack_node_under_attack_count(0), attack_node_moves_count(0), defense_node_count(0), defense_node_under_attack_count(0), defense_node_moves_count(0), pass_count(0), pass_success_count(0), pass_attack_count(0), pass_attack_success_count(0), sibling_defense_count(0), sibling_defense_success_count(0), sibling_attack_count(0), sibling_attack_success_count(0), isshogi_defense_count(0), isshogi_defense_success_count(0), isshogi_attack_count(0), isshogi_attack_success_count(0), immediate_win(0), immediate_lose(0), attack_back_count(0), proof_without_inversion_count(0), proof_AND_count(0), disproof_by_inversion_count(0) { NtesukiRecord::table = &table; NtesukiRecord::state = &state; NtesukiRecord::mg = mg; NtesukiRecord::split_count = 0; NtesukiRecord::confluence_count = 0; if (this->max_pass > (int)NtesukiRecord::SIZE) this->max_pass = NtesukiRecord::SIZE; if (verbose) { std::cerr << "NtesukiSearcher \n" << "IWScheme:\t" << iwscheme << "\n" << "PSScheme:\t" << psscheme << "\n" << "ISScheme:\t" << isscheme << "\n" << "Fixed:\t" << NtesukiRecord::fixed_search_depth<< "\n" << "Tsumero cost:\t" << tsumero_cost << "\n" << "Tsumero estimate:\t" << tsumero_estimate << "\n" << "Inversion cost:\t" << NtesukiRecord::inversion_cost << "\n" ; std::cerr << "enhancements: "; if(NtesukiSearcher::ptt_uncle) std::cerr << " PTT_UNCLE"; if(NtesukiSearcher::ptt_siblings_fail) std::cerr << " PTT_SIBLINGS_FAIL"; if(NtesukiSearcher::ptt_siblings_success) std::cerr << " PTT_SIBLINGS_SUCCESS"; if(NtesukiSearcher::delay_non_pass) std::cerr << " DELAY_NON_PASS"; if (NtesukiSearcher::ptt_invalid_defense) std::cerr << " PASS_SIMULATION"; if (NtesukiSearcher::delay_interpose) std::cerr << " DELAY_INTERPOSE"; if(NtesukiSearcher::delay_nopromote) std::cerr << " DELAY_NOPROMOTE"; if(NtesukiSearcher::delay_non_attack) std::cerr << " DELAY_NON_ATTACK"; if(NtesukiSearcher::read_attack_only) std::cerr << " READ_ATTACK_ONLY"; if(NtesukiSearcher::ptt_non_attack) std::cerr << " PTT_NON_ATTACK"; if (NtesukiRecord::use_dominance) std::cerr << " USE_DOMINANCE"; std::cerr << "\n"; } } osl::ntesuki::NtesukiSearcher:: ~NtesukiSearcher() { if (verbose) { std::cerr << "~NtesukiSearcher " << table.size() << "/" << node_count << "/" << read_node_limit << "\t" << "pass(" << pass_success_count << "/" << pass_count << ")\n" << "attack_node\t" << attack_node_under_attack_count << "/" << attack_node_count << "\t" << attack_node_moves_count << "moves\n" << "defense_node\t" << defense_node_under_attack_count << "/" << defense_node_count << "\t" << defense_node_moves_count << "moves\n" << "immidate(" << immediate_win << ", " << immediate_lose << ")\n" << "attack_back(" << attack_back_count << ")\n" << "sibling_success(" << sibling_defense_success_count << "/" << sibling_defense_count << ")\n" << "sibling_fail(" << sibling_attack_success_count << "/" << sibling_attack_count << ")\n" << "is_att(" << isshogi_attack_success_count << "/" << isshogi_attack_count << ")\t" << "is_def(" << isshogi_defense_success_count << "/" << isshogi_defense_count << ")\n" << "inversion_win(" << disproof_by_inversion_count << "/" << proof_AND_count << "/" << proof_without_inversion_count << ")\n" << "DAG\t" << NtesukiRecord::split_count << "/" << NtesukiRecord::confluence_count << "\n" ; } } NtesukiTable& osl::ntesuki::NtesukiSearcher:: getTable() { return table; } /* explicit instantiation */ namespace osl { namespace ntesuki { template int NtesukiSearcher::search(); template int NtesukiSearcher::search(); } } libosl-0.8.0.orig/full/osl/ntesuki/ntesukiTable.cc0000644000000000000000000003615712316770314020642 0ustar rootroot/* ntesukiTable.cc */ #include "osl/ntesuki/ntesukiTable.h" #include "osl/ntesuki/ntesukiTable.tcc" #include "osl/ntesuki/ntesukiRecord.h" #include "osl/ntesuki/ntesukiSearcher.h" #include "osl/state/numEffectState.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/effect_util/effectUtil.h" #include "osl/record/csaRecord.h" #ifdef NDEBUG # include "osl/ntesuki/ntesukiRecord.tcc" #endif #include #include #include int osl::ntesuki::NtesukiTable::Table:: largeGCCount = 0; osl::ntesuki::NtesukiTable::Table:: Table(unsigned int c, unsigned int g, bool v) : ntesuki_hash_map(c), capacity(c), default_gc_size(g), verbose(v), no_gc(false), gc_request(false), numEntry(0), numCacheHit(0), gcCount(0) { } osl::ntesuki::NtesukiTable::Table:: ~Table() { } osl::ntesuki::NtesukiRecord * osl::ntesuki::NtesukiTable::Table:: allocate(const HashKey& key, const PieceStand& white_stand, signed short distance) { int full = 0; reallocate: if (numEntry < capacity || no_gc) { if (numEntry >= capacity) gc_request = true; NtesukiRecord::RecordList *record_list = &(ntesuki_hash_map::operator[](key.getSignatureKey())); for (NtesukiRecord::RecordList::iterator p = record_list->begin(); p != record_list->end(); ++p) { if (p->key.getPieceStand() == key.getPieceStand()) { ++numCacheHit; return &(*p); } } ++numEntry; const NtesukiRecord r(distance, key, white_stand, record_list); record_list->push_front(r); NtesukiRecord *result = &(record_list->front()); return result; } NtesukiRecord *result = find(key); if (result == 0 && full++ == 0 && capacity) { if (default_gc_size > 0) { collectGarbage(default_gc_size); goto reallocate; } } return result; } struct CompareChildSize { bool operator()(const osl::ntesuki::NtesukiRecord *lhs, const osl::ntesuki::NtesukiRecord *rhs) { return lhs->getChildCount() < rhs->getChildCount(); } }; struct RecordPrinter { /* Prints each node. * Leaf nodes are not printed. */ osl::state::NumEffectState &state; osl::ntesuki::NtesukiTable::Table &table; std::vector records; std::set read_keys; int depth, pass_count, pass_depth; RecordPrinter(osl::state::NumEffectState &s, osl::ntesuki::NtesukiTable::Table &t, osl::ntesuki::NtesukiRecord *r) : state(s), table(t), depth(-1), pass_count(0) { } void enter(osl::ntesuki::NtesukiRecord *r) { read_keys.insert(r->key); records.push_back(r); ++depth; } void exit() { read_keys.erase(records.back()->key); records.pop_back(); if (pass_depth) pass_count--; --depth; } bool withChildMove(const osl::ntesuki::NtesukiMove& move, osl::ntesuki::NtesukiRecord *child) { if (move.isPass()) { if (pass_count) return false; pass_count++; pass_depth = depth; } if (read_keys.find(child->key) != read_keys.end()) { return false; } int i = 0; for (; i <= depth; i++) std::cerr << "*"; std::cerr << record::csa::show(move.getMove()); for (; i <= 11; i++) std::cerr << " "; if (child->isVisited()) std::cerr << "(*)"; if (depth > 8) { std::cerr << "\t" << child->getChildCount() << "\t" << child->getValue(0) << " \t" << child->getValue(1) << " |\n"; return false; } else { std::cerr << "\t" << child->getChildCount() << "\t" << child->getValue(0) << " \t" << child->getValue(1) << "\n"; } return true; } void noChildMove(const osl::ntesuki::NtesukiMove& move) { } bool operator()(const osl::ntesuki::NtesukiMove& lhs, const osl::ntesuki::NtesukiMove& rhs) { osl::ntesuki::NtesukiRecord *record = records.back(); ntesuki_assert(record); NtesukiRecord *lchild = table.find(record->key.newHashWithMove(lhs.getMove())); if (!lchild) return false; NtesukiRecord *rchild = table.find(record->key.newHashWithMove(rhs.getMove())); if (!rchild) return true; if (lchild->isVisited()) return true; if (rchild->isVisited()) return false; return lchild->getChildCount() > rchild->getChildCount(); } struct Compare { bool operator()(const osl::ntesuki::NtesukiMove& lhs, const osl::ntesuki::NtesukiMove& rhs) { return lhs.getMove() < rhs.getMove(); } }; }; struct RecordPrinter2 { /* Prints each node. * Leaf nodes are printed as well. */ osl::state::NumEffectState &state; osl::ntesuki::NtesukiTable::Table &table; std::vector records; std::set read_keys; int depth, pass_count, pass_depth, depth_visited; RecordPrinter2(osl::state::NumEffectState &s, osl::ntesuki::NtesukiTable::Table &t, osl::ntesuki::NtesukiRecord *r) : state(s), table(t), depth(-1), pass_count(0), pass_depth(0), depth_visited(0) { } void enter(osl::ntesuki::NtesukiRecord *r) { if (r->isVisited()) ++depth_visited; read_keys.insert(r->key); records.push_back(r); ++depth; } void exit() { read_keys.erase(records.back()->key); records.pop_back(); if (pass_depth) pass_count--; --depth; } bool withChildMove(const osl::ntesuki::NtesukiMove& move, osl::ntesuki::NtesukiRecord *child) { if (move.isPass()) { if (pass_count) return false; pass_count++; pass_depth = depth; } bool result = true; if (depth < depth_visited) { return false; } int i = 0; for (; i <= depth; i++) std::cerr << "*"; for (; i <= 10; i++) std::cerr << " "; std::cerr << record::csa::show(move.getMove()); if (child->isVisited()) std::cerr << "(*)"; if (read_keys.find(child->key) != read_keys.end()) { std::cerr << "loop"; result = false; } std::cerr << "\t" << child->getChildCount() << "\t" << child->getValue(0) << "\t" << child->getValue(1) << "\n"; return result; } void noChildMove(const osl::ntesuki::NtesukiMove& move) { if (depth < depth_visited) { return; } int i = 0; for (; i <= depth; i++) std::cerr << "*"; for (; i <= 10; i++) std::cerr << " "; std::cerr << record::csa::show(move.getMove()) << "|\t" << move.h_a_proof << "/" << move.h_a_disproof << "\t" << move.h_d_proof << "/" << move.h_d_disproof << "\n"; } bool operator()(const osl::ntesuki::NtesukiMove& lhs, const osl::ntesuki::NtesukiMove& rhs) { osl::ntesuki::NtesukiRecord *record = records.back(); ntesuki_assert(record); NtesukiRecord *lchild = table.find(record->key.newHashWithMove(lhs.getMove())); if (!lchild) return false; NtesukiRecord *rchild = table.find(record->key.newHashWithMove(rhs.getMove())); if (!rchild) return true; if (lchild->isVisited()) return true; if (rchild->isVisited()) return false; return lchild->getChildCount() > rchild->getChildCount(); } struct Compare { bool operator()(const osl::ntesuki::NtesukiMove& lhs, const osl::ntesuki::NtesukiMove& rhs) { return lhs.getMove() < rhs.getMove(); } }; }; struct MarkAndSweep { osl::state::NumEffectState &state; osl::ntesuki::NtesukiTable::Table &table; std::set reachable_keys; int depth; MarkAndSweep(osl::state::NumEffectState &s, osl::ntesuki::NtesukiTable::Table &t, osl::ntesuki::NtesukiRecord *r) : state(s), table(t) { } ~MarkAndSweep() { typedef std::vector keys_t; keys_t garbage_list; for (osl::ntesuki::NtesukiTable::Table::iterator it = table.begin(); it != table.end(); ++it) { for (NtesukiRecord::RecordList::iterator p = it->second.begin(); p != it->second.end(); ++p) { NtesukiRecord *record = &(*p); if (reachable_keys.find(record->key) == reachable_keys.end()) { garbage_list.push_back(record->key); } else { reachable_keys.erase(record->key); } } } for (keys_t::iterator it = garbage_list.begin(); it != garbage_list.end(); ++it) { table.erase(*it); } } void enter(osl::ntesuki::NtesukiRecord *r) { reachable_keys.insert(r->key); } void exit() { } bool withChildMove(const osl::ntesuki::NtesukiMove& move, osl::ntesuki::NtesukiRecord *child) { return reachable_keys.find(child->key) == reachable_keys.end(); } void noChildMove(const osl::ntesuki::NtesukiMove& move) { } struct Compare { bool operator()(const osl::ntesuki::NtesukiMove& lhs, const osl::ntesuki::NtesukiMove& rhs) { return lhs.getMove() < rhs.getMove(); } }; }; void osl::ntesuki::NtesukiTable::Table:: collectGarbage(unsigned int gc_size) { if (gc_size == 0) { throw TableFull(); } if (largeGCCount >= 0 && gcCount >= static_cast(largeGCCount)) { if (verbose) { std::cerr << "\ntoo many GCs, failing\n\n"; //forEachRecordFromRoot();//DEBUG } throw TableFull(); } ++gcCount; #if 0 const unsigned int garbage_size = numEntry - gc_size; if (verbose) { std::cerr << "GC: "; for (int i = 0; i < 2; i++) { std::cerr << root->getValue(i) << "\t" << root->getValue(i) << "\t"; } std::cerr << " " << numEntry << " -> "; } std::priority_queue, CompareChildSize> garbage_list; for (iterator it = begin(); it != end(); ++it) { for (NtesukiRecord::RecordList::iterator p = it->second.begin(); p != it->second.end(); ++p) { NtesukiRecord *record = &(*p); if (record->isVisited() //|| record->isFinal() ) { record->addChildCount(garbage_size); continue; } garbage_list.push(record); if (garbage_list.size() > garbage_size) { garbage_list.pop(); } } } std::cerr << "\n*before GC\n";//DEBUG //forEachRecordFromRoot();//DEBUG forEachRecordFromRoot();//DEBUG while (!garbage_list.empty()) { NtesukiRecord *garbage = garbage_list.top(); erase(garbage->key); garbage_list.pop(); } if (verbose) { std::cerr << numEntry << "\n"; } std::cerr << "*after GC\n";//DEBUG forEachRecordFromRoot();//DEBUG //forEachRecordFromRoot();//DEBUG //throw TableFull();//DEBUG #else if (verbose) { std::cerr << "GC: "; for (int i = 0; i < 2; i++) { std::cerr << root->getValue(i) << "\t" << root->getValue(i) << "\t"; } std::cerr << "\n"; } //std::cerr << "\n*before GC\n";//DEBUG //forEachRecordFromRoot();//DEBUG //forEachRecordFromRoot();//DEBUG unsigned int orig_size = numEntry; unsigned int small_subtree_size = 1, garbage_size = 0; while (numEntry > gc_size) { for (iterator list_it = begin(); list_it != end(); ++list_it) { /* テーブルã«ç™»éŒ²ã•れ㟠record ã® list ã«ã¤ã„ã¦ï¼Œ * リストã®å„è¦ç´ ã® subtree ã®ã‚µã‚¤ã‚ºã‚’見ã¦ï¼Œå¿…è¦ãªã‚‰ collect ã™ã‚‹. * ã“ã“ã§ã® list ã¯æ‰€è¬‚ same board list. */ /* 対象ã¨ã™ã‚‹ record ãŒå‰Šé™¤ã•れãŸå ´åˆã«ã¯ï¼Œãã® record ã¸ã® iterator ã¯ç„¡åйã«ãªã‚‹ã®ã§ï¼Œ * 先頭ã‹ã‚‰èª¿ã¹ç›´ã™. */ retry_collect_list: for (NtesukiRecord::RecordList::iterator r = list_it->second.begin(); r != list_it->second.end(); ++r) { NtesukiRecord *record = &(*r); if (record->isVisited()) { continue; } if (record->getChildCount() < small_subtree_size && record->rev_refcount == 0) { ++garbage_size; --numEntry; for (NtesukiRecord::RecordPList::const_iterator pit = record->parents.begin(); pit != record->parents.end(); ++pit) { (*pit)->rev_refcount--; } list_it->second.erase(r); /* ã“ã®æ™‚点㧠r ã¯ç„¡åй */ goto retry_collect_list; } } } #ifdef MARK_AND_SWEEP_AFTER_SMALLTREEGC unsigned int before_mark_and_sweep = numEntry; forEachRecordFromRoot(); garbage_size += before_mark_and_sweep - numEntry; #endif //std::cerr << small_subtree_size << "\t" << garbage_size << "\t" << numEntry << "\n";//DEBUG small_subtree_size += 4; } small_subtree_size -= 4; for (iterator it = begin(); it != end(); ++it) { for (NtesukiRecord::RecordList::iterator p = it->second.begin(); p != it->second.end(); ++p) { NtesukiRecord *record = &(*p); if (record->isVisited()) { record->addChildCount(garbage_size); } } } if (verbose) { std::cerr << numEntry << "\tcollected up to " << small_subtree_size << "\n"; std::cerr << " " << orig_size << " -> " << numEntry << "\n"; } //std::cerr << "*after GC\n";//DEBUG //forEachRecordFromRoot();//DEBUG //forEachRecordFromRoot();//DEBUG //if (largeGCCount >= 0 && gc_count >= largeGCCount) throw TableFull();//DEBUG //throw TableFull();//DEBUG #endif } osl::ntesuki::NtesukiRecord * osl::ntesuki::NtesukiTable::Table:: find(const HashKey& key) { ntesuki_hash_map::iterator hit = ntesuki_hash_map::find(key.getSignatureKey()); if (hit == ntesuki_hash_map::end()) { return 0; } for (NtesukiRecord::RecordList::iterator p = hit->second.begin(); p != hit->second.end(); ++p) { if (p->key.getPieceStand() == key.getPieceStand()) { ++numCacheHit; return &(*p); } } return 0; } void osl::ntesuki::NtesukiTable::Table:: erase(const HashKey key) { ntesuki_hash_map::iterator hit = ntesuki_hash_map::find(key.getSignatureKey()); if (hit == ntesuki_hash_map::end()) { return; } for (NtesukiRecord::RecordList::iterator p = hit->second.begin(); p != hit->second.end(); ++p) { if (p->key.getPieceStand() == key.getPieceStand()) { hit->second.erase(p); --numEntry; return; } } } osl::ntesuki::NtesukiTable:: NtesukiTable(unsigned int capacity, unsigned int gc_size, bool verbose) : table(new Table(capacity, gc_size, verbose)), verbose(verbose), depths(200,0) {} osl::ntesuki::NtesukiTable:: ~NtesukiTable() { //forEachRecordFromRoot();//DEBUG if (verbose) { std::cerr << "~NtesukiTable size " << size() << ", cache hit " << table->numCacheHit << ", table full " << table->gcCount << "\n"; ntesuki_hash_map::const_iterator hit = this->begin(); while (hit != this->end()) { const NtesukiRecord::RecordList& record_list = hit->second; for (NtesukiRecord::RecordList::const_iterator p = record_list.begin(); p != record_list.end(); ++p) { const NtesukiRecord& r = *p; const unsigned short d = r.distance; if (d >= 200) { std::cerr << d << r << "\n"; } depths[d]++; } hit++; } for (int depth = 0; depth < 200; depth++) { if (depths[depth] != 0) { std::cerr << "depth: " << depth << " " << depths[depth] << "\n"; } } } } bool osl::ntesuki::NtesukiTable:: isVerbose() const { return verbose; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMove.cc0000644000000000000000000001466412316770314020520 0ustar rootroot/* ntesukiMove.cc */ #include "osl/ntesuki/ntesukiMove.h" #include "osl/ntesuki/ntesukiMove.tcc" #include /* Constructors and destructors */ osl::ntesuki::NtesukiMove:: NtesukiMove() : move(Move::INVALID()), flags(0), order(-1) {}; osl::ntesuki::NtesukiMove:: NtesukiMove(osl::Move m) : move(m), flags(0), order(-1), h_a_proof(1), h_a_disproof(1), h_d_proof(1), h_d_disproof(1) {}; osl::ntesuki::NtesukiMove:: NtesukiMove(osl::Move m, Flags f) : move(m), flags(f), order(-1), h_a_proof(1), h_a_disproof(1), h_d_proof(1), h_d_disproof(1) {}; osl::ntesuki::NtesukiMove:: NtesukiMove(const NtesukiMove& m) : move(m.move), flags(m.flags), order(m.order), h_a_proof(1), h_a_disproof(1), h_d_proof(1), h_d_disproof(1) {}; osl::ntesuki::NtesukiMove osl::ntesuki::NtesukiMove:: operator=(const NtesukiMove& m) { if (this == &m) return *this; move = m.move; flags = m.flags; order = m.order; h_a_proof = m.h_a_proof; h_a_disproof = m.h_a_disproof; h_d_proof = m.h_d_proof; h_d_disproof = m.h_d_disproof; return *this; }; osl::ntesuki::NtesukiMove:: ~NtesukiMove() { } /* static methods */ osl::ntesuki::NtesukiMove osl::ntesuki::NtesukiMove:: INVALID() { return NtesukiMove(Move::INVALID()); } /* about the state of the node */ void osl::ntesuki::NtesukiMove:: setCheck() { ntesuki_assert(!(flags & CHECK_FLAG)); flags |= CHECK_FLAG; }; bool osl::ntesuki::NtesukiMove:: isCheck() const { return flags & CHECK_FLAG; } void osl::ntesuki::NtesukiMove:: setOrder(int o) { ntesuki_assert(order == -1); order = o; }; int osl::ntesuki::NtesukiMove:: getOrder() const { //ntesuki_assert(order != -1); return order; } void osl::ntesuki::NtesukiMove:: setNoPromote() { ntesuki_assert(!(flags & NOPROMOTE)); flags |= NOPROMOTE; }; bool osl::ntesuki::NtesukiMove:: isNoPromote() const { return flags & NOPROMOTE; } void osl::ntesuki::NtesukiMove:: setInterpose() { ntesuki_assert(!(flags & INTERPOSE)); flags |= INTERPOSE; }; bool osl::ntesuki::NtesukiMove:: isInterpose() const { return flags & INTERPOSE; } void osl::ntesuki::NtesukiMove:: setLameLong() { ntesuki_assert(!(flags & LAME_LONG)); flags |= LAME_LONG; } bool osl::ntesuki::NtesukiMove:: isLameLong() const { return flags & LAME_LONG; } void osl::ntesuki::NtesukiMove:: setToOld() { flags |= TO_OLDER_CHILD; }; bool osl::ntesuki::NtesukiMove:: isToOld() const { return flags & TO_OLDER_CHILD; } /* setImmediateCheckmate is defiend in .tcc */ bool osl::ntesuki::NtesukiMove:: isImmediateCheckmate()const { return flags & IMMEDIATE_CHECKMATE; }; void osl::ntesuki::NtesukiMove:: setBySimulation() { flags |= BY_SIMULATION; }; bool osl::ntesuki::NtesukiMove:: isBySimulation() const { return flags & BY_SIMULATION; } /* Pawn drop checkmates */ void osl::ntesuki::NtesukiMove:: setPawnDropCheckmate() { flags |= PAWN_DROP_CHECKMATE_FLAG; }; bool osl::ntesuki::NtesukiMove:: isPawnDropCheckmate() const { return (flags & PAWN_DROP_CHECKMATE_FLAG) == PAWN_DROP_CHECKMATE_FLAG; } void osl::ntesuki::NtesukiMove:: setHEstimates(unsigned short p_a, unsigned short d_a, unsigned short p_d, unsigned short d_d) { h_a_proof = p_a; h_a_disproof = d_a; h_d_proof = p_d; h_d_disproof = d_d; } bool osl::ntesuki::NtesukiMove:: isCheckmateSuccessSlow(Player P, int pass_left) const { if (P == BLACK) return isCheckmateSuccess(pass_left); else return isCheckmateSuccess(pass_left); } bool osl::ntesuki::NtesukiMove:: isCheckmateFailSlow(Player P, int pass_left) const { if (P == BLACK) return isCheckmateFail(pass_left); else return isCheckmateFail(pass_left); } /* about the move */ bool osl::ntesuki::NtesukiMove:: isValid() const { return move.isValid(); } bool osl::ntesuki::NtesukiMove:: isInvalid() const { return move.isInvalid(); } bool osl::ntesuki::NtesukiMove:: isNormal() const { return move.isNormal(); } bool osl::ntesuki::NtesukiMove:: isPass() const { return move.isPass(); } bool osl::ntesuki::NtesukiMove:: isDrop() const { return move.isDrop(); } osl::Square osl::ntesuki::NtesukiMove:: to() const { return move.to(); } osl::Ptype osl::ntesuki::NtesukiMove:: ptype() const { return move.ptype(); } osl::Move osl::ntesuki::NtesukiMove:: getMove() const { return move; } /* for moves */ bool osl::ntesuki::NtesukiMove:: operator==(const NtesukiMove& rhs) const { return move == rhs.move; }; bool osl::ntesuki::NtesukiMove:: operator!=(const NtesukiMove& rhs) const { return move != rhs.move; }; /* output to stream */ void osl::ntesuki::NtesukiMove:: flagsToStream(std::ostream& os) const { int tmp = flags; for (int i = 0; i < 32; ++i) { if (1 == (tmp % 2)) os << " " << NtesukiMove::FlagsStr[i]; tmp = tmp >> 1; } } std::ostream& osl::ntesuki:: operator<<(std::ostream& os, const osl::ntesuki::NtesukiMove& move) { os << "(" << move.getMove(); os << "o=" << move.getOrder() << " "; move.flagsToStream(os); return os << ")"; } namespace osl { namespace ntesuki { template void NtesukiMove::setCheckmateSuccess(int pass_left); template void NtesukiMove::setCheckmateSuccess(int pass_left); template void NtesukiMove::setCheckmateFail(int pass_left); template void NtesukiMove::setCheckmateFail(int pass_left); template void NtesukiMove::setImmediateCheckmate(); template void NtesukiMove::setImmediateCheckmate(); } } std::string osl::ntesuki::NtesukiMove::FlagsStr[] = { /* 2^0 CHECK_FLAG*/ "CHECK", /* 2^1 PAWN_DROP_CHECKMATE_FLAG = 2 */ "PAWN_CHECKMATE", /* 2^2 */ "(BUG)", /* 2^3 IMMEDIATE_CHECKMATE */ "IMMEDIATE", /* 2^4 TO_OLDER_CHILD */ "OLD_CHILD", /* 2^5 NOPROMOTE */ "NOPROMOTE", /* 2^6 INTERPOSE */ "INTERPOSE", /* 2^7 */ "ATTACK", /* 2^8 */ "BY_SIMULATION", /* 2^9 */ "LAME_LONG", /* 2^10 */ "(BUG)", /* 2^11 */ "(BUG)", /* 2^12 */ "(BUG)", /* 2^13 */ "(BUG)", /* 2^14 */ "(BUG)", /* 2^15 */ "(BUG)", /* 16-19 BLACK SUCCESS */ "BLACK_SUCC_1", "BLACK_SUCC_2", "BLACK_SUCC_3", "BLACK_SUCC_4", /* 20-23 WHITE SUCCESS */ "WHITE_SUCC_1", "WHITE_SUCC_2", "WHITE_SUCC_3", "WHITE_SUCC_4", /* 24-27 BLACK FAIL */ "BLACK_FAIL_1", "BLACK_FAIL_2", "BLACK_FAIL_3", "BLACK_FAIL_4", /* 28-31 WHITE FAIL */ "WHITE_FAIL_1", "WHITE_FAIL_2", "WHITE_FAIL_3", "WHITE_FAIL_4", }; libosl-0.8.0.orig/full/osl/ntesuki/ntesukiResult.cc0000644000000000000000000000100512316770314021051 0ustar rootroot#include "osl/ntesuki/ntesukiResult.h" #include std::ostream& osl::ntesuki::operator<<(std::ostream& os, osl::ntesuki::NtesukiResult nr) { if (osl::ntesuki::NTESUKI_YES == nr) { return os << "NTESUKI_YES"; } else if (osl::ntesuki::NTESUKI_NO == nr) { return os << "NTESUKI_NO"; } assert (osl::ntesuki::isUnknown(nr)); return os << "NTESUKI_UNKNOWN(" << osl::ntesuki::getDepth(nr) << ")"; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/ntesuki/ntesukiMoveGenerator.h0000644000000000000000000000323712316770314022223 0ustar rootroot/* ntesukiMoveGenerator.h */ #ifndef _NTEUSKI_MOVE_GENERATOR_H #define _NTEUSKI_MOVE_GENERATOR_H #include "osl/ntesuki/ntesukiMoveList.h" #include "osl/state/numEffectState.h" namespace osl { namespace ntesuki { class NtesukiRecord; /** * ntesuki ã§ä½¿ã† move generator ã® base class. * - 基本的ã«ã¯å…¨ã¦ã®æ‰‹ã‚’生æˆ. * - 王手㯠CHECKMATE_FLAG ã‚’ãŸã¦ã‚‹. * - 攻撃ã«é–¢ä¿‚ã—ãã†ãªæ‰‹ã¯ ATTACK_FLAG ã‚’ãŸã¦ã‚‹. */ struct NtesukiMoveGenerator { bool verbose; NtesukiMoveGenerator(bool verbose = false); ~NtesukiMoveGenerator(); template void generate(const NumEffectState& state, NtesukiMoveList& moves); void generateSlow(const Player T, const NumEffectState& state, NtesukiMoveList& moves) { if (T == BLACK) generate(state, moves); else generate(state, moves); } template void generateWithRzone(const NumEffectState& state, NtesukiRecord *record, int pass_left, NtesukiMoveList& moves); void generateWithRzoneSlow(const Player T, const NumEffectState& state, NtesukiRecord *record, int pass_left, NtesukiMoveList& moves) { if (T == BLACK) generateWithRzone(state, record, pass_left, moves); else generateWithRzone(state, record, pass_left, moves); } private: template void setOrder(const NumEffectState& state, NtesukiMoveList& moves); }; } //ntesuki } //osl #endif /* _NTEUSKI_MOVE_GENERATOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/0000755000000000000000000000000012316770314017217 5ustar rootrootlibosl-0.8.0.orig/full/osl/move_generator/additionalLance.cc0000644000000000000000000000232612316770314022604 0ustar rootroot/* additionalLance.cc */ #include "osl/move_generator/additionalLance.h" template void osl::move_generator::AdditionalLance

:: generate(const NumEffectState& state, Square pawn, MoveVector& out) { assert((state.hasPieceOnStand(P))); assert(state.pieceOnBoard(pawn).ptype() == PAWN); Square back_position = pawn + DirectionPlayerTraits::offset(); Piece target = state.pieceAt(back_position); while (target.isEmpty()) { if (state.hasEffectAt(back_position)) break; out.push_back(Move(back_position, LANCE, P)); back_position = back_position + DirectionPlayerTraits::offset(); target = state.pieceAt(back_position); } } template void osl::move_generator::AdditionalLance

:: generateIfHasLance(const NumEffectState& state, Square pawn, MoveVector& out) { if (state.hasPieceOnStand(P)) generate(state, pawn, out); } namespace osl { namespace move_generator { template struct AdditionalLance; template struct AdditionalLance; } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/attackToPinned.h0000644000000000000000000000244612316770314022306 0ustar rootroot#ifndef OSL_MOVE_GENERATOR_ATTACK_TO_PINNED_H #define OSL_MOVE_GENERATOR_ATTACK_TO_PINNED_H #include "osl/numEffectState.h" #include "osl/move_generator/move_action.h" namespace osl { namespace move_generator { /** * 敵ã®pinã•れã¦ã„ã‚‹é§’ã‚’æ”»ã‚ã‚‹. * pinã®é•·ã„利ãを付ã‘ã¦ã„ã‚‹é§’ã§æ”»ã‚ã‚‹å¯èƒ½æ€§ã‚‚ã‚ã‚‹ãŒç¨€ * pinã—ã¦ã„ã‚‹æ–¹å‘ã‹ã‚‰ã¯æ”»ã‚ã¦ã—ã¾ã†ã“ã¨ã‚‚ã‚る. * æ­©ã‚‚æ”»ã‚る. * 利ãã®æ•°ãŒå‹ã£ã¦ã„ã‚‹ã‹ã©ã†ã‹ã¯ã¨ã‚Šã‚ãˆãšã¯å•ã‚ãªã„. * P - 攻撃å´ã®ãƒ—レイヤ */ template class AttackToPinned { public: /** * 手を生æˆã™ã‚‹ï¼Ž * @param state - ç›¤é¢ * @param action - ç”Ÿæˆæ™‚ã®call back */ template static void generate(const NumEffectState& state,Action& action); static void generate(const NumEffectState& state,MoveVector& out) { move_action::Store store(out); generate(state, store); } }; struct GenerateAttackToPinned { static void generate(Player player,const NumEffectState& state, move_action::Store& store); }; } } #endif /* OSL_MOVE_GENERATOR_ATTACK_TO_PINNED_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/addEffect8.h0000644000000000000000000000724012316770314021330 0ustar rootroot#ifndef OSL_MOVE_GENERATOR_ADD_EFFECT8_H #define OSL_MOVE_GENERATOR_ADD_EFFECT8_H #include "osl/numEffectState.h" #include "osl/move_generator/move_action.h" namespace osl { namespace move_generator { /** * 敵ã®8è¿‘å‚ã«åˆ©ãを付ã‘る. * çŽ‹æ‰‹ã®æ‰‹ã¯é‡è¤‡ã‚’é¿ã‘ã‚‹ãŸã‚ã«ï¼Œãªã‚‹ã¹ã生æˆã—ãªã„ * (æ„図ã›ãšã«çŽ‹æ‰‹ã«ãªã‚‹ã®ã¯ä»•æ–¹ãŒãªã„) * promote, captureã¯ç”Ÿæˆã—ãªã„. * @param P(template) - 手番ã®å´ã®ãƒ—レイヤー */ template class AddEffect8 { public: /** * 敵ã®8è¿‘å‚ã«åˆ©ãを付ã‘る手ã®ç”Ÿæˆï¼Ž * 欲ã—ã„仕様ã¯8è¿‘å‚ã®ã©ã“ã‹ã«ã“れã¾ã§åˆ©ãã®ãªã‹ã£ãŸé§’ã®åˆ©ããŒè¿½åŠ ã•れるã“ã¨ï¼Ž * \li 全体ã¨ã—ã¦ãã®ãƒžã‚¹ã¸ã®åˆ©ããŒæ¸›ã£ã¦ã‚‚å¯ï¼Ž * (例) * * * * * * +GI * -OU * +GI ->-OU * * * * * * * * * * 21,23ã®åˆ©ãã¯æ¸›ã£ã¦ã„ã‚‹ãŒ22ã®åˆ©ããŒç™ºç”Ÿã—ã¦ã„ã‚‹ * \li 王手ã¯é™¤å¤–ã™ã‚‹ï¼Ž * \li 王ã«ã‚ˆã£ã¦8è¿‘å‚ã«åˆ©ãã‚’ã¤ã‘る手も除外ã™ã‚‹ï¼Ž * \li 自殺手ã¯ç”Ÿæˆã—ã¦ã—ã¾ã£ã¦ã‚‚よã„. * \li 盤外ã«åˆ©ãを付ã‘ã¦ã—ã¾ã†ã“ã¨ã‚‚ã‚る. * 追加利ãã§å¯¾å¿œã—ãªã„例 * +RY * * * +RY+NG * * * * +GI * -OU -> * * * -OU * * * * * * * * * * open attackã¯åŒã˜æ‰‹ã‚’2回生æˆã—ã¦ã—ã¾ã†ã“ã¨ãŒã‚る. * effectUtilを使ãˆã°OK -> 未 * open attackã¯çŽ‹æ‰‹ã‚’ç”Ÿæˆã—ã¦ã—ã¾ã†ã“ã¨ãŒã‚る. * TODO: pawn,rook,bishopãŒæˆã‚Œã‚‹ã¨ãã¯å¸¸ã«æˆã‚‹ -> DONE * (openã«ã‚ˆã‚‹attackã®æ™‚ã¯æˆã‚‰ãªã„ã“ã¨ã‚‚ã‚ã‚‹ -> å›°ã£ãŸ) * 2段目ã®é¦™è»Šã¯å¿…ãšæˆã‚‹ -> DONE * é£›è»Šè§’ã¯æ•µã®åˆ©ãã®ã‚ã‚‹ã¨ã“ã‚ã«ã¯ç§»å‹•ã—ãªã„ * 飛車角ã®drop以外ã¨é£›è»Šè§’ã®drop * 飛車角ã®dropã¯å…¨éƒ¨ä½œã‚‰ãªã„ * - 敵ã®åˆ©ãã®ãªã„一番近ã„ã¨ã“ã‚ã¨äºŒç•ªç›®ã«è¿‘ã„ã¨ã“ã‚ã®ã¿ä½œã‚‹ -> DONE * -> 本当ã¯è‡ªåˆ†ã®longã‚’ãµã•ãŒãªã„ã‚‚ã®ãŒæ¬²ã—ã„ -> 未 * 追加利ãã‚‚ã¤ã‘ã‚‹ * æ­©ã®å‰ã«ã¯æ­©ä»¥å¤–ã¯?? -> 未 * 利ãã®æ•°ãŒ(敵玉もå«ã‚ã¦)evenä»¥ä¸Šã®æ™‚ -> 未 * @param state - 対象ã¨ã™ã‚‹å±€é¢ * @param action - 手ãŒå­˜åœ¨ã—ãŸæ™‚ã«å‘¼ã³å‡ºã™ã‚³ãƒ¼ãƒ«ãƒãƒƒã‚¯é–¢æ•° */ template static void generate(const NumEffectState& state,Action& action); static void generate(const NumEffectState& state, MoveVector& out) { move_action::Store store(out); generate(state, store); } /** * 大駒ã®drop以外 */ template static void generateNotBigDrop(const NumEffectState& state,Action& action); /** * 大駒ã®drop */ template static void generateBigDrop(const NumEffectState& state,Action& action); }; struct GenerateAddEffect8 { /** * 対象ã¨ã™ã‚‹ãƒžã‚¹ã«åˆ©ãを付ã‘る手を生æˆã™ã‚‹. * Note: Action ãŒPlayerã§åž‹ä»˜ã‘ã•れã¦ã„ã‚‹ã¨ï¼Œç„¡é§„ãŒã‚ã‚‹ã®ã§Storeé™å®šã« */ static void generate(Player player, const NumEffectState& state, move_action::Store& store); static void generateBigDrop(Player player, const NumEffectState& state, move_action::Store& store); static void generateNotBigDrop(Player player, const NumEffectState& state, move_action::Store& store); }; } } #endif /* OSL_MOVE_GENERATOR_ADD_EFFECT8_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/attackToPinned.tcc0000644000000000000000000000300512316770314022620 0ustar rootroot#ifndef _MOVE_GENERATOR_ATTACK_TO_PINNED_TCC #define _MOVE_GENERATOR_ATTACK_TO_PINNED_TCC #include "osl/move_generator/attackToPinned.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/bits/ptypeTable.h" namespace osl { namespace move_generator { namespace { template void generatePtype(const NumEffectState& state,Action& action) { Square target=state.template kingSquare(); for(int num=PtypeTraits::indexMin;num::indexLimit;num++){ Piece p=state.pieceOf(num); if(p.template isOnBoardByOwner

()){ Square from=p.square(); EffectContent effect=Ptype_Table.getEffect(newPtypeO(P,T),from,target); if(effect.hasEffect()){ Offset offset=effect.offset(); assert(!offset.zero()); Piece p1; Square pos=target-offset; for(;(p1=state.pieceAt(pos)).isEmpty();pos-=offset) ; if(p1.canMoveOn

() && state.hasEffectByPiece(p,pos)){ AddEffectWithEffect::template generate(state,pos,action); } } } } } } template template void AttackToPinned

:: generate(const NumEffectState& state,Action& action) { generatePtype(state,action); generatePtype(state,action); generatePtype(state,action); } } } #endif /* _MOVE_GENERATOR_ATTACK_TO_PINNED_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/addEffect8Table.h0000644000000000000000000001205012316770314022273 0ustar rootroot#ifndef _ADD_EFFECT8_TABLE_H #define _ADD_EFFECT8_TABLE_H #include "osl/numEffectState.h" #include namespace osl { namespace move_generator { namespace addeffect8 { /** * 利ãã‚’ã¤ã‘る手を生æˆã™ã‚‹ãŸã‚ã®ãƒ†ãƒ¼ãƒ–ル. * */ typedef std::pair OffsetPair; typedef std::pair PO; typedef std::pair POO; class AddEffect8Table { static const int maxDropSquare=32; CArray3d dropSquare; static const int maxLongDropDirect=8; CArray3d longDropDirect; static const int maxLongDropSquare=32; CArray3d longDropSquare; static const int maxLongDrop2Square=8; CArray3d longDrop2Square; static const int maxShortMoveOffset=32; CArray3d shortMoveOffset; static const int maxShortPromoteMoveOffset=32; CArray3d shortPromoteMoveOffset; static const int maxLongMoveOffset=32; CArray3d longMoveOffset; CArray2d betweenOffset; public: void init(); /** * ptypeã®é§’を打ã£ã¦æ•µã®çމã®8è¿‘å‚ã«çŸ­ã„利ããŒã¤ã地点ã®ç›¸å¯¾ä½ç½®. * é•·ã„利ãã‚’8è¿‘å‚内ã«ã¤ã‘ã‚‹ã®ã‚‚å¯ * é»’ã‹ã‚‰è¦‹ã¦kingSquare+offsetã«é§’を打ã¤ã¨è‰¯ã„ * 手番ã‹ã‚‰è¦‹ãŸç›¸æ‰‹ã®çމã®Square */ Square getDropSquare(Ptype ptype,Square kingSquare,int i) const { // std::cerr << "getDropOffset(" << ptype << "," << i << ")" << std::endl; return dropSquare[ptype][kingSquare.index()][i]; } /** * ptypeã®é§’を打ã£ã¦æ•µã®çމã®8è¿‘å‚ã«é•·ã„利ãã‚’ã¤ã‘ã‚‹. * é–“ã«é§’ãŒãªã‘れã°ï¼ŒçŽ‹æ‰‹ã«ãªã‚‹ã‚¿ã‚¤ãƒ— */ Offset getLongDropDirect(Ptype ptype,Square kingSquare,int i) const { return longDropDirect[ptype][kingSquare.index()][i]; } /** * ptypeã®é§’を打ã£ã¦æ•µã®çމã®8è¿‘å‚ã«é•·ã„利ãã‚’ã¤ã‘ã‚‹. * 1æ–¹å‘ * é»’ã‹ã‚‰è¦‹ã¦kingSquare+firstã«æ‰“ã¤æ‰‹ã‹ã‚‰å§‹ã‚ã¦ï¼Œ+secondã—ã¦ã„ã£ã¦ã‚‚ * emptyãªã‚‰OK */ PO getLongDropSquare(Ptype ptype,Square kingSquare,int i) const { return longDropSquare[ptype][kingSquare.index()][i]; } /** * ptypeã®é§’を打ã£ã¦æ•µã®çމã®8è¿‘å‚ã«é•·ã„利ãã‚’ã¤ã‘ã‚‹. * 1æ–¹å‘ * é»’ã‹ã‚‰è¦‹ã¦kingSquare+firstã«æ‰“ã¤æ‰‹ã‹ã‚‰å§‹ã‚ã¦ï¼Œ+secondã—ã¦ã„ã£ã¦ã‚‚ * emptyãªã‚‰OK */ POO getLongDrop2Square(Ptype ptype,Square kingSquare,int i) const { return longDrop2Square[ptype][kingSquare.index()][i]; } /** * ptypeã®é§’ã‚’å‹•ã‹ã—ã¦(é•·ã„å‹•ãã‚‚å¯ * )敵ã®çމã®8è¿‘å‚ã«çŸ­ã„利ããŒã¤ã地点ã®ç›¸å¯¾ä½ç½®. * é»’ã‹ã‚‰è¦‹ã¦kingSquare+offsetã«é§’を移動ã™ã‚‹ã¨è‰¯ã„ * @param isPromote - promoteã™ã‚‹ã‹ã—ãªã„ã‹ * @param ptype - 移動å‰ã®é§’ã®ç¨®é¡ž * @param o32 - targetã‹ã‚‰ã¿ãŸfromã®ç›¸å¯¾ä½ç½® = Offset32(from,target) * @param i - 何番目㋠*/ Offset getShortMoveOffset(bool isPromote,Ptype ptype,Offset32 o32,int i) const { if(!isPromote){ assert(i struct SafeDropMajorPiece { template static void generate(const NumEffectState& state, Action& action) { const bool has_bishop = state.template hasPieceOnStand(P); const bool has_rook = state.template hasPieceOnStand(P); if (!has_rook && !has_bishop) return; int start_y; if (P == BLACK) start_y = 1; else start_y = 7; for (int x = 1; x <= 9; x++) { for (int y = start_y; y < start_y + 3; y++) { Square position(x, y); if (state.pieceOnBoard(position).isEmpty() && !state.hasEffectAt(alt(P), position)) { if (has_rook) { action.dropMove(position, ROOK, P); } if (has_bishop) { action.dropMove(position, BISHOP, P); } } } } } template static void generateMoves(const NumEffectState& state, FixedCapacityVector& out) { move_action::Store store(out); generate(state, store); } }; } } // namespace osl #endif /* _GENERATE_SAFE_DROP_MAJOR_PIECE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/attackToPinned.cc0000644000000000000000000000124612316770314022441 0ustar rootroot#include "osl/move_generator/attackToPinned.h" #include "osl/move_generator/attackToPinned.tcc" template void osl::move_generator::AttackToPinned::generate(const NumEffectState&, move_action::Store&); template void osl::move_generator::AttackToPinned::generate(const NumEffectState&, move_action::Store&); void osl::move_generator::GenerateAttackToPinned:: generate(Player player, const NumEffectState& state, move_action::Store& store){ assert(state.turn()==player); if(player==BLACK) AttackToPinned::generate(state,store); else AttackToPinned::generate(state,store); } libosl-0.8.0.orig/full/osl/move_generator/addEffect8.tcc0000644000000000000000000004212612316770314021654 0ustar rootroot#ifndef _MOVE_GENERATOR_ADD_EFFECT8_TCC #define _MOVE_GENERATOR_ADD_EFFECT8_TCC #include "osl/move_generator/addEffect8.h" #include "osl/move_generator/pieceOnBoard.h" #include "osl/move_generator/addEffect8Table.h" namespace osl { namespace move_generator { namespace addeffect8{ /** * 5x5領域ã¸ã®é§’ã®dropã«ã‚ˆã‚‹æ‰‹ç”Ÿæˆ. * BISHOPã‚„ROOKã¯æ•µã®åˆ©ãã®ãªã„å ´åˆã®ã¿ç”Ÿæˆ * -> pinned以外ã®åˆ©ãã«å¤‰æ›´(2009/12/24) * @param P(template) - 手番ã®ãƒ—レイヤー * @param T(template) - ç½®ã“ã†ã¨ã™ã‚‹é§’ã®ç¨®é¡ž(当然basic) * @param state - ç›¤é¢ * @param target - 相手ã®çމã®position(redundantã ãŒ) * @param action - 手生æˆã®callback */ template void generateShortDrop(NumEffectState const& state,Square target,Action& action) { Square targetForP=target.squareForBlack(P); for(int i=0;;i++){ Square pos=Add_Effect8_Table.getDropSquare(T,targetForP,i); if(pos.isPieceStand()) break; pos=pos.squareForBlack

(); if(state.pieceAt(pos).isEmpty() && (T!=PAWN || !state.isPawnMaskSet

(pos.x()))){ if((T==BISHOP || T==ROOK) && state.hasEffectByNotPinnedAndKing(alt(P),pos)) continue; action.dropMove(pos,T,P); } } } /** * æ–¹å‘を決ã‚ã¦ï¼Œlong dropを作æˆã™ã‚‹ï¼Ž * @param P(template) - 手番ã®ãƒ—レイヤー * @param T(template) - ç½®ã“ã†ã¨ã™ã‚‹é§’ã®ç¨®é¡ž(当然basic) * @param state - ç›¤é¢ * @param to - 利ãを追加ã™ã‚‹ç‚¹ * @param from - ç½®ãå§‹ã‚る点 * @param offset - 次ã«ç½®ã点ã¸ã®offset * @param action - 手生æˆã®callback */ template void generateLongDropWithOffset(NumEffectState const& state,Square to,Square from, Offset offset,int countMax,Action& action){ const Player altP=alt(P); int count=0; for(;;){ Piece p; for(;(p=state.pieceAt(from)).isEmpty();from+=offset){ if(T==LANCE) action.dropMove(from,T,P); else if(!state.hasEffectAt(from)){ action.dropMove(from,T,P); if(++count>=countMax) return; } } if(!p.isOnBoardByOwner

()) return; if(!Ptype_Table.getEffect(p.ptypeO(),from,to).hasEffect()) return; from+=offset; } } /** * é•·ã„利ãã‚’æŒã¤é§’ã®dropã«ã‚ˆã‚‹æ‰‹ç”Ÿæˆ. * 追加利ãも生æˆã™ã‚‹. * @param P(template) - 手番ã®ãƒ—レイヤー * @param T(template) - ç½®ã“ã†ã¨ã™ã‚‹é§’ã®ç¨®é¡ž(当然basic) * @param state - ç›¤é¢ * @param target - 相手ã®çމã®position(redundantã ãŒ) * @param action - 手生æˆã®callback */ template void generateLongDrop(NumEffectState const& state,Square target,Action& action) { static_assert(T==ROOK || T==BISHOP || T==LANCE, ""); // 8è¿‘å‚以内ã¸ã®dropã¯short扱ã„ã§ä½œã‚‹ï¼Ž generateShortDrop(state,target,action); Square targetForP=target.squareForBlack(P); // 8è¿‘å‚ã«é§’ãŒã‚る時(王手ã«ãªã‚‰ãªã„)ã«ç›´æŽ¥æ–¹å‘ã®åˆ©ã for(int i=0;;i++){ Offset offset=Add_Effect8_Table.getLongDropDirect(T,targetForP,i); if(offset.zero()) break; offset=offset.blackOffset

(); Square pos=target+offset; assert(pos.isOnBoard()); Square from=pos+offset; if(state.pieceAt(pos).isEmpty()){ Piece p=state.pieceAt(from); // 一ã¤ç½®ã„ã¦çŸ­ã„利ãã®æ™‚ã®ã¿OK if(!p.isOnBoardByOwner

() || !state.hasEffectByPiece(p,pos)) continue; from+=offset; } generateLongDropWithOffset(state,pos,from,offset,2,action); } for(int i=0;;i++){ PO po=Add_Effect8_Table.getLongDropSquare(T,targetForP,i); if(po.first.isPieceStand()) break; Square pos=po.first.squareForBlack

(); Offset offset=po.second.blackOffset

(); assert(!offset.zero()); generateLongDropWithOffset(state,pos-offset,pos,offset,2,action); } if(T==BISHOP){ for(int i=0;;i++){ POO poo=Add_Effect8_Table.getLongDrop2Square(T,targetForP,i); if(poo.first.isPieceStand()) break; Square pos=poo.first.squareForBlack

(); Offset offset1=poo.second.first.blackOffset

(); assert(!offset1.zero()); Offset offset2=poo.second.second.blackOffset

(); assert(!offset2.zero()); Piece p=state.pieceAt(pos); if(p.isEmpty()){ generateLongDropWithOffset(state,pos-offset1, pos,offset1,2,action); generateLongDropWithOffset(state,pos-offset2, pos+offset2,offset2,1, action); } else if(p.isOnBoardByOwner

()){ if(state.hasEffectByPiece(p,pos-offset1)){ generateLongDropWithOffset(state,pos-offset1, pos+offset1,offset1, 2,action); } if(state.hasEffectByPiece(p,pos-offset2)){ generateLongDropWithOffset(state,pos-offset2, pos+offset2,offset2, 2,action); } } } } } /** * unblockableãªå‹•ãã§unblockableãªåˆ©ãã‚’ã¤ã‘る手生æˆ. * @param P(template) - 攻撃å´ã®ãƒ—レイヤー * @param T(template) - 攻撃å´ã®é§’ã®ç¨®é¡ž * @param state - å±€é¢ * @param from - 攻撃ã—よã†ã¨ã™ã‚‹é§’ã®ä½ç½® * @param target - 攻撃ã—よã†ã¨ã™ã‚‹ãƒžã‚¹ */ template void generateShortMove(NumEffectState const& state,Piece attacker, Square target, Action& action) { Square from=attacker.square(); Offset32 o32=Offset32(from,target).blackOffset32

(); for(int i=0;;i++){ Offset o=Add_Effect8_Table.getShortMoveOffset(false,T,o32,i); if(o.zero()) break; Square pos=target+o.blackOffset

(); if((T!=KNIGHT && pos.isEdge()) || (T==KNIGHT && !pos.isOnBoard())) continue; if((T==PAWN ? pos.canPromote

() : (PtypeTraits::isBasic && !Ptype_Table.canDropTo(P,T,pos) // !PtypePlayerTraits::canDropTo(pos) ))) continue; Piece p=state.pieceAt(pos); if(p.isEmpty()){ if(!state.pinOrOpen(P).test(attacker.number()) || state.pinnedCanMoveTo

(attacker,pos)) action.simpleMove(from,pos,T,false,P); } } } /** * fromã«ãƒ—レイヤーPã®é§’ãŒã‚る. * toã¯çމã®8è¿‘å‚ã§PãŒfromã‹ã‚‰é•·ã„利ãã‚’æŒã¡ã†ã‚‹ãƒžã‚¹ã ã¨ã™ã‚‹ï¼Ž * 味方ã®é§’ã§8è¿‘å‚ã¸ã®åˆ©ãã‚’blockã—ã¦ã„ã‚‹é§’(å‘³æ–¹ã‹æ•µã‹ã‚’å•ã‚ãš)ãŒã‚ã‚‹ã‹ã©ã†ã‹ã‚’ãƒã‚§ãƒƒã‚¯ã—, * ã‚ã‚‹ãªã‚‰blockerã«å…¥ã‚Œã¦trueを返㙠*/ template bool findBlocker(NumEffectState const& state,Piece attacker, Square target, Square from,Square& pos,Piece& blocker, Offset offset) { if(state.hasEffectByPiece(attacker,pos)){ blocker=state.pieceAt(pos); if(!blocker.isEmpty()) return blocker.isOnBoardByOwner

(); pos-=offset; if(abs(pos.x()-target.x())>1 || abs(pos.y()-target.y())>1) return false; blocker=state.pieceAt(pos); return blocker.isOnBoardByOwner

(); } else{ // TODO effectedNumTableを使ãˆã‚‹? for(Square pos1=from+offset;pos1!=pos;pos1+=offset){ Piece p=state.pieceAt(pos1); if(!p.isEmpty()){ if(!p.isOnBoardByOwner

()) return false; if(!Ptype_Table.getEffect(p.ptypeO(),pos1,pos).hasEffect()){ blocker=p; for(pos1+=offset;pos1!=pos;pos1+=offset){ p=state.pieceAt(pos1); if(!p.isEmpty()){ if(!p.isOnBoardByOwner

() || !Ptype_Table.getEffect(p.ptypeO(),pos1,pos).hasEffect()) return false; } } pos=blocker.square(); return true; } if(pos1==pos-offset && (pos+offset).isOnBoard() && !Ptype_Table.getEffect(p.ptypeO(),pos1,pos+offset).hasEffect()){ blocker=p; pos=blocker.square(); return true; } return false; } } return false; } } /** * fromã«ãƒ—レイヤーPã®ç¨®é¡žTã®é§’ãŒã‚ã£ãŸã‚‰åˆ©ããŒã‚る盤é¢ã‹ã©ã†ã‹. * 追加もå«ã‚ã‚‹. * é–“ãŒå…¨éƒ¨ç©ºç™½ãªã‚‰åˆ©ããŒã‚ã‚‹ã®ãŒå‰æï¼Ž * @param P(template) - 利ãã‚’ã¤ã‘るプレイヤー * @param T - é§’ã®ç¨®é¡ž(ROOK, BISHOP, LANCEã®ã„ãšã‚Œã‹) * @param state - 盤é¢ã®çŠ¶æ…‹ * @param from - é§’ãŒã‚ã‚‹ã¨ä»®å®šã™ã‚‹ãƒžã‚¹ * @param to - 利ãã®æœ‰ç„¡ã‚’判定ã—ãŸã„マス * @param blocker - 利ããŒãªã„時ã«ãƒ–ロックã—ã¦ã„る駒を返㙠* @param offset - toã‹ã‚‰fromã¸ã®offset(redundant) */ template bool canAddLongEffect(NumEffectState const& state,Square from,Square to,Piece& blocker,Offset offset) { for(Square pos=to+offset;pos!=from;pos+=offset){ Piece p=state.pieceAt(pos); if(!p.isEmpty()){ if(!p.isOnBoardByOwner

() || !Ptype_Table.getEffect(p.ptypeO(),pos,to).hasEffect()){ blocker=p; assert(!blocker.isEdge()); return false; } } } return true; } /** * fromã«ãƒ—レイヤーPã®ç¨®é¡žTã®é§’ãŒã‚ã£ãŸã‚‰åˆ©ããŒã‚る盤é¢ã‹ã©ã†ã‹. * 追加もå«ã‚ã‚‹. * é–“ãŒå…¨éƒ¨ç©ºç™½ãªã‚‰åˆ©ããŒã‚ã‚‹ã®ãŒå‰æï¼Ž * @param P(template) - 利ãã‚’ã¤ã‘るプレイヤー * @param T - é§’ã®ç¨®é¡ž(ROOK, BISHOP, LANCEã®ã„ãšã‚Œã‹) * @param state - 盤é¢ã®çŠ¶æ…‹ * @param from - é§’ãŒã‚ã‚‹ã¨ä»®å®šã™ã‚‹ãƒžã‚¹ * @param to - 利ãã®æœ‰ç„¡ã‚’判定ã—ãŸã„マス * @param blocker - 利ããŒãªã„時ã«ãƒ–ロックã—ã¦ã„る駒を返㙠*/ template bool canAddLongEffect(NumEffectState const& state,Square from,Square to,Piece& blocker) { Offset offset=Board_Table.getShortOffset(Offset32(from,to)); return canAddLongEffect(state,from,to,blocker,offset); } /** * é•·ã„利ãã‚‚æŒã¤é§’ã®æ‰‹ç”Ÿæˆ. * @param P(template) - 攻撃å´ã®ãƒ—レイヤー * @param T(template) - 攻撃å´ã®é§’ã®ç¨®é¡ž * @param isPromotion(template) - æˆã£ã¦ã®æ”»æ’ƒ(æˆã‚Œã‚‹ã‹ã¯å†…部ã§ãƒã‚§ãƒƒã‚¯) * @param state - å±€é¢ * @param attacker - 攻撃ã—よã†ã¨ã™ã‚‹é§’ * @param from - 攻撃ã—よã†ã¨ã™ã‚‹é§’ã®ä½ç½® * @param target - 攻撃ã—よã†ã¨ã™ã‚‹ãƒžã‚¹ */ template void generateLongMove(NumEffectState const& state,Piece attacker, Square target, Action& action) { Square from=attacker.square(); // 飛車,角ã¯promoteã§ãる時ã¯promoteã™ã‚‹æ‰‹ã‚’ç”Ÿæˆæ¸ˆã¿ if((T==ROOK || T==BISHOP) && from.canPromote

()) return; Offset32 o32=Offset32(from,target).blackOffset32

(); // é–“ã®å‘³æ–¹ã®é§’ã®open OffsetPair op=Add_Effect8_Table.getBetweenOffset(T,o32); if(!op.first.zero()){ Square pos=target+op.first.blackOffset

(); Offset offset=op.second.blackOffset

(); if(pos.isOnBoard()){ Piece blocker=Piece::EMPTY(); if(findBlocker

(state,attacker,target,from,pos,blocker,offset)){ Direction d=longToShort(Board_Table.getLongDirection(Offset32(pos,from).blackOffset32

())); // std::cerr << "blocker=" << blocker << ",d=" << d << std::endl; PieceOnBoard::template generate( state,blocker,action,1<(); if(!pos.isOnBoard()) continue; if ((!canPromote(T) || !pos.canPromote

()) && state.hasEffectByPiece(attacker,pos) && state.pieceAt(pos).isEmpty()){ if(!state.pinOrOpen(P).test(attacker.number()) || state.pinnedCanMoveTo

(attacker,pos)) action.simpleMove(from,pos,T,false,P); } } // 移動後ã«é•·ã„利ãã§è¿«ã‚‹ for(int i=0;;i++){ OffsetPair op=Add_Effect8_Table.getLongMoveOffset(T,o32,i); if(op.first.zero()) break; Square pos1=target+op.first.blackOffset

(); Square pos2=target+op.second.blackOffset

(); Piece blocker=Piece::EMPTY(); if(pos1.isOnBoard() && pos2.isOnBoard() && state.pieceAt(pos1).isEmpty() && (!canPromote(T) || !pos1.canPromote

()) && state.hasEffectByPiece(attacker,pos1) && canAddLongEffect(state,pos1,pos2,blocker)){ if(!state.pinOrOpen(P).test(attacker.number()) || state.pinnedCanMoveTo

(attacker,pos1)) action.simpleMove(from,pos1,T,false,P); } } } /** * promoteå¯èƒ½ãªè¶³ã®çŸ­ã„é§’ã«ã‚ˆã‚‹åˆ©ãã®ç”Ÿæˆç”¨ Functor */ template class ShortPieceAction { NumEffectState const& state; Square target; Action& action; public: ShortPieceAction(NumEffectState const& s,Square p,Action& a) :state(s),target(p),action(a) {} /** * forEachOnBoardã‹ã‚‰å‘¼ã°ã‚Œã‚‹ */ void operator()(Piece p) { if (p.isPromotedNotKingGold()) { generateShortMove::promotePtype,Action>(state,p,target,action); } else { generateShortMove(state,p,target,action); } } }; /** * Goldã«ã‚ˆã‚‹åˆ©ãã®ç”Ÿæˆç”¨ Functor */ template class GoldAction { NumEffectState const& state; Square target; Action& action; public: GoldAction(NumEffectState const& s,Square p,Action& a) :state(s),target(p),action(a) {} /** * forEachOnBoardã‹ã‚‰å‘¼ã°ã‚Œã‚‹ */ void operator()(Piece p) { generateShortMove(state,p,target,action); } }; /** * promoteå¯èƒ½ãªè¶³ã®é•·ã„é§’ã«ã‚ˆã‚‹åˆ©ãã®ç”Ÿæˆç”¨ Functor */ template class LongPieceAction { NumEffectState const& state; Square target; Action& action; public: LongPieceAction(NumEffectState const& s,Square p,Action& a) :state(s),target(p),action(a) {} /** * forEachOnBoardã‹ã‚‰å‘¼ã°ã‚Œã‚‹ */ void operator()(Piece p) { if (p.isPromotedNotKingGold()) { if (T==LANCE) generateShortMove::promotePtype,Action>(state,p,target,action); else generateLongMove::promotePtype,Action>(state,p,target,action); } else { generateLongMove(state,p,target,action); } } }; template void generateShort(const NumEffectState& state,Square target, Action& action) { static_assert((PtypeTraits::isBasic), ""); static_assert((PtypeTraits::canPromote), ""); typedef ShortPieceAction action_t; action_t gkAction(state,target,action); state.template forEachOnBoard(gkAction); /** drop move */ if (state.template hasPieceOnStand(P)){ generateShortDrop(state,target,action); } } template void generateLong(const NumEffectState& state,Square target, Action& action) { static_assert((PtypeTraits::isBasic), ""); static_assert((PtypeTraits::canPromote), ""); typedef LongPieceAction action_t; action_t gkAction(state,target,action); state.template forEachOnBoard(gkAction); } template void generateGold(const NumEffectState& state,Square target, Action& action) { typedef GoldAction action_t; action_t gkAction(state,target,action); state.template forEachOnBoard(gkAction); /** drop move */ if (state.template hasPieceOnStand(P)){ generateShortDrop(state,target,action); } } } template template void AddEffect8

:: generateBigDrop(const NumEffectState& state,Action& action) { using namespace addeffect8; Square target=state.kingSquare(); if (state.template hasPieceOnStand(P)){ generateLongDrop(state,target,action); } if (state.template hasPieceOnStand(P)){ generateLongDrop(state,target,action); } } template template void AddEffect8

:: generateNotBigDrop(const NumEffectState& state,Action& action) { using namespace addeffect8; Square target=state.kingSquare(); generateShort(state,target,action); generateLong(state,target,action); if (state.template hasPieceOnStand(P)){ generateLongDrop(state,target,action); } generateShort(state,target,action); generateShort(state,target,action); generateGold(state,target,action); // no king move generateLong(state,target,action); generateLong(state,target,action); } template template void AddEffect8

:: generate(const NumEffectState& state,Action& action) { generateNotBigDrop(state,action); generateBigDrop(state,action); } } } #endif /* _MOVE_GENERATOR_ADD_EFFECT8_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/addEffect8Table.cc0000644000000000000000000001562212316770314022441 0ustar rootroot#include "osl/move_generator/addEffect8Table.h" #include "osl/oslConfig.h" #include osl::move_generator::addeffect8::AddEffect8Table osl::move_generator::Add_Effect8_Table; static osl::SetUpRegister _initializer([](){ osl::move_generator::Add_Effect8_Table.init(); }); namespace osl { namespace move_generator { namespace addeffect8{ bool #ifdef __GNUC__ __attribute__ ((const)) #endif sameDirection(int dx0, int dy0, int dx1, int dy1) { return dx0*dy1==dx1*dy0; } /** * targetã‹ã‚‰(+dx,+dy)ã®ä½ç½®ã«ã‚ã‚‹é»’ã®ç¨®é¡žptypeã®é§’ãŒdirectãªåˆ©ãã‚’æŒã¤ã‹. */ bool #ifdef __GNUC__ __attribute__ ((pure)) #endif hasUnblockableEffect(Ptype ptype,int dx,int dy) { if(std::abs(dx)>8 || std::abs(dy)>8) return false; const EffectContent effect =Ptype_Table.getEffect(newPtypeO(BLACK,ptype),Offset32(dx,dy)); return effect.hasUnblockableEffect(); } bool #ifdef __GNUC__ __attribute__ ((pure)) #endif hasShortEffect(Ptype ptype,int dx,int dy) { if(std::abs(dx)>8 || std::abs(dy)>8) return false; const EffectContent effect =Ptype_Table.getEffect(newPtypeO(BLACK,ptype),Offset32(dx,dy)); return effect.hasEffect() && effect.offset().zero(); } bool #ifdef __GNUC__ __attribute__ ((pure)) #endif hasEffect(Ptype ptype,int dx,int dy) { if(std::abs(dx)>8 || std::abs(dy)>8) return false; return Ptype_Table.getEffect(newPtypeO(BLACK,ptype),Offset32(dx,dy)).hasEffect(); } } } // move_generator } void osl::move_generator::addeffect8::AddEffect8Table::initDropSquare() { for(int i=PTYPE_BASIC_MIN;i<=PTYPE_MAX;i++){ Ptype ptype=static_cast(i); if(ptype==KING) continue; if(Ptype_Table.hasLongMove(ptype)) continue; for(int x=1;x<=9;x++) for(int y=1;y<=9;y++){ Square pos(x,y); int index=0; for(int x1=1;x1<=9;x1++) for(int y1=1;y1<=9;y1++){ Square pos1(x1,y1); if(pos==pos1)continue; // 直接利ããŒã‚る時ã¯é™¤ã if(hasUnblockableEffect(ptype,x-x1,y-y1)) continue; for(int dx0=-1;dx0<=1;dx0++) for(int dy0=-1;dy0<=1;dy0++){ int x2=x+dx0,y2=y+dy0; Square pos2(x2,y2); if(!pos2.isOnBoard()) continue; if(hasUnblockableEffect(ptype,x2-x1,y2-y1)) goto found; } continue; found: dropSquare[ptype][pos.index()][index++]=pos1; } } } } void osl::move_generator::addeffect8::AddEffect8Table::initLongDropSquare() { for(int i=PTYPE_BASIC_MIN;i<=PTYPE_MAX;i++){ Ptype ptype=static_cast(i); if(!Ptype_Table.hasLongMove(ptype)) continue; assert(ptype==ROOK || ptype==BISHOP || ptype==LANCE); for(int x=1;x<=9;x++) for(int y=1;y<=9;y++){ const Square pos(x,y); int sIndex=0,dIndex=0,index1=0,index2=0; for(int x1=1;x1<=9;x1++) for(int y1=1;y1<=9;y1++){ Square pos1(x1,y1); if(pos==pos1)continue; // 直接利ããŒã‚る時ã¯directã«ãƒãƒ£ãƒ¬ãƒ³ã‚¸ if(hasEffect(ptype,x-x1,y-y1)){ if(!hasUnblockableEffect(ptype,x-x1,y-y1)) continue; Square pos2(x+(x1-x)*2,y+(y1-y)*2); if(!pos2.isOnBoard()) continue; longDropDirect[ptype][pos.index()][dIndex++]=Offset(x1-x,y1-y); continue; } int count=0; CArray dxs, dys; for(int dx0=-1;dx0<=1;dx0++) for(int dy0=-1;dy0<=1;dy0++){ int x2=x+dx0,y2=y+dy0; Square pos2(x2,y2); if(pos2==pos) continue; if(!pos2.isOnBoard()) continue; if(hasUnblockableEffect(ptype,x2-x1,y2-y1)){ dxs[count]=x1-x2; dys[count++]=y1-y2; } } if(count>0){ if(abs(x-x1)<=1 && abs(y-y1)<=1) dropSquare[ptype][pos.index()][sIndex++]=pos1; else if(count==1){ longDropSquare[ptype][pos.index()][index1++]= PO(pos1,Offset(dxs[0],dys[0])); } else if(count==2){ longDrop2Square[ptype][pos.index()][index2++]= POO(pos1,OffsetPair(Offset(dxs[0],dys[0]), Offset(dxs[1],dys[1]))); } } } } } } void osl::move_generator::addeffect8::AddEffect8Table::initMoveOffset() { for(int i=PTYPE_PIECE_MIN;i<=PTYPE_MAX;i++){ Ptype ptype=static_cast(i); for(int dx=-8;dx<=8;dx++) for(int dy=-8;dy<=8;dy++){ if(dx==0 && dy==0) continue; Offset32 o32(dx,dy); // targetã‹ã‚‰è¦‹ãŸé§’ã®ä½ç½® // 最åˆã‹ã‚‰çŽ‹æ‰‹ã«ãªã£ã¦ã„ã‚‹å ´åˆã¯é™¤ã if(hasUnblockableEffect(ptype,-dx,-dy)) continue; // 最åˆã‹ã‚‰8è¿‘å‚ã«ã‚ãŸã‚‹é•·ã„利ãã‚’æŒã¤å ´åˆ for(int dx1=-1;dx1<=1;dx1++){ for(int dy1=-1;dy1<=1;dy1++){ if(dx1==0 && dy1==0) continue; if(hasEffect(ptype,dx1-dx,dy1-dy) && !hasUnblockableEffect(ptype,dx1-dx,dy1-dy)){ int div=std::max(std::abs(dx1-dx),std::abs(dy1-dy)); // 8è¿‘å‚ã®ç«¯ã®å ´åˆã—ã‹èˆˆå‘³ãŒãªã„. if(abs(dx1+(dx-dx1)/div)>1 || abs(dy1+(dy-dy1)/div)>1){ betweenOffset[ptype][o32.index()]= OffsetPair(Offset(dx1,dy1), Offset((dx1-dx)/div,(dy1-dy)/div)); } } } } int sIndex=0,lIndex=0,spIndex=0; for(int dx0=-8;dx0<=8;dx0++) for(int dy0=-8;dy0<=8;dy0++){ if(dx0==0 && dy0==0) continue; // 移動ã§ããªã„å ´åˆã¯å•題外 if(!hasEffect(ptype,dx0-dx,dy0-dy)) continue; int effectDx=9,effectDy=9; bool unblockableEffect=false; bool effect=false; bool promotedUnblockableEffect=false; for(int dx1=-1;dx1<=1;dx1++){ for(int dy1=-1;dy1<=1;dy1++){ if(dx1==0 && dy1==0) continue; if(hasUnblockableEffect(ptype,dx1-dx0,dy1-dy0)){ // 元々利ããŒã‚ã£ãŸãªã‚‰æ•°ãˆãªã„ if(!hasUnblockableEffect(ptype,dx1-dx,dy1-dy) && (!hasEffect(ptype,dx1-dx,dy1-dy) || !sameDirection(dx1-dx0,dy1-dy0,dx1-dx,dy1-dy) || (abs(dx0)<=1 && abs(dy0)<=1) )){ unblockableEffect=true; effect=true; } } else if(hasEffect(ptype,dx1-dx0,dy1-dy0) && !hasEffect(ptype,dx1-dx,dy1-dy)){ if(std::abs(effectDx)>=std::abs(dx1-dx0) && std::abs(effectDy)>=std::abs(dy1-dy0)){ effectDx=dx1-dx0; effectDy=dy1-dy0; effect=true; } else{ effect=true; } } if(canPromote(ptype) && hasUnblockableEffect(osl::promote(ptype),dx1-dx0,dy1-dy0) && !hasUnblockableEffect(ptype,dx1-dx,dy1-dy) ){ promotedUnblockableEffect=true; } } } if(unblockableEffect // && !hasUnblockableEffect(ptype,-dx0,-dy0) ){ shortMoveOffset[ptype][o32.index()][sIndex++]=Offset(dx0,dy0); } else if(effect){ // åŒã˜æ–¹å‘ã®æ™‚ã¯ï¼Œbetweenã«ã™ã‚‹ longMoveOffset[ptype][o32.index()][lIndex++]= OffsetPair(Offset(dx0,dy0),Offset(dx0+effectDx,dy0+effectDy)); } if(promotedUnblockableEffect // &&!hasUnblockableEffect(promote(ptype),-dx0,-dy0) ){ shortPromoteMoveOffset[ptype][o32.index()][spIndex++]= Offset(dx0,dy0); } } } } } void osl::move_generator::addeffect8::AddEffect8Table::init() { initDropSquare(); initLongDropSquare(); initMoveOffset(); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_generator/addEffect8.cc0000644000000000000000000000333112316770314021463 0ustar rootroot#include "osl/move_generator/addEffect8.h" #include "osl/move_generator/addEffect8.tcc" template void osl::move_generator::AddEffect8::generate(const NumEffectState&,move_action::Store&); template void osl::move_generator::AddEffect8::generate(const NumEffectState&,move_action::Store&); template void osl::move_generator::AddEffect8::generateBigDrop(const NumEffectState&,move_action::Store&); template void osl::move_generator::AddEffect8::generateBigDrop(const NumEffectState&,move_action::Store&); template void osl::move_generator::AddEffect8::generateNotBigDrop(const NumEffectState&,move_action::Store&); template void osl::move_generator::AddEffect8::generateNotBigDrop(const NumEffectState&,move_action::Store&); void osl::move_generator::GenerateAddEffect8:: generate(Player player, const NumEffectState& state, move_action::Store& store){ assert(state.turn()==player); if(player==BLACK) AddEffect8::generate(state,store); else AddEffect8::generate(state,store); } void osl::move_generator::GenerateAddEffect8:: generateBigDrop(Player player, const NumEffectState& state, move_action::Store& store){ assert(state.turn()==player); if(player==BLACK) AddEffect8::generateBigDrop(state,store); else AddEffect8::generateBigDrop(state,store); } void osl::move_generator::GenerateAddEffect8:: generateNotBigDrop(Player player, const NumEffectState& state, move_action::Store& store){ assert(state.turn()==player); if(player==BLACK) AddEffect8::generateNotBigDrop(state,store); else AddEffect8::generateNotBigDrop(state,store); } libosl-0.8.0.orig/full/osl/move_generator/additionalLance.h0000644000000000000000000000133412316770314022444 0ustar rootroot/* additionalLance.h */ #ifndef OSL_ADDITIONALLANCE_H #define OSL_ADDITIONALLANCE_H #include "osl/numEffectState.h" namespace osl { namespace move_generator { template struct AdditionalLance { /** * pawn ã«é¦™è»Šã‚’打ã£ã¦è¿½åŠ åˆ©ãã‚’ã¤ã‘る指手を生æˆ. * 敵ã®åˆ©ããŒã‚ã‚‹ã¨ã“ã‚ã§ç”Ÿæˆã‚’ã‚„ã‚ã‚‹. */ static void generate(const NumEffectState&, Square pawn, MoveVector& out); static void generateIfHasLance(const NumEffectState&, Square pawn, MoveVector& out); }; } // namespace move_generator } // namespace osl #endif /* OSL_ADDITIONALLANCE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_order/0000755000000000000000000000000012316770314016344 5ustar rootrootlibosl-0.8.0.orig/full/osl/move_order/moveSorter.h0000644000000000000000000000100112316770314020652 0ustar rootroot#ifndef _MOVE_ORDER_MOVESORTER_H #define _MOVE_ORDER_MOVESORTER_H #include "osl/container.h" #include namespace osl { namespace move_order { struct MoveSorter { template static void sort(MoveVector& moves, const Compare& comp) { std::sort(moves.begin(), moves.end(), comp); } }; } // namespace move_order } // namespace osl #endif /** _MOVE_ORDER_MOVESORTER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_order/captureSort.h0000644000000000000000000000176612316770314021042 0ustar rootroot/* captureSort.h */ #ifndef MOVE_ORDER_CAPTURESORT_H #define MOVE_ORDER_CAPTURESORT_H #include "osl/basic_type.h" #include namespace osl { namespace move_order { /** * å–る手をå‰ã«ã‚‚ã£ã¦ãã‚‹ */ struct CaptureSort { template static void sort(Iterator first, Iterator last) { while (first < --last) { while (true) { if (first->capturePtype() == PTYPE_EMPTY) break; ++first; if (! (first < last)) return; } assert(first->capturePtype() == PTYPE_EMPTY); while (true) { if (! (first < last)) return; if (last->capturePtype() != PTYPE_EMPTY) break; --last; } assert(last->capturePtype() != PTYPE_EMPTY); assert(first < last); std::swap(*first, *last); ++first; } } }; } // namespace move_order using move_order::CaptureSort; } // namespace osl #endif /* MOVE_ORDER_CAPTURESORT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/move_order/cheapPtype.h0000644000000000000000000000131412316770314020616 0ustar rootroot/* cheapPtype.h */ #ifndef _CHEAPPTYPE_H #define _CHEAPPTYPE_H #include "osl/move_order/promotion.h" #include "osl/eval/pieceEval.h" namespace osl { namespace move_order { /** * 安ã„é§’ã‹ã‚‰ä½¿ã† */ struct CheapPtype { bool operator()(Move l, Move r) const { const Ptype old_ptype_l = l.oldPtype(); const Ptype old_ptype_r = r.oldPtype(); if (old_ptype_l != old_ptype_r) return (eval::Ptype_Eval_Table.value(old_ptype_l) < eval::Ptype_Eval_Table.value(old_ptype_r)); return Promotion()(l, r); } }; } // namespace move_order } // namespace osl #endif /* _CHEAPPTYPE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_order/captureEstimation.h0000644000000000000000000000247412316770314022224 0ustar rootroot/* captureEstimation.h */ #ifndef _MOVE_ORDER_CAPTUREESTIMATION_H #define _MOVE_ORDER_CAPTUREESTIMATION_H #include "osl/move_order/promotion.h" #include "osl/numEffectState.h" #include "osl/eval/pieceEval.h" namespace osl { namespace move_order { struct CaptureEstimation { const NumEffectState& state; explicit CaptureEstimation(const NumEffectState& s) : state(s) { } bool operator()(Move l, Move r) const { const Ptype capture_ptype_l = l.capturePtype(); const Ptype capture_ptype_r = r.capturePtype(); const Ptype old_ptype_l = l.oldPtype(); const Ptype old_ptype_r = r.oldPtype(); const Player turn = l.player(); int value_l = eval::Ptype_Eval_Table.value(capture_ptype_l); if (state.hasEffectAt(alt(turn), l.to())) value_l -= eval::Ptype_Eval_Table.value(old_ptype_l); int value_r = eval::Ptype_Eval_Table.value(capture_ptype_r); if (state.hasEffectAt(alt(turn), r.to())) value_r -= eval::Ptype_Eval_Table.value(old_ptype_r); // 実入ã®å¤§ããã†ãªæ‰‹ã‹ã‚‰æŒ‡ã™ if (value_l != value_r) return value_l > value_r; // æˆã‚‹æ‰‹ã‹ã‚‰èª­ã‚€ return Promotion()(l, r); } }; } // namespace move_order } // namespace osl #endif /* _MOVE_ORDER_CAPTUREESTIMATION_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/move_order/promotion.h0000644000000000000000000000107412316770314020545 0ustar rootroot/* promotion.h */ #ifndef _MOVE_ORDER_PROMOTION_H #define _MOVE_ORDER_PROMOTION_H #include "osl/basic_type.h" namespace osl { namespace move_order { /** * æˆã‚‹æ‰‹ã‚’優先 */ struct Promotion { bool operator()(Move l, Move r) const { const int promotion_l = l.promoteMask(); const int promotion_r = r.promoteMask(); return promotion_l > promotion_r; } }; } // namespace move_order } // namespace osl #endif /* _MOVE_ORDER_PROMOTION_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/0000755000000000000000000000000012715504335015451 5ustar rootrootlibosl-0.8.0.orig/full/osl/search/quiescenceSearch2.tcc0000644000000000000000000016712312316770314021511 0ustar rootroot/* quiescenceSearch2.tcc */ #ifndef OSL_QUIESCENCESEARCH2_TCC #define OSL_QUIESCENCESEARCH2_TCC #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceGenerator.h" #include "osl/search/quiescenceLog.h" #include "osl/search/searchTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/search/simpleHashTable.h" #include "osl/search/sortCaptureMoves.h" #include "osl/search/moveStackRejections.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/hash/hashCollision.h" #include "osl/effect_util/effectUtil.h" #include "osl/move_order/captureSort.h" #include "osl/move_classifier/check_.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/pawnDropCheckmate.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/eval/see.h" #include "osl/stat/ratio.h" #include "osl/hash/hashRandom.h" #include "osl/oslConfig.h" #include "osl/centering3x3.h" #ifdef STAT_WIDTH_VS_LIMIT # include "osl/stat/average.h" # include #endif #define quiecence_assert(x,m) assert((x) || state.abort(m)) #ifdef RICH_QSEARCH // 増減1割 # define QSEARCH_LAST_CHECK_PENALTY // 5-20% # define QSEARCH_PESSIMISTIC_ESCAPE_THREAT // 8% # define QSEARCH_THREATMATE #endif #ifdef EXTRA_RICH_QSEARCH // 2å€ # define QSEARCH_SET_MINIMUM_MOVES #endif // recordãŒãªã„ã¨æ„味ãŒã‚ã¾ã‚Šãªã„ // #define MAKE_PV_IN_QUIESCE2 const int allocate_depth_in_threatmate = 400; namespace osl { namespace search { struct QSearch2PrivateTraits { enum { KnightCaptureDepth = 1, PawnCaptureDepth = 3, FullPromoteDepth = 3, UtilizePromotedDepth = 5, AttackPinnedDepth = 6, }; enum { EscapeDepthFromRoot = 1, EscapeFromLastMoveDepthFromRoot = 3, AttackKnightDepthFromRoot = 2, AttackGoldSilverDepthFromRoot = 2, DropDepthFromRoot = 2, AttackMajorPieceDepthFromRoot = 2, AdvanceBishopDepthFromRoot = 2, AttackKing8DepthFromRoot = 2, }; enum { ThreatMateDepthFromRoot = 2, }; enum { /** pass ã‚’ã—ãŸæ™‚ã«æ¶ˆè²»ã™ã‚‹æ·±ã• */ PassExtraDepth = 4, }; enum { /** * 指手ãŒå°‘ãªã‘ã‚Œã°æ·±ã•ãŒå…ˆã§ã‚‚読む. * "以下4手目以é™ã§ã¯6手〜13手程度" (yss) */ #ifdef QSEARCH_SET_MINIMUM_MOVES MinimumMoves = 6, #else MinimumMoves = 0, #endif }; }; struct QSearch2HelperBase { int& result; int alpha, beta; Move last_move; QSearch2HelperBase(int& r, int a, int b, Move l) : result(r), alpha(a), beta(b), last_move(l) { } }; template struct QSearch2NextMove : public QSearch2HelperBase { typedef typename QSearch2::eval_t eval_t; QSearch2 *searcher; eval_t& ev; int additional_depth; QSearch2NextMove(int& r, QSearch2 *s, int a, int b, eval_t& e, Move l, int additional) : QSearch2HelperBase(r, a, b, l), searcher(s), ev(e), additional_depth(additional) { } void operator()(Square) { result = (*searcher).template searchInternal (beta, alpha, ev, last_move, additional_depth, QSearch2::BeforeUpdate); } }; template struct QSearch2NextTakeBack : QSearch2HelperBase { typedef typename QSearch2::eval_t eval_t; QSearch2 *searcher; eval_t& ev; QSearch2NextTakeBack(int& r, QSearch2 *s, int a, int b, eval_t& e, Move l) : QSearch2HelperBase(r, a, b, l), searcher(s), ev(e) { } void operator()(Square) { ev.update(searcher->currentState(), last_move); result = (*searcher).template takeBackValue (beta, alpha, ev, last_move); } }; template struct QSearch2TakeBackOrChase : QSearch2HelperBase { typedef typename QSearch2::eval_t eval_t; QSearch2 *searcher; eval_t& ev; QSearch2TakeBackOrChase(int& r, QSearch2 *s, int a, int b, eval_t& e, Move l) : QSearch2HelperBase(r, a, b, l), searcher(s), ev(e) { } void operator()(Square) { ev.update(searcher->currentState(), last_move); result = (*searcher).template takeBackOrChase (beta, alpha, ev, last_move); } }; template struct QSearch2SafeEscape { const NumEffectState *state; Eval& eval; Piece target; bool has_safe_escape; bool is_invalid; Move last_move; QSearch2SafeEscape(const NumEffectState *s, Piece t, Eval& e, Move l) : state(s), eval(e), target(t), has_safe_escape(false), is_invalid(false), last_move(l) { } void operator()(Square) { const Player Turn = alt(P); assert(state->turn() == Turn); if (state->inCheck(alt(Turn))) { is_invalid = true; return; } eval.update(*state, last_move); MoveVector dummy; has_safe_escape = QuiescenceGenerator::escapeByMoveOnly(*state, target, dummy); } }; template struct QSearch2Util { static bool moreMoves(const QuiescenceRecord *) { return false; // TODO: count number of moves outside of record // return (record->moves_size() < QSearch2PrivateTraits::MinimumMoves); } }; } // namespace search } // namespace osl template template int osl::search::QuiescenceSearch2:: searchProbCut(int alpha, int beta, eval_t& ev, Move last_move) { if (alpha != beta) { max_depth = QSearchTraits::MaxDepth/2; const int pawn_value2 = EvalT::captureValue(newPtypeO(alt(P),PAWN)); const int margin = pawn_value2/2; const int alpha4 = EvalTraits

::max(alpha-margin, base_t::winThreshold(alt(P))); assert(EvalTraits

::notLessThan(alpha, alpha4)); const int beta4 = EvalTraits

::min(beta +margin, base_t::winThreshold(P)); assert(EvalTraits

::notLessThan(beta4, beta)); const int val4 = searchInternal

(alpha4, beta4, ev, last_move); if (EvalTraits

::betterThan(val4, beta4)) return val4 - (beta4-beta); if (EvalTraits

::betterThan(alpha4, val4)) return val4 - (alpha4-alpha); } max_depth = QSearchTraits::MaxDepth; return searchInternal

(alpha, beta, ev, last_move); } template template inline bool osl::search::QuiescenceSearch2:: generateAndExamineTakeBack2(MoveVector& moves, QuiescenceThreat& threat2, QuiescenceThreat& threat1, int beta1, int beta2, eval_t const& ev) { mask_t pieces = state.state().effectedMask(P).template selectBit() & state.state().piecesOnBoard(alt(P)).getMask(PtypeFuns::indexNum); if (PTYPE == PAWN || PTYPE == LANCE || PTYPE == KNIGHT) pieces &= ~state.state().effectedMask(alt(P)).getMask(PtypeFuns::indexNum); while (pieces.any()) { const Piece target = state.state().pieceOf(pieces.takeOneBit()+PtypeFuns::indexNum*32); assert(target.isOnBoardByOwner()); assert(moves.empty()); QuiescenceGenerator

::capture1(currentState(), target.square(), moves); const bool result = examineTakeBack2(moves, threat2, threat1, beta1, beta2, ev); moves.clear(); if (result) return result; } return false; } template template inline bool osl::search::QuiescenceSearch2:: examineCapture(QuiescenceRecord *record, int& cur_val, MoveVector& moves, int& alpha, int beta, eval_t const& ev, Piece last_move_piece, int additional_depth) { assert(alpha % 2); assert(beta % 2); { moves.clear(); QuiescenceGenerator

::template capture(state.state(), moves, last_move_piece); SortCaptureMoves::sortByTakeBack(state.state(), moves); return examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth, last_move_piece.square()); } return false; } #ifdef STAT_WIDTH_VS_LIMIT namespace osl { namespace { struct Reporter { stat::Average average; int count; Reporter() : count(0) {} ~Reporter() { std::cerr << "QuiescenceSearch2 " << average.getAverage() << std::endl; } void newRoot() { average.add(count); count=0; } void add() { ++count; } } _reporter; } } #endif template template bool osl::search::QuiescenceSearch2:: examineMoves(QuiescenceRecord *record, int& cur_val, const Move *first, const Move *last, int& alpha, int beta, eval_t const& ev, int additional_depth, Square dont_capture) { assert(alpha % 2); assert(beta % 2); assert(EvalTraits

::notLessThan(alpha, cur_val)); #if (! defined NDEBUG) && (! defined OSL_SMP) const bool in_pv = (alpha != beta); #endif while (first != last) { const Move move = *first++; if (move_type == CHECK) { if (depth() <= 0 && ! move.isCapture() && ! isMajor(move.ptype())) continue; } if (has_dont_capture) { const Square to = move.to(); if (to == dont_capture) continue; } assert((move_type == KING_ESCAPE) || (move_type == UNKNOWN) || (! ShouldPromoteCut::canIgnoreAndNotDrop

(move))); if(MoveStackRejections::probe

(state.state(),state.history(),state.curDepth(),move,alpha,state.repetitionCounter().checkCount(alt(P)))){ continue; } #ifdef QSEARCH_DEBUG QuiescenceLog::pushMove(depth(), move, record); #endif const HashKey new_hash = state.currentHash().newHashWithMove(move); int result; // åƒæ—¥æ‰‹ç¢ºèª const Sennichite next_sennichite = state.repetitionCounter().isAlmostSennichite(new_hash); if (next_sennichite.isDraw()) { result = base_t::drawValue(); } else if (next_sennichite.hasWinner()) { result = base_t::winByFoul(next_sennichite.winner()); } else { eval_t new_ev = ev; #ifdef STAT_WIDTH_VS_LIMIT if (depthFromRoot() == 0) _reporter.add(); #endif assert(next_sennichite.isNormal()); typedef QSearch2NextMove helper_t; if (has_record && alpha != beta && record->bestMove().isNormal()) { // cut node helper_t helper(result, this, alpha, alpha, new_ev, move, additional_depth); state.doUndoMoveOrPass(new_hash, move, helper); if (EvalTraits

::betterThan(result, alpha)) { new_ev = ev; helper_t helper(result, this, alpha, beta, new_ev, move, additional_depth); state.doUndoMoveOrPass(new_hash, move, helper); } } else { // pv or all node helper_t helper(result, this, alpha, beta, new_ev, move, additional_depth); state.doUndoMoveOrPass(new_hash, move, helper); } // 打歩詰を厳密㫠if (base_t::isWinValue(P, result) && (! move.isPass()) && move_classifier::MoveAdaptor > ::isMember(state.state(), move)) { result = base_t::winByFoul(alt(P)); } } if (EvalTraits

::betterThan(result, cur_val)) { cur_val = result; if (EvalTraits

::betterThan(result, alpha)) { alpha = result + EvalTraits

::delta; if (has_record) { if (base_t::isWinValue(P, cur_val)) { Square king = state.state().kingSquare(alt(P)); if (Ptype_Table.hasUnblockableEffect(move.ptypeO(), move.to(), king)) { record->setLowerBound(QSearchTraits::CheckmateSpecialDepth, cur_val, move); } else { // ç¾åœ¨ã¯å–りåˆã„ã®çµæžœè©°ã§ã‚‚本当ã«è©°ã¨ã¯é™ã‚‰ãªã„ c.f. 中åˆã„ record->setLowerBound(QSearchTraits::MaxDepth, cur_val, move); } assert(EvalTraits

::notLessThan(result, beta)); return true; } else { #ifndef OSL_SMP assert((record->lowerDepth() < depth()) || EvalTraits

::notLessThan(cur_val, record->lowerBound()) || in_pv || state.abort(move)); #endif record->setLowerBound(depth(), cur_val, move); } } if (EvalTraits

::notLessThan(result, beta)) { state.setKillerMove(move); if (! move.isCapture()) { const int d = depth(); state.historyTable().add(move, d*d); } return true; } } } } return false; } namespace osl { namespace search { inline QuiescenceRecord *qallocate(SimpleHashTable& table, const HashKey& key, int minusDepthFromRoot, SearchState2Core& state) { assert(minusDepthFromRoot <= 0 || minusDepthFromRoot == allocate_depth_in_threatmate); SimpleHashRecord *record = table.allocate(key, minusDepthFromRoot); if (record) { state.setCurrentRecord(record); return &record->qrecord; } return 0; } } } template template inline int osl::search::QuiescenceSearch2:: staticValue(eval_t const& ev, int alpha, int beta, QuiescenceRecord *record) { const bool in_pv = (alpha != beta); #ifndef DONT_USE_CHECKMATE if (! in_pv) { bool in_threatmate = has_record && record->threatmate.maybeThreatmate(P); if (! in_threatmate && (state.hasLastRecord(1) && state.lastRecord(1))) in_threatmate = (state.lastRecord(1)->threatmate().status(P).status() == ThreatmateState::CHECK_AFTER_THREATMATE); if (in_threatmate) { const int result = ev.value() + base_t::threatmatePenalty(P); return result; } } if (in_pv) { const Move last_move = state.lastMove(); const Square king = state.state().kingSquare(P); const bool one_hop_prook = (last_move.isNormal() && last_move.ptype() == PROOK && (last_move.capturePtype() == GOLD || last_move.capturePtype() == SILVER) && ((king.y() == last_move.to().y() && abs(king.x() - last_move.to().x()) < 3) || (king.x() == last_move.to().x() && abs(king.y() - last_move.to().y()) < 3))); if (one_hop_prook && ! has_record) { record = qallocate(table, state.currentHash(), allocate_depth_in_threatmate, state); } if (has_record || record) { // try simulation if record exists Move checkmate_move=Move::INVALID(); int threatmate_node = 0; if (record && record->threatmate.maybeThreatmate(P)) { threatmate_node += 50; } else if (one_hop_prook) { threatmate_node += 20; } #ifdef QSEARCH_THREATMATE else if ((depthFromRoot() < QSearch2PrivateTraits::ThreatMateDepthFromRoot) && state.tryThreatmate()) threatmate_node += 20; #endif bool lose = state.isThreatmateState

(record->threatmateNodesLeft(threatmate_node), checkmate_move); if (! lose && record->threatmateNodesLeft(2)) lose = state.isThreatmateStateShort

(2, checkmate_move); if (lose) { const int result = ev.value() + base_t::threatmatePenalty(P); assert(checkmate_move.isValid()); record->threatmate.setThreatmate(P, checkmate_move); record->setStaticValue(QuiescenceRecord::EXACT, result, QSearchTraits::CheckmateSpecialDepth); assert(result % 2 == 0); return result; } } } #endif if (! in_pv && has_record) { int static_value, static_value_depth; QuiescenceRecord::StaticValueType type; if (record->hasStaticValue(static_value, static_value_depth, type)) { // upper bound 㯠depth ã«å› ã‚‰ãªã„ if (EvalTraits

::betterThan(alpha, static_value)) { assert(static_value % 2 == 0); return static_value; } if (type == QuiescenceRecord::EXACT && (static_value_depth >= depth())) { assert(static_value % 2 == 0); return static_value; } } } Move threatmate_move; if (ImmediateCheckmate::hasCheckmateMove (state.state(), threatmate_move)) { const int result = ev.value() + base_t::threatmatePenalty(P); if (has_record) { record->threatmate.setThreatmate(P, threatmate_move); record->setStaticValue(QuiescenceRecord::EXACT, result, QSearchTraits::CheckmateSpecialDepth); } assert(result % 2 == 0); return result; } if (alpha == beta && EvalTraits

::betterThan(ev.value(), beta)) { // futility pruning of threat int expect = ev.value() + ev.captureValue(newPtypeO(P, GOLD)); Piece threat = state.state().findThreatenedPiece(P); if (threat.isPiece()) expect += ev.captureValue(threat.ptypeO()); if (EvalTraits

::betterThan(expect, beta)) return expect; } const int eval_alpha = alpha; QuiescenceThreat threat1, threat2; const int result = staticValueWithThreat

(ev, eval_alpha, threat1, threat2); if (has_record) { record->setStaticValue(EvalTraits

::betterThan(eval_alpha, result) ? QuiescenceRecord::UPPER_BOUND : QuiescenceRecord::EXACT, result, depth(), threat1, threat2); } assert(result % 2 == 0); return result; } template template int osl::search::QuiescenceSearch2:: searchInternal(int alpha, int beta, eval_t& ev, Move last_move, int additional_depth, EvalUpdateState need_eval_update) { #ifdef STAT_WIDTH_VS_LIMIT if (depthFromRoot() == 0) _reporter.newRoot(); #endif #ifdef QSEARCH_DEBUG if (depthFromRoot() == 0) QuiescenceLog::enter(state.state()); #endif #ifdef MAKE_PV_IN_QUIESCE2 state.initPV(); #endif ++node_count; assert(alpha % 2); assert(beta % 2); quiecence_assert(EvalTraits

::notLessThan(beta, alpha), last_move); assert(EvalTraits

::notLessThan(alpha, base_t::winThreshold(alt(P)))); assert(EvalTraits

::notLessThan(base_t::winThreshold(P), beta)); assert(last_move.player() == alt(P)); // 自殺手を手生æˆã§ãƒ•ィルタã™ã‚‹ã¨é…ããªã‚‹ã®ã§å‹•ã‹ã—ã¦ã‹ã‚‰ãƒã‚§ãƒƒã‚¯ if (state.state().inCheck(alt(P))) return base_t::winByFoul(P); assert(state.hasLastRecord()); QuiescenceRecord *record = qallocate(table, state.currentHash(), depth()-QSearchTraits::MaxDepth, state); const QuiescenceRecord *parent = (state.hasLastRecord(1) && state.lastRecord(1)) ? &(state.lastRecord(1)->qrecord) : 0; const bool near_checkmate = parent && (parent->threatmate.maybeThreatmate(alt(P)) || parent->threatmate.mayHaveCheckmate(P) || (parent->threatmate.status(P).status() == ThreatmateState::CHECK_AFTER_THREATMATE)); if (! record && near_checkmate) { const int depth = (alpha != beta) ? allocate_depth_in_threatmate : 0; record = qallocate(table, state.currentHash(), depth, state); } int result; if (! record) { result = searchMain(0, alpha, beta, ev, last_move, additional_depth, need_eval_update); if (near_checkmate) { if ((EvalTraits

::betterThan(alpha, result) && parent->threatmate.maybeThreatmate(alt(P))) || (EvalTraits

::betterThan(result, alpha) && parent->threatmate.status(P).status() == ThreatmateState::CHECK_AFTER_THREATMATE)) { record = qallocate(table, state.currentHash(), allocate_depth_in_threatmate, state); } } } if (record) { const bool is_king_in_check = state.state().inCheck(); record->updateThreatmate(P, (parent ? &(parent->threatmate) : 0), is_king_in_check); result = searchMain(record, alpha, beta, ev, last_move, additional_depth, need_eval_update); #ifdef MAKE_PV_IN_QUIESCE2 if ((alpha != beta) && EvalTraits

::betterThan(result, alpha)) state.makePV(record->bestMove()); #endif } #ifdef QSEARCH_DEBUG QuiescenceLog::node(depth(), alpha, beta, result); #endif assert(result % 2 == 0); return result; } template int osl::search::QuiescenceSearch2:: currentValueWithLastThreat(eval_t const& ev, Piece last_move_piece) { int static_value = ev.value(); if (! (depthFromRoot() < QSearch2PrivateTraits::EscapeFromLastMoveDepthFromRoot)) return static_value; assert(last_move_piece.isPiece()); const Player P = last_move_piece.owner(); PieceVector targets; const Square from = last_move_piece.square(); EffectUtil::findThreat(state.state(), from, last_move_piece.ptypeO(), targets); if (targets.empty()) return static_value; if (targets[0].ptype() == KING) { if (targets.size() < 2) return static_value; // 王手ã®ä¸¡å–り int threat = eval_t::captureValue(targets[1].ptypeO()); if (state.state().hasEffectAt(alt(P), targets[1].square())) threat += eval_t::captureValue(last_move_piece.ptypeO()); assert(eval::betterThan(P, threat, 0)); return static_value + threat; } int first_threat = eval_t::captureValue(targets[0].ptypeO()); if (state.state().hasEffectAt(alt(P), targets[0].square())) first_threat += eval_t::captureValue(last_move_piece.ptypeO()); assert(eval::betterThan(P, first_threat, 0)); first_threat /= SecondThreat; if (targets.size() < 2) return static_value + (first_threat & (~0x1)); int second_threat = eval_t::captureValue(targets[1].ptypeO()); if (state.state().hasEffectAt(alt(P), targets[1].square())) second_threat += eval_t::captureValue(last_move_piece.ptypeO()); assert(eval::betterThan(P, second_threat, 0)); return static_value + ((first_threat + second_threat) & (~0x1)); } template template int osl::search::QuiescenceSearch2:: passValue(int alpha, int beta, eval_t const& ev) { // TODO: // - pass pass を許ã™ãªã‚‰loopç¢ºèª static_assert(QSearch2PrivateTraits::EscapeDepthFromRoot <= 2, ""); const Move pass = Move::PASS(P); int result; typedef QSearch2NextMove helper_t; helper_t helper(result, this, alpha, beta, ev, pass, 0); const HashKey new_hash = state.currentHash().newHashWithMove(pass); max_depth -= QSearch2PrivateTraits::PassExtraDepth; state.doUndoMoveOrPass(new_hash, pass, helper); max_depth += QSearch2PrivateTraits::PassExtraDepth; return result; } template template int osl::search::QuiescenceSearch2:: searchMain(QuiescenceRecord *record, int alpha, int beta, eval_t& ev, Move last_move, int additional_depth, EvalUpdateState& need_eval_update) { const bool in_pv = (alpha != beta); #if (! defined NDEBUG) && (! defined OSL_USE_RACE_DETECTOR) static stat::Ratio ratio("QSearch2: cut"); #endif assert((! has_record) || record); assert(alpha % 2); assert(beta % 2); assert((last_move == state.lastMove()) || ! last_move.isNormal() || ! state.lastMove().isNormal()); #if (!defined OSL_USE_RACE_DETECTOR) && (!defined MINIMAL) state.depth_node_count_quiesce[state.curDepth()]++; #endif #ifndef DONT_USE_CHECKMATE const int node_count_before = node_count; #endif const Square last_to = last_move.to(); int cur_val = base_t::winByCheckmate(alt(P)); if (has_record) { if ((! in_pv && record->lowerDepth() >= depth()) || record->lowerDepth() >= QSearchTraits::HistorySpecialDepth) { if (EvalTraits

::notLessThan(record->lowerBound(), cur_val)) { cur_val = record->lowerBound(); if (EvalTraits

::betterThan(record->lowerBound(), alpha)) { alpha = record->lowerBound() + EvalTraits

::delta; if (EvalTraits

::betterThan(record->lowerBound(), beta)) { #if (! defined NDEBUG) && (! defined OSL_USE_RACE_DETECTOR) ratio.add(true); #endif return record->lowerBound(); } } } } #ifndef DONT_USE_CHECKMATE assert(record); // try simulation if record exists if (in_pv) { Move checkmate_move=Move::INVALID(); if (need_eval_update == BeforeUpdate) { ev.update(state.state(), last_move); need_eval_update = AfterUpdate; } bool win = state.isWinningState

(0, checkmate_move); if (! win && record->threatmate.mayHaveCheckmate(alt(P))) { win = state.isWinningStateShort

(2, checkmate_move); } if (win) { const int result = base_t::winByCheckmate(P); assert(checkmate_move.isValid()); assert(state.state().isValidMove(checkmate_move)); record->setLowerBound(QSearchTraits::CheckmateSpecialDepth, result, checkmate_move); return result; } } #endif if ((! in_pv && record->upperDepth() >= depth()) || record->upperDepth() >= QSearchTraits::HistorySpecialDepth) { if (EvalTraits

::betterThan(beta, record->upperBound())) { beta = record->upperBound() - EvalTraits

::delta; if (EvalTraits

::betterThan(alpha, record->upperBound())) { #if (! defined NDEBUG) && (! defined OSL_USE_RACE_DETECTOR) ratio.add(true); #endif return record->upperBound(); } } } #if (! defined NDEBUG) && (! defined OSL_USE_RACE_DETECTOR) ratio.add(false); #endif } if (need_eval_update == BeforeUpdate) { ev.update(state.state(), last_move); need_eval_update = AfterUpdate; } const bool is_king_in_check = state.state().inCheck(); MoveVector moves; if (is_king_in_check) { if (last_move.isNormal() && last_move.isCapture() && unpromote(last_move.capturePtype()) == ROOK && unpromote(last_move.ptype()) != ROOK) ++additional_depth; else // 王手ã§ã®takebackã®å¿œé…¬ã®å»¶é•· if (state.lastMove(2).isNormal() // hasLastMove(3)ã‚’å…¼ã­ã‚‹ && state.lastMove(3).isNormal() && state.lastMove(4).isNormal() && state.lastMove(2).to() == last_move.to() && state.lastMove(3).to() == last_move.to() && state.lastMove(4).to() == last_move.to()) ++additional_depth; // 王手ãŒã‹ã‹ã£ã¦ã„る時ã¯ãã¡ã‚“ã¨é€ƒã’ã‚‹ { QuiescenceGenerator

::escapeKing(state.state(), moves); // GenerateEscape ã¯çމã§å–る手ãŒé€ƒã’る手より後回ã—ã«ãªã‚‹ã“ã¨ãŒã‚ã‚‹ã®ã§ move_order::CaptureSort::sort(moves.begin(), moves.end()); examineMoves (record, cur_val, &*moves.begin(), &*moves.end(),alpha, beta, ev, additional_depth); } if (has_record) { if (EvalTraits

::betterThan(beta, cur_val)) record->setUpperBound(depth(), cur_val); } return cur_val; } assert(! is_king_in_check); King8Info king_info(state.state().Iking8Info(alt(P))); PieceMask pins = state.state().pin(alt(P)); Move checkmate_move=Move::INVALID(); Square kingSquare=state.state().template kingSquare(); if ((depth() <= 4) ? ImmediateCheckmate::hasCheckmateMove

(state.state(), king_info,kingSquare,checkmate_move) : state.isWinningStateShort

(2, checkmate_move)) { const int result = base_t::winByCheckmate(P); assert(checkmate_move.isValid()); if(has_record) { assert(state.state().isValidMove(checkmate_move)); record->setLowerBound(QSearchTraits::CheckmateSpecialDepth, result, checkmate_move); } return result; } // assert(ev.value() == eval_t(state.state()).value()); // !!! SLOW !!! if (depth() <= 0 && has_record) { if (record->threatmate.maybeThreatmate(P)) return ev.value() + base_t::threatmatePenalty(P); if (record->threatmate.mayHaveCheckmate(alt(P))) return ev.value() + base_t::threatmatePenalty(alt(P)); } const Ptype last_capture = last_move.isNormal() ? last_move.capturePtype() : PTYPE_EMPTY; const Ptype last_ptype = last_move.isNormal() ? last_move.ptype() : PTYPE_EMPTY; const bool king_escape = (last_ptype == KING) && last_capture == PTYPE_EMPTY; if ((depth() + std::min(additional_depth,2) <= -2) || (depth() <= 0 && additional_depth == 0) || (! king_escape && ((depth() + additional_depth <= 0) || (depth() <= 0 && last_capture != PTYPE_EMPTY && last_ptype != KING)))) { if (ev.progress16().value() == 15 && state.tryThreatmate() && ImmediateCheckmate::hasCheckmateMove(state.state())) return ev.value() + base_t::threatmatePenalty(P); const int base = takeBackValue

(alpha, beta, ev, last_move); #ifdef QSEARCH_LAST_CHECK_PENALTY if ((last_move.ptype() == KING) && (last_capture == PTYPE_EMPTY)) { // æœ€å¾Œã®æ‰‹ãŒçŽ‹æ‰‹å›žé¿ => ペナルティ // 銀ãらã„å–れãㆠreturn base+eval_t::captureValue(newPtypeO(alt(P), KNIGHT)); } #endif return base; } // 王手ã§ãªã‘れã°ãƒ‘スをèªã‚ã‚‹ã®ã§æœ€åˆã«é™çš„評価値を求ã‚ã‚‹ const int static_value = ((depth() <= 0) ? takeBackValue

(alpha, beta, ev, last_move) #ifdef QSEARCH_REAL_PASS : ((depthFromRoot() < QSearch2PrivateTraits::EscapeDepthFromRoot) && (! last_move.isPass())) ? passValue

(alpha, beta, ev) #endif : staticValue(ev, alpha, beta, record)) #ifndef MINIMAL + (OslConfig::evalRandom() ? HashRandom::value(state.currentHash()): 0) #endif ; assert(static_value % 2 == 0); assert(! isWinValue(alt(P), static_value)); #ifdef QSEARCH_DEBUG QuiescenceLog::staticValue(depth(), static_value); #endif if (EvalTraits

::notLessThan(static_value, cur_val)) { cur_val = static_value; if (EvalTraits

::betterThan(cur_val, alpha)) { alpha = cur_val + EvalTraits

::delta; if (has_record) { #ifndef OSL_SMP assert((record->lowerDepth() < depth()) || EvalTraits

::notLessThan(cur_val, record->lowerBound()) || in_pv); #endif record->setLowerBound(depth(), cur_val, record->bestMove()); } if (EvalTraits

::betterThan(cur_val, beta)) return cur_val; } } // åæ˜ æ¸ˆã®ã¯ãš assert(alpha == EvalTraits

::max(alpha, cur_val + EvalTraits

::delta)); assert(EvalTraits

::notLessThan(beta, alpha)); Piece last_capture_piece = Piece::EMPTY(); if (! has_record) { state.getBigramKillerMoves(moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; moves.clear(); } else { // has_record // best move const Move bestmove_in_record=record->bestMove(); if (bestmove_in_record.isNormal()) { assert(state.state().template isAlmostValidMove(bestmove_in_record)); assert(moves.empty()); moves.push_back(bestmove_in_record); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; moves.clear(); last_capture_piece = state.state().pieceOnBoard(bestmove_in_record.to()); } // killer moves MoveVector killer_moves; state.getBigramKillerMoves(killer_moves); assert(moves.empty()); MoveVector record_moves; record->loadMoves(record_moves); for (Move move: killer_moves) { if (std::find(record_moves.begin(), record_moves.end(), move) == record_moves.end()) moves.push_back(move); } record->addKillerMoves(moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; // already generated moves if (examineMoves (record, cur_val, &*record_moves.begin(), &*record_moves.end(), alpha, beta, ev, additional_depth)) return cur_val; moves.clear(); } // TakeBack 優先 assert(moves.empty()); if (((! has_record) || record->movesEmpty()) && (! last_to.isPieceStand())) { last_capture_piece = state.state().pieceOnBoard(last_to); QuiescenceGenerator

::capture(state.state(), last_capture_piece.square(), moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(),alpha, beta, ev, additional_depth)) { if (has_record) { // 後ã§é‡è¤‡ã—ã¦ã—ã¾ã†ãŒè¨˜éŒ²ã—ã¦ãれãªã„ã¨å›°ã‚‹ã®ã§ record->addKillerMoves(moves); } return cur_val; } } // è©°ã‚ã‚防止 const bool has_threatmate = has_record && record->threatmate.isThreatmate(P) #ifdef OSL_SMP && record->threatmate.threatmateMove(P).isNormal() #endif ; if (has_threatmate) { moves.clear(); QuiescenceGenerator

::breakThreatmate (state.state(), record->threatmate.threatmateMove(P), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } // å–る手 if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; if ((depth() >= QSearch2PrivateTraits::KnightCaptureDepth) || max_depth <= 2 || QSearch2Util::moreMoves(record)) { if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; } // suggested move by evaluation function { const Move suggested = ev.suggestMove(state.state()); if (suggested.isNormal()) { assert(state.state().isAlmostValidMove(suggested)); moves.clear(); moves.push_back(suggested); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) { return cur_val; } } } // 王手 const Move last2_move = state.lastMove(2); if ((depth() > 2 || (depth() > 0 && !(has_record && record->threatmate.maybeThreatmate(P))) || (last2_move.isNormal() && last2_move.capturePtype() == ROOK)) && ! (! in_pv && has_record && record->threatmate.maybeThreatmate(P))) { moves.clear(); if (has_record) QuiescenceGenerator

::check(state.state(), pins, (king_info.liberty() == 0), record->sendOffSquare

(state.state()), moves); else QuiescenceGenerator

::check(state.state(), pins, moves, (king_info.liberty() == 0)); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } const Square my_king = state.state().template kingSquare

(); if (depth() <= 0) goto finish; // futility pruning if (! in_pv && EvalTraits

::betterThan(alpha, ev.value() + (200+350+50*depth())*ev.captureValue(newPtypeO(alt(P),PAWN))/200)) goto king_walk; if ((depth() >= QSearch2PrivateTraits::AttackPinnedDepth) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::attackToPinned(state.state(), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } if ((depthFromRoot() < QSearch2PrivateTraits::DropDepthFromRoot) || (isMajorBasic(last2_move.capturePtype()) && ((depthFromRoot() < QSearch2PrivateTraits::DropDepthFromRoot+2) || (has_record && record->movesSizeLessThan(4)) )) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::dropMajorPiece3(state.state(), moves, state.historyTable()); if (last_move.isNormal() && isPiece(last_move.capturePtype()) && unpromote(last_move.capturePtype())== BISHOP && last2_move.isNormal() && last2_move.capturePtype() == BISHOP && unpromote(last2_move.ptype()) == BISHOP) // åˆã‚ã›ãŸè§’ã‚’å–ã£ãŸ { const Square drop_again = last2_move.from(); if (! state.state().template hasEffectAt(drop_again) // ã“れ以é™ã¯å¤šåˆ†å¸¸ã«true && state.state().pieceOnBoard(drop_again) == Piece::EMPTY() && state.state().template hasPieceOnStand(P)) moves.push_back(Move(drop_again, BISHOP, P)); } if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } if ((depth() >= QSearch2PrivateTraits::PawnCaptureDepth) || max_depth <= 2 || QSearch2Util::moreMoves(record)) { if (examineCapture (record, cur_val, moves, alpha, beta, ev, last_capture_piece, additional_depth)) return cur_val; } if ((depth() >= QSearch2PrivateTraits::FullPromoteDepth) || max_depth <= 2) { moves.clear(); QuiescenceGenerator

::promote(state.state(), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } else { moves.clear(); QuiescenceGenerator

::template promoteN(state.state(), moves, state.historyTable()); QuiescenceGenerator

::template promoteN(state.state(), moves, state.historyTable()); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; moves.clear(); QuiescenceGenerator

::template promoteN(state.state(), moves, state.historyTable()); QuiescenceGenerator

::template promoteN(state.state(), moves, state.historyTable()); QuiescenceGenerator

::template promoteN(state.state(), moves, state.historyTable()); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } if (depthFromRoot() < QSearch2PrivateTraits::EscapeDepthFromRoot) { { moves.clear(); QuiescenceGenerator

::escapeAll(state.state(), moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } else if ((depthFromRoot() < QSearch2PrivateTraits::EscapeFromLastMoveDepthFromRoot) || (last_move.isDrop() && isMajorBasic(last_move.ptype())) || (last_move.isNormal() && last2_move.isNormal() && isMajor(last2_move.ptype()) && state.state().hasEffectByPiece (state.state().pieceOnBoard(last_to), last2_move.to())) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::template escapeFromLastMove(state.state(), last_move, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } if ((depthFromRoot() < QSearch2PrivateTraits::AttackMajorPieceDepthFromRoot) || (isMajor(last_move.ptype()) && last_move.isCapture() && last_to.template canPromote

()) || (state.state().hasEffectAt(P, last_to) && (state.state(). template hasEffectByPtype(alt(P), last_to))) || ((depthFromRoot() < QSearch2PrivateTraits::AttackMajorPieceDepthFromRoot+2) && ((last2_move.capturePtype()==KNIGHT) || (last2_move.capturePtype()==LANCE) || (last2_move.capturePtype()==BISHOP))) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::attackMajorPiece(state.state(), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } { const QuiescenceRecord *parent = (state.hasLastRecord(1) && state.lastRecord(1)) ? &(state.lastRecord(1)->qrecord) : 0; if ((depthFromRoot() < QSearch2PrivateTraits::AttackKing8DepthFromRoot) || (last_move.isNormal() && last_move.ptype() == KING && last_move.isCapture()) || (((parent && parent->threatmate.isThreatmate(alt(P))) || (king_info.liberty() == 0)) && depthFromRoot() < 2+QSearch2PrivateTraits::AttackKing8DepthFromRoot) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::attackKing8(state.state(), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } } if ((depthFromRoot() < QSearch2PrivateTraits::AttackGoldSilverDepthFromRoot) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::attackGoldWithPawn(state.state(), pins, moves); QuiescenceGenerator

::attackSilverWithPawn(state.state(), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } if ((depthFromRoot() < QSearch2PrivateTraits::AttackKnightDepthFromRoot) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::attackKnightWithPawn(state.state(), pins, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } if ((depth() >= QSearch2PrivateTraits::UtilizePromotedDepth) || QSearch2Util::moreMoves(record)) { if (last2_move.isNormal()) { const Piece last_piece = state.state().pieceOnBoard(last2_move.to()); assert(last_piece.isPiece()); if (last_piece.owner() == P) { moves.clear(); QuiescenceGenerator

::utilizePromoted(state.state(), last_piece, moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } } if ((depthFromRoot() < QSearch2PrivateTraits::AdvanceBishopDepthFromRoot) || QSearch2Util::moreMoves(record)) { { moves.clear(); QuiescenceGenerator

::advanceBishop(state.state(), moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } king_walk: if (has_threatmate || (! my_king.template canPromote() //自陣以外 && last2_move.isNormal() && last2_move.ptype() == KING)) { { moves.clear(); QuiescenceGenerator

::kingWalk(state.state(), moves); if (examineMoves (record, cur_val, &*moves.begin(), &*moves.end(), alpha, beta, ev, additional_depth)) return cur_val; } } finish: // cut ã—ãªã‹ã£ãŸ assert(EvalTraits

::betterThan(beta, cur_val)); assert(! isWinValue(alt(P), cur_val)); #ifndef DONT_USE_CHECKMATE const bool threatmate = EvalTraits

::betterThan(ev.captureValue(newPtypeO(P,KING)), cur_val); int check_after_threatmate = 0; if (in_pv && (threatmate || (check_after_threatmate = state.countCheckAfterThreatmate(alt(P),2)))) { // test sudden checkmate int checkmate_nodes = (node_count - node_count_before)/2; if (check_after_threatmate) { if (depthFromRoot() == 1) { const int sacrifice = state.countCheckAfterThreatmateSacrifice(alt(P),2); checkmate_nodes = std::max(checkmate_nodes, sacrifice*125+check_after_threatmate*50); } else { checkmate_nodes = std::max(50, checkmate_nodes); } } if (threatmate) { if (! has_record) record = qallocate(table, state.currentHash(), allocate_depth_in_threatmate, state); checkmate_nodes = std::max(checkmate_nodes, 200); } Move check_move; const bool win = (record && checkmate_nodes >= 50) ? state.isWinningState

(record->checkmateNodesLeft(checkmate_nodes), checkmate_move) : (((record && record->checkmateNodesLeft(2)) || (! has_record && threatmate)) ? state.isWinningStateShort

(2, checkmate_move) : false); if (win) { const int result = base_t::winByCheckmate(P); assert(checkmate_move.isValid()); if (! has_record && ! record) record = qallocate(table, state.currentHash(), allocate_depth_in_threatmate, state); if (has_record || record) { assert(state.state().isValidMove(checkmate_move)); record->setLowerBound(QSearchTraits::CheckmateSpecialDepth, result, checkmate_move); } return result; } } #if 0 // cache ãŒãªã„ã¨é‡ã„ã®ã§ã¨ã‚Šã‚ãˆãšoff // ã—ょã†ãŒãªã„ã®ã§è©°å°†æ£‹ (シミュレーションã®ã¿) を呼㶠if (! has_record) { assert(! record); Move checkmate_move=Move::INVALID(); AttackOracleAges oracle_age_dummy; const bool win_found // TODO: last move ã®ã¿ã¨ã©ã¡ã‚‰ãŒè‰¯ã„? = state.isWinningState

(0, checkmate_move, oracle_age_dummy); if (win_found) { const int result = base_t::winByCheckmate(P); assert(checkmate_move.isValid()); record = qallocate(table, state.currentHash(), allocate_depth_in_threatmate, state); if (record) { record->setLowerBound(QSearchTraits::CheckmateSpecialDepth, result, checkmate_move); } return result; } } #endif #endif if (has_record) { if (EvalTraits

::betterThan(beta, cur_val)) record->setUpperBound(depth(), cur_val); } return cur_val; } namespace osl { inline bool importantMove(const NumEffectState& state, Move move, Square my_king, Square op_king) { if (move.ptype() == KING) return true; my_king = Centering3x3::adjustCenter(my_king); op_king = Centering3x3::adjustCenter(op_king); if (Neighboring8Direct::hasEffect(state, move.ptypeO(), move.to(), op_king) || Neighboring8Direct::hasEffect(state, move.ptypeO(), move.to(), my_king)) return true; return move.isCapture() && ((! move.isDrop() && state.longEffectAt(move.from()).any()) || Neighboring8Direct::hasEffect(state, move.capturePtypeO(), move.to(), my_king) || Neighboring8Direct::hasEffect(state, move.capturePtypeO(), move.to(), op_king)); } } template template bool osl::search::QuiescenceSearch2:: examineTakeBack(const MoveVector& moves, int& cur_val, int& alpha, int beta, eval_t const& ev) { assert(alpha % 2); assert(beta % 2); assert(EvalTraits

::betterThan(alpha, cur_val)); assert(EvalTraits

::notLessThan(beta, alpha)); const Square my_king = state.state().template kingSquare

(); const Square op_king = state.state().template kingSquare(); for (Move move: moves) { #ifdef QSEARCH_DEBUG QuiescenceLog::pushMove(depth(), move, 0); #endif const int see = See::see(state.state(), move, state.state().pin(P), state.state().pin(alt(P)), &eval_t::Piece_Value); int result; if (see > 0 && importantMove(state.state(), move, my_king, op_king)) { eval_t new_ev = ev; // TODO: futility pruning here typedef QSearch2NextTakeBack helper_t; helper_t helper(result, this, alpha, beta, new_ev, move); // 表を使ã‚ãªã„ã®ã§cast state.doUndoMoveLight(move, helper); } else { result = ev.value() + see*eval_t::seeScale()*EvalTraits

::delta; } // 安ã„é †ã«sortã—ãŸã®ã§ä¸€ç›´ç·šã«èª­ã‚€ 王手回é¿ã¯ã™ã‚‹ if (! base_t::isWinValue(alt(P), result)) { cur_val = EvalTraits

::max(cur_val, result); return EvalTraits

::notLessThan(result, beta); } } assert(EvalTraits

::betterThan(beta, cur_val)); return false; } template template bool osl::search::QuiescenceSearch2:: examineTakeBack2(const MoveVector& moves, QuiescenceThreat& threat2, QuiescenceThreat& threat1, int beta1, int beta2, eval_t const& ev) { if (moves.empty()) return false; // P ã¯å–ã‚‹å´ using move_classifier::Check; using move_classifier::MoveAdaptor; assert(beta1 % 2); assert(beta2 % 2); assert(EvalTraits

::notLessThan(threat1.value, threat2.value)); // threat1 >= threat2 assert(EvalTraits

::betterThan(beta1, threat1.value)); // beta1 > threat1 assert(EvalTraits

::betterThan(beta2, threat2.value)); // beta2 > threat2 assert(EvalTraits

::notLessThan(beta1, beta2)); // beta1 >= beta2 assert(state.state().turn() == P); const Square my_king = state.state().template kingSquare

(); const Square op_king = state.state().template kingSquare(); int best_value = threat2.value; for (Move move: moves) { const Square to = move.to(); assert(! ShouldPromoteCut::canIgnoreAndNotDrop

(move)); if (calm_move_only && (state.state().countEffect(alt(P),to) > state.state().countEffect(P,to))) continue; #ifdef QSEARCH_DEBUG QuiescenceLog::pushMove(depth(), move, 0); #endif int result; const int see = See::see(state.state(), move, state.state().pin(P), state.state().pin(alt(P)), &eval_t::Piece_Value); if (see > 0 && importantMove(state.state(), move, my_king, op_king)) { eval_t new_ev = ev; // TODO: futility pruning here const int beta = EvalTraits

::notLessThan(threat1.value, beta2) ? beta2 : beta1; typedef QSearch2NextTakeBack helper_t; helper_t helper(result, this, threat2.value+EvalTraits

::delta, beta, new_ev, move); state.doUndoMoveLight(move, helper); } else { result = ev.value() + see*eval_t::seeScale()*EvalTraits

::delta; } // first_normal_move_only:安ã„é †ã«sortã—ãŸã®ã§ä¸€ç›´ç·šã«èª­ã‚€ (王手回é¿ã¯ã™ã‚‹) if (base_t::isWinValue(alt(P), result)) continue; // çµ‚äº†å‡¦ç† if (EvalTraits

::betterThan(result, best_value)) { best_value = result; if (EvalTraits

::notLessThan(best_value, threat1.value)) { threat2 = threat1; threat1 = QuiescenceThreat(best_value, move); if (EvalTraits

::betterThan(threat1.value, beta1) || EvalTraits

::betterThan(threat2.value, beta2)) return true; } else { assert(EvalTraits

::notLessThan(best_value, threat2.value)); threat2 = QuiescenceThreat(best_value, move); if (EvalTraits

::betterThan(threat2.value, beta2)) return true; } } if (first_normal_move_only) break; } return false; // å–ã‚Šè¿”ã™æ‰‹ã§cutã—ãªã‹ã£ãŸå ´åˆ: // 逃ã’られãªã„è„…å¨ã®è©•価 (Opponent ãŒé€ƒã’ã‚‹) // 逃ã’られãªã„å ´åˆã¯threat1 ã ã‘ã§ãªãthreat2ã«ã‚‚setã™ã‚‹ assert(! moves.empty()); if (! EvalTraits

::betterThan(best_value, threat2.value)) return false; const Move threat_move = *moves.begin(); if (! first_normal_move_only) { assert(state.lastMove().isPass()); state.popPass(); bool cut_by_threat2 = false; // æˆã‚‹æ‰‹ãŒé˜²ã’ã‚‹ã‹? TODO: é•·ã„利ãã‚’è¿‘ãã§æ­¢ã‚ã‚‹ const Player Opponent = alt(P); MoveVector moves; move_generator::GenerateAddEffectWithEffect::generate (Opponent, state.state(), threat_move.to(), moves); if (moves.empty()) { threat2 = QuiescenceThreat(best_value, threat_move); if (EvalTraits

::betterThan(threat2.value, beta2)) cut_by_threat2 = true; } state.pushPass(); return cut_by_threat2; } else if ((depthFromRoot() < QSearch2PrivateTraits::EscapeFromLastMoveDepthFromRoot) || (unpromote(moves[0].capturePtype()) == ROOK) || (unpromote(moves[0].capturePtype()) == BISHOP)) { assert(state.lastMove().isPass()); state.popPass(); bool cut_by_threat2 = false; const Square to = threat_move.to(); const Piece target = state.state().pieceOnBoard(to); bool tried_escape = (depthFromRoot() < QSearch2PrivateTraits::EscapeDepthFromRoot); #ifdef QSEARCH_PESSIMISTIC_ESCAPE_THREAT if (state.lastMove().isNormal()) { // ç›´å‰ã®åˆ©ãã¯é€ƒã’ã¦ã„ã‚‹ã¯ãšãªã®ã§ï¼Œãƒ‘ス㯠pessimistic ã« // TODO: escapeFromOtherThanPawnã«åˆã‚ã›ã¦ hasEffectIf ã«å¤‰æ›´ const Offset32 offset32(to, state.lastMove().to()); const EffectContent effect = Ptype_Table.getEffect(state.lastMove().ptypeO(),offset32); tried_escape = effect.hasEffect(); } #endif if (! tried_escape) { const Player Opponent = alt(P); MoveVector escape; const bool safe_escape = QuiescenceGenerator::escapeByMoveOnly(state.state(), target, escape); if (safe_escape) goto finish; for (Move move: escape) { eval_t new_ev = ev; new_ev.update(state.state(), Move::PASS(P)); int result; if (isMajor(move.ptype())) { typedef QSearch2TakeBackOrChase helper_t; helper_t helper(result, this, best_value+EvalTraits::delta, threat2.value+EvalTraits

::delta, new_ev, move); state.doUndoMoveLight(move, helper); } else { typedef QSearch2NextTakeBack helper_t; helper_t helper(result, this, best_value+EvalTraits::delta, threat2.value+EvalTraits

::delta, new_ev, move); state.doUndoMoveLight(move, helper); } if (EvalTraits::betterThan(result, best_value)) { best_value = result; if (EvalTraits::notLessThan(result, threat2.value)) break; } } } if (EvalTraits

::betterThan(best_value, threat2.value)) { threat2 = QuiescenceThreat(best_value, threat_move); if (EvalTraits

::betterThan(threat2.value, beta2)) { cut_by_threat2 = true; goto finish; } } finish: state.pushPass(); return cut_by_threat2; } return false; } template template int osl::search::QuiescenceSearch2:: takeBackOrChase(int alpha, int beta, eval_t const& ev, Move last_move) { assert(last_move.isNormal()); int best_value = takeBackValue

(alpha, beta, ev, last_move); if (EvalTraits

::betterThan(best_value, beta)) return best_value; MoveVector moves; QuiescenceGenerator

::capture1(state.state(), last_move.from(), moves); if (moves.empty()) return best_value; for (Move move: moves) { eval_t new_ev = ev; typedef QSearch2SafeEscape helper_t; helper_t helper(&state.state(), state.state().pieceOnBoard(last_move.to()), new_ev, move); state.doUndoMoveLight(move, helper); if (helper.is_invalid) continue; int result = new_ev.value(); if (! helper.has_safe_escape) result += new_ev.captureValue(last_move.ptypeO()); if (state.state().template hasEffectByPtype(P, move.from())) result += (new_ev.captureValue(newPtypeO(alt(P),PROOK)) - new_ev.captureValue(newPtypeO(alt(P),ROOK))); best_value = EvalTraits

::max(result, best_value); break; // 追撃ã¯ä¸€æ‰‹ã ã‘試㙠} return best_value; } template template int osl::search::QuiescenceSearch2:: takeBackValue(int alpha, int beta, eval_t const& ev, Move last_move) { assert(alpha % 2); assert(beta % 2); ++node_count; assert(EvalTraits

::notLessThan(beta, alpha)); if (state.state().inCheck(alt(P))) return base_t::winByFoul(P); if (last_move.isPass()) return ev.value(); const Square last_to = last_move.to(); MoveVector moves; const Piece last_move_piece = state.state().pieceOnBoard(last_to); int cur_val; if (state.state().inCheck()) { const bool check_by_lance = state.state().template hasEffectByPtypeStrict (alt(P), state.state().template kingSquare

()); const bool has_safe_move = QuiescenceGenerator

::escapeKingInTakeBack(state.state(), moves, check_by_lance); cur_val = (has_safe_move ? currentValueWithLastThreat(ev, last_move_piece) : base_t::winByCheckmate(alt(P))); assert(cur_val % 2 == 0); } else { cur_val = currentValueWithLastThreat(ev, last_move_piece); assert(cur_val % 2 == 0); if (EvalTraits

::betterThan(cur_val, beta)) // generate ã®çœç•¥ return cur_val; QuiescenceGenerator

::capture1(state.state(), last_move_piece.square(), moves); } if (EvalTraits

::betterThan(cur_val, alpha)) { alpha = cur_val + EvalTraits

::delta; if (EvalTraits

::betterThan(cur_val, beta)) { return cur_val; } } assert(EvalTraits

::betterThan(alpha, cur_val)); if (examineTakeBack

(moves, cur_val, alpha, beta, ev)) { assert(cur_val % 2 == 0); return cur_val; } // cut ã—ãªã‹ã£ãŸ assert(cur_val % 2 == 0); return cur_val; } template template int osl::search::QuiescenceSearch2:: staticValueWithThreat(eval_t const& ev, int alpha, QuiescenceThreat& threat1, QuiescenceThreat& threat2) { assert(alpha % 2); assert(! state.state().inCheck()); const int static_value = ev.value(); if (EvalTraits

::notLessThan(alpha, static_value)) return static_value; const Player O = alt(P); const int FirstThreat = QSearchTraits::FirstThreat; const int SecondThreat = (depthFromRoot() < QSearch2PrivateTraits::EscapeDepthFromRoot) ? 1 : QSearchTraits::SecondThreat; const int o_beta1 = (EvalTraits::min(base_t::winByCheckmate(O), static_value - FirstThreat*(static_value - alpha)) - ((FirstThreat % 2) ? 0 : EvalTraits::delta)); const int o_beta2 = (EvalTraits::min(base_t::winByCheckmate(O), static_value - SecondThreat*(static_value - alpha)) - ((SecondThreat % 2) ? 0 : EvalTraits::delta)); threat1.value = static_value; threat2.value = static_value; assert(state.state().turn() == P); state.pushPass(); assert(! state.state().inCheck()); assert(EvalTraits::betterThan(o_beta1, threat1.value)); assert(EvalTraits::betterThan(o_beta2, threat1.value)); assert(EvalTraits::notLessThan(o_beta1, o_beta2)); EvalT ev2(ev); ev2.update(state.state(), Move::PASS(P)); MoveVector moves; if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; // æˆã‚‹æ‰‹ã¯é£›è»Šã¨è§’ã¨æ­© (TODO: 玉ã®è¿‘å‚) QuiescenceGenerator::template promoteN(state.state(), moves, state.historyTable()); if (examineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; moves.clear(); QuiescenceGenerator::template promoteN(state.state(), moves, state.historyTable()); if (examineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; moves.clear(); QuiescenceGenerator::template promoteN(state.state(), moves, state.historyTable()); if (examineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; moves.clear(); if (depth() >= QSearch2PrivateTraits::PawnCaptureDepth || max_depth <= 2) { if (generateAndExamineTakeBack2(moves, threat2, threat1, o_beta1, o_beta2, ev2)) goto finish; } finish: state.popPass(); // handle the first threat more seriously in some condition if (threat1.move == threat2.move && threat1.move.isNormal()) { const Piece target = state.state().pieceOnBoard(threat1.move.to()); if (isMajorBasic(target.ptype()) && target.square().template canPromote()) { assert(alt(target.owner()) == O); assert(threat1.value % 2 == 0); return threat1.value; } } // usual KFEND-like threat handling const int result1 = (static_value - (static_value - threat1.value)/FirstThreat); const int result2 = (static_value - (static_value - threat2.value)/SecondThreat); const int result = EvalTraits::max(result1, result2) & (~0x1); assert(result % 2 == 0); return result; } #endif /* OSL_QUIESCENCESEARCH2_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchRecorder.h0000644000000000000000000001330612316770314020557 0ustar rootroot/* searchRecorder.h */ #ifndef _MTDF_RECORDER_H #define _MTDF_RECORDER_H #include "osl/numEffectState.h" #include "osl/misc/lightMutex.h" #include namespace osl { class MoveLogProb; namespace search { /** * recorder of MTDF/AlphaBeta * * destructor ã¯virtualã«ã™ã‚‹ã“ã¨ã§ç®¡ç†ã‚’容易ã«ã™ã‚‹ï¼Ž * method ã¯virtualã«*ã—ãªã„*ã“ã¨ã§ï¼Œã‚­ãƒ£ã‚¹ãƒˆã—ãŸã‚‰ä¸Šä½ã‚¯ãƒ©ã‚¹ã¨ã—㦠* 振る舞ã†ã‚ˆã†ã«ã™ã‚‹ï¼Ž */ class CountRecorder { size_t node_count; size_t quiescence_count; size_t checkmate_count; #ifdef OSL_SMP mutable LightMutex mutex; #endif public: CountRecorder(); virtual ~CountRecorder(); /** 探索ã®é€”中終了ã§ä½¿ãˆã‚‹ã‚ˆã†ã«å¿…ãšæ•°ãˆã‚‹ */ void addNodeCount(int count=1) { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif node_count += count; } void addQuiescenceCount(int count=1) { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif quiescence_count += count; } void addCheckmateCount(int count=1) { #ifdef OSL_SMP SCOPED_LOCK(lk,mutex); #endif checkmate_count += count; } void setCheckmateCount(int count) { #ifdef OSL_SMP SCOPED_LOCK(lk,mutex); #endif checkmate_count = count; } void resetNodeCount(); size_t nodeCount() const { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif return node_count; } size_t quiescenceCount() const { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif return quiescence_count; } size_t checkmateCount() const { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif return checkmate_count; } size_t searchNodeCount() const { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif return node_count + quiescence_count; } size_t allNodeCount() const { #if (defined OSL_SMP) && (defined OSL_USE_RACE_DETECTOR) SCOPED_LOCK(lk,mutex); #endif return node_count + quiescence_count + checkmate_count; } double checkmateRatio() const { const double checkmate = checkmateCount(); const double search = searchNodeCount(); return checkmate / (checkmate + search); } /** recordValue ã¨ã‚»ãƒƒãƒˆã§å‘¼ã¶ */ void tryMove(const MoveLogProb& /*m*/, int /*last_f*/, int /*limit*/) const {} /** recordValue ã¨ã‚»ãƒƒãƒˆã§å‘¼ã¶ */ void retryMove(const MoveLogProb& /*m*/, int /*last_f*/, int /*limit*/, int /*retryCount*/) const {} /** tryMove ã¨ã‚»ãƒƒãƒˆã§å‘¼ã¶ */ void recordValue(const MoveLogProb&, int /*val*/, bool /*better_move*/, int /*limit*/) const {} /** ä¸»ã«æ•°ã®è¨˜éŒ²ç”¨ */ void recordTopLevelLowFail(const MoveLogProb& /* best */, int /*last_f*/) const {} void recordTopLevelHighFail(const MoveLogProb& /*best */, int /*last_f*/) const {} void tableHitLowerBound(Player, int, int /*last_f*/, int /*limit*/) const {} void tableHitUpperBound(Player, int, int /*last_f*/, int /*limit*/) const {} void tableStoreLowerBound(Player, const MoveLogProb&, int, int) const {} void tableStoreUpperBound(Player, const MoveLogProb&, int, int) const {} void startSearch(int /*limit*/) const {} /** ã“れã¯é…ãã¦ã‚‚æ°—ã«ã—ãªã„ */ virtual void finishSearch(Move best, double seconds_consumed, bool verbose) const; void recordInvalidMoveInTable(const SimpleState&, const MoveLogProb&, int limit) const; void newCategory(const char * /*name*/, int /*limit*/) const {} /** 詰将棋無é™ãƒ«ãƒ¼ãƒ—発見用 */ void gotoCheckmateSearch(const SimpleState&, int) const {} void backFromCheckmateSearch() const {} void reportCount(std::ostream&, double seconds) const; void reportCount(std::ostream&) const; }; class SearchRecorder : public CountRecorder { struct Recorder; /** hide implementation */ std::unique_ptr recorder; public: explicit SearchRecorder(const char *filename="mtdf.log"); ~SearchRecorder(); /** ã©ã®ç¨‹åº¦æ·±ã記録をå–ã‚‹ã‹æŒ‡ç¤º */ void setLogMargin(int margin=500); void tryMove(const MoveLogProb& m, int last_f, int limit) const; void retryMove(const MoveLogProb& m, int last_f, int limit, int retryCount) const; void recordValue(const MoveLogProb& m, int val, bool betterMove, int limit) const; void tableHitLowerBound(Player p, int val, int last_f, int limit) const; void tableHitUpperBound(Player p, int val, int last_f, int limit) const; void tableStoreLowerBound(Player p, const MoveLogProb& best_move, int val, int limit) const; void tableStoreUpperBound(Player p, const MoveLogProb& best_move, int val, int limit) const; void recordTopLevelLowFail(const MoveLogProb& /* best */, int last_f) const; void recordTopLevelHighFail(const MoveLogProb& best_move, int last_f) const; void startSearch(int limit) const; void finishSearch(Move best_move, double seconds_consumed, bool verbose) const; void newCategory(const char *name, int limit) const; void gotoCheckmateSearch(const SimpleState&, int nodeLimit) const; void backFromCheckmateSearch() const; /** ログã«ãƒ¡ãƒƒã‚»ãƒ¼ã‚¸ã‚’æ··ãœãŸã„ã¨ãã«ä½¿ã† */ std::ostream& stream() const; }; } // namespace search using search::CountRecorder; using search::SearchRecorder; } // namespace osl #endif /* _MTDF_RECORDER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/timeControl.h0000644000000000000000000000056012316770314020121 0ustar rootroot/* timeControl.h */ #ifndef _SEARCH_TIMECONTROL_H #define _SEARCH_TIMECONTROL_H namespace osl { namespace search { struct TimeControl { static int secondsForThisMove(int total_seconds); }; } // namespace search } // namespace osl #endif /* _SEARCH_TIMECONTROL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/killerMoveTable.h0000644000000000000000000000265512316770314020712 0ustar rootroot/* killerMoveTable.h */ #ifndef OSL_KILLERMOVETABLE_H #define OSL_KILLERMOVETABLE_H #include "osl/search/lRUMoves.h" #include "osl/numEffectState.h" #include #include namespace osl { namespace search { /** * å˜ç´”ãªkiller move * * æ·±ã•ã”ã¨ã®æœ€å–„手を登録ã™ã‚‹ï¼Žãƒ†ãƒ¼ãƒ–ルã«ç™»éŒ²ã•れã¦ã„ãªã„å±€é¢ã§ï¼Œ * 「自分ãŒä½•を指ãã†ãŒç›¸æ‰‹ã‹ã‚‰ã“ã†æŒ‡ã•れるã¨å›°ã‚‹ã€ã¨è¨€ã†ã¨ãã«æœ‰ * 効.最善ã®åˆ¤å®šã¯ã„ã„加減ã§ï¼Œãã®æ·±ã•ã§æœ€å¾Œã«bestMoveã¨ã—ã¦ç™ºè¦‹ã•れãŸmove */ class KillerMoveTable { public: static const int KillerMoveMax = 64; private: CArray killer_moves; public: KillerMoveTable(); ~KillerMoveTable(); void clear(); void setMove(size_t depth, const Move& move) { assert(move.isValid()); killer_moves[depth].setMove(move); } void getMove(const NumEffectState& state, size_t depth, MoveVector& out) const { const LRUMoves& moves = killer_moves[depth]; for (size_t i=0; i(m)) out.push_back(m); } } }; } // namespace search } // namespace osl #endif /* OSL_KILLERMOVETABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/killerMoveTable.cc0000644000000000000000000000067112316770314021044 0ustar rootroot/* killerMoveTable.cc */ #include "osl/search/killerMoveTable.h" osl::search:: KillerMoveTable::KillerMoveTable() { clear(); } osl::search:: KillerMoveTable::~KillerMoveTable() { } void osl::search:: KillerMoveTable::clear() { for (LRUMoves& l: killer_moves) l.clear(); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceRecord.cc0000644000000000000000000000311712316770314021244 0ustar rootroot/* quiescenceRecord.cc */ #include "osl/search/quiescenceRecord.h" #include "osl/csa.h" #include #include #ifndef MINIMAL void osl::search:: QuiescenceRecord::dump(std::ostream& os) const { os << "QuiescenceRecord " << this << "\n"; os << lower_bound << " (" << (int)lower_depth << ")" << upper_bound << " (" << (int)upper_depth << ")"; if (hasStaticValue()) { os << " s " << static_value << toString(staticValueType()); os << " t1 " << threat1.value << " " << csa::show(threat1.move) << " t2 " << threat2.value << " " << csa::show(threat2.move); } os << "\n"; os << "checkmate read " << checkmate_nodes << "\t" << "threatmate read " << threatmate_nodes << "\n"; os << "best move " << csa::show(bestMove()) << "\n"; os << "threatmate " << threatmate << "\n"; os << "sendoffs " << (unsigned int)threatmate.sendoffs << "\n"; os << "moves " << moves_size(); size_t i=0; MoveVector moves_copy; loadMoves(moves_copy); for (MoveVector::const_iterator p=moves_copy.begin(); p!=moves_copy.end(); ++p, ++i) { os << " " << csa::show(*p); if (i % 8 == 7) os << "\n"; } if (i % 8 != 7) os << "\n"; } const char *osl::search:: QuiescenceRecord::toString(StaticValueType type) { switch (type) { case UNKNOWN: return "?"; case UPPER_BOUND: return ">"; case EXACT: return "="; default: assert(0); } return "!"; // should not occur } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/interimReport.h0000644000000000000000000000367512335610143020471 0ustar rootroot/* interimReport.h */ #ifndef OSL_INTERIMREPORT_H #define OSL_INTERIMREPORT_H #include "osl/basic_type.h" #include #include #include #include #include namespace osl { namespace search { constexpr int usi_pawn_value = 100; constexpr int usi_win_value = usi_pawn_value*300; struct PVInfo { volatile int depth, score; volatile double elapsed; std::vector moves; PVInfo() : depth(0), score(0), elapsed(0.0) {} void clear() { moves.clear(); } void push_back(const std::string& m) { moves.push_back(m); } bool empty() const { return moves.empty(); } size_t size() const { return moves.size(); } const std::string& operator[](size_t i) const { assert(i pv_table; struct InterimReport { int owner; PVInfo pv; pv_table alternatives; std::string last_string, result_line; /** sign of best_value: relative in UsiSlave, fixed in SearchNode */ volatile int depth_head; volatile int64_t node_count; volatile double elapsed; volatile bool stopped, aborted, last_message_ignored; explicit InterimReport(int owner=-1); ~InterimReport(); /** @return importance on search tree */ bool updateByInfo(const std::string& line, int id); void finished(const std::string& line); std::string composeInfo(bool negate_score=false) const; std::string joinPV() const; std::string makeSearchResult() const; void set(osl::Player turn, const InterimReport&); bool finishedNormally() const { return ! stopped && ! aborted; } int bestValue() const { return pv.score; } static std::function info, warn, error; }; } } #endif /* OSL_INTERIMREPORT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta3.h0000644000000000000000000000726412316770314017576 0ustar rootroot/* alphaBeta3.h */ #ifndef OSL_ALPHABETA3_H #define OSL_ALPHABETA3_H #include "osl/numEffectState.h" #include "osl/search/searchTimer.h" #include "osl/search/fixedEval.h" // temporal #include "osl/search/searchState2.h" #include "osl/eval/openMidEndingEval.h" #include "osl/eval/progressEval.h" namespace osl { namespace search { class CountRecorder; class SimpleHashTable; struct MoveWithComment; class AlphaBeta3 : public SearchTimer, FixedEval { public: // interface required for game_playing::SearchPlayer typedef SearchState2::checkmate_t checkmate_t; typedef eval::ml::OpenMidEndingEval eval_t; // typedef eval::PieceEval eval_t; // typedef eval::ProgressEval eval_t; AlphaBeta3(const NumEffectState& s, checkmate_t& checker, SimpleHashTable *t, CountRecorder&); ~AlphaBeta3(); Move computeBestMoveIteratively(int limit, int step, int initial_limit=600, size_t node_limit=1600000, const TimeAssigned& assign=TimeAssigned(milliseconds(60*1000)), MoveWithComment *additional_info=0); bool isReasonableMove(Move move, int pawn_sacrifice=1); void setRootIgnoreMoves(const MoveVector *rim, bool); void setHistory(const MoveStack& h); void enableMultiPV(unsigned int) {} static void showNodeDepth(std::ostream&); static void clearNodeDepth(); // original staff enum MoveCategory { Initial, KingEscape, Pass, TakeBack, Capture, Killer, CaptureAll, All }; enum { MaxDepth = 64 }; enum NodeType { PvNode = 0, CutNode = 1, AllNode = -1 }; struct SearchInfo; struct PVInfo { Move move; int height; bool in_check; }; struct PVVector : public FixedCapacityVector { void setPV(Move m, const SearchInfo&, const PVVector&); }; struct SearchInfo { SearchInfo(); // input // (modified: alpha, node_type, eval) Move moved; HashKey hash_key; PathEncoding path; int height, extended; int alpha, beta; NodeType node_type; eval_t eval; // before moved // output int search_value; int moves_tried; bool in_check; PVVector pv; // work area MoveVector moves; MoveCategory move_type; unsigned int move_index; }; private: template struct CallSearch; template struct CallQuiesce; friend struct CallSearch; friend struct CallSearch; friend struct CallQuiesce; friend struct CallQuiesce; Move searchRoot(int limit); template int makeMoveAndSearch(Move, int consume); template void presearch(); template void search(); template Move nextMove(); template void quiesceRoot(); template int makeMoveAndQuiesce(Move); template void quiesce(); private: volatile int stop_by_alarm; NumEffectState state; int depth; CountRecorder& recorder; SimpleHashTable *table_common; public: // public for test template static void generateAllMoves(const NumEffectState& state, const SearchInfo&, SearchInfo&); template static void generateCapture(const NumEffectState& state, SearchInfo&); template static void generateCaptureAll(const NumEffectState& state, SearchInfo&); template static bool seePlusLight(const NumEffectState& state, Move m); private: bool reductionOk() const; int evalValue() const; }; } using search::AlphaBeta3; } #endif /* OSL_ALPHABETA3_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/lRUMoves.h0000644000000000000000000000240212316770314017333 0ustar rootroot/* lRUMoves.h */ #ifndef OSL_SEARCH_LRUMOVES_H #define OSL_SEARCH_LRUMOVES_H #include "osl/basic_type.h" #include "osl/container.h" #ifdef OSL_SMP # include "osl/misc/lightMutex.h" #endif namespace osl { namespace search { class LRUMoves { typedef CArray moves_t; moves_t moves; #ifdef OSL_SMP typedef osl::misc::LightMutex Mutex; mutable Mutex mutex; #endif public: LRUMoves() {} LRUMoves(const LRUMoves& src) : moves(src.moves) { } LRUMoves& operator=(const LRUMoves& src) { if (this != &src) moves = src.moves; return *this; } void clear() { #ifdef OSL_SMP SCOPED_LOCK(lk,mutex); #endif moves.fill(Move::INVALID()); } void setMove(Move best_move) { #ifdef OSL_SMP SCOPED_LOCK(lk,mutex); #endif if (best_move.isNormal() && moves[0] != best_move) { moves[1] = moves[0]; moves[0] = best_move; } } const Move operator[](size_t i) const { #ifdef OSL_USE_RACE_DETECTOR SCOPED_LOCK(lk,mutex); #endif return moves[i]; } static size_t size() { return moves_t::size(); } }; } } // namespace osl #endif /* OSL_SEARCH_LRUMOVES_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveGenerator.h0000644000000000000000000001123512316770314020440 0ustar rootroot/* moveGenerator.h */ #ifndef OSL_MOVEGENERATOR_H #define OSL_MOVEGENERATOR_H #include "osl/search/simpleHashRecord.h" #include "osl/search/searchState2.h" #include "osl/rating/ratingEnv.h" #include "osl/progress.h" #include "osl/container/moveLogProbVector.h" #include "osl/container/moveStack.h" namespace osl { namespace search { namespace analyzer { class CategoryMoveVector; } class SearchState2; class MoveMarker { typedef uint8_t value_t; CArray2d marker; value_t cur; public: MoveMarker(); void clear(); static unsigned int pieceIndex(const NumEffectState& state, Move m) { if (m.isPass() || m.isDrop()) return Piece::SIZE*2+m.ptype(); int base = state.pieceOnBoard(m.from()).number(); if (m.isPromotion()) return base+ Piece::SIZE; return base; } static unsigned int toIndex(Move m) { return m.to().index()-Square::onBoardMin().index(); } void registerMove(const NumEffectState& state, Move m) { marker[toIndex(m)][pieceIndex(state,m)] = cur; } bool registerIfNew(const NumEffectState& state, Move m); bool registered(const NumEffectState& state, Move m) const; }; class MoveGenerator { enum State { INITIAL, KING_ESCAPE, TAKE_BACK, BREAK_THREATMATE, CAPTURE, TACTICAL_FINISH, TESUJI, ALL, FINISH }; typedef void (MoveGenerator::*generator_t)(const SearchState2&); static const CArray2d Generators; static const CArray GeneratorNames; MoveLogProbVector moves; int cur_state; size_t cur_index; const SimpleHashRecord *record; int limit; int tried; MoveMarker marker; RatingEnv env; Progress32 progress; Move eval_suggestion; #ifndef MINIMAL bool in_quiesce; #endif bool in_pv; public: MoveGenerator(); template void init(int limit, const SimpleHashRecord *record, const EvalT&, const NumEffectState&, bool in_pv, Move hash_move, bool quiesce=false); /** @param P turn */ template const MoveLogProb nextTacticalMove(const SearchState2& state) { assert(cur_state < TACTICAL_FINISH); if (cur_index < moves.size()) { ++tried; return moves[cur_index++]; } return nextTacticalMoveWithGeneration

(state); } template const MoveLogProb nextMove(const SearchState2& state) { assert(cur_state >= TACTICAL_FINISH); if (cur_index < moves.size()) { ++tried; return moves[cur_index++]; } if (cur_state < FINISH) return nextMoveWithGeneration

(state); return MoveLogProb(); } /** killer move ãªã© */ void registerMove(const NumEffectState& state, Move m) { ++tried; if (! m.isNormal()) return; marker.registerMove(state, m); } int triedMoves() const { return tried; } const PieceMask& myPins() const { return env.my_pin; } void dump() const; // construct直後ã«å‘¼ã¶ã“㨠void generateAll(Player P, const SearchState2& state, analyzer::CategoryMoveVector&); template void generateAll(const SearchState2&, MoveLogProbVector&); void generateAll(Player P, const SearchState2& state, MoveLogProbVector& out); const MoveLogProbVector& generated() const { return moves; } static int captureValue(Ptype); template void quiesceCapture(const NumEffectState&, Square); private: template const MoveLogProb nextMoveWithGeneration(const SearchState2&) ; template const MoveLogProb nextTacticalMoveWithGeneration(const SearchState2&) ; template void generateKingEscape(const SearchState2& state); template void generateTakeBack(const SearchState2& state); template void generateBreakThreatmate(const SearchState2& state); template void generateCapture(const SearchState2& state); template void generateTesuji(const SearchState2& state); template void generateAllExp(const SearchState2& state); template void generateAll(const SearchState2& state); template void addCapture(const NumEffectState&, const RatingEnv&, const MoveVector&); public: /** call this before any use of instance of MoveGenerator */ static void initOnce(); }; } } #endif /* OSL_MOVEGENERATOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/search/realizationProbability.h0000644000000000000000000000127512316770314022350 0ustar rootroot/* realizationProbability.h */ #ifndef INCLUDED_REALIZATIONPROBABILITY #define INCLUDED_REALIZATIONPROBABILITY namespace osl { namespace search { struct RealizationProbability { enum { DefaultProb = 500, ReSearch = 100, KillerMove = 200, TableMove = 100, }; }; struct FullWidthMoveProbability { enum { DefaultProb = 500, ReSearch = 500, KillerMove = 500, TableMove = 500, }; }; } // namespace search using search::RealizationProbability; using search::FullWidthMoveProbability; } // namespace osl #endif /* INCLUDED_REALIZATIONPROBABILITY */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/simpleHashTable.h0000644000000000000000000000653712316770314020701 0ustar rootroot/* simpleHashTable.h */ #ifndef OSL_SIMPLE_HASHTABLE_H #define OSL_SIMPLE_HASHTABLE_H #include "osl/search/generalSimpleHashTable.h" #include "osl/container.h" namespace osl { namespace search { class SimpleHashRecord; /** * 基本的㪠hash table. * ã¨ã‚Šã‚ãˆãš g++ (SGI STL) ã® hash_map を使ã£ã¦å®Ÿè£… * * 機能: * - lower bound 㨠upper bound を登録ã™ã‚‹ã€‚ * - ã‚‚ã—æ—¢ã«ç™»éŒ²ã•れã¦ã„ã‚‹å±€é¢ã«å†ã³ç™»éŒ²ãŒã‚ã£ãŸã‚‰ï¼Œå…¨ã¦ä¸Šæ›¸ãã™ã‚‹ * - メモリãŒã‚ãµã‚ŒãŸã‚‰å˜ã«ç„¡è¦–ã™ã‚‹ * - upperBound 㨠lowerBound 㯠player ä¾å­˜(betterThan)ãªã®ã§ * 手番ã®é•ã†åŒä¸€å±€é¢ãŒã‚ã‚‹ã¨ç ´ç¶»ã™ã‚‹ * - 最善手ã®ç™»éŒ² * * ã‚ã‚‹ç¨‹åº¦åŸºæœ¬çš„ãªæ©Ÿèƒ½ã‚’実装ã—ãŸã‚‰ï¼Œè‡ªåˆ†ã§å®Ÿè£…ã—ãªãŠã™ã»ã†ãŒbetter。 * ã“ã® hash_map ã§ã¯ GCを実装ã™ã‚‹ã“ã¨ã¯å›°é›£ã¨æ€ã‚れるãŸã‚ * * find, allocate ã§ ãƒã‚¤ãƒ³ã‚¿ã‚’è¿”ã™ãŸã‚,è¦ç´ ã‚’追加ã—ã¦ã‚‚,既存ã®è¦ç´ ã® * アドレスãŒå¤‰åŒ–ã—ãªã„データ構造を用ã„ã‚‹å¿…è¦ãŒã‚る. */ class SimpleHashTable : private container::GeneralSimpleHashTable { private: int minimum_limit; int verbose; public: /** * @param capacity 表ã«ä¿æŒã™ã‚‹æœ€å¤§å±€é¢ * @param minimumRecordLimit recordUpperBound, recordLowerBound ã«ãŠã„㦠* limit ãŒã“れ未満ã®ã‚‚ã®ã¯ç™»éŒ²è¦æ±‚を無視ã™ã‚‹. * 末端ã®é™æ­¢æŽ¢ç´¢ã‚‚記録ã™ã‚‹å ´åˆã¯ãƒžã‚¤ãƒŠã‚¹ã«ã™ã‚‹ */ explicit SimpleHashTable(size_t capacity=100000, int minimum_record_limit=0, int verbose=0); ~SimpleHashTable(); using GeneralSimpleHashTable::clear; /** * @param new_limit recordUpperBound, recordLowerBound ã«ãŠã„㦠* limit ãŒã“れ未満ã®ã‚‚ã®ã¯ç™»éŒ²è¦æ±‚を無視ã™ã‚‹ */ void setMinimumRecordLimit(int new_limit); /** * 表を探ã—,登録ã•れã¦ãªã‘ã‚Œã°æ–°è¦ã‚¨ãƒ³ãƒˆãƒªã‚’登録ã™ã‚‹ * @return テーブルãŒã„ã£ã±ã„ã ã£ãŸã‚Šlimit ãŒå°ã•ã™ãŽã‚‹ã¨0。 * ãã†ã§ãªã‘れã°å†…部ã§ç¢ºä¿ã—ãŸå ´æ‰€ã¸ã®ãƒã‚¤ãƒ³ã‚¿ * (é–“é•ã£ã¦ã‚‚ delete ã—ãªã„ã“ã¨) * @throw TableFull */ SimpleHashRecord *allocate(const HashKey& key, int limit); /** * 表を探ã™ï¼Žæ–°ãŸã«ç™»éŒ²ã™ã‚‹äº‹ã¯ãªã„ * @return 存在ã—ãªã‘れã°0 * ãã†ã§ãªã‘れã°å†…部ã§ç¢ºä¿ã—ãŸå ´æ‰€ã¸ã®ãƒã‚¤ãƒ³ã‚¿ * (é–“é•ã£ã¦ã‚‚ delete ã—ãªã„ã“ã¨) */ using GeneralSimpleHashTable::find; int minimumRecordLimit() const; using GeneralSimpleHashTable::size; using GeneralSimpleHashTable::capacity; void setVerbose(int verbose=1); int verboseLevel() const; bool isVerbose() const { return verboseLevel(); } bool isConsistent() const; int divSize() const; void getPV(const HashKey&, MoveVector&, size_t *quiesce_start=0) const; uint64_t memoryUse() const; }; } // namespace search using search::SimpleHashTable; } // namespace osl #endif /* OSL_SIMPLE_HASHTABLE_H_ */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/threatmateState.h0000644000000000000000000000450712316770314020766 0ustar rootroot/* threatmateState.h */ #ifndef SEARCH_THREATMATESTATE_H #define SEARCH_THREATMATESTATE_H #include "osl/basic_type.h" #ifdef OSL_SMP # include "osl/misc/lightMutex.h" #endif #include "osl/container.h" #include namespace osl { namespace search { struct ThreatmateStateData { char current_status; }; class DualThreatmateState; /** * è©°ã‚ã‚を考慮ã—ãŸè©°å°†æ£‹æŽ¢ç´¢ã®ãŸã‚ã®çŠ¶æ…‹ç®¡ç†. * http://www31.ocn.ne.jp/~kfend/inside_kfend/ptc.html#c3 * * - (MAYBE_)THREATMATE --(check)--> CHECK_AFTER_THREATMATE * - (MAYBE_)THREATMATE --(no-check)--> MAY_HAVE_CHECKMATE * - CHECK_AFTER_THREATMATE --(escape)--> MAYBE_THREATMATE */ class ThreatmateState : protected ThreatmateStateData { friend class DualThreatmateState; public: enum Status { UNKNOWN = 0, /** threatmate found by checkmate search */ THREATMATE, /** threatmate, not sure */ MAYBE_THREATMATE, /** status after threatmate responded by check */ CHECK_AFTER_THREATMATE, /** status after threatmate responded by non-check move */ MAY_HAVE_CHECKMATE, }; private: static const CArray transition; public: ThreatmateState(Status s=UNKNOWN) { current_status = s; } void setThreatmate(Status s) { current_status = s; } bool isUnknown() const { return current_status == UNKNOWN; } bool isThreatmate() const { return current_status == THREATMATE; } bool maybeThreatmate() const { return (current_status == THREATMATE) || (current_status == MAYBE_THREATMATE); } bool mayHaveCheckmate() const { return current_status == MAY_HAVE_CHECKMATE; } Status status() const { return static_cast(current_status); } const ThreatmateState newStatus(bool is_check) const { return transition[current_status*2+is_check]; } void update(const ThreatmateState *parent, bool in_check) { if (maybeThreatmate() || ! parent) return; const ThreatmateState new_status = parent->newStatus(in_check); *this = new_status; } }; std::ostream& operator<<(std::ostream&, ThreatmateState); } // namespace search } // osl #endif /* SEARCH_THREATMATESTATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/threatmateState.cc0000644000000000000000000000221212316770314021113 0ustar rootroot/* threatmateState.cc */ #include "osl/search/threatmateState.h" #include "osl/csa.h" #include const osl::CArray osl::search::ThreatmateState::transition = {{ /*UNKNOWN*/ UNKNOWN, UNKNOWN, /*THREATMATE*/ MAY_HAVE_CHECKMATE, CHECK_AFTER_THREATMATE, /*MAYBE_THREATMATE*/ MAY_HAVE_CHECKMATE, CHECK_AFTER_THREATMATE, /*CHECK_AFTER_THREATMATE*/ MAYBE_THREATMATE, UNKNOWN, /*MAY_HAVE_CHECKMATE*/ UNKNOWN, UNKNOWN, }}; #ifndef MINIMAL std::ostream& osl::search::operator<<(std::ostream& os, ThreatmateState s) { switch (s.status()) { case ThreatmateState::THREATMATE: return os << "THREATMATE "; // << csa::show(s.threatmate_move); case ThreatmateState::MAYBE_THREATMATE: return os << "maybe threatmate"; case ThreatmateState::MAY_HAVE_CHECKMATE: return os << "may have checkmate"; case ThreatmateState::CHECK_AFTER_THREATMATE: return os << "check after threatmate"; default: return os << "unkown"; } } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/limitToCheckCount.cc0000644000000000000000000000153612316770314021354 0ustar rootroot#include "osl/search/limitToCheckCount.h" namespace osl { namespace checkmate { CArray LimitToCheckCountTable={{ 0, // 0-127 0, // 128- 0, // 256- 0, // 384- 70, // 512- 80, // 640- 90, // 768- 100, // 896- 150, // 1024- 200, 250, // 1280 300, 300, 300, 300, 300, 300, // 1664- 1600, 2400, 3200, 4800, // 2560 6400, 9600, 12800, 19200, 25600, 38400, 51200, 76800, 102400, 409600, 1920000, }}; } // namespace checkmate } // namespace osl /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta2.h0000644000000000000000000002710212316770314017566 0ustar rootroot/* alphaBeta2.h */ #ifndef OSL_ALPHA_BETA2_H #define OSL_ALPHA_BETA2_H #include "osl/search/realizationProbability.h" #include "osl/search/searchBase.h" #include "osl/search/searchState2.h" #include "osl/search/searchRecorder.h" #include "osl/search/passCounter.h" #include "osl/search/killerMoveTable.h" #include "osl/search/searchTimer.h" #include "osl/eval/evalTraits.h" #include "osl/eval/openMidEndingEval.h" #include "osl/eval/progressEval.h" #include "osl/container/moveStack.h" #include "osl/container/moveLogProbVector.h" #include "osl/stat/average.h" #include "osl/oslConfig.h" #include #include #include namespace osl { namespace search { class SimpleHashRecord; class SimpleHashTable; class MoveGenerator; struct MoveWithComment; class AlphaBeta2Window { CArray values; public: explicit AlphaBeta2Window(int a=0) { values.fill(a); } AlphaBeta2Window(int a, int b) { values[0] = a; values[1] = b; } AlphaBeta2Window(Player P, int a=0, int b=0) { alpha(P) = a; beta(P) = b; } int& alpha(Player P) { return values[P]; } int& beta(Player P) { return values[alt(P)]; } int alpha(Player P) const { return values[P]; } int beta(Player P) const { return values[alt(P)]; } bool isConsistent() const { return eval::notLessThan(BLACK, beta(BLACK), alpha(BLACK)); } bool null() const { return values[0] == values[1]; } bool operator==(const AlphaBeta2Window& r) const { return values == r.values; } }; /** * AlphaBeta2Tree ã®ãƒ‡ãƒ¼ã‚¿ãƒ¡ãƒ³ãƒãƒ¼ã§default copy constructor ã§copyå¯èƒ½ãªã‚‚ã®ã€‚ */ template struct AlphaBeta2Common #if OSL_WORDSIZE == 32 : public misc::Align16New #endif { static int rootLimitBias() { return 0; } static int leafLimit() { static int value = 300 + rootLimitBias(); return value; } enum { MaxDepth = SearchState2Core::MaxDepth }; EvalT eval; PassCounter pass_count; enum MoveType { INITIAL, HASH=INITIAL, TACTICAL, KILLER, PASS, ALL, FINISH }; /** ç¾åœ¨ã®æ·±ã•ã§ã®ä½œæˆçŠ¶æ…‹, nextMove() ã§åˆ©ç”¨ */ CArray move_type; CArray in_pv; typedef FixedCapacityVector killer_t; CArray killers; const MoveVector *root_ignore_moves; // acquaintance bool prediction_for_speculative_search; /** experimental */ int multi_pv; explicit AlphaBeta2Common(const NumEffectState& s) : eval(s), root_ignore_moves(0), prediction_for_speculative_search(false), multi_pv(0) { in_pv[0] = true; } }; struct RootPV { SearchState2::PVVector pv; int depth, eval; RootPV(int root_limit, const SearchState2::PVVector &p, int v) : pv(p), depth(root_limit), eval(v) { } }; struct AlphaBeta2SharedRoot { /** value for each pv-update, for each iteration */ std::vector root_values, root_values_for_iteration; std::vector best_move_for_iteration; /** history of pv */ std::vector last_pv; /** best move of the previous completed iteration */ Move last_root_move; /** interim value for the current iteration */ int last_root_value_update; AlphaBeta2SharedRoot() : last_root_value_update(0) { } void showLastPv(int limit) const; int sameBestMoves() const { int ret = 0; for (int i=best_move_for_iteration.size()-2; i>=0; --i, ++ret) if (best_move_for_iteration[i] != best_move_for_iteration[i+1]) break; return ret; } }; template struct AlphaBeta2Parallel; /** * "tree" of AlphaBeta2, copied by split */ template class AlphaBeta2Tree : public SearchBase, public SearchState2, public SearchTimer, protected AlphaBeta2Common, boost::noncopyable { public: typedef EvalT eval_t; typedef AlphaBeta2Common common_t; enum { MaxDepth = SearchState2Core::MaxDepth }; protected: /** 陿­¢æŽ¢ç´¢ã‚‚å«ã‚ãŸãƒŽãƒ¼ãƒ‰æ•° */ size_t node_count; FixedCapacityVector generators; stat::Average mpn, mpn_cut, alpha_update, last_alpha_update; stat::Average ext, ext_limit; std::shared_ptr > shared; std::shared_ptr shared_root; protected: static CArray depth_node_count; AlphaBeta2Tree(const NumEffectState& s, checkmate_t& checker, SimpleHashTable *t, CountRecorder&); // share parallel data for split AlphaBeta2Tree(const AlphaBeta2Tree& src, AlphaBeta2Parallel *); ~AlphaBeta2Tree(); private: void throwStop(); public: struct BetaCut {}; bool stopping() const { return stop_tree || SearchTimer::stopping(); } void testStop() { throwIfNoMoreTime(this->recorder.allNodeCount()); if (stop_tree) throw BetaCut(); } public: typedef AlphaBeta2Window Window; size_t nodeCount() const { return node_count; } static int rootAlpha(Player P, int last_value, Progress16 progress); static int stableThreshold(Player P, int last_value); template const MoveLogProb nextMove(); protected: void updateRootPV(Player P, std::ostream&, int, Move); void addMultiPV(Player P, int, Move); bool isStable(Player P, int new_value) const; void showFailLow(int result, Move m) const; private: void showPV(std::ostream&, int, Move, char stable) const; public: template struct NextMove; friend struct NextMove; friend struct NextMove; template struct NextQMove; friend struct NextQMove; friend struct NextQMove; protected: /** * alphaBetaSearch (move) * - makeMove(move) * - => alphaBetaSearchAfterMove * -- search extension etc. * -- => searchAllMoves => alphaBetaSearch (child move) * - unmakeMove(move) */ template int alphaBetaSearch(const MoveLogProb& move, Window window, bool in_pv); template int alphaBetaSearchAfterMove(const MoveLogProb& move, Window window, bool in_pv); template int quiesce(Window); template int quiesceStable(Window); template int quiesceExp(Window); template int searchAllMoves(SimpleHashRecord*, Window w); template int searchAllMoves(Move m, int limit_consumption, SimpleHashRecord*, Window w); /** åˆã‚ã®æ–¹ã§è©°ã¿ã‚’読む */ template bool tryCheckmate(SimpleHashRecord *record, bool in_pv, Move& checkmate_move); /** è² ã‘ãã†ãªæ™‚ã«ã•らã«è©°ã¿ã‚’読む */ template bool tryCheckmateAgain(SimpleHashRecord *record, Move& checkmate_move, int node_count, int best_value); /** è©°ã‚ã‚ã®æœ‰ç„¡ã‚’ç¢ºèª */ template void testThreatmate(SimpleHashRecord *record, bool in_pv); /** alphaå€¤ãŒæ±‚ã¾ã£ãŸå¾Œã§ä»–ã®æ‰‹ã‚’調ã¹ã‚‹ */ template void examineMovesRoot(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); template int quiesceRoot(Window, int depth_left, Move& best_move, DualThreatmateState); template int quiesce(Window, int depth_left, DualThreatmateState); template bool quiesceWithMove(Move, Window&, int, Move&, int&, const DualThreatmateState&); void updateCheckmateCount(); bool tryPass(SimpleHashRecord *record, Player P) const; MoveGenerator& makeGenerator(); static MoveGenerator *alloc(); static void dealloc(MoveGenerator *); #ifdef OSL_SMP public: friend struct AlphaBeta2Parallel; struct NodeProperty; template struct SearchJob; struct SearchJobData; struct Shared; friend struct Shared; friend struct SearchJob; friend struct SearchJob; protected: template void examineMovesRootPar(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); void examineMovesRootPar(int tree_id); template void testMoveRoot(int tree_id, const MoveLogProb&); template bool examineMovesOther(Window& w, MoveLogProb& best_move, int& best_value, int& tried_moves, int& alpha_update, int& last_alpha_update); void examineMovesOther(int tree_id); template bool testMoveOther(int tree_id, const MoveLogProb&, size_t index, bool in_pv); #endif }; /** * AlphaBeta ã®æ›¸ãç›´ã—版 */ template class AlphaBeta2 : public AlphaBeta2Tree { public: typedef AlphaBeta2Tree base_t; typedef typename base_t::checkmate_t checkmate_t; typedef typename base_t::Window Window; public: AlphaBeta2(const NumEffectState& s, checkmate_t& checker, SimpleHashTable *t, CountRecorder&); ~AlphaBeta2(); /** * entrance of alpha beta window search. * * see http://www.logos.t.u-tokyo.ac.jp/~gekisashi/algorithm/re_search.html. * rootDepth, curLimit are initialized here. */ template int alphaBetaSearchRoot(Window window, MoveLogProb& best_move, int limit); static const Window fullWindow(Player P) { return Window(P, base_t::winThreshold(alt(P)), base_t::winThreshold(P)); } int alphaBetaSearchRoot(Window window, MoveLogProb& best_move, int limit) { const Player P = this->state().turn(); if (P == BLACK) return alphaBetaSearchRoot(window, best_move, limit); else return alphaBetaSearchRoot(window, best_move, limit); } int alphaBetaSearchRoot(MoveLogProb& best_move, int limit); /** * entrance of alpha beta iterative search. */ Move computeBestMoveIteratively(int limit, const int step=100, int initialLimit=600, size_t nodeLimit=1600000, const TimeAssigned& assign=TimeAssigned(milliseconds(60*1000)), MoveWithComment *additional_info=0); bool isReasonableMove(Move move, int pawn_sacrifice=1); void setRootIgnoreMoves(const MoveVector *rim, bool prediction) { assert(!prediction || rim); this->root_ignore_moves = rim; this->prediction_for_speculative_search = prediction; } static void showNodeDepth(std::ostream&); static void clearNodeDepth(); void enableMultiPV(unsigned int width) { this->multi_pv = width; } const AlphaBeta2SharedRoot sharedRootInfo() const { return *(this->shared_root); } public: void setRoot(int limit); void makeMove(Move); private: enum PVCheckmateStatus { PVStable, PVThreatmateNotRecord, PVThreatmate, PVCheckmate, }; PVCheckmateStatus findCheckmateInPV(int verify_node, CArray& king_in_threat); }; // class AlphaBeta2 } // namespace search typedef search::AlphaBeta2 AlphaBeta2ProgressEval; typedef search::AlphaBeta2 AlphaBeta2OpenMidEndingEval; } // namespace osl #endif /* OSL_ALPHA_BETA2_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveStackRejections.h0000644000000000000000000001457712316770314021621 0ustar rootroot/* moveStackRejections.h */ #ifndef _MOVE_STACK_REJECTIONS_H #define _MOVE_STACK_REJECTIONS_H #include "osl/numEffectState.h" #include "osl/container/moveStack.h" #include namespace osl { namespace search { /** * Moveを分解ã—ãŸå·®åˆ†è¦ç´ ã®ã†ã¡ã®ç›¤é¢ä¸Šã®é§’ã«é–¢ã—ã¦ä¿æŒã™ã‚‹ãƒ‡ãƒ¼ã‚¿ * pos, ptypeOã‚’shortã«å…¥ã‚Œã‚‹ï¼Ž */ struct OnBoardElement { short posPtypeO; OnBoardElement() {} OnBoardElement(Square pos_,PtypeO ptypeO_){ posPtypeO=makePosPtypeO(pos_,ptypeO_); } static short makePosPtypeO(Square pos,PtypeO ptypeO) { return static_cast(pos.uintValue()+(ptypeO<<8)); } Square pos() const{ return Square::makeDirect(posPtypeO&0xff); } PtypeO ptypeO() const{ return static_cast(posPtypeO>>8); } }; /** * Moveを分解ã—ãŸå·®åˆ†è¦ç´ ã®ã†ã¡æŒé§’ã®å¢—減ã®ã¿ã‚’管ç†ã™ã‚‹ï¼Ž * ç›¸æ‰‹ã®æŒã¡é§’ãŒå¢—ãˆãŸã‹ï¼Œæå¾—ãªã—ã‹ã‚’高速ã«åˆ¤å®šã§ãる. */ struct StandElements { union { CArray c8; unsigned long long l8; } v; StandElements() { v.l8=0x8080808080808080ull; } /** * altPã«ã¨ã£ã¦å¢—ãˆã‚‹ */ void add(Ptype ptype){ assert(ptype>=PTYPE_BASIC_MIN); v.c8[ptype-PTYPE_BASIC_MIN]++; } /** * altPã«ã¨ã£ã¦æ¸›ã‚‹ */ void sub(Ptype ptype){ assert(ptype>=PTYPE_BASIC_MIN); v.c8[ptype-PTYPE_BASIC_MIN]--; } bool isZero() const{ return v.l8==0x8080808080808080ull; } bool gtZero() const{ return !isZero() && geZero(); } bool geZero() const{ return (v.l8&0x8080808080808080ull)==0x8080808080808080ull; } }; /** * 複数ã®moveã«ã‚ˆã‚‹å·®åˆ†ã‚’分解ã—ãŸã‚‚ã® * 一回ã®moveã§OnBoarPlusã¯æ‰‹ç•ªã®é§’ã®ã¿ * OnBoardMinusã¯æ‰‹ç•ªã¨ç›¸æ‰‹ã®é§’ãŒã‚りã†ã‚‹ * OnBoardPlus㯠最大深ã•/2 * OnBoardMinus㯠最大深ã•分用æ„ã™ã‚‹ï¼Ž */ struct StateElements { FixedCapacityVector myOnboardPlus; FixedCapacityVector opOnboardPlus; FixedCapacityVector myOnboardMinus; FixedCapacityVector opOnboardMinus; StandElements stand; public: StateElements() { } void clear() { } /** * 相手ãŒé§’ã‚’å–りptypeã®æŒé§’ãŒå¢—ãˆãŸï¼Ž * 自分ãŒptypeã®æŒé§’を使ã£ãŸ */ void addStand(Ptype ptype); /** * 相手ãŒtypeã®æŒé§’を使ã£ãŸ * 自分ãŒé§’ã‚’å–りptypeã®æŒé§’ãŒå¢—ãˆãŸï¼Ž */ void subStand(Ptype ptype); /** * */ void addMyBoard(Square pos,PtypeO ptypeO); void subMyBoard(Square pos,PtypeO ptypeO); void addOpBoard(Square pos,PtypeO ptypeO); void subOpBoard(Square pos,PtypeO ptypeO); /** * 自分ã®moveã«å¾“ã£ã¦æ›´æ–°ã€€ */ void addMyMove(Move move); /** * 相手ã®moveã«å¾“ã£ã¦æ›´æ–° */ void addOpMove(Move move); /** * 盤é¢ãŒå¢—減ãªã— */ bool isLoop() const{ return myOnboardPlus.size()==0 && opOnboardPlus.size()==0 && myOnboardMinus.size()==0 && opOnboardMinus.size()==0; } /** * Pã«ã‚ˆã‚‹SimpleMoveãŒå¯èƒ½ */ template bool validSimpleMove(NumEffectState const& state,OnBoardElement const& fromElement,OnBoardElement const& toElement) const; /** * stateã«lastMoveã‚’æ–½ã—ãŸå¾Œã®ç›¤é¢ã§ã€€ * Pã«ã‚ˆã‚‹SimpleMoveãŒå¯èƒ½ */ template bool validSimpleMove(NumEffectState const& state,OnBoardElement const& fromElement,OnBoardElement const& toElement,Move lastMove) const; /** * Pã«ã‚ˆã‚‹captureMoveãŒå¯èƒ½ */ template bool validCaptureMove(NumEffectState const& state, OnBoardElement const& fromElement,OnBoardElement const& toElement,OnBoardElement const& captureElement) const; /** * stateã«lastMoveã‚’æ–½ã—ãŸå¾Œã®ç›¤é¢ã§ã€€ * Pã«ã‚ˆã‚‹CaptureMoveãŒå¯èƒ½ */ template bool validCaptureMove(NumEffectState const& state, OnBoardElement const& fromElement,OnBoardElement const& toElement,OnBoardElement const& captureElement,Move lastMove) const; /** * PãŒã‚ã‚‹moveã‚’ã™ã‚‹å‰ã®2n手å‰ã‹ã‚‰move後ã¸ã®å·®åˆ†ã‹ã‚‰rejectã™ã‚‹ã‹ã©ã†ã‹æ±ºã‚る. * playerã«å–ã£ã¦æœ‰åˆ©ãªæŒã¡é§’渡ã—ãŒã‚ã‚‹ -> false * playerã«å–ã£ã¦ä¸åˆ©ãªæŒã¡é§’渡ã—ãŒã‚ã‚‹ * 差分ãŒãªã„å ´åˆ -> 一手パス+é§’æ -> true * 差分ãŒè‡ªåˆ†ä¸€æ‰‹åˆ†ã®æ™‚ -> ãã®æ‰‹ãŒ2n手å‰ã«å¯èƒ½ãªã‚‰true * 差分ãŒç›¸æ‰‹ä¸€æ‰‹åˆ†ã®æ™‚ -> move後ã«ç›¸æ‰‹ãŒå¯èƒ½ãªã‚‰true * æŒã¡é§’渡ã—ãŒãªã„ * 差分ãŒãªã„å ´åˆ -> 一手パス * isRootMoveã®æ™‚㯠false(rootã§ã¯PASSã§ããªã„) * root以外ã§ã¯ true * 差分ãŒè‡ªåˆ†ä¸€æ‰‹åˆ†ã®æ™‚ -> ãã®æ‰‹ãŒ2n手å‰ã«å¯èƒ½ãªã‚‰true * 差分ãŒç›¸æ‰‹ä¸€æ‰‹åˆ†ã®æ™‚ -> move後ã«ç›¸æ‰‹ãŒå¯èƒ½ã§ * mayRejectSennichiteã®æ™‚㯠true (有利ã ã£ãŸã‚‰ç›¸æ‰‹ã«åƒæ—¥æ‰‹ã®ãƒãƒ£ãƒ³ã‚¹ã‚’è€ãˆãªã„) * ãã†ã§ãªã„ã¨ã㯠false (åƒæ—¥æ‰‹ã®æ–¹ãŒã¾ã—ãªå¯èƒ½æ€§ãŒã‚ã‚‹) */ template bool canReject(NumEffectState const& state,bool mayRejectSennichite,bool isRootMove,Move lastMove,Move actualMove) const; }; std::ostream& operator<<(std::ostream&,OnBoardElement const&); std::ostream& operator<<(std::ostream&,StandElements const&); std::ostream& operator<<(std::ostream&,StateElements const&); class MoveStackRejections { public: /** * P - 手番(mã®player)ã®ç«‹å ´ã§åˆ¤åˆ¥ * state - m を実行ã™ã‚‹å‰ã®çŠ¶æ…‹ * history - mã‚’å«ã¾ãªã„éŽåŽ»ã®è¨˜éŒ²ï¼Ž * ply - 探索開始ã‹ã‚‰ã®æ·±ã• * m - ãƒã‚§ãƒƒã‚¯ã™ã‚‹æ‰‹ * alpha - windowã®Pã«å–ã£ã¦ã®ä¸‹é™ * checkCountOfAltP - 相手ãŒé€£ç¶šçŽ‹æ‰‹ã®æ™‚ã«ã„ãã¤ç¶šã„ãŸã‹ */ template static bool probe(NumEffectState const& state,MoveStack const& history,int ply,Move const& m,int alpha, int checkCountOfAltP); }; } } #endif /* _MOVE_STACKREJECTIONS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/historyTable.cc0000644000000000000000000000167212316770314020436 0ustar rootroot/* historyTable.cc */ #include "osl/search/historyTable.h" #include #include #include void osl::search:: HistoryTable::extractTopN(Player p, std::vector& out, size_t limit) const { out.clear(); for (size_t i=0; i<=Square(9,9).uintValue(); ++i) for (size_t j=Square(1,1).uintValue(); j<=Square(9,9).uintValue(); ++j) if (table[p][i][j].value > 100) out.push_back(OutputEntry(i, j, table[p][i][j].value)); std::sort(out.begin(), out.end(), std::greater()); if (limit < out.size()) out.resize(limit); } std::ostream& osl::search::operator<<(std::ostream& os, const HistoryTable::OutputEntry& e) { os << '('; if (e.from_or_ptype < PTYPE_SIZE) os << Ptype(e.from_or_ptype); else os << Square::makeDirect(e.from_or_ptype); return os << " => " << e.to << " " << e.value << ")"; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveWithComment.cc0000644000000000000000000000042512316770314021105 0ustar rootroot/* moveWithComment.cc */ #include "osl/search/moveWithComment.h" osl::search::MoveWithComment::~MoveWithComment() { } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveGenerator.cc0000644000000000000000000003574112316770314020606 0ustar rootroot/* moveGenerator.cc */ #include "osl/search/moveGenerator.h" #include "osl/search/searchState2.h" #include "osl/move_classifier/shouldPromoteCut.h" #include "osl/search/sortCaptureMoves.h" #include "osl/search/breakThreatmate.h" #include "osl/search/analyzer/categoryMoveVector.h" #include "osl/move_generator/capture_.h" #include "osl/move_generator/escape_.h" #include "osl/move_generator/promote_.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/attackToPinned.h" #include "osl/move_classifier/check_.h" #include "osl/move_classifier/safeMove.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/effect_util/effectUtil.h" #include "osl/rating/featureSet.h" #include "osl/rating/ratingEnv.h" #include "osl/eval/pieceEval.h" #include "osl/eval/progressEval.h" #include "osl/eval/openMidEndingEval.h" #include "osl/stat/average.h" #include #include // #define STAT_WIDTH_VS_LIMIT #ifndef NDEBUG # define SAFE_MOVE_ONLY #endif const int max_see = 20000; static const osl::rating::FeatureSet *static_feature_set; static const osl::rating::FeatureSet& feature_set() { return *static_feature_set; } void osl::search::MoveGenerator::initOnce() { if (static_feature_set == 0) static_feature_set = &rating::StandardFeatureSet::instance(); } namespace osl { namespace search { const CArray2d MoveGenerator::Generators = {{ 0, &MoveGenerator::generateKingEscape, &MoveGenerator::generateTakeBack, &MoveGenerator::generateBreakThreatmate, &MoveGenerator::generateCapture, 0, &MoveGenerator::generateTesuji, &MoveGenerator::generateAll, 0, &MoveGenerator::generateKingEscape, &MoveGenerator::generateTakeBack, &MoveGenerator::generateBreakThreatmate, &MoveGenerator::generateCapture, 0, &MoveGenerator::generateTesuji, &MoveGenerator::generateAll, }}; const CArray MoveGenerator::GeneratorNames = {{ "INITIAL", "KING_ESCAPE", "TAKEBACK", "BREAK_THREATMATE", "TACTICAL", "SENTINEL", "TESUJI", "ALL", }}; #ifdef STAT_WIDTH_VS_LIMIT struct WidthVSLimit { CArray averages; ~WidthVSLimit() { report(); } stat::Average& average(int limit) { limit /= 100 - 3; return averages[std::min(std::max(limit,0),(int)averages.size()-1)]; } void report() { std::cerr << "WidthVSLimit@MoveGenerator\n"; for (int limit=300; limit<300+(int)averages.size()*100; limit+=100) { std::cerr << std::setw(5) << limit << " " << average(limit).getAverage() << std::endl; } } } Width_VS_Limit; #endif template void MoveGenerator::init( int limit, const SimpleHashRecord *record, const osl::eval::ProgressEval&, const NumEffectState&, bool in_pv, Move hash_move, bool quiesce); template void MoveGenerator::init( int limit, const SimpleHashRecord *record, const osl::eval::ml::OpenMidEndingEval&, const NumEffectState&, bool in_pv, Move hash_move, bool quiesce); } } /* ------------------------------------------------------------------------- */ osl::search:: MoveMarker::MoveMarker() : cur(1) { marker.fill(0); } void osl::search:: MoveMarker::clear() { ++cur; if (cur == 0) { marker.fill(0); cur = 1; } } bool osl::search:: MoveMarker::registerIfNew(const NumEffectState& state, Move m) { value_t& val = marker[toIndex(m)][pieceIndex(state, m)]; if (val == cur) return false; val = cur; return true; } bool osl::search:: MoveMarker::registered(const NumEffectState& state, Move m) const { return marker[toIndex(m)][pieceIndex(state, m)] == cur; } /* ------------------------------------------------------------------------- */ osl::search:: MoveGenerator::MoveGenerator() : record(0), progress(16) { } int osl::search:: MoveGenerator::captureValue(Ptype ptype) { if (! isPiece(ptype)) return 0; int result = eval::Ptype_Eval_Table.captureValue(newPtypeO(WHITE, ptype)); assert(result >= 0); return result; } template void osl::search:: MoveGenerator::init(int l, const SimpleHashRecord *r, const EvalT& eval, const NumEffectState& state, bool in_pv, Move hash_move, bool quiesce) { assert(r); assert(l > 0); limit = l; record = r; cur_state = INITIAL; moves.clear(); cur_index = tried = 0; progress = eval.progress32(); eval_suggestion = eval.suggestMove(state); marker.clear(); env.make(state, state.pin(state.turn()), state.pin(alt(state.turn())), eval.progress16()); if (hash_move.isNormal()) marker.registerMove(state, hash_move); #ifndef MINIMAL in_quiesce = quiesce; #endif this->in_pv = in_pv; } void osl::search:: MoveGenerator::dump() const { std::cerr << "generator " << cur_state << " index " << cur_index << " limit " << limit << " tried " << tried << "\n"; std::cerr << moves.size() << "\n" #ifndef MINIMAL << moves #endif ; } template const osl::MoveLogProb osl::search:: MoveGenerator::nextTacticalMoveWithGeneration(const SearchState2& state) { assert(record); while (true) { assert(cur_index >= moves.size()); if (cur_state == KING_ESCAPE && record->inCheck()) { cur_state = FINISH; break; } if (++cur_state >= TACTICAL_FINISH) break; // generate assert(Generators[playerToIndex(P)][cur_state]); (this->*Generators[playerToIndex(P)][cur_state])(state); if (cur_index < moves.size()) { ++tried; return moves[cur_index++]; } } return MoveLogProb(); } template const osl::MoveLogProb osl::search:: MoveGenerator::nextMoveWithGeneration(const SearchState2& state) { assert(record); while (true) { assert(cur_index >= moves.size()); if (++cur_state >= FINISH) break; // generate assert(Generators[playerToIndex(P)][cur_state]); (this->*Generators[P][cur_state])(state); if (cur_index < moves.size()) { ++tried; return moves[cur_index++]; } } return MoveLogProb(); } template void osl::search:: MoveGenerator::generateKingEscape(const SearchState2& sstate) { env.history = sstate.history(); if (! record->inCheck()) return; const NumEffectState& state = sstate.state(); const Piece king = state.kingPiece

(); assert(state.hasEffectAt(alt(P), king.square())); MoveVector src; move_generator::GenerateEscape

::generate(state,king,src); size_t last = src.size(); for (size_t i=0; i()) src.push_back(src[i].unpromote()); if (src.size() == 1) { moves.push_back(MoveLogProb(src[0], 20)); return; } for (Move move: src) { const int prob = std::min(limit, feature_set().logProbKingEscape(state, env, move)); assert(prob > 0); moves.push_back(MoveLogProb(move, prob)); } moves.sortByProbability(); } template void osl::search:: MoveGenerator::generateBreakThreatmate(const SearchState2& sstate) { const NumEffectState& state = sstate.state(); const Move threatmate_move = record->threatmate().threatmateMove(state.turn()); if (! threatmate_move.isNormal()) return; BreakThreatmate::generate(limit, state, threatmate_move, moves); for (const MoveLogProb& move: moves) marker.registerMove(state, move.move()); } template void osl::search:: MoveGenerator::generateTakeBack(const SearchState2& sstate) { using namespace move_action; const Move last_move = sstate.lastMove(); if (! last_move.isNormal()) return; const Square last_to = last_move.to(); const NumEffectState& state = sstate.state(); #ifndef MINIMAL if (in_quiesce) return quiesceCapture

(state, last_to); #endif MoveVector src; move_generator::GenerateCapture::generate(state, last_to, src); assert(moves.empty()); for (Move move: src) { assert(! ShouldPromoteCut::canIgnoreMove

(move)); const int prob = feature_set().logProbTakeBack(state, env, move); #ifdef OSL_SMP if (! move.isDrop() && move.ptype() != KING && env.my_pin.test(state.pieceOnBoard(move.from()).number())) { if (move_classifier::KingOpenMove

::isMember(state, move.ptype(), move.from(), move.to())) continue; } #endif if (prob <= std::min(200, limit) && marker.registerIfNew(state, move)) moves.push_back(MoveLogProb(move, prob)); } moves.sortByProbability(); } namespace osl { template static void makeCapture(const NumEffectState& state, MoveVector& out) { move_action::Store store(out); mask_t pieces = state.piecesOnBoard(alt(P)).template selectBit() & state.effectedMask(P).getMask(PtypeFuns::indexNum); while (pieces.any()) { const Piece p = state.pieceOf(pieces.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner()); move_generator::GenerateCapture::generate(P,state, p.square(), store); } } } template void osl::search:: MoveGenerator::addCapture(const NumEffectState& state, const RatingEnv& env, const MoveVector& src) { #ifndef MINIMAL if (in_quiesce) { for (Move move: src) { assert(!ShouldPromoteCut::canIgnoreMove

(move)); const int see = PieceEval::computeDiffAfterMoveForRP(state, move); if (see < 0) continue; moves.push_back(MoveLogProb(move, max_see - see)); } return; } #endif for (Move move: src) { assert(! ShouldPromoteCut::canIgnoreMove

(move)); #ifdef SAFE_MOVE_ONLY if (! move.isDrop() && move.ptype() != KING && env.my_pin.test(state.pieceOnBoard(move.from()).number())) { if (move_classifier::KingOpenMove

::isMember(state, move.ptype(), move.from(), move.to())) continue; } #endif const int prob = feature_set().logProbSeePlus(state, env, move); // const int prob = feature_set().logProbTakeBack(state, env, move); if (prob <= 200 && marker.registerIfNew(state, move)) { moves.push_back(MoveLogProb(move, prob)); } } return; } template void osl::search:: MoveGenerator::generateCapture(const SearchState2& sstate) { using namespace move_action; const NumEffectState& state = sstate.state(); MoveVector src; #if 1 // lance, bishop, rook makeCapture(state, src); makeCapture(state, src); makeCapture(state, src); // knight, silver, gold makeCapture(state, src); makeCapture(state, src); makeCapture(state, src); #else makeCaptureOtherThanPawn

(state, src); #endif addCapture

(state, env, src); } template void osl::search:: MoveGenerator::generateTesuji(const SearchState2& sstate) { const NumEffectState& state = sstate.state(); if (! state.inCheck() && eval_suggestion.isNormal() && marker.registerIfNew(state, eval_suggestion)) { assert(sstate.state().isValidMove(eval_suggestion)); moves.push_back(MoveLogProb(eval_suggestion, 250)); } #ifndef MINIMAL if (in_quiesce) { MoveVector src; move_generator::Promote

::generate(state, src); makeCapture(state, src); addCapture

(state, env, src); } #endif } #ifndef MINIMAL template void osl::search:: MoveGenerator::quiesceCapture(const NumEffectState& state, Square to) { MoveVector moves; move_generator::GenerateCapture::generate(state, to, moves); for (Move move: moves) { assert(!ShouldPromoteCut::canIgnoreAndNotDrop

(move)); int see = PieceEval::computeDiffAfterMoveForRP(state, move); if (see < 0) continue; this->moves.push_back(MoveLogProb(move, max_see - see)); } this->moves.sortByProbabilityReverse(); } #endif template void osl::search:: MoveGenerator::generateAll(const SearchState2& sstate) { #ifndef MINIMAL if (in_quiesce) return; #endif const NumEffectState& state = sstate.state(); MoveLogProbVector all; feature_set().generateLogProb(state, env, limit, all, in_pv); #ifdef STAT_WIDTH_VS_LIMIT const size_t moves_size_before = moves.size(); #endif for (const MoveLogProb& move: all) { assert(!ShouldPromoteCut::canIgnoreAndNotDrop

(move.move())); const Move m = move.move(); int limit = move.logProb(); if (this->limit >= 400) { using namespace move_classifier; if (m.isCaptureOrPromotion() || (in_pv && MoveAdaptor >::isMember(state, move.move()))) limit = std::min(limit, 400); } if (limit <= this->limit && marker.registerIfNew(state, move.move())) { #ifndef NDEBUG if (! m.isDrop()) { assert(! (env.my_pin.test(state.pieceOnBoard(m.from()).number()) && move_classifier::KingOpenMove

::isMember(state, m.ptype(), m.from(), m.to()))); assert(! (m.ptype() == KING && state.hasEffectAt(alt(P), m.to()))); } #endif moves.push_back(MoveLogProb(move.move(), limit)); } } #ifdef STAT_WIDTH_VS_LIMIT Width_VS_Limit.average(limit).add(moves.size() - moves_size_before); #endif } #ifndef MINIMAL void osl::search:: MoveGenerator::generateAll(Player P, const SearchState2& state, analyzer::CategoryMoveVector& out) { assert(moves.size() == 0); for (int i=0; i*Generators[playerToIndex(P)][i])(state); out.push_front(analyzer::CategoryMoves(moves, GeneratorNames[i])); bool generated = moves.size(); moves.clear(); if (i == KING_ESCAPE && generated) break; } out.reverse(); } #endif template void #if (defined __GNUC__) && (! defined GPSONE) && (! defined GPSUSIONE) __attribute__ ((used)) #endif osl::search:: MoveGenerator::generateAll(const SearchState2& state, MoveLogProbVector& out) { using namespace move_classifier; for (MoveLogProb m = nextTacticalMove

(state); m.validMove(); m = nextTacticalMove

(state)) { assert(state.state().isValidMove(m.move())); if (ConditionAdaptor::isMember(state.state(), m.move())) out.push_back(m); } for (MoveLogProb m = nextMove

(state); m.validMove(); m = nextMove

(state)) { assert(state.state().isValidMove(m.move())); if (ConditionAdaptor::isMember(state.state(), m.move())) out.push_back(m); } } void osl::search:: MoveGenerator::generateAll(Player P, const SearchState2& state, MoveLogProbVector& out) { if (P==BLACK) generateAll(state, out); else generateAll(state, out); } namespace osl { namespace search { template const MoveLogProb MoveGenerator::nextMoveWithGeneration(const SearchState2&); template const MoveLogProb MoveGenerator::nextMoveWithGeneration(const SearchState2&); template const MoveLogProb MoveGenerator::nextTacticalMoveWithGeneration(const SearchState2&); template const MoveLogProb MoveGenerator::nextTacticalMoveWithGeneration(const SearchState2&); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchTimer.cc0000644000000000000000000000630012316770314020224 0ustar rootroot/* hasTimer.cc */ #include "osl/search/searchTimer.h" #include "osl/search/usiReporter.h" #include osl::search::SearchTimer::~SearchTimer() { } void osl::search::SearchTimer::throwStop() { assert(shared_timer->stop_all); if (shared_timer->stop_reason == SearchTimerCommon::NoMoreMemory) throw NoMoreMemory(); throw misc::NoMoreTime(); } static uint64_t maximum_node_count = 0; static double maximum_memory_use_ratio = 0.0; void osl::search:: SearchTimer::testAndUpdateNextTimeTest(uint64_t node_count) { SCOPED_LOCK(lk,shared_timer->mutex); if (shared_timer->stop_all) throwStop(); if (shared_timer->next_node_count > node_count) return; const double elapsed = this->elapsed(); if (elapsed > toSeconds(shared_timer->assigned.max) || (shared_timer->stable && elapsed > toSeconds(shared_timer->assigned.standard)) || node_count > shared_timer->node_count_hard_limit) { shared_timer->stop_reason = SearchTimerCommon::NoMoreTime; shared_timer->stop_all = true; throwStop(); } time_point now = clock::now(); shared_timer->nps = node_count / (0.1+toSeconds(now - shared_timer->start_time)); const int period100 = (shared_timer->node_count_hard_limit != std::numeric_limits::max()) ? 1 : 25; shared_timer->next_node_count = node_count + static_cast(shared_timer->nps * period100 / 100.0); shared_timer->last_tested = now; static int skip = 0; if (++skip % (100 / period100) == 0) { const double memory_use_ratio = OslConfig::memoryUseRatio(); shared_timer->last_memory_use1000 = static_cast(1000*memory_use_ratio); if (memory_use_ratio > 0.85) { if (maximum_node_count > 0) { if (node_count > maximum_node_count || (memory_use_ratio > maximum_memory_use_ratio && node_count > 0.85*maximum_node_count) || (memory_use_ratio > 0.87 && node_count > 0.8*maximum_node_count)) { if (memory_use_ratio > 0.87 && memory_use_ratio > maximum_memory_use_ratio) { maximum_memory_use_ratio = std::min(0.88, memory_use_ratio); maximum_node_count = maximum_node_count * 0.9; } shared_timer->stop_reason = SearchTimerCommon::NoMoreMemory; shared_timer->stop_all = true; std::cerr << "stop by memory full " << memory_use_ratio << " " << node_count << "\n"; throwStop(); } } maximum_memory_use_ratio = std::max(memory_use_ratio, maximum_memory_use_ratio); } else if (memory_use_ratio < 0.82) { maximum_node_count = std::max(maximum_node_count, node_count); maximum_memory_use_ratio = 0.82; } #ifndef GPSONE if (elapsed > 1.0) { std::lock_guard lk(OslConfig::lock_io); for (const std::shared_ptr& monitor: this->monitors()) { monitor->timeInfo(node_count, elapsed); monitor->hashInfo(memory_use_ratio); } } #endif } } void osl::search::SearchTimer::adjustMemoryUseLimit(double scale) { maximum_node_count *= scale; } void osl::search::SearchTimer:: addMonitor(const std::shared_ptr& monitor) { shared_timer->monitors.push_back(monitor); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceSearch2.h0000644000000000000000000002033312316770314021156 0ustar rootroot/* quiescenceSearch2.h */ #ifndef _QUIESCENCESEARCH2_H #define _QUIESCENCESEARCH2_H #include "osl/search/fixedEval.h" #include "osl/search/quiescenceRecord.h" #include "osl/search/searchState2.h" #include "osl/eval/pieceEval.h" #include "osl/numEffectState.h" #include "osl/pathEncoding.h" namespace osl { namespace container { class MoveVector; } namespace hash { class HashKey; } namespace search { class SimpleHashTable; /** * å–りåˆã„探索 (陿­¢æŽ¢ç´¢). * * - 試ã™ã®ã¯å–ã‚‹æ‰‹ã¨æˆã‚‹æ‰‹ã®ã¿ * - KFENDæµ http://www31.ocn.ne.jp/~kfend/inside_kfend/quiescence.html * - 高速化ã®ãŸã‚末端ã®å–り返ã—ã¯ï¼Œä¸€ç›´ç·šã«èª­ã‚€ * - åˆé§’ãŒç„¡é§„ã‹ã©ã†ã‹ã‚’考慮ã™ã‚‹ * - 「逃れるã“ã¨ãŒã§ããªã„è„…å¨ã€ã¯ã¾ã å®Ÿè£…ã—ã¦ã„ãªã„ * - æœ«ç«¯ã®æˆã‚‹æ‰‹ã¯ï¼Œé£›è»Šã¨è§’ã ã‘ã§ï¼Œå–り返ã•れãªã„å ´åˆã ã‘ * * TODO: * - å°†æ¥ã¯ï¼Œé€ƒã’る手,有効王手も候補? * */ template class QuiescenceSearch2 : protected FixedEval, private QSearchTraits { typedef FixedEval base_t; SearchState2Core& state; SimpleHashTable& table; int root_depth; int max_depth; /** * 探索ノード数 */ int node_count; /** rootã‹ã‚‰ã®æ·±ã• */ int depthFromRoot() const { return state.path().getDepth() - root_depth; } /** 残り深㕠*/ int depth() const { return max_depth - depthFromRoot(); } public: typedef EvalT eval_t; typedef NumEffectState effect_state_t; using base_t::isWinValue; QuiescenceSearch2(SearchState2Core& s, SimpleHashTable& t) : state(s), table(t), root_depth(s.path().getDepth()), max_depth(QSearchTraits::MaxDepth), node_count(0) { } template int search(eval_t& ev, Move last_move, int depth=QSearchTraits::MaxDepth) { assert(last_move.player() == alt(P)); assert(state.state().turn() == P); max_depth = depth; return searchInternal

(base_t::winThreshold(alt(P)), base_t::winThreshold(P), ev, last_move); } int search(Player P, eval_t& ev, Move last_move, int depth=QSearchTraits::MaxDepth) { if (P == BLACK) return search(ev, last_move, depth); else return search(ev, last_move, depth); } template int searchIteratively(eval_t& ev, Move last_move, int depth=QSearchTraits::MaxDepth) { assert(last_move.player() == alt(P)); assert(state.state().turn() == P); return searchIteratively

(base_t::winThreshold(alt(P)), base_t::winThreshold(P), ev, last_move, depth); } int searchIteratively(Player P, eval_t& ev, Move last_move, int depth=QSearchTraits::MaxDepth) { if (P == BLACK) return searchIteratively(ev, last_move, depth); else return searchIteratively(ev, last_move, depth); } template int searchIteratively(int alpha, int beta, eval_t& ev, Move last_move, int depth) { assert(depth >= 2); int result=0; for (int i=2; i<=depth; i+=2) { max_depth = i; result=searchInternal

(alpha, beta, ev, last_move); } return result; } template int search(int alpha, int beta, eval_t& ev, Move last_move, int depth=QSearchTraits::MaxDepth) { max_depth = depth; return searchInternal

(alpha, beta, ev, last_move); } int search(Player P, int alpha, int beta, eval_t& ev, Move last_move, int depth){ if (P == BLACK) return search(alpha, beta, ev, last_move, depth); else return search(alpha, beta, ev, last_move, depth); } template int searchProbCut(int alpha, int beta, eval_t& ev, Move last_move); int searchProbCut(Player P, int alpha, int beta, eval_t& ev, Move last_move) { if (P == BLACK) return searchProbCut(alpha, beta, ev, last_move); else return searchProbCut(alpha, beta, ev, last_move); } enum EvalUpdateState { AfterUpdate, BeforeUpdate }; template int searchInternal(int alpha, int beta, eval_t& ev, Move last_move, int additional_depth=0, EvalUpdateState need_eval_update=AfterUpdate); private: template int searchMain(QuiescenceRecord *record, int alpha, int beta, eval_t& ev, Move last_move, int additional_depth, EvalUpdateState& need_eval_update); /** * PTYPE ã‚’å–る手を生æˆã—㦠examineMoves を呼㶠* @return cut ã§ãã‚‹ã‹ */ template bool examineCapture(QuiescenceRecord *record, int& curVal, MoveVector& working, int& alpha, int beta, eval_t const& ev, Piece last_piece, int additional_depth); public: template int staticValue(eval_t const& ev, int alpha, int beta, QuiescenceRecord *record); private: template int passValue(int alpha, int beta, eval_t const& ev); int currentValueWithLastThreat(eval_t const& ev, Piece last_move_piece); public: /** * @return cut ã§ãã‚‹ã‹ * @param dont_capture TakeBack ã§è©¦ã—ãŸæ‰‹ã‚’後ã‹ã‚‰é‡è¤‡ã—ã¦è©¦ã•ãªã„ãŸã‚ã«ä½¿ã†. * template parameter ã® has_dont_capture ãŒtrue ã®æ™‚ã ã‘見る */ template bool examineMoves(QuiescenceRecord *record, int& curVal, const Move *first, const Move *last, int& alpha, int beta, eval_t const& ev, int additional_depth, Square dont_capture=Square::STAND()); /** * å˜ç´”ãªå–り返ã—ã®æŽ¢ç´¢. * PieceEval::computeDiffAfterMoveForRP ã¨ç•°ãªã‚Šï¼Œç›¤é¢ã‚’å‹•ã‹ã™ï¼Ž * 王手を正確ã«åˆ¤å®šã—,利ãも伸ã³ã‚‹ * @param attack_piece last_move ãŒçŽ‹æ‰‹å›žé¿ã®æ™‚ã«çŽ‹æ‰‹ã‚’ã‹ã‘ã¦ã„ãŸé§’ */ template int takeBackValue(int alpha, int beta, eval_t const& ev, Move last_move); template bool examineTakeBack(const MoveVector& moves, int& cur_val, int& alpha, int beta, eval_t const& ev); /** * 末端ã®å–り返ã—用. 二ã¤threatを求ã‚ã‚‹ * @param threat1 最大ã®è„…å¨ * @param threat2 2番目ã®è„…å¨ * @param calm_move_only 相手ã®åˆ©ããŒã‚るマスã«ã¯ã„ã‹ãªã„ * @param king_attack_piece P ã«çŽ‹æ‰‹ã‚’ã‹ã‘ã¦ã„ã‚‹é§’(ã®ã†ã¡ã®ä¸€ã¤) */ template bool examineTakeBack2(const MoveVector& moves, QuiescenceThreat& threat2, QuiescenceThreat& threat1, int beta, int beta2, eval_t const& ev); /** 末端ã®å–り返ã—用. * å„å–ã‚Œã‚‹é§’æ¯Žã«æŒ‡æ‰‹ã‚’生æˆã—㦠examineTakeBack2 を呼㶠*/ template bool generateAndExamineTakeBack2(MoveVector& moves, QuiescenceThreat& threat2, QuiescenceThreat& threat1, int beta1, int beta2, eval_t const& ev); /** * last_move ãŒé€ƒã’る手ã§ã€é€ƒã’ãŸå…ˆã®å–り返ã—ã€ã¾ãŸã¯è¿½æ’ƒã®ä¾¡å€¤ã‚’判定 */ template int takeBackOrChase(int alpha, int beta, eval_t const& ev, Move last_move); template int staticValueWithThreat(eval_t const& ev, int alpha, QuiescenceThreat& threat1, QuiescenceThreat& threat2); template int staticValueWithThreat(eval_t const& ev) { QuiescenceThreat t1, t2; return staticValueWithThreat

(ev, base_t::winThreshold(alt(P)), t1, t2); } int staticValueWithThreat(eval_t const& ev) { if (state.state().turn() == BLACK) return staticValueWithThreat(ev); else return staticValueWithThreat(ev); } int nodeCount() const { return node_count; } const NumEffectState& currentState() const { return state.state(); } }; } // namespace search using search::QuiescenceSearch2; } // namespace osl #endif /* _QUIESCENCESEARCH2_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/simpleHashTable.cc0000644000000000000000000000566512316770314021040 0ustar rootroot/* simpleHashTable.cc */ #include "osl/search/simpleHashTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/search/analyzer/recordSet_.h" #include "osl/search/generalSimpleHashTable.tcc" #include namespace osl { template class container::GeneralSimpleHashTable ; } // namespace osl osl::search::SimpleHashTable:: SimpleHashTable(size_t capacity, int minimum_recordlimit, int v) : GeneralSimpleHashTable(capacity), minimum_limit(minimum_recordlimit), verbose(v) { } uint64_t osl::search::SimpleHashTable:: memoryUse() const { return 1ull * (sizeof(SimpleHashRecord)+sizeof(HashKey)+sizeof(SimpleHashRecord*)) * size(); } osl::search::SimpleHashTable:: ~SimpleHashTable() { const uint64_t memory_use = memoryUse(); if ((verbose > 1 && size()) || memory_use > (1024*(1ull<<20))) { std::cerr << "SimpleHashTable size: " << size() << " (" << memory_use / (1ull<<20) << "MB)" << ", cache hit " << table->num_cache_hit << ", table full " << table->num_record_after_full << "\n"; } } void osl::search::SimpleHashTable:: setVerbose(int v) { verbose = v; } void osl::search::SimpleHashTable:: setMinimumRecordLimit(int new_limit) { minimum_limit = new_limit; } int osl::search::SimpleHashTable:: minimumRecordLimit() const { return minimum_limit; } osl::search::SimpleHashRecord * osl::search::SimpleHashTable:: allocate(const HashKey& key, int limit) { if (limit < minimumRecordLimit()) return find(key); return GeneralSimpleHashTable ::allocate (key); } int osl::search::SimpleHashTable:: verboseLevel() const { return verbose; } bool osl::search::SimpleHashTable:: isConsistent() const { return true; } int osl::search::SimpleHashTable:: divSize() const { return GeneralSimpleHashTable::divSize(); } #ifndef MINIMAL void osl::search::SimpleHashTable:: getPV(const HashKey& root, MoveVector& out, size_t *quiesce_start) const { analyzer::RecordSet dejavu; HashKey key = root; const SimpleHashRecord *record; while (true) { record = table->find(key); if (! record || dejavu.find(record) != dejavu.end()) { break; } const Move best_move = record->bestMove().move(); if (best_move.isInvalid()) { break; } dejavu.insert(record); out.push_back(best_move); key = key.newHashWithMove(best_move); } if (! quiesce_start || ! record) return; *quiesce_start = out.size(); while (true) { const Move best_move = record->qrecord.bestMove(); if (best_move.isInvalid()) { break; } out.push_back(best_move); key = key.newHashWithMove(best_move); record = table->find(key); if (! record || dejavu.find(record) != dejavu.end()) { break; } dejavu.insert(record); } } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta4.h0000644000000000000000000000331712316770314017572 0ustar rootroot/* alphaBeta4.h */ #ifndef OSL_SEARCH_ALPHABETA4_H #define OSL_SEARCH_ALPHABETA4_H #include "osl/numEffectState.h" #include "osl/search/searchTimer.h" #include "osl/search/fixedEval.h" // temporal #include "osl/search/searchState2.h" #include "osl/eval/openMidEndingEval.h" #include "osl/eval/progressEval.h" namespace osl { namespace search { class CountRecorder; class SimpleHashTable; struct MoveWithComment; } namespace search4 { using search::CountRecorder; using search::SimpleHashTable; using search::MoveWithComment; using search::SearchState2; using search::SearchTimer; using search::FixedEval; using search::TimeAssigned; class AlphaBeta4 : public SearchTimer, FixedEval { public: // interface required for game_playing::SearchPlayer typedef SearchState2::checkmate_t checkmate_t; typedef eval::ml::OpenMidEndingEval eval_t; // typedef eval::PieceEval eval_t; // typedef eval::ProgressEval eval_t; AlphaBeta4(const NumEffectState& s, checkmate_t& checker, SimpleHashTable *t, CountRecorder&); ~AlphaBeta4(); Move computeBestMoveIteratively (int limit, int step, int initial_limit=600, size_t node_limit=1600000, const TimeAssigned& assign=TimeAssigned(milliseconds(60*1000)), MoveWithComment *additional_info=0); bool isReasonableMove(Move move, int pawn_sacrifice=1); void setRootIgnoreMoves(const MoveVector *rim, bool); void setHistory(const MoveStack& h); void enableMultiPV(unsigned int) {} }; } using search4::AlphaBeta4; } #endif /* OSL_SEARCH_ALPHABETA4_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/hashRejections.h0000644000000000000000000000203512316770314020572 0ustar rootroot/* hashRejections.h */ #ifndef _HASHREJECTIONS_H #define _HASHREJECTIONS_H #include "osl/numEffectState.h" #include "osl/hashKey.h" namespace osl { namespace search { class HashRejections { struct RootTable; struct Table; std::shared_ptr root_table; std::unique_ptr

table; public: HashRejections(); HashRejections(const HashRejections&); ~HashRejections(); HashRejections& operator=(const HashRejections&); void addRejectionRoot(const NumEffectState& parent, const HashKey& key, Move move); void clearRejectionRoot(const NumEffectState& parent, const HashKey& key, Move move); void addRejection(const NumEffectState& parent, const HashKey& key, Move move); void clearRejection(const NumEffectState& parent, const HashKey& key, Move move); bool rejectionProbe(const HashKey& cur, const HashKey& parent) const; }; } } #endif /* _HASHREJECTIONS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceGenerator.cc0000644000000000000000000001062612316770314021757 0ustar rootroot/* quiescenceGenerator.cc */ #include "osl/search/quiescenceGenerator.h" #include "osl/search/quiescenceGenerator.tcc" #include "osl/move_generator/promote_.tcc" #include "osl/move_generator/pieceOnBoard.tcc" #include "osl/eval/openMidEndingEval.h" #include "osl/eval/progressEval.h" namespace osl { namespace search { template struct QuiescenceGenerator; template struct QuiescenceGenerator; template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); template void QuiescenceGenerator::capture(const NumEffectState&, MoveVector&, Piece); #ifndef MINIMAL template void QuiescenceGenerator::escapeFromLastMove(const NumEffectState&, Move, MoveVector&); template void QuiescenceGenerator::escapeFromLastMove(const NumEffectState&, Move, MoveVector&); template void QuiescenceGenerator::escapeFromLastMove(const NumEffectState&, Move, MoveVector&); template void QuiescenceGenerator::escapeFromLastMove(const NumEffectState&, Move, MoveVector&); #endif template void QuiescenceGenerator::escapeFromLastMove(const NumEffectState&, Move, MoveVector&); template void QuiescenceGenerator::escapeFromLastMove(const NumEffectState&, Move, MoveVector&); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/dualThreatmateState.h0000644000000000000000000000433012316770314021566 0ustar rootroot/* dualThreatmateState.h */ #ifndef OSL_SEARCH__DUALTHREATMATESTATE_H #define OSL_SEARCH__DUALTHREATMATESTATE_H #include "osl/search/threatmateState.h" #include "osl/effect_util/sendOffSquare.h" #include namespace osl { namespace search { class DualThreatmateState { CArray threatmate_move; CArray king_status; ThreatmateState& wstatus(Player king) { return king_status[king]; } public: /** XXX: QuiescenceRecord ã¸ã®è©°ã‚è¾¼ã¿ã®ãŸã‚ */ mutable SendOffSquare::SendOff8 sendoffs; struct Flags { #ifdef OSL_SMP volatile #endif bool is_king_in_check:4; #ifdef OSL_SMP volatile #endif char static_value_type:4; } flags; explicit DualThreatmateState(ThreatmateState::Status b=ThreatmateState::UNKNOWN, ThreatmateState::Status w=ThreatmateState::UNKNOWN) : sendoffs(SendOffSquare::invalidData()) { wstatus(BLACK) = b; wstatus(WHITE) = w; flags.is_king_in_check = false; flags.static_value_type = 0; } const ThreatmateState& status(Player king) const { return king_status[king]; } void setThreatmate(Player king, Move m) { assert(m.isNormal()); wstatus(king).setThreatmate(ThreatmateState::THREATMATE); threatmate_move[king] = m; } bool isThreatmate(Player king) const { return status(king).isThreatmate(); } const Move threatmateMove(Player king) const { return threatmate_move[king]; } bool maybeThreatmate(Player king) const { return status(king).maybeThreatmate(); } bool mayHaveCheckmate(Player king) const { return status(king).mayHaveCheckmate(); } void updateInLock(Player turn, const DualThreatmateState *parent, bool in_check) { if (parent) { if (! maybeThreatmate(turn)) wstatus(turn).update(&parent->status(turn), in_check); if (! mayHaveCheckmate(alt(turn))) wstatus(alt(turn)).update(&parent->status(alt(turn)), in_check); } } }; std::ostream& operator<<(std::ostream&, DualThreatmateState); } } // namespace osl #endif /* OSL_SEARCH__DUALTHREATMATESTATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/search/simpleHashRecord.cc0000644000000000000000000000156412316770314021221 0ustar rootroot/* simpleHashRecord.cc */ #include "osl/search/simpleHashRecord.h" #include "osl/csa.h" #include #include #include #ifndef MINIMAL void osl::search:: SimpleHashRecord::dump(std::ostream& os) const { os << "SimpleHashRecord " << this << " node_count " << nodeCount() << "\n"; os << "best move " << csa::show(best_move.move()) << " " << best_move.logProb() << "\t"; os << "limit: l " << lower_limit << " u " << upper_limit << "\n"; os << "in_check " << inCheck() << "\n"; if (hasLowerBound(0)) os << lowerBound(); else os << "*"; os << " < "; if (hasUpperBound(0)) os << upperBound(); else os << "*"; os << "\n"; qrecord.dump(os); } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveScore.h0000644000000000000000000000227112316770314017565 0ustar rootroot/* moveScore.h */ #ifndef OSL_SEARCH_MOVESCORE_H #define OSL_SEARCH_MOVESCORE_H #include "osl/numEffectState.h" namespace osl { namespace search { struct MoveScore { Move move; int score; static MoveScore* sortPositive(MoveScore *f, MoveScore *l); static MoveScore* generateCapture (const NumEffectState& state, MoveScore *out); template static MoveScore* generateCapture (const NumEffectState& state, MoveScore *out); static MoveScore* generateNoCapture (const NumEffectState& state, MoveScore *out); static MoveScore* generateCheckNoCapture (const NumEffectState& state, MoveScore *out); static MoveScore* generateAll (const NumEffectState& state, MoveScore *out); static MoveScore* generateKingEscape (const NumEffectState& state, MoveScore *out); }; inline bool operator<(const MoveScore& f, const MoveScore& s) { return f.score < s.score; } inline bool operator>(const MoveScore& f, const MoveScore& s) { return f.score > s.score; } } } #endif /* OSL_SEARCH_MOVESCORE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceGenerator.tcc0000644000000000000000000013010412316770314022135 0ustar rootroot/* quiescenceGenerator.tcc */ #ifndef QUIESCENCEGENERATOR_TCC #define QUIESCENCEGENERATOR_TCC #include "osl/search/quiescenceGenerator.h" #include "osl/search/breakThreatmate.h" #include "osl/additionalEffect.h" #include "osl/effect_util/sendOffSquare.h" #include "osl/effect_util/shadowEffect.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/effect_util/effectUtil.h" #include "osl/effect_util/pin.h" #include "osl/move_generator/attackToPinned.h" #include "osl/move_generator/addEffectWithEffect.h" template template void osl::search::QuiescenceGenerator

:: capture(const NumEffectState& state, MoveVector& moves, Piece dont_capture) { mask_t pieces = state.effectedMask(P).template selectBit() & state.piecesOnBoard(alt(P)).getMask(PtypeFuns::indexNum); if (has_dont_capture && dont_capture.isPiece() && (dont_capture.ptype() == PTYPE)) { while (pieces.any()) { const Piece target = state.pieceOf(pieces.takeOneBit()+PtypeFuns::indexNum*32); if (target != dont_capture) capture(state, target.square(), moves); } } else { while (pieces.any()) { const Piece target = state.pieceOf(pieces.takeOneBit()+PtypeFuns::indexNum*32); capture(state, target.square(), moves); } } if (((PTYPE == KNIGHT) || (PTYPE == BISHOP)) && state.hasPieceOnStand(P)) { // æ­©ã§é§’ã‚’å–る手ãŒã‚ã‚‹å ´åˆã¯ï¼Œè¿½åŠ åˆ©ãã‚’ã¤ã‘ã‚‹ // NOTE: MoveVector ã¯push_backã—ã¦ã‚‚iteratorã‚’invalidate // ã—ãªã„ã¨ã„ã†ä»•様ã«ä¾å­˜ MoveVector::const_iterator original_end = moves.end(); for (MoveVector::const_iterator p=moves.begin(); p!=original_end; ++p) { const Square from = p->from(); if ((p->oldPtype() == PAWN) && (state.hasEffectAt(p->to()))) { move_generator::AdditionalLance

::generate(state, from, moves); } } } } template inline void osl::search::QuiescenceGenerator

:: attackMajorPieceFirstSelection(const NumEffectState& state, PieceMask pins, const MoveVector& all_moves, MoveVector& moves, MoveVector& expensive_drops) { for (Move m: all_moves) { const Square to = m.to(); { const int defense = state.countEffect(alt(P),to, pins); int offense = state.countEffect(P,to) + (m.isDrop() ? 1 : 0); if (defense >= offense) offense += AdditionalEffect::count2(state, to, P); if (m.ptype() != PAWN) { if (defense > offense) continue; } else { if (defense && (offense==1)) { if (! (state.hasEffectByPtype(alt(P),to) && state.hasEffectByPtype(alt(P),to))) continue; } } const Ptype ptype = m.ptype(); if ((defense >= offense) && (unpromote(ptype) != PAWN)) continue; if (ptype != PAWN) { const Square front_position = to + DirectionPlayerTraits::offset(); const Piece front_piece = state.pieceAt(front_position); if (front_piece.ptypeO() == newPtypeO(alt(P),PAWN)) continue; } if (m.isDrop() && (m.ptype() == PAWN) && to.canPromote

()) { // 垂れ歩 const Square back_position = to + DirectionPlayerTraits::offset(); if (state.pieceOnBoard(back_position).isEmpty()) moves.push_back(Move(back_position, PAWN, P)); } const int ptype_value = eval::Ptype_Eval_Table.value(ptype); const bool is_large_piece = (ptype_value > eval::PtypeEvalTraits::val); if ((m.isDrop() && (ptype_value > eval::PtypeEvalTraits::val)) || (is_large_piece && defense)) expensive_drops.push_back(m); else moves.push_back(m); } } } template inline void osl::search::QuiescenceGenerator

:: attackMajorPieceSecondSelection(bool target_has_support, const MoveVector& src, MoveVector& out) { for (Move m: src) { const Ptype ptype = m.ptype(); if (target_has_support && (eval::Ptype_Eval_Table.value(ptype) >= eval::PtypeEvalTraits::val)) continue; out.push_back(m); } } template void osl::search::QuiescenceGenerator

:: attackMajorPieceZerothSelection(const NumEffectState& state, const MoveVector& src, Square target, MoveVector& open_out, MoveVector& out) { for (Move m: src) { assert(!ShouldPromoteCut::canIgnoreAndNotDrop

(m)); const bool is_open = (! m.isDrop()) && state.hasEffectAt

(m.from()) && (state.hasEffectByPtype(P, m.from()) || state.hasEffectByPtype(P, m.from()) || state.hasEffectByPtype(P, m.from())) && ! state.hasEffectIf(m.ptypeO(), m.to(), target); // å–る手ã¯é‡è¤‡ const bool may_overlap = m.isCaptureOrPromotion(); if (is_open) { if (! may_overlap // å–り返ã•れる場åˆã¯ãŸã¶ã‚“é‡è¤‡ã—ãªã„ || state.hasEffectAt(m.to())) open_out.push_back(m); } else { if (! may_overlap) out.push_back(m); } } } template void osl::search::QuiescenceGenerator

:: attackMajorPiece(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; MoveVector work; MoveVector unsupported, supported; assert(PtypeTraits::indexLimit == PtypeTraits::indexMin); for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; i++) { const Piece p = state.pieceOf(i); if (p.isOnBoardByOwner()) { const Square target = p.square(); assert(isMajor(p.ptype())); const bool unstable_rook = (p.ptype() == ROOK) && (state.pieceAt(target + DirectionPlayerTraits::offset()) != Piece::EMPTY()); // å‰ã«é€²ã‚ãªã„ work.clear(); if (state.hasEffectAt(alt(P), target) && (! unstable_rook)) { move_generator::GenerateAddEffectWithEffect::generate (P, state, target, work); attackMajorPieceZerothSelection(state, work, target, moves, supported); } else if (unstable_rook || (! state.hasEffectAt(P, target))) { // ãŸã ã§å–れる時ã«ã¯åˆ©ãã‚’ã¤ã‘ãªã„ move_generator::GenerateAddEffectWithEffect::generate (P, state, target, work); attackMajorPieceZerothSelection(state, work, target, moves, unsupported); } } } // first pass MoveVector drops_supported, drops_unsupported; attackMajorPieceFirstSelection(state, pins, unsupported, moves, drops_unsupported); attackMajorPieceFirstSelection(state, pins, supported, moves, drops_supported); // second pass if (moves.size() > 5) return; attackMajorPieceSecondSelection(false, drops_unsupported, moves); if (moves.size() > 5) return; attackMajorPieceSecondSelection(true, drops_supported, moves); } template void osl::search::QuiescenceGenerator

:: escapeNormalPiece(const NumEffectState& state, Piece escape, MoveVector& moves, bool add_support_only) { assert(escape.ptype() != KING); using namespace move_action; MoveVector all_moves; const Piece attack_piece = state.findCheapAttack(alt(P), escape.square()); const int attack_ptype_value = eval::Ptype_Eval_Table.value(unpromote(attack_piece.ptype())); const Square escape_from = escape.square(); if (! add_support_only) { GenerateEscape

::generateCheap(state, escape, all_moves); for (Move m: all_moves) { const Square to = m.to(); if (m.isDrop()) { if (! state.hasEffectAt

(to)) continue; // ä¸­åˆ #ifdef QSEARCH_EXPENSIVE_BLOCK if (eval::Ptype_Eval_Table.value(m.ptype()) > attack_ptype_value) continue; #else if (m.ptype() != PAWN) continue; #endif moves.push_back(m); } else { if (m.from() != escape_from) { // ç§»å‹•åˆ if (! state.hasMultipleEffectAt(P, to)) continue; if (eval::Ptype_Eval_Table.value(m.ptype()) > attack_ptype_value) continue; } // å–る手ã¯é‡è¤‡ // TODO: KnightCaptureDepth assert(! ShouldPromoteCut::canIgnoreMove

(m)); if (! m.isCaptureOrPromotion()) { moves.push_back(m); } } } } // ç´ã‚’ã¤ã‘ã‚‹ if (unpromote(attack_piece.ptype()) == PAWN) return; if ((eval::Ptype_Eval_Table.value(escape.ptype()) - attack_ptype_value) >= (eval::PtypeEvalTraits::val - eval::PtypeEvalTraits::val)) return; if (state.hasEffectAt

(escape_from) || (state.countEffect(alt(P), escape_from) != 1)) return; all_moves.clear(); move_generator::GenerateAddEffectWithEffect::generate (P, state, escape_from, all_moves); const size_t escape_moves = moves.size(); MoveVector not_drop; for (Move m: all_moves) { const Square to = m.to(); if (m.isDrop()) { if (state.hasEffectAt(to) && (! state.hasEffectAt

(to))) continue; // æ‰“ã¤æ‰‹ã¯æ­©ã‹é¦™è»Šã ã‘ if ((m.ptype() != PAWN) && (m.ptype() != LANCE)) continue; moves.push_back(m); } else { // 移動 const int defense = state.countEffect(P,to); const int offense = state.countEffect(alt(P),to); if (offense >= defense) continue; // å–る手ã¯é‡è¤‡ // TODO: KnightCaptureDepth assert(! ShouldPromoteCut::canIgnoreMove

(m)); if (! m.isCaptureOrPromotion()) { moves.push_back(m); } } } // åˆã‚ã›è§’ if (state.hasEffectByPtype(alt(P), escape_from) && state.hasPieceOnStand(P)) { const Piece bishop = state.findAttackAt(alt(P), escape_from); assert(unpromote(bishop.ptype()) == BISHOP); { Square p = bishop.square(); const Offset offset = Board_Table.getShortOffset(Offset32(p,escape_from)); p += offset; while (state.pieceAt(p).isEmpty()) { if (state.hasEffectAt

(p)) { moves.push_back(Move(p, BISHOP, P)); break; } p += offset; } } } if (escape_moves == moves.size()) // drop not found moves.push_back(not_drop.begin(), not_drop.end()); } template void osl::search::QuiescenceGenerator

:: escapeAll(const NumEffectState& state, MoveVector& moves) { // 逃ã’ã‚‹ã®ã¯å¤§é§’ã‹ä¾¡å€¤ã®ä¸€ç•ªé«˜ã„é§’ã®ã¿ const PieceMask pieces = state.effectedMask(alt(P)) & state.piecesOnBoard(P); bool found_attacked_piece = false; mask_t m = pieces.selectBit(); while (m.any()) { const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); found_attacked_piece = true; escapeNormalPiece(state, p, moves); } m = pieces.selectBit(); while (m.any()) { const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); found_attacked_piece = true; escapeNormalPiece(state, p, moves); } if (found_attacked_piece) goto finish; m = pieces.selectBit(); while (m.any()) { const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); escapeNormalPiece(state, p, moves); goto finish; } m = pieces.selectBit(); while (m.any()) { const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); escapeNormalPiece(state, p, moves); goto finish; } m = pieces.selectBit(); while (m.any()) { // æˆæ¡‚ã¯é€ƒã’ãªã„ const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); escapeNormalPiece(state, p, moves, p.ptype()==PKNIGHT); goto finish; } m = pieces.selectBit(); while (m.any()) { // 香,æˆé¦™ã¯é€ƒã’ãªã„ const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); escapeNormalPiece(state, p, moves, true); goto finish; } m = pieces.selectBit(); while (m.any()) { // 歩,ã¨é‡‘ã¯é€ƒã’ãªã„ const Piece p = state.pieceOf(m.takeOneBit()+PtypeFuns::indexNum*32); assert(p.isOnBoardByOwner

() && state.hasEffectAt(p.square())); escapeNormalPiece(state, p, moves, true); goto finish; } finish: return; } template template void osl::search::QuiescenceGenerator

:: escapeFromLastMoveOtherThanPawn(const NumEffectState& state, Move last_move, MoveVector& moves) { if (! last_move.isNormal()) return; assert(last_move.ptype() != PAWN); PieceVector targets; const Square from = last_move.to(); EffectUtil::findThreat(state, from, last_move.ptypeO(), targets); if (targets.empty()) return; assert(targets[0].ptype() != KING); escapeNormalPiece(state, targets[0], moves, (last_move.ptype() != PAWN) && (eval::Ptype_Eval_Table.value(targets[0].ptype()) <= eval::Ptype_Eval_Table.value(KNIGHT))); if (targets.size() > 1) escapeNormalPiece(state, targets[1], moves, (last_move.ptype() != PAWN) && (eval::Ptype_Eval_Table.value(targets[1].ptype()) <= eval::Ptype_Eval_Table.value(KNIGHT))); } template bool osl::search::QuiescenceGenerator

:: escapeByMoveOnly(const NumEffectState& state, Piece piece, MoveVector& moves) { assert(piece.isOnBoardByOwner

()); MoveVector all_moves; GeneratePieceOnBoard::generate(state.turn(),state,piece,all_moves); const Player Opponent = alt(P); const Square from = piece.square(); const bool consider_shadowing = state.hasEffectByPtype(Opponent, from) || state.hasEffectByPtype(Opponent, from) || state.hasEffectByPtype(Opponent, from); const bool is_major = isMajor(piece.ptype()); const bool chase_danger = (! state.hasEffectAt(P, from) && (state.hasMultipleEffectAt(alt(P), from) || AdditionalEffect::hasEffect(state, from, alt(P)))); for (Move m: all_moves) { assert(m.from() == piece.square()); if (m.isCapture()) continue; const Square to = m.to(); const bool safe_position = (consider_shadowing ? (! state.hasEffectByWithRemove(to, from)) : (! state.hasEffectAt(to))); if (safe_position) { if (! is_major || ! chase_danger) return true; if (! to.canPromote()) return true; // 自陣以外も対象ã«ã™ã‚‹å ´åˆã¯ QuiescenceSearch も調整 if ((to - from) != Board_Table.getShortOffset(Offset32(to, from))) return true; // 二歩以上逃ã’られれã°è‰¯ã— } moves.push_back(m); } return false; } template void osl::search::QuiescenceGenerator

:: check(const NumEffectState& state, PieceMask pins, MoveVector& moves, bool no_liberty) { Square8 sendoffs; const Square king_position = state.kingSquare(alt(P)); effect_util::SendOffSquare::find

(state, king_position, sendoffs); check(state, pins, no_liberty, sendoffs, moves); } template void osl::search::QuiescenceGenerator

:: check(const NumEffectState& state, PieceMask pins, bool no_liberty, const Square8& sendoffs, MoveVector& moves) { using namespace move_action; MoveVector all_moves; const Square king_position = state.kingSquare(alt(P)); move_generator::GenerateAddEffectWithEffect::generate (P, state, king_position, all_moves); MoveVector merginal_moves; for (Move m: all_moves) { // å–る手,æˆã‚‹æ‰‹ã¯é‡è¤‡ assert(! ShouldPromoteCut::canIgnoreAndNotDrop

(m)); if (m.isPromotion()) continue; const Square to = m.to(); const Ptype captured = m.capturePtype(); if ((captured != PTYPE_EMPTY) && (eval::Ptype_Eval_Table.value(captured) >= eval::PtypeEvalTraits::val)) continue; const bool is_open = (! m.isDrop()) && state.hasEffectAt

(m.from()) && (state.hasEffectByPtype(P, m.from()) || state.hasEffectByPtype(P, m.from()) || state.hasEffectByPtype(P, m.from())) && ! state.hasEffectIf(m.ptypeO(), m.to(), king_position); if (! is_open) { if ((m.ptype() != PAWN) && (m.ptype() != KNIGHT)) { // æ­©ã®å‰ã¯èª­ã¾ãªã„ const Square front_position = to + DirectionPlayerTraits::offset(); const Piece front_piece = state.pieceAt(front_position); if (front_piece.ptypeO() == newPtypeO(alt(P),PAWN)) continue; } if (! sendoffs.isMember(to)) { const int defense = state.countEffect(alt(P),to, pins); int offense = state.countEffect(P,to) + no_liberty; const bool may_effective = offense && (! sendoffs.empty()); if (m.isDrop()) ++offense; if (defense >= offense) offense += AdditionalEffect::count2(state, to, P); if (defense >= offense) offense += ShadowEffect::count2(state, to, P); if (m.ptype() == KNIGHT) { const Square front_position = to + DirectionPlayerTraits::offset(); if (state.hasEffectAt

(front_position)) offense+=1; // pin ã‚‚ã—ãã¯ç©ºã„ãŸå ´æ‰€ã«ä½•ã‹æ‰“ã¦ã‚‹ã‹ã‚‚ } if (defense > offense) { const bool side_attack = (king_position.x() == 1 || king_position.x() == 9) && m.ptype() == PAWN; if (! side_attack) continue; // 乱暴ãªçŽ‹æ‰‹ã¯æŒ‡ã•ãªã„ } else if (defense == offense) { if ((unpromote(m.ptype()) == PAWN) || state.hasEffectByPtype(P, to) || state.hasEffectByPtype(P, to)) moves.push_back(m); else if (may_effective) merginal_moves.push_back(m); continue; } } } if (m.isDrop() && (m.ptype() == PAWN) && to.canPromote

()) { // 垂れ歩 const Square back_position = to + DirectionPlayerTraits::offset(); if (state.pieceOnBoard(back_position).isEmpty()) moves.push_back(Move(back_position, PAWN, P)); } moves.push_back(m); } if (moves.size() < 3) moves.push_back(merginal_moves.begin(), merginal_moves.end()); } template void osl::search::QuiescenceGenerator

:: promote(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; MoveVector all_moves; move_generator::Promote

::generate(state, all_moves); for (Move m: all_moves) { const Square to = m.to(); const int defense = state.countEffect(alt(P),to, pins); int offense = state.countEffect(P,to); if (defense >= offense) offense += AdditionalEffect::count2(state, to, P); if (m.ptype() == PPAWN && defense && offense + 1 >= defense) { // æ­©ãŒæˆã‚Œã‚‹æ™‚ã¯è¿½åŠ åˆ©ãã‚’ã¤ã‘ã¦ã¿ã‚‹? if (m.ptype() == PPAWN) { // é£›è»ŠãŒæ¨ªã«å‹•ã for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece rook = state.pieceOf(i); if (! rook.isOnBoardByOwner

() || rook.ptype() == PROOK || rook.square().template canPromote

()) continue; const Square mid(m.from().x(), rook.square().y()); if (state.pieceOnBoard(mid).isEmpty() && state.isEmptyBetween(m.from(), mid) && state.isEmptyBetween(rook.square(), mid)) { const Move m(rook.square(), mid, ROOK, PTYPE_EMPTY, false, P); moves.push_back(m); } } if (state.hasPieceOnStand(P)) move_generator::AdditionalLance

::generate(state, m.from(), moves); // ã‚ã¨ã¯æ¡‚馬ãらã„? } } if (defense > offense) { continue; // æˆã‚Šã§ã¯ã‚ã¾ã‚Šä¹±æš´ãªæ‰‹ã¯æŒ‡ã•ãªã„ } if ((defense == offense) && (m.ptype() != PPAWN)) continue; moves.push_back(m); } } template void osl::search::QuiescenceGenerator

:: attackKing8(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; MoveVector all_moves; MoveVector not8; MoveVector not_drop; MoveVector major_drop; move_generator::AddEffect8

::generate(state, all_moves); const Square king_position = state.kingSquare(alt(P)); const int king_x = king_position.x(); for (Move m: all_moves) { // å–る手,æˆã‚‹æ‰‹ã¯é‡è¤‡ assert(! ShouldPromoteCut::canIgnoreAndNotDrop

(m)); assert(! m.isPromotion()); const Square to = m.to(); #ifndef NDEBUG const Ptype captured = m.capturePtype(); assert(captured==PTYPE_EMPTY); #endif const Ptype ptype = m.ptype(); const int defense = state.countEffect(alt(P),to,pins); int offense = state.countEffect(P,to) + (m.isDrop() ? 1 : 0); if (defense >= offense) offense += AdditionalEffect::count2(state, to, P); if (ptype == PAWN) { const Square head = to + DirectionPlayerTraits::offset(); if (state.hasEffectAt

(head)) ++offense; } if (defense > offense) continue; if (defense == offense) { if (ptype != PAWN) continue; } if (isMajor(ptype)) { if (defense == 0) { // 大駒ã¯åˆ©ãã®ã‚ã‚‹ã¨ã“ã‚ã«ã¯ã„ã‹ãªã„ TODO: kingã®ã¿è¨±å¯? if (isPromoted(ptype) && to.x() == king_x && abs(to.y() - king_position.y()) <= 2) moves.push_back(m); else if (m.isDrop()) major_drop.push_back(m); else not_drop.push_back(m); } continue; } if (Ptype_Table.getMoveMask(m.ptype()) == PtypeTraits::moveMask) { const int y = to.y(); if (((P == BLACK) && (y == 1)) || ((P == WHITE) && (y == 9))) continue; // 1段目ã®é‡‘類 } // æ­©ã®å‰ã¯èª­ã¾ãªã„ TODO: 桂馬ã ã‘許ã™? if (ptype != PAWN) { if (state.hasEffectByPtype(alt(P), to)) continue; if (state.hasEffectByPtype(alt(P), to)) { not_drop.push_back(m); continue; } } if (! king_position.isNeighboring8(to)) not8.push_back(m); else if (! m.isDrop()) not_drop.push_back(m); else moves.push_back(m); } const size_t minimum_moves = (king_position.squareForBlack

().y() == 1) ? 3 : 2; for (MoveVector::const_iterator p=not8.begin(); (p!=not8.end()) && (moves.size() <= minimum_moves); ++p) { moves.push_back(*p); } for (MoveVector::const_iterator p=not_drop.begin(); (p!=not_drop.end()) && (moves.size() <= minimum_moves); ++p) { moves.push_back(*p); } for (MoveVector::const_iterator p=major_drop.begin(); (p!=major_drop.end()) && (moves.size() <= minimum_moves); ++p) { moves.push_back(*p); } } template void osl::search::QuiescenceGenerator

:: attackToPinned(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; MoveVector all_moves; move_generator::AttackToPinned

::generate(state, all_moves); for (Move m: all_moves) { // å–る手,æˆã‚‹æ‰‹ã¯é‡è¤‡ assert(!ShouldPromoteCut::canIgnoreAndNotDrop

(m)); if (m.isPromotion()) continue; const Square to = m.to(); const Ptype captured = m.capturePtype(); if (captured != PTYPE_EMPTY) continue; const Ptype ptype = m.ptype(); const int defense = state.countEffect(alt(P),to,pins); int offense = state.countEffect(P,to) + (m.isDrop() ? 1 : 0); if (defense >= offense) offense += AdditionalEffect::count2(state, to, P); if (ptype == PAWN) { const Square head = to + DirectionPlayerTraits::offset(); if (state.hasEffectAt

(head)) ++offense; } if (defense > offense) continue; if (defense == offense) { if (ptype != PAWN) continue; } // æ­©ã®å‰ã¯èª­ã¾ãªã„ TODO: 桂馬ã ã‘許ã™? if (ptype != PAWN) { const Square front_position = to + DirectionPlayerTraits::offset(); const Piece front_piece = state.pieceAt(front_position); if (front_piece.ptypeO() == newPtypeO(alt(P),PAWN)) continue; } moves.push_back(m); } } template void osl::search::QuiescenceGenerator

:: utilizePromoted(const NumEffectState& state, Piece target, MoveVector& moves) { if (! target.isPromoted()) return; if (/*isMajor*/ target.ptype() == ROOK || target.ptype() == BISHOP) return; MoveVector all_moves; move_generator::GeneratePieceOnBoard::generate(P,state, target, all_moves); MoveVector others; const Player Opponent = alt(P); bool has_good_capture = false; bool may_have_additional = false; // 飛車ã®å‰ã¨ã‹ for (Move m: all_moves) { assert(m.from() == target.square()); if (m.isCapture()) { if (m.capturePtype() != PAWN) has_good_capture =true; continue; } const Square to = m.to(); int offense = state.countEffect(P, to); const int defense = state.countEffect(Opponent, to); const int additional = AdditionalEffect::count2(state, to, P); if (defense >= offense) { offense += additional; may_have_additional |= (additional > 0); } if (defense >= offense) { others.push_back(m); continue; } moves.push_back(m); } if ((! has_good_capture) && may_have_additional) moves.push_back(others.begin(), others.end()); } template void osl::search::QuiescenceGenerator

:: breakThreatmate(const NumEffectState& state, Move threatmate, PieceMask pins, MoveVector& moves) { MoveVector all_moves, major_piece, major_sacrifice; assert(threatmate.isNormal()); const Square target = threatmate.to(); // defense by add effect move_generator::GenerateAddEffectWithEffect::generate (P, state, target, all_moves); for (Move m: all_moves) { const Ptype ptype = m.ptype(); if (ptype == KING) continue; // KING_WALK will generate if (! m.isDrop()) { assert(!ShouldPromoteCut::canIgnoreAndNotDrop

(m)); if (m.isPromotion()) continue; if (isMajor(ptype) && state.hasEffectByPiece(state.pieceOnBoard(m.from()), target)) continue; // already have effect } const Square to = m.to(); const int me = state.countEffect(P, to) + (m.isDrop() ? 1 : 0); const int op = state.countEffect(alt(P), to, pins); if ((me >= 2) || (op == 0)) { if (isMajor(ptype)) { if (op) major_sacrifice.push_back(m); else major_piece.push_back(m); } else // ! major { if (m.isDrop() && (ptype == GOLD || ptype == SILVER) && (to.x() == 1 || to.x() == 9)) major_piece.push_back(m); else moves.push_back(m); } } } all_moves.clear(); if (threatmate.isDrop()) { // 場所を指定ã—ã¦ã€Drop を作る方法ã¯? if (state.hasPieceOnStand(P) && ! state.isPawnMaskSet(P, target.x()) && PtypePlayerTraits::canDropTo(target)) moves.push_back(Move(target, PAWN, P)); else if (state.hasPieceOnStand(P) && PtypePlayerTraits::canDropTo(target)) moves.push_back(Move(target, LANCE, P)); else if (state.hasPieceOnStand(P) && PtypePlayerTraits::canDropTo(target)) moves.push_back(Move(target, KNIGHT, P)); else if (state.hasPieceOnStand(P)) moves.push_back(Move(target, SILVER, P)); else if (state.hasPieceOnStand(P)) moves.push_back(Move(target, GOLD, P)); } // é•·ã„利ãã®blockä»– BreakThreatmate::findBlockLong(state, threatmate, all_moves); if (! all_moves.empty()) { Ptype cheapest = PTYPE_EMPTY; if (state.hasPieceOnStand(P)) cheapest = PAWN; else if (state.hasPieceOnStand(P)) cheapest = LANCE; else if (state.hasPieceOnStand(P)) cheapest = KNIGHT; for (Move m: all_moves) { const int d = state.countEffect(P, m.to()) + m.isDrop(); const int a = state.countEffect(alt(P), m.to()); if (a >= d && ! (d >= 2 && m.ptype() == PAWN)) continue; if (m.ptype() != cheapest && cheapest != PTYPE_EMPTY && Ptype_Table.canDropTo(P, cheapest, m.to())) continue; moves.push_back(m); break; } all_moves.clear(); } const Square king_position = state.kingSquare(P); // make a space for king { for (int i=SHORT8_DIRECTION_MIN; i<=SHORT8_DIRECTION_MAX; ++i) { const Piece p = state.pieceAt(Board_Table.nextSquare (P,king_position,Direction(i))); if (! (p.isPiece() && p.owner() == P)) continue; if (state.hasEffectAt(alt(P), p.square())) continue; move_generator::GeneratePieceOnBoard::generate(P,state, p, all_moves); } for (Move m: all_moves) { assert(! m.isDrop()); assert(!ShouldPromoteCut::canIgnoreAndNotDrop

(m)); if (m.isPromotion()) continue; const Ptype captured = m.capturePtype(); if ((captured != PTYPE_EMPTY) && (eval::Ptype_Eval_Table.value(captured) >= eval::PtypeEvalTraits::val)) continue; moves.push_back(m); } } // defence by add effect: unusual moves const size_t minimum_moves = 8; for (MoveVector::const_iterator p=major_piece.begin(); p!=major_piece.end() && moves.size() < minimum_moves; ++p) { moves.push_back(*p); } for (MoveVector::const_iterator p=major_sacrifice.begin(); p!=major_sacrifice.end() && moves.size() < minimum_moves; ++p) { moves.push_back(*p); } } template void osl::search::QuiescenceGenerator

:: attackGoldWithPawn(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; const bool has_pawn = state.hasPieceOnStand(P); const bool has_lance = state.hasPieceOnStand(P); const bool has_knight = state.hasPieceOnStand(P); const bool has_silver = state.hasPieceOnStand(P); for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece p = state.pieceOf(i); if (! p.isOnBoardByOwner()) continue; const Square head = p.square() + DirectionPlayerTraits::offset(); if (state.pieceAt(head).isEmpty()) { // TODO: ãŸã ã®æ­©ã¯åˆ©ããŒã¯ãšã‚Œã‚‹æ™‚ã«è¨±ã™ const int defense = state.countEffect(alt(P), head, pins); int attack = state.countEffect(P, head) + state.hasEffectByPtype(P, p.square()); if (defense >= attack) attack += AdditionalEffect::count2(state, head, P); // move if (! head.canPromote

()) // æˆã‚Šã¯ã™ã§ã«ç”Ÿæˆã•れã¦ã„ã‚‹ã¯ãš { const Square origin = head + DirectionPlayerTraits::offset(); if (defense <= attack || state.hasEffectByPtype(P, origin)) // open attack { const Piece candidate = state.pieceAt(origin); if (candidate.ptype() == PAWN && candidate.owner() == P) { const Move move(origin, head, PAWN, PTYPE_EMPTY, false, P); moves.push_back(move); ++attack; // æ­©ã®åˆ©ããŒã‚ã‚‹ } } } // drop if (defense <= attack) { if (has_pawn && !state.template isPawnMaskSet

(head.x())) { const Move move(head, PAWN, P); moves.push_back(move); } if (has_lance) { const Move move(head, LANCE, P); moves.push_back(move); } if (has_silver) { const Move move(head, SILVER, P); moves.push_back(move); } } const bool generate_long_lance = has_lance && (! state.hasPieceOnStand(alt(P)) || state.template isPawnMaskSet(head.x())); if (generate_long_lance) { for (Square to=head + DirectionPlayerTraits::offset(); state.pieceAt(to).isEmpty(); to+=DirectionPlayerTraits::offset()) { const int defense = state.countEffect(alt(P), to, pins); const int attack = state.countEffect(P, to); if (defense > attack) continue; const Move move(to, LANCE, P); moves.push_back(move); } } } // knight if (! state.pieceAt(head).isEdge()) { const Square knight_l = head+DirectionPlayerTraits::offset(); attackWithKnight(state, pins, knight_l, has_knight, moves); const Square knight_r = head+DirectionPlayerTraits::offset(); attackWithKnight(state, pins, knight_r, has_knight, moves); } } } template void osl::search::QuiescenceGenerator

:: attackWithKnight(const NumEffectState& state, PieceMask pins, Square attack_from, bool has_knight, MoveVector& moves) { if (state.pieceAt(attack_from) != Piece::EMPTY()) return; const int defense = state.countEffect(alt(P), attack_from, pins); int attack = state.countEffect(P, attack_from); if (defense == 1 && (attack == 1 || (has_knight && attack == 0))) { const Piece gold = state.findAttackAt(alt(P), attack_from); if (gold.ptype() == GOLD) { // å–ã‚‹ã¨æ•µã®é‡‘ã®å®ˆã‚ŠãŒå¤–れる const Square guarded = gold.square()+DirectionPlayerTraits::offset(); if (state.pieceAt(guarded).isOnBoardByOwner(alt(P)) && (state.countEffect(alt(P), guarded) <= state.countEffect(P, guarded))) ++attack; } // å–ã‚‹ã¨è§’é“ãŒé–‹ã const Square head = attack_from + DirectionPlayerTraits::offset(); const Piece head_piece = state.pieceOnBoard(head); if (head_piece.isOnBoardByOwner()) { if (state.hasEffectByPiece(head_piece, attack_from) && state.hasEffectByPtype(P, head)) ++attack; } } if (defense > attack) return; if (has_knight) { const Move drop(attack_from, KNIGHT, P); moves.push_back(drop); } if (defense < attack) { mask_t mask=state.effectSetAt(attack_from).getMask(PtypeFuns::indexNum); mask &= mask_t::makeDirect(PtypeFuns::indexMask); mask &= state.piecesOnBoard(P).getMask(PtypeFuns::indexNum); static_assert(PtypeTraits::indexLimit < 32, ""); while (mask.any()) { const int n = mask.takeOneBit(); const Piece knight = state.pieceOf(n); if (knight.isPromoted()) continue; const Move move(knight.square(), attack_from, KNIGHT, PTYPE_EMPTY, false, P); assert(state.isAlmostValidMove(move)); moves.push_back(move); } } } template void osl::search::QuiescenceGenerator

:: attackKnightWithPawn(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; const bool has_pawn = state.hasPieceOnStand(P); for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece p = state.pieceOf(i); if (p.isOnBoard() && p.ptype() == KNIGHT && p.owner() == alt(P)) { const Square head = p.square()+DirectionPlayerTraits::offset(); // ãŸã ã®æ­©ã‚’許ã™ã‹ã©ã†ã‹... if (state.pieceAt(head).isEmpty()) { const int defense = state.countEffect(alt(P), head, pins); const int offense = state.countEffect(P, head); if ((defense <= offense) && (! head.canPromote

())) // æˆã‚Šã¯ã™ã§ã«ç”Ÿæˆã•れã¦ã„ã‚‹ã¯ãš { const Square origin = head+DirectionPlayerTraits::offset(); const Piece candidate = state.pieceAt(origin); if (candidate.ptype() == PAWN && candidate.owner() == P) { const Move move(origin, head, PAWN, PTYPE_EMPTY, false, P); moves.push_back(move); } } if (has_pawn && !state.template isPawnMaskSet

(head.x()) && (defense <= offense+1)) { const Move move(head, PAWN, P); moves.push_back(move); } } } } } template void osl::search::QuiescenceGenerator

:: attackSilverWithPawn(const NumEffectState& state, PieceMask pins, MoveVector& moves) { using namespace move_action; const bool has_pawn = state.hasPieceOnStand(P); const bool has_lance = state.hasPieceOnStand(P); const bool has_knight = state.hasPieceOnStand(P); const bool has_silver = state.hasPieceOnStand(P); const Square opponent_king = state.kingSquare(alt(P)); for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece p = state.pieceOf(i); if (! p.isOnBoardByOwner()) continue; const Square head = p.square()+DirectionPlayerTraits::offset(); if (state.pieceAt(head).isEmpty()) { const int defense = state.countEffect(alt(P), head, pins); int attack = state.countEffect(P, head) + state.hasEffectByPtype(P, p.square()); if (defense >= attack) attack += AdditionalEffect::count2(state, head, P); const bool near_king = Neighboring8Direct::hasEffect(state, p.ptypeO(), p.square(), opponent_king); if (defense > attack) { if (! near_king) continue; // TODO: ãŸã ã®æ­©ã¯åˆ©ããŒã¯ãšã‚Œã‚‹æ™‚ã«è¨±ã™ } if (! head.canPromote

()) // æˆã‚Šã¯ã™ã§ã«ç”Ÿæˆã•れã¦ã„ã‚‹ã¯ãš { const Square origin = head+DirectionPlayerTraits::offset(); const Piece candidate = state.pieceAt(origin); if (candidate.ptype() == PAWN && candidate.owner() == P) { const Move move(origin, head, PAWN, PTYPE_EMPTY, false, P); moves.push_back(move); } } if (has_pawn && !state.template isPawnMaskSet

(head.x())) { const Move move(head, PAWN, P); moves.push_back(move); } if (! near_king) continue; if (defense <= attack) { if (has_lance) { const Move move(head, LANCE, P); moves.push_back(move); } if (has_silver) { const Move move(head, SILVER, P); moves.push_back(move); } } } // knight if (! state.pieceAt(head).isEdge()) { const Square knight_l = head+DirectionPlayerTraits::offset(); attackWithKnight(state, pins, knight_l, has_knight, moves); const Square knight_r = head+DirectionPlayerTraits::offset(); attackWithKnight(state, pins, knight_r, has_knight, moves); } // ppawn const CArray side = {{ p.square() + DirectionTraits::blackOffset(), p.square() + DirectionTraits::blackOffset(), }}; for (Square s: side) { if (! state.pieceAt(s).isEmpty()) continue; if (state.countEffect(P, s) < state.countEffect(alt(P), s)) continue; MoveVector candidate; move_generator::GenerateCapture::generate(P,state, s, candidate); for (Move m: candidate) { if (m.isPromotion() || state.hasEffectByPiece(state.pieceOnBoard(m.from()), p.square())) continue; assert(! ShouldPromoteCut::canIgnoreMove

(m)); moves.push_back(m); } } } } template void osl::search::QuiescenceGenerator

:: kingWalk(const NumEffectState& state, MoveVector& moves) { const Piece my_king = state.kingPiece

(); MoveVector all_moves; move_generator::GeneratePieceOnBoard::generate(P,state, my_king, all_moves); for (Move m: all_moves) { if (state.hasEffectAt(alt(P), m.to())) continue; moves.push_back(m); } } template void osl::search::QuiescenceGenerator

:: escapeKing(const NumEffectState& state, MoveVector& moves) { MoveVector all_moves; GenerateEscape

::generateCheap(state, state.template kingPiece

(), all_moves); for (Move m: all_moves) { const Square to = m.to(); if (m.isDrop()) { // 焦点以外ã®ä¸­åˆã¯èª­ã¾ãªã„ if (! state.hasEffectAt

(to)) { if (! ((m.ptype() == PAWN) && state.hasMultipleEffectAt(alt(P), to))) continue; } } else if (m.ptype() != KING) { // 焦点以外ã®ä¸­åˆã¯èª­ã¾ãªã„ if (! m.isCapture()) { if (! state.hasMultipleEffectAt(P, to)) { if (! ((m.ptype() == PAWN) && state.hasMultipleEffectAt(alt(P), to))) continue; } } } moves.push_back(m); } } template bool osl::search::QuiescenceGenerator

:: escapeKingInTakeBack(const NumEffectState& state, MoveVector& moves, bool check_by_lance) { bool has_safe_move = false; assert(moves.empty()); MoveVector all_moves; GenerateEscape

::generate(state, state.template kingPiece

(), all_moves); Square last_drop_to = Square::STAND(); MoveVector drops; for (Move m: all_moves) { const Square to = m.to(); if (m.ptype() == KING) { // TODO: 何ã‹çŠ ç‰²ãŒã‚ã‚‹ã¯ãš has_safe_move = true; // KFEND æµ: 逃ã’る場所ãŒã‚れã°è‰¯ã—ã¨ã™ã‚‹ continue; } if (m.isCapture()) { moves.push_back(m); continue; } // ç„¡é§„åˆã¯èª­ã¾ãªã„ const int attack_count = state.countEffect(alt(P),to); const int defense_count = state.countEffect(P,to) + (m.isDrop() ? 1 : 0); if (defense_count <= attack_count) continue; if ((attack_count == 1) && (! check_by_lance)) { // å¤§é§’ã®æ”»æ’ƒã«å¯¾ã—ã¦è‡ªåˆ†ã®åˆ©ããŒå……分ãªã‚‰è‰¯ã„ã¨ã™ã‚‹ has_safe_move = true; continue; } // 攻方ãŒã“れ以上drop ã®çŽ‹æ‰‹ã‚’ã‹ã‘ãªã„ã®ã§åˆé§’ã¯1手ã§è©°ã®åˆ¤å®šã«ã¯å……分 // TODO: 一番安ã„é§’ã«ã™ã‚‹ if (to != last_drop_to) { last_drop_to = to; drops.push_back(m); } } if (! has_safe_move) moves.push_back(drops.begin(), drops.end()); return has_safe_move; } template void osl::search::QuiescenceGenerator

:: advanceBishop(const NumEffectState& state, MoveVector& moves) { for (int i = PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece bishop = state.pieceOf(i); if (! bishop.isOnBoardByOwner

()) continue; if (bishop.ptype() != BISHOP) continue; const Square from = bishop.square(); if (state.hasEffectAt(from)) continue; // escape ã¯é‡è¤‡ advanceBishop

    (state, from, moves); advanceBishop(state, from, moves); } } template template void osl::search::QuiescenceGenerator

    :: advanceBishop(const NumEffectState& state, const Square from, MoveVector& moves) { const Offset offset = DirectionPlayerTraits::offset(); for (Square to=from+offset;; to+=offset) { if (! state.pieceAt(to).isEmpty()) break; // capture ã¯é‡è¤‡ï¼Žã¤ã„ã§ã«ç›¤å¤–判定 if (to.canPromote

    ()) break; // promote ã¯é‡è¤‡ if (state.hasEffectAt(to)) continue; const Move move(from, to, BISHOP, PTYPE_EMPTY, false, P); assert(state.isAlmostValidMove(move)); moves.push_back(move); } } template template void osl::search::QuiescenceGenerator

    :: escapeFromLastMove(const NumEffectState& state, Move last_move, MoveVector& moves) { if (! last_move.isNormal()) return; if (last_move.ptype() != PAWN) { escapeFromLastMoveOtherThanPawn(state, last_move, moves); return; } const Square attack_from = last_move.to(); const Square attack_to = attack_from+DirectionPlayerTraits::offset(); const Piece target = state.pieceOnBoard(attack_to); if (! target.isOnBoardByOwner

    ()) return; using namespace move_action; MoveVector all_moves; GenerateEscape

    ::generate(state, target, all_moves); for (Move m: all_moves) { assert(! m.isDrop()); const Square to = m.to(); // 逃ã’る時ã«ã¯åˆ©ãã®å……分ãªã¨ã“ã‚㸠const int defense = state.countEffect(P, to); const int offense = state.countEffect(alt(P), to); if (offense > defense) continue; if (to == attack_from) { // å–る手ã¯é‡è¤‡ã ã‘ã©æ­©ã®å ´åˆã¯æ·±ã•ã«ã‚ˆã‚‹ã®ã§å…¥ã‚Œã¦ãŠã if (offense == defense) continue; assert(m.capturePtype() == PAWN); assert(! ShouldPromoteCut::canIgnoreMove

    (m)); moves.push_back(m); continue; } assert(m.from() == attack_to); if ((offense == defense) && (m.isCapture())) continue; // TODO: KnightCaptureDepth assert(! ShouldPromoteCut::canIgnoreMove

    (m)); if (! m.isPromotion()) { moves.push_back(m); } } } template void osl::search::QuiescenceGenerator

    :: dropMajorPiece(const NumEffectState& state, MoveVector& moves) { move_generator::SafeDropMajorPiece

    ::generateMoves(state, moves); } template void osl::search::QuiescenceGenerator

    :: dropMajorPiece3(const NumEffectState& state, MoveVector& moves, const HistoryTable& table) { FixedCapacityVector all; move_generator::SafeDropMajorPiece

    ::generateMoves(state, all); FixedCapacityVector, 27*2> selected; for (Move m: all) selected.push_back(std::make_pair(table.value(m), m)); std::sort(selected.begin(), selected.end()); for (int i=0; i namespace osl { namespace checkmate { inline size_t limitToCheckCount(int limit) { assert(limit >= 0); extern CArray LimitToCheckCountTable; return LimitToCheckCountTable[limit>>7]; } } } #endif /* _LIMITTOCHECKCOUNT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta2Parallel.cc0000644000000000000000000006341312335610142021377 0ustar rootroot/* alphaBeta2Parallel.cc */ #ifdef OSL_SMP #include "osl/search/alphaBeta2Parallel.h" #include "osl/search/simpleHashTable.h" #include "osl/search/usiReporter.h" #include #include #ifdef _WIN32 # include # include # include #endif #define DEBUG_SMP 0 #define ONLY_HELP_DESCENDANT // #define OSL_BUSY_WAIT /* ------------------------------------------------------------------------- */ struct osl::search::AlphaBeta2ParallelCommon::LivingThreadLock { AlphaBeta2ParallelCommon *shared; LivingThreadLock(AlphaBeta2ParallelCommon *s) : shared(s) { std::lock_guard lk(shared->living_threads_lock); shared->living_threads += 1; shared->living_threads_condition.notify_one(); } ~LivingThreadLock() { std::lock_guard lk(shared->living_threads_lock); shared->living_threads -= 1; shared->living_threads_condition.notify_one(); } }; /* ------------------------------------------------------------------------- */ template osl::search::AlphaBeta2Parallel:: Worker::Worker(int tid, AlphaBeta2Parallel *s) : shared(s), thread_id(tid) { } template void #ifdef __GNUC__ # ifdef _WIN32 __attribute__((noinline)) __attribute__((force_align_arg_pointer)) # endif #endif osl::search::AlphaBeta2Parallel::Worker::operator()() { #if DEBUG_SMP > 1 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "thread " << thread_id << " started\n"; } #endif try { AlphaBeta2ParallelCommon::LivingThreadLock lk(shared); shared->threadWait(thread_id, -1); } catch (std::exception& e) { std::cerr << "warning caught exception in thread root " << e.what() << "\n"; } catch (...) { std::cerr << "warning caught unknown exception in thread root\n"; } } /* ------------------------------------------------------------------------- */ static osl::misc::AtomicCounter parallel_counter; osl::search::AlphaBeta2ParallelCommon:: AlphaBeta2ParallelCommon() : smp_idle(0), quit(false), parallel_splits(0), max_split_depth(0), descendant_reject(0), descendant_test(0), living_threads(0), max_threads(OslConfig::concurrency()), max_thread_group(5), split_min_limit(400), my_id(parallel_counter.valueAndinc()), started(false) { job.fill(0); info[0].thread_id = 0; info[0].used = true; info[0].parent = -1; waiting.fill(0); threads.fill(nullptr); checkmate.fill(nullptr); for (int i=1; i 1 std::cerr << "<= AlphaBeta2Parallel " << my_id << "\n"; #endif #if DEBUG_SMP > 2 std::cerr << "descendant_reject " << descendant_reject << " / " << descendant_test << " = " << (double)descendant_reject/descendant_test << "\n"; std::cerr << "max_split_depth " << max_split_depth << "\n"; #endif } void osl::search:: AlphaBeta2ParallelCommon::waitAll() { #ifndef OSL_BUSY_WAIT { std::lock_guard lk(lock_smp); #endif quit = true; started = false; #ifndef OSL_BUSY_WAIT condition_smp.notify_all(); } #endif std::unique_lock lk(living_threads_lock); while (living_threads != (quit ? 0 : smp_idle)) { living_threads_condition.wait(lk); } for (int i=1; ijoin(); delete threads[i]; } threads[i] = 0; } } bool osl::search::AlphaBeta2ParallelCommon::isDescendant(int elder, int younger) { #ifndef ONLY_HELP_DESCENDANT return true; #else ++descendant_test; if (elder < 0) return true; while (younger >= 0) { if (elder == younger) return true; younger = info[younger].parent; } ++descendant_reject; return false; #endif } /* ------------------------------------------------------------------------- */ template osl::search::AlphaBeta2Parallel:: AlphaBeta2Parallel(AlphaBeta2Tree *m) : AlphaBeta2ParallelCommon(), master(m) { #if DEBUG_SMP > 0 std::cerr << "=> AlphaBeta2Parallel " << max_threads << " threads "; # if DEBUG_SMP > 1 std::cerr << " id " << my_id; # endif std::cerr << "\n"; #endif tree.fill(nullptr); tree[0] = master; checkmate[0] = checkmateSearcher(*master); } template osl::search::AlphaBeta2Parallel:: ~AlphaBeta2Parallel() { } template void osl::search::AlphaBeta2Parallel:: threadStart() { if (started) return; started = true; quit = false; int i=1; for (; icheckmateSearcher()); threads[i] = new std::thread(Worker(i, this)); break; } catch (std::exception& e) { std::cerr << e.what() << "\n"; } std::cerr << "wait for thread " << i << " started\n"; const int microseconds = (j+1)*100000; #ifdef _WIN32 std::this_thread::sleep_for(std::chrono::microseconds(microseconds)); #else usleep(microseconds); #endif } if (j == max_retry) break; } if (i < max_threads) { std::cerr << "error in start thread #" << i << "\n"; for (int j=i; j lk(living_threads_lock); while (living_threads+1 != max_threads) { living_threads_condition.wait(lk); } } template void osl::search::AlphaBeta2Parallel:: search(int tree_id) { TreeInfo *info = &this->info[tree_id]; assert(tree[tree_id]); if (info->is_root) tree[tree_id]->examineMovesRootPar(tree_id); else tree[tree_id]->examineMovesOther(tree_id); } template int osl::search:: AlphaBeta2Parallel::treeId(AlphaBeta2Tree *t) { if (t == master) return 0; for (size_t i=1; i void osl::search::AlphaBeta2Parallel:: threadWait(int thread_id, int waiting) { #if DEBUG_SMP > 2 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "thread " << thread_id << " ready, waiting " << waiting << "\n"; } #endif while (1) { this->waiting[thread_id] = waiting; { std::lock_guard lk(lock_smp); smp_idle++; } { #ifndef OSL_BUSY_WAIT std::unique_lock lk(lock_smp); #endif while (! job[thread_id] && ! quit && (waiting < 0 || info[waiting].nprocs)) { #ifndef OSL_BUSY_WAIT condition_smp.wait(lk); #endif } if (quit) { { #ifdef OSL_BUSY_WAIT std::lock_guard lk(lock_smp); #endif --smp_idle; } #if DEBUG_SMP > 1 std::lock_guard lk(OslConfig::lock_io); std::cerr << "thread " << thread_id << " exiting\n"; #endif return; } { #ifdef OSL_BUSY_WAIT std::lock_guard lk(lock_smp); #endif if (! job[thread_id]) job[thread_id] = waiting; --smp_idle; } } if (job[thread_id] == waiting) { #ifndef NDEBUG if (waiting >= 0) { for (int i=0; i 3 std::lock_guard lk(OslConfig::lock_io); std::cerr << "thread " << thread_id << " go up " << waiting << " " << info[job[thread_id]].best_move << "\n"; #endif return; } if (quit || job[thread_id] == -1) { return; } int my_job = job[thread_id]; #if DEBUG_SMP > 3 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "thread " << thread_id << " go to job " << my_job << " waiting " << waiting << "\n"; if (! tree[my_job]) { std::cerr << "thread " << thread_id << " null job " << my_job << " waiting " << waiting << "\n"; } } #endif assert(tree[my_job]); search(my_job); int parent = info[my_job].parent; std::lock_guard lk(lock_smp); { SCOPED_LOCK(lk,info[parent].lock); copyToParent(parent, my_job); info[parent].nprocs--; info[parent].siblings[thread_id] = 0; #ifndef OSL_BUSY_WAIT if (info[parent].nprocs == 0) condition_smp.notify_all(); #endif } job[thread_id] = 0; delete tree[my_job]; tree[my_job] = 0; #if DEBUG_SMP > 3 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "thread " << thread_id << " back from job " << my_job << " waiting " << waiting; if (waiting >= 0) std::cerr << " rest " << info[waiting].nprocs; std::cerr << "\n"; } #endif } } template bool osl::search::AlphaBeta2Parallel:: split(AlphaBeta2Tree *tree, int tree_id, int thread_id, int max_split) { TreeInfo *pinfo = &info[tree_id]; #if DEBUG_SMP > 2 { unsigned int depth = 0; int parent = pinfo->parent; while (parent >= 0) ++depth, parent = info[parent].parent;; max_split_depth = std::max(depth, max_split_depth); } for (int i=0; isiblings[i] == 0); } #endif assert(tree == master || tree == this->tree[tree_id]); { std::lock_guard lk(lock_smp); { int tid=0; for (; tidstop_tree) return false; } parallel_splits++; job[pinfo->thread_id] = 0; pinfo->nprocs = 0; int nblocks = 0; if (const int child_id = copyToChild(tree_id, thread_id)) { // first, assgin job to splitting thread nblocks++; pinfo->siblings[thread_id] = child_id; info[child_id].thread_id = thread_id; info[child_id].parent = tree_id; pinfo->nprocs++; } if (max_split <= 0) max_split = std::max(max_threads/2, max_thread_group); else max_split = std::min(max_split, std::max(max_threads/2, max_thread_group)); for (int tid = 0; tid < max_threads && nblocks < max_split; ++tid) { assert(pinfo->siblings[tid] == 0 || tid == thread_id); if (job[tid] || tid == thread_id) // he is working continue; if (! isDescendant(waiting[tid], pinfo->parent)) continue; int child_id = copyToChild(tree_id, tid); if (!child_id) continue; #if DEBUG_SMP > 3 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "split " << tree_id << " in " << thread_id << " => " << child_id << " in " << tid << "\n"; } #endif nblocks++; pinfo->siblings[tid] = child_id; info[child_id].thread_id = tid; info[child_id].parent = tree_id; pinfo->nprocs++; } pinfo->search_value = pinfo->value; if (!nblocks) { job[pinfo->thread_id] = tree_id; return false; } for (int tid=0; tid< max_threads; ++tid) if (pinfo->siblings[tid]) job[tid] = pinfo->siblings[tid]; } #ifndef OSL_BUSY_WAIT condition_smp.notify_all(); #endif threadWait(pinfo->thread_id, tree_id); return true; } template void osl::search:: AlphaBeta2Parallel::stopThread(int tree_id) { TreeInfo *info = &this->info[tree_id]; AlphaBeta2Tree *tree = this->tree[tree_id]; SCOPED_LOCK(lk,info->lock); tree->stop_tree = true; for (int tid = 0; tidsiblings[tid]) stopThread(info->siblings[tid]); } template void osl::search:: AlphaBeta2Parallel::copyToParent(int parent, int child) { TreeInfo *c = &info[child]; AlphaBeta2Tree *cc = tree[child], *pp = tree[parent]; c->used = 0; pp->node_count += cc->nodeCount(); pp->mpn.merge(cc->mpn); pp->mpn_cut.merge(cc->mpn_cut); pp->alpha_update.merge(cc->alpha_update); pp->last_alpha_update.merge(cc->last_alpha_update); pp->ext.merge(cc->ext); pp->ext_limit.merge(cc->ext_limit); } template int osl::search:: AlphaBeta2Parallel::copyToChild(int parent, int thread_id) { static int warnings = 0; int first = thread_id * MaxBlocksPerCpu + 1; int last = first + MaxBlocksPerCpu; int maxb = max_threads * MaxBlocksPerCpu + 1; int cid=first; for (; cid < last && info[cid].used; cid++) ; if (cid >= last) { if (++warnings < 6) { std::lock_guard lk(OslConfig::lock_io); std::cerr << "WARNING. optimal SMP block cannot be allocated, thread " << thread_id << "\n"; } for (cid=1; cid= maxb) { if (warnings < 6) { std::lock_guard lk(OslConfig::lock_io); std::cerr << "ERROR. no SMP block can be allocated\n"; } return 0; } } TreeInfo *c = &info[cid], *p = &info[parent]; try { assert(tree[cid] == 0); tree[cid] = new AlphaBeta2Tree(*tree[parent], this); } catch (std::bad_alloc&) { std::lock_guard lk(OslConfig::lock_io); std::cerr << "ERROR. split failed due to bad_alloc\n"; return 0; } c->set(*p, max_threads); tree[cid]->setCheckmateSearcher(checkmate[thread_id]); return cid; } template const std::pair osl::search:: AlphaBeta2Parallel::nextMove(int tree_id) { int parent = info[tree_id].parent; TreeInfo *info = &this->info[parent]; SCOPED_LOCK(lk,info->lock); const size_t old_index = info->move_index; if (tree[parent]->stop_tree) return std::make_pair(MoveLogProb(), old_index); if (info->is_root) { if (old_index < info->moves.size()) { ++(info->move_index); return std::make_pair(info->moves[old_index], old_index); } return std::make_pair(MoveLogProb(), old_index); } else { MoveLogProb m = (info->turn == BLACK) ? tree[parent]->template nextMove() : tree[parent]->template nextMove(); if (m.validMove()) { assert(m.player() == info->turn); ++(info->move_index); } return std::make_pair(m, old_index); } } template size_t osl::search:: AlphaBeta2Parallel::checkmateCount() const { return master->checkmateSearcher().totalNodeCount(); } template size_t osl::search:: AlphaBeta2Parallel::mainCheckmateCount() const { return master->checkmateSearcher().mainNodeCount(); } /* ------------------------------------------------------------------------- */ template template void osl::search:: AlphaBeta2Tree::testMoveRoot(int tree_id, const MoveLogProb& m) { if (stop_tree) { std::cerr << "root tree stop\n"; return; } Window w; AlphaBeta2ParallelCommon::TreeInfo *parent = shared->parent(tree_id); { SCOPED_LOCK(lk,parent->lock); w = parent->window; assert(w.isConsistent()); } assert(P == m.player()); #ifndef GPSONE if (this->multi_pv) { int width = this->multi_pv*this->eval.captureValue(newPtypeO(P, PAWN))/200; if (width % 2 == 0) width -= EvalTraits

    ::delta; w.alpha(P) = parent->search_value + width; } #endif const int result = alphaBetaSearch

    (m, w, false); if (eval::betterThan(P, result, parent->search_value)) { makePV(m.move()); if (eval::betterThan(P, result, w.beta(P))) { { std::lock_guard lk_smp(shared->lock_smp); SCOPED_LOCK(lk,parent->lock); if (! stop_tree) { #if DEBUG_SMP > 2 std::cerr << "beta cut root " << tree_id << "\n"; #endif for (int tid=0; tidmax_threads; tid++) if (parent->siblings[tid] && tid != shared->info[tree_id].thread_id) shared->stopThread(parent->siblings[tid]); } } shared->parallel_abort.inc(); } SCOPED_LOCK(lk,parent->lock); if (! stopping() && (eval::betterThan(P, result, parent->search_value))) { assert(parent->window.isConsistent()); parent->window.alpha(P) = result + EvalTraits

    ::delta; parent->best_move = m; parent->search_value = result; updateRootPV(P, std::cerr, result, m.move()); assert(parent->window.isConsistent()); shared->tree[shared->parentID(tree_id)]->pv[0] = pv[0]; } } #ifndef GPSONE else if (this->multi_pv && !stopping() && eval::betterThan(P, result, w.alpha(P))) addMultiPV(P, result, m.move()); #endif } template template void osl::search::AlphaBeta2Tree:: examineMovesRootPar(const MoveLogProbVector& moves, size_t start, Window window, MoveLogProb& best_move, int& best_value) { const int id = shared->treeId(this); #if DEBUG_SMP > 3 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "start split root " << id << " turn " << P << " parent " << shared->info[id].parent << "\n"; history().dump(); } #endif AlphaBeta2ParallelCommon::TreeInfo *info = &shared->info[id]; info->window = window; info->is_root = true; info->in_pv = false; info->value = best_value; info->moves = moves; info->move_index = start; info->turn = P; info->best_move = best_move; if (! shared->split(this, id, info->thread_id, -1)) { shared->cancelled_splits.inc(); throw AlphaBeta2ParallelCommon::SplitFailed(); } SCOPED_LOCK(lk,info->lock); best_value = info->search_value; best_move = info->best_move; } template void osl::search::AlphaBeta2Tree:: examineMovesRootPar(int tree_id) { AlphaBeta2ParallelCommon::TreeInfo *info = &shared->info[tree_id]; const Player my_turn = info->turn; for (MoveLogProb m = shared->nextMove(tree_id).first; m.validMove() && ! stopping(); m = shared->nextMove(tree_id).first) { #ifndef GPSONE if (this->elapsed() > 1.0) { std::lock_guard lk(OslConfig::lock_io); for (const std::shared_ptr& monitor: this->monitors()) monitor->rootMove(m.move()); } #endif try { if (my_turn == BLACK) testMoveRoot(tree_id, m); else testMoveRoot(tree_id, m); if (this->root_limit >= 1600) this->checkmate_searcher->runGC(this->table->isVerbose(), lastMemoryUseRatio1000()); } catch (BetaCut& e) { std::cerr << "caught BetaCut at root " << info->thread_id << "\n"; assert(stop_tree); break; } catch (std::runtime_error&) { stop_tree = true; this->stopNow(); break; } catch (std::exception& e) { #if DEBUG_SMP > 0 std::lock_guard lk(OslConfig::lock_io); std::cerr << "caught " << e.what() << " at root " << info->thread_id << "\n"; #endif stop_tree = true; this->stopNow(); break; } catch (...) { std::lock_guard lk(OslConfig::lock_io); std::cerr << "caught something at root " << info->thread_id << "\n"; stop_tree = true; this->stopNow(); break; } } // cut or no more moves to search } template template bool osl::search:: AlphaBeta2Tree::testMoveOther(int tree_id, const MoveLogProb& m, size_t index, bool in_pv) { if (stopping()) return false; Window w; AlphaBeta2ParallelCommon::TreeInfo *parent = shared->parent(tree_id); { SCOPED_LOCK(lk,parent->lock); w = parent->window; } assert(w.isConsistent() || stop_tree); if (stopping()) return false; assert(P == m.player()); const int result = alphaBetaSearch

    (m, w, in_pv); if (stopping()) return false; bool cut = false; int parent_search_value; { #ifdef OSL_USE_RACE_DETECTOR SCOPED_LOCK(lk,parent->lock); #endif parent_search_value = parent->search_value; } if (eval::betterThan(P, result, parent_search_value)) { makePV(m.move()); if (eval::betterThan(P, result, w.beta(P))) { cut = true; { std::lock_guard lk_smp(shared->lock_smp); SCOPED_LOCK(lk,parent->lock); if (! stop_tree) { #if DEBUG_SMP > 2 std::cerr << "beta cut " << tree_id << "\n"; #endif for (int tid=0; tidmax_threads; tid++) if (parent->siblings[tid] && tid != shared->info[tree_id].thread_id) shared->stopThread(parent->siblings[tid]); } } shared->parallel_abort.inc(); } SCOPED_LOCK(lk,parent->lock); if (! stopping() && eval::betterThan(P, result, parent->search_value)) { parent->window.alpha(P) = result + EvalTraits

    ::delta; parent->best_move = m; parent->search_value = result; parent->alpha_update++; parent->last_alpha_update = index; assert(cut || shared->tree[shared->info[tree_id].parent]->stop_tree || parent->window.isConsistent()); AlphaBeta2Tree *pp = shared->tree[shared->parentID(tree_id)]; pp->pv[pp->curDepth()] = pv[curDepth()]; if (cut) return true; } } return false; } template template bool osl::search::AlphaBeta2Tree:: examineMovesOther(Window& w, MoveLogProb& best_move, int& best_value, int& tried_moves, int& alpha_update, int& last_alpha_update) { assert(w.isConsistent()); const int id = shared->treeId(this); #if DEBUG_SMP > 3 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "start split at " << curLimit() << " " << id << " turn " << P << " move " << tried_moves << " parent " << shared->info[id].parent << "\n"; history().dump(); } #endif AlphaBeta2ParallelCommon::TreeInfo *info = &shared->info[id]; info->window = w; info->is_root = false; info->in_pv = (! w.null()) && (! best_move.validMove()); info->value = best_value; info->move_index = tried_moves; info->turn = P; info->best_move = best_move; info->alpha_update = alpha_update; info->last_alpha_update = last_alpha_update; if (! shared->split(this, id, info->thread_id, shared->max_thread_group)) { #if DEBUG_SMP > 2 std::lock_guard lk(OslConfig::lock_io); std::cerr << "failed split " << id << " turn " << P << "\n"; for (int i=0; imax_threads; ++i) { std::cerr << " " << i << " " << shared->job[i] << "\n"; } #endif shared->cancelled_splits.inc(); throw AlphaBeta2ParallelCommon::SplitFailed(); } SCOPED_LOCK(lk,info->lock); best_value = info->search_value; best_move = info->best_move; w = info->window; tried_moves = info->move_index; alpha_update += info->alpha_update; last_alpha_update = info->last_alpha_update; #if DEBUG_SMP > 3 { std::lock_guard lk(OslConfig::lock_io); std::cerr << "back from split at " << curLimit() << " " << id << " turn " << P << " parent " << shared->info[id].parent << "\n"; } #endif testStop(); return EvalTraits

    ::betterThan(best_value, w.beta(P)); } template void osl::search::AlphaBeta2Tree:: examineMovesOther(int tree_id) { AlphaBeta2ParallelCommon::TreeInfo *parent = shared->parent(tree_id); for (std::pair m = shared->nextMove(tree_id); m.first.validMove() && !stopping(); m = shared->nextMove(tree_id)) { bool in_pv = parent->in_pv; if (in_pv) { in_pv = ! parent->best_move.validMove(); } assert(parent->turn == m.first.player()); try { const bool cut_by_move = (parent->turn == BLACK) ? testMoveOther(tree_id, m.first, m.second, in_pv) : testMoveOther(tree_id, m.first, m.second, in_pv); if (cut_by_move) { break; } testStop(); } catch (BetaCut&) { assert(stop_tree); } catch (TableFull&) { stop_tree = true; this->stopNow(); break; } catch (misc::NoMoreTime&) { stop_tree = true; this->stopNow(); #if DEBUG_SMP > 2 std::lock_guard lk(OslConfig::lock_io); std::cerr << "caught timeout in tree " << tree_id << " thread " << shared->info[tree_id].thread_id << "\n"; #endif break; } catch (NoMoreMemory&) { stop_tree = true; this->stopNow(); #if DEBUG_SMP > 2 std::lock_guard lk(OslConfig::lock_io); std::cerr << "caught memory full in tree " << tree_id << " thread " << shared->info[tree_id].thread_id << "\n"; #endif break; } catch (std::exception& e) { this->stopNow(); stop_tree = true; std::lock_guard lk(OslConfig::lock_io); std::cerr << "caught exception at " << tree_id << " " << e.what() << "\n"; break; } catch (...) { std::lock_guard lk(OslConfig::lock_io); std::cerr << "caught unknown exception at " << tree_id << "\n"; throw; } } // cut or no more moves to search } namespace osl { namespace search { #ifndef MINIMAL template struct AlphaBeta2Parallel; template bool AlphaBeta2Tree::examineMovesOther(Window&, MoveLogProb&, int&, int&, int&, int&); template bool AlphaBeta2Tree::examineMovesOther(Window&, MoveLogProb&, int&, int&, int&, int&); template void AlphaBeta2Tree::examineMovesRootPar(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); template void AlphaBeta2Tree::examineMovesRootPar(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); #endif template struct AlphaBeta2Parallel; template bool AlphaBeta2Tree::examineMovesOther(Window&, MoveLogProb&, int&, int&, int&, int&); template bool AlphaBeta2Tree::examineMovesOther(Window&, MoveLogProb&, int&, int&, int&, int&); template void AlphaBeta2Tree::examineMovesRootPar(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); template void AlphaBeta2Tree::examineMovesRootPar(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); } } #endif /* OSL_SMP */ /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/bigramKillerMove.cc0000644000000000000000000000516312316770314021217 0ustar rootroot/* bigramKillerMove.cc */ #include "osl/search/bigramKillerMove.h" #include osl::search:: BigramKillerMove::BigramKillerMove() { clear(); } osl::search:: BigramKillerMove::~BigramKillerMove() { } void osl::search:: BigramKillerMove::clear() { for (size_t i=0; i(bigram_move)) out.push_back(bigram_move); } } void osl::search:: BigramKillerMove::dump() const { for (int y=1; y<=9; ++y) { for (int x=1; x<=9; ++x) { const Square position(x,y); for (int p=PTYPEO_MIN; p<=PTYPEO_MAX; ++p) { const PtypeO ptypeo = static_cast(p); const LRUMoves& moves = killer_moves[position.index()][ptypeOIndex(ptypeo)]; if (moves[0].isNormal()) { std::cerr << position << " " << moves[0]; if (moves[1].isNormal()) std::cerr << " " << moves[1]; std::cerr << "\n"; } } } } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/fixedEval.h0000644000000000000000000000464712316770314017543 0ustar rootroot/* fixedEval.h */ #ifndef SEARCH_FIXEDEVAL_H #define SEARCH_FIXEDEVAL_H #include "osl/eval/evalTraits.h" namespace osl { namespace search { class FixedEval { int draw_value; protected: ~FixedEval() {} public: FixedEval() : draw_value(0) { } void setDrawValue(int value) { draw_value = value; } int drawValue() const { return draw_value; } /** * 相手ã®çŽ‹æ‰‹åƒæ—¥æ‰‹ï¼Œæ‰“æ­©è©°. * è€ƒæ…®å¯¾è±¡å¤–ã®æ‰‹ã¯è©°ã‚ˆã‚Šè©•価を下ã’る. */ static int winByFoul(Player P) { return eval::convert(P, EvalTraits::MAX_VALUE); } /** * é§’å¾—ã™ã‚‹ãƒ«ãƒ¼ãƒ—. * è€ƒæ…®å¯¾è±¡å¤–ã®æ‰‹ã¯è©°ã‚ˆã‚Šè©•価を下ã’る. */ static int winByLoop(Player P) { return winByFoul(P); } /** * è©°ã«ã‚ˆã‚‹å‹ */ static int winByCheckmate(Player P) { return eval::convert(P, EvalTraits::MAX_VALUE-2); } /** * 探索windowã®ä¸‹é™ (è² ã‘ã§ã‚‚æ›´æ–°ã•れる値) */ static int minusInfty(Player P) { return winByCheckmate(alt(P)); } /** * ã“ã®å€¤ã‚’è¶Šãˆã‚Œã°å‹. (奇数). loopå‹ã‚‚å«ã‚ã‚‹ */ static int winThreshold(Player P) { return eval::convert(P, EvalTraits::MAX_VALUE-3); } /** * 探索ã—ã¦æ„味ãŒã‚る範囲 (å¶æ•°) */ static int windowMax(Player P) { return winByCheckmate(P); } /** * å¿…æ­»(ã«è¦‹ãˆã‚‹)å±€é¢ã®è©•価値 * PãŒè² ã‘ãㆠ* @param limit å—を生æˆã—ãŸé–¾å€¤ 大ãã„æ–¹ãŒä¿¡é ¼ã§ãã‚‹å¿…æ­» */ static int brinkmatePenalty(Player P, int limit) { return (winByFoul(alt(P))*3/4+eval::convert(alt(P), limit*16)) & (~1); } /** * 末端ã§è©°ã‚ã‚ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã®ãƒšãƒŠãƒ«ãƒ†ã‚£. * P ã«è©°ã‚ã‚ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã« threatmatePenalty(P)を足㙠*/ static int threatmatePenalty(Player P) { return winByFoul(alt(P))/2; } /** * å‹ã‹ã©ã†ã‹. loopå‹ã‚‚å«ã‚ã‚‹ */ static int isWinValue(Player P, int val) { return eval::notLessThan(P, val, winByCheckmate(P)); } }; } // namespace search } // namespace osl #endif /* SEARCH_FIXEDEVAL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceRecord.h0000644000000000000000000002240712316770314021111 0ustar rootroot/* quiescenceRecord.h */ #ifndef _QUIESCENCERECORD_H #define _QUIESCENCERECORD_H #include "osl/search/dualThreatmateState.h" #ifdef OSL_SMP # include "osl/misc/lightMutex.h" #endif #include #include namespace osl { namespace search { struct QSearchTraits { enum { /** é€šå¸¸æŽ¢ç´¢ã®æœ€å¤§ */ MaxDepth = 8, /** å³è©°ã®æ·±ã• */ CheckmateSpecialDepth = 127, /** é§’æãƒ«ãƒ¼ãƒ—ã®æ·±ã• */ HistorySpecialDepth = 126, }; enum { FirstThreat = 6, SecondThreat = 2 }; enum MoveType { UNKNOWN, KING_ESCAPE, CAPTURE, PROMOTE, CHECK, ESCAPE, ATTACK, OTHER, }; }; /** * QuiescenceSearch ã§ãƒ‘スã—ãŸå ´åˆã®ç›¸æ‰‹ã®æœ‰åŠ›ãªæŒ‡æ‰‹ */ struct QuiescenceThreat { int value; Move move; explicit QuiescenceThreat(int v=0, Move m=Move::INVALID()) : value(v), move(m) { } }; struct BestMoves : public CArray { BestMoves() { // automaticallyfilled by invalid data by constructor } size_t capacity() const { return size(); } size_t sizeFilled() const { for (size_t i=0; i copy = *this; clear(); size_t size = 0; if (copy[0].isNormal()) operator[](size++) = copy[0]; for (size_t i=0; i const Square8 sendOffSquare(const NumEffectState& state) const { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif assert(Turn == state.turn()); Square8 ret; const Square king_position = state.kingSquare(alt(Turn)); if (threatmate.sendoffs == SendOffSquare::invalidData()) threatmate.sendoffs = SendOffSquare::find(state, king_position, ret); else SendOffSquare::unpack(threatmate.sendoffs, king_position, ret); return ret; } const Square8 sendOffSquare(Player turn, const NumEffectState& state) const { if (turn == BLACK) return sendOffSquare(state); else return sendOffSquare(state); } /** * @param max ã“ã®recordã§ä½¿ã£ã¦è‰¯ã„ノード数 * @return 詰将棋ã«ä½¿ãˆã‚‹ãƒŽãƒ¼ãƒ‰æ•°ã‚’返㙠*/ int checkmateNodesLeft(int max) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif if (max > checkmate_nodes) { const int left = max - checkmate_nodes; checkmate_nodes = max; return left; } return 0; } /** * @param max ã“ã®recordã§ä½¿ã£ã¦è‰¯ã„ノード数 * @return è©°ã‚ã‚確èªã®è©°å°†æ£‹ã«ä½¿ãˆã‚‹ãƒŽãƒ¼ãƒ‰æ•°ã‚’返㙠*/ int threatmateNodesLeft(int max) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif if (max > threatmate_nodes) { const int left = max - threatmate_nodes; threatmate_nodes = max; return left; } return 0; } /** 今ã¾ã§ã«è©°å°†æ£‹ã§æŽ¢ã—ãŸãƒŽãƒ¼ãƒ‰æ•° */ int checkmateNodes() const { return checkmate_nodes; } int threatmateNodes() const { return threatmate_nodes; } void clear() { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif best_moves.clear(); upper_depth = lower_depth = static_value_depth = InitialDepth; } void setStaticValue(StaticValueType type, int value, int depth, const QuiescenceThreat& t1=QuiescenceThreat(), const QuiescenceThreat& t2=QuiescenceThreat()) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif assert((depth <= QSearchTraits::MaxDepth) || (depth == QSearchTraits::CheckmateSpecialDepth)); assert(value % 2 == 0); static_value = value; threat1 = t1; threat2 = t2; static_value_depth = depth; threatmate.flags.static_value_type = type; } public: void setLowerBound(int depth, int bound, Move best_move) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif assert((depth <= QSearchTraits::MaxDepth) || (depth == QSearchTraits::CheckmateSpecialDepth)); if (depth >= lower_depth) { best_moves.add(best_move); lower_bound = bound; lower_depth = depth; } } void setUpperBound(int depth, int bound) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif assert((depth <= QSearchTraits::MaxDepth) || (depth == QSearchTraits::CheckmateSpecialDepth)); if (depth >= upper_depth) { upper_bound = bound; upper_depth = depth; } } void setHistoryValue(int value) { lower_bound = upper_bound = value; lower_depth = upper_depth = QSearchTraits::HistorySpecialDepth; } void setHistoryValue(Move best_move, int value) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif best_moves.add(best_move); setHistoryValue(value); } public: void addKillerMoves(const MoveVector& new_moves) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif best_moves.addSecondary(new_moves); } StaticValueType staticValueType() const { return static_cast(threatmate.flags.static_value_type); } bool hasStaticValue() const { return staticValueType() != UNKNOWN; } bool hasStaticValue(int& value, int& depth, StaticValueType& type) const { type = staticValueType(); if (type == UNKNOWN) return false; #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif type = staticValueType(); value = static_value; depth = static_value_depth; return type != UNKNOWN; } int staticValue() const { assert(hasStaticValue()); return static_value; } int staticValueDepth() const { return static_value_depth; } int upperDepth() const { return upper_depth; } int lowerDepth() const { return lower_depth; } int upperBound() const { return upper_bound; } int lowerBound() const { return lower_bound; } const Move bestMove() const { return best_moves[0]; } int movesEmpty() const { return ! best_moves[1].isNormal(); } int movesSizeLessThan(size_t n) const { return best_moves.capacity() < n || ! best_moves[n-1].isNormal(); } int moves_size() const { return std::max(0, (int)best_moves.sizeFilled()-1); } void loadMoves(MoveVector& dst) const{ #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,mutex); #endif dst.clear(); for (size_t i=1; i #include namespace osl { namespace hash { class HashKey; } namespace container { struct TableFull : std::runtime_error { TableFull() : std::runtime_error("table full") { } }; /** * 基本的㪠hash table * ã¨ã‚Šã‚ãˆãš g++ (SGI STL) ã® hash_map を使ã£ã¦å®Ÿè£… * * 機能: * - ã‚‚ã—æ—¢ã«ç™»éŒ²ã•れã¦ã„ã‚‹å±€é¢ã«å†ã³ç™»éŒ²ãŒã‚ã£ãŸã‚‰ï¼Œå…¨ã¦ä¸Šæ›¸ãã™ã‚‹ * - メモリãŒã‚ãµã‚ŒãŸã‚‰å˜ã«ç„¡è¦–ã™ã‚‹ * * ã‚ã‚‹ç¨‹åº¦åŸºæœ¬çš„ãªæ©Ÿèƒ½ã‚’実装ã—ãŸã‚‰ï¼Œè‡ªåˆ†ã§å®Ÿè£…ã—ãªãŠã™ã»ã†ãŒbetter。 * ã“ã® hash_map ã§ã¯ GCを実装ã™ã‚‹ã“ã¨ã¯å›°é›£ã¨æ€ã‚れるãŸã‚ * * find, allocate ã§ ãƒã‚¤ãƒ³ã‚¿ã‚’è¿”ã™ãŸã‚,è¦ç´ ã‚’追加ã—ã¦ã‚‚,既存ã®è¦ç´ ã® * アドレスãŒå¤‰åŒ–ã—ãªã„データ構造を用ã„ã‚‹å¿…è¦ãŒã‚る. */ template class GeneralSimpleHashTable { protected: struct Table; std::unique_ptr

table; public: typedef hash::HashKey HashKey; /** * @param capacity 表ã«ä¿æŒã™ã‚‹æœ€å¤§å±€é¢ */ explicit GeneralSimpleHashTable(size_t capacity=100000); ~GeneralSimpleHashTable(); void clear(); /** * 表を探ã—,登録ã•れã¦ãªã‘ã‚Œã°æ–°è¦ã‚¨ãƒ³ãƒˆãƒªã‚’登録ã™ã‚‹ * @return テーブルãŒã„ã£ã±ã„。 * ãã†ã§ãªã‘れã°å†…部ã§ç¢ºä¿ã—ãŸå ´æ‰€ã¸ã®ãƒã‚¤ãƒ³ã‚¿ * (é–“é•ã£ã¦ã‚‚ delete ã—ãªã„ã“ã¨) * @throw TableFull */ Record *allocate(const HashKey& key); /** * 表を探ã™ï¼Žæ–°ãŸã«ç™»éŒ²ã™ã‚‹äº‹ã¯ãªã„ * @return 存在ã—ãªã‘れã°0 * ãã†ã§ãªã‘れã°å†…部ã§ç¢ºä¿ã—ãŸå ´æ‰€ã¸ã®ãƒã‚¤ãƒ³ã‚¿ * (é–“é•ã£ã¦ã‚‚ delete ã—ãªã„ã“ã¨) */ Record *find(const HashKey& key); const Record *find(const HashKey& key) const; size_t size() const; size_t capacity() const; int numCacheHit() const; int numRecordAfterFull() const; bool isVerbose() const; /** lock contention を下ã’ã‚‹ãŸã‚ã«åˆ†å‰²ã—ãŸå¤§ãã• */ int divSize() const; }; } // namespace container using container::TableFull; using container::GeneralSimpleHashTable; } // namespace osl #endif /* _GENERALSIMPLE_HASHTABLE_H_ */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/hashRejections.cc0000644000000000000000000000662512316770314020741 0ustar rootroot/* hashRejections.cc */ #include "osl/search/hashRejections.h" #include struct osl::search::HashRejections::Table { struct Entry { PieceStand black_stand; }; typedef std::unordered_map> table_t; table_t table; }; struct osl::search::HashRejections::RootTable { struct Entry { PieceStand black_stand; HashKey parent; }; typedef std::unordered_map> table_t; table_t table; }; osl::search::HashRejections:: HashRejections() : root_table(new RootTable), table(new Table) { } osl::search::HashRejections:: HashRejections(const HashRejections& src) : root_table(src.root_table), table(new Table(*src.table)) { } osl::search:: HashRejections::~HashRejections() { } osl::search::HashRejections& osl::search::HashRejections:: operator=(const HashRejections& src) { if (this != &src) { root_table = src.root_table; table.reset(); table.reset(new Table(*src.table)); } return *this; } void osl::search:: HashRejections::addRejectionRoot(const NumEffectState& parent, const HashKey& key, Move move) { MoveVector moves; parent.generateLegal(moves); assert(HashKey(parent) == key); for (Move m: moves) { if (m == move) continue; const HashKey new_key = key.newHashWithMove(m); RootTable::Entry& e = root_table->table[new_key.boardKey()]; e.parent = key; e.black_stand = new_key.blackStand(); } } void osl::search:: HashRejections::clearRejectionRoot(const NumEffectState& parent, const HashKey& key, Move move) { MoveVector moves; parent.generateLegal(moves); for (Move m: moves) { if (m == move) continue; const HashKey new_key = key.newHashWithMove(m); root_table->table.erase(new_key.boardKey()); } } void osl::search:: HashRejections::addRejection(const NumEffectState& parent, const HashKey& key, Move move) { MoveVector moves; parent.generateLegal(moves); for (Move m: moves) { if (m == move) continue; const HashKey new_key = key.newHashWithMove(m); Table::Entry& e = table->table[new_key.boardKey()]; e.black_stand = new_key.blackStand(); } } void osl::search:: HashRejections::clearRejection(const NumEffectState& parent, const HashKey& key, Move move) { MoveVector moves; parent.generateLegal(moves); for (Move m: moves) { if (m == move) continue; const HashKey new_key = key.newHashWithMove(m); table->table.erase(new_key.boardKey()); } } bool osl::search:: HashRejections::rejectionProbe(const HashKey& cur, const HashKey& parent) const { { RootTable::table_t::const_iterator p = root_table->table.find(cur.boardKey()); if (p != root_table->table.end() && p->second.parent != parent) { if (cur.turn() == BLACK) { if (cur.blackStand().isSuperiorOrEqualTo(p->second.black_stand)) return true; } else { if (p->second.black_stand.isSuperiorOrEqualTo(cur.blackStand())) return true; } } } { Table::table_t::const_iterator p = table->table.find(cur.boardKey()); if (p != table->table.end()) { if (cur.turn() == BLACK) { if (cur.blackStand().isSuperiorOrEqualTo(p->second.black_stand)) return true; } else { if (p->second.black_stand.isSuperiorOrEqualTo(cur.blackStand())) return true; } } } return false; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/breakThreatmate.h0000644000000000000000000000173612316770314020733 0ustar rootroot/* breakThreatmate.h */ #ifndef OSL_CATEGORY_BREAKTHREATMATE_H #define OSL_CATEGORY_BREAKTHREATMATE_H #include "osl/numEffectState.h" #include "osl/container/moveLogProbVector.h" namespace osl { namespace search { struct BreakThreatmate { static void generateAddEffect(int limit, const NumEffectState&, Square to, const MoveVector& src, MoveLogProbVector& out); static void generateBreakDrop(int limit, const NumEffectState&, Square to, int default_prob, MoveLogProbVector& out); static void generateOpenRoad(int limit, const NumEffectState&, Square target, MoveLogProbVector& out); static void generate(int limit, const NumEffectState&, Move threatmate_move, MoveLogProbVector& out); static void findBlockLong(const NumEffectState& state, Move threatmate_move, MoveVector& out); }; } } #endif /* OSL_CATEGORY_BREAKTHREATMATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/historyTable.h0000644000000000000000000000403212316770314020271 0ustar rootroot/* historyTable.h */ #ifndef OSL_HISTORYTABLE_H #define OSL_HISTORYTABLE_H #include "osl/basic_type.h" #include "osl/container.h" #ifdef OSL_SMP # include "osl/misc/lightMutex.h" #endif #include #include namespace osl { namespace search { class HistoryTable { public: struct Entry { uint64_t value; #ifdef OSL_SMP mutable LightMutex mutex; #endif Entry() : value(0) { } }; private: CArray,2> table; public: uint64_t value(Move move) const { if (! move.isNormal()) return 0; const int from_index = move.isDrop() ? (int)move.ptype() : (int)move.from().uintValue(); const Entry& e = table[move.player()][from_index][move.to().uintValue()]; return e.value; } void add(Move move, int inc) { if (! move.isNormal()) return; const int from_index = move.isDrop() ? (int)move.ptype() : (int)move.from().uintValue(); Entry& e = table[move.player()][from_index][move.to().uintValue()]; #ifdef OSL_SMP SCOPED_LOCK(lk, e.mutex); #endif e.value += inc; } void clear(Move move) { if (! move.isNormal()) return; const int from_index = move.isDrop() ? (int)move.ptype() : (int)move.from().uintValue(); Entry& e = table[move.player()][from_index][move.to().uintValue()]; e.value = 0; } struct OutputEntry { int from_or_ptype; Square to; uint64_t value; explicit OutputEntry(int i=0, int j=0, uint64_t v=0) : from_or_ptype(i), to(Square::makeDirect(j)), value(v) { } bool operator>(const OutputEntry& r) const { if (value != r.value) return value > r.value; if (from_or_ptype != r.from_or_ptype) return from_or_ptype > r.from_or_ptype; return to > r.to; } }; void extractTopN(Player p, std::vector& out, size_t limit) const; }; std::ostream& operator<<(std::ostream&, const HistoryTable::OutputEntry&); } }; #endif /* OSL_HISTORYTABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/usiReporter.cc0000644000000000000000000001566412316770314020316 0ustar rootroot/* usiReporter.cc */ #include "osl/search/usiReporter.h" #include "osl/usi.h" #include "osl/misc/lightMutex.h" #include "osl/misc/milliSeconds.h" #include "osl/oslConfig.h" #include void osl::search:: UsiReporter::newDepth(std::ostream& os, int depth) { if (OslConfig::usiModeInSilent()) return; os << "info depth " << depth << "\n"; } void osl::search:: UsiReporter::showPV(std::ostream& os, int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, bool ignore_silent) { if (OslConfig::usiModeInSilent() && ! ignore_silent) return; int seldepth = last-first; if (last == first || *first != cur) ++seldepth; if (ignore_silent) std::cerr << "info depth " << depth << " seldepth " << seldepth << " time " << static_cast(elapsed*1000) << " score cp " << value << " nodes " << node_count << " nps " << static_cast(node_count/elapsed) << " pv " << usi::show(cur) << "\n"; os << "info depth " << depth << " seldepth " << seldepth << " time " << static_cast(elapsed*1000) << " score cp " << value << " nodes " << node_count << " nps " << static_cast(node_count/elapsed); os << " pv " << usi::show(cur); if (first != last) { if (cur == *first) ++first; while (first != last) { os << ' ' << usi::show(*first++); } } os << "\n"; } void osl::search:: UsiReporter::showPVExtended(std::ostream& os, int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool *tfirst, const bool *tlast) { if (OslConfig::usiModeInSilent()) return; int seldepth = last-first; assert(seldepth == tlast-tfirst); if (last - first && *first != cur) ++seldepth; os << "info depth " << depth << " seldepth " << seldepth << " time " << static_cast(elapsed*1000) << " score cp " << value << " nodes " << node_count << " nps " << static_cast(node_count/elapsed); os << " pv " << usi::show(cur); if (first != last) { if (cur == *first) ++first, ++tfirst; while (first != last) { os << ' ' << usi::show(*first++); if (tfirst != tlast && *tfirst++) os << "(^)"; } } os << "\n"; } static osl::misc::LightMutex usi_root_move_mutex; void osl::search:: UsiReporter::rootMove(std::ostream& os, Move cur, bool allow_frequent_display) { if (OslConfig::usiModeInSilent()) return; static time_point prev; if (! allow_frequent_display) { time_point now = clock::now(); { SCOPED_LOCK(lk, usi_root_move_mutex); if (toSeconds(now - prev) < 0.5) return; prev = now; } } os << "info currmove " << usi::show(cur) << "\n"; } void osl::search:: UsiReporter::timeInfo(std::ostream& os, size_t node_count, double elapsed) { if (OslConfig::usiModeInSilent()) return; os << "info time " << static_cast(elapsed*1000) << " nodes " << node_count << " nps " << static_cast(node_count/elapsed) << "\n"; os << std::flush; } void osl::search:: UsiReporter::hashInfo(std::ostream& os, double ratio) { if (OslConfig::usiModeInSilent()) return; os << "info hashfull " << static_cast(ratio*1000) << "\n"; os << std::flush; } osl::search:: UsiMonitor::UsiMonitor(bool ex, std::ostream& o, double s) : silent_period(s), extended(ex), os(o), udp_socket(0), udp_endpoint(0), client_id("") { } osl::search:: UsiMonitor::~UsiMonitor() { } void osl::search:: UsiMonitor::showDeferred(bool forced) { if ((!forced && elapsedSeconds(depth0) < silent_period) || deferred.empty()) return; os << deferred << std::flush; if (udp_socket) { if (client_id != "") deferred = client_id + " " + deferred; boost::system::error_code ignored_error; udp_socket->send_to(boost::asio::buffer(deferred.c_str(), deferred.length()), *udp_endpoint, 0, ignored_error); } deferred.clear(); } void osl::search:: UsiMonitor::newDepth(int depth) { last_root_move = Move(); if (depth == 0) { depth0 = clock::now(); return; } if (elapsedSeconds(depth0) >= silent_period) { showDeferred(); UsiReporter::newDepth(os, depth); } } void osl::search:: UsiMonitor::showPV(int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool *threatmate_first, const bool *threatmate_last) { const bool defer = elapsedSeconds(depth0) < silent_period; std::ostringstream ss; if (extended) UsiReporter::showPVExtended(ss, depth, node_count, elapsed, value, cur, first, last, threatmate_first, threatmate_last); else UsiReporter::showPV(ss, depth, node_count, elapsed, value, cur, first, last); if (defer) deferred = ss.str(); else { std::string msg = ss.str(); os << msg << std::flush; if (udp_socket) { if (client_id != "") msg = client_id + " " + msg; boost::system::error_code ignored_error; udp_socket->send_to(boost::asio::buffer(msg.c_str(), msg.length()), *udp_endpoint, 0, ignored_error); } deferred.clear(); // msg sent was newer than deferred } } void osl::search::UsiMonitor:: showFailLow(int depth, size_t node_count, double elapsed, int value, Move cur) { showPV(depth, node_count, elapsed, value, cur, 0, 0, 0, 0); } void osl::search:: UsiMonitor::rootMove(Move cur) { showDeferred(); last_root_move = cur; } void osl::search:: UsiMonitor::rootFirstMove(Move cur) { showDeferred(); last_root_move = cur; UsiReporter::rootMove(os, cur, true); } void osl::search:: UsiMonitor::timeInfo(size_t node_count, double elapsed) { showDeferred(); { std::ostringstream ss; UsiReporter::timeInfo(ss, node_count, elapsed); std::string msg = ss.str(); os << msg << std::flush; if (udp_socket) { if (client_id != "") msg = client_id + " " + msg; boost::system::error_code ignored_error; udp_socket->send_to(boost::asio::buffer(msg.c_str(), msg.length()), *udp_endpoint, 0, ignored_error); } } UsiReporter::rootMove(os, last_root_move); } void osl::search:: UsiMonitor::hashInfo(double ratio) { showDeferred(); UsiReporter::hashInfo(os, ratio); } void osl::search:: UsiMonitor::rootForcedMove(Move the_move) { if (OslConfig::usiModeInSilent()) return; showDeferred(); os << "info string forced move at the root: " << usi::show(the_move) << "\n"; os << std::flush; } void osl::search:: UsiMonitor::rootLossByCheckmate() { if (OslConfig::usiModeInSilent()) return; deferred.clear(); os << "info string loss by checkmate\n"; os << std::flush; } void osl::search:: UsiMonitor::setUdpLogging(std::string& udp_client_id, boost::asio::ip::udp::socket *s, boost::asio::ip::udp::endpoint *e) { client_id = udp_client_id; udp_socket = s; udp_endpoint = e; } void osl::search:: UsiMonitor::searchFinished() { showDeferred(true); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchMonitor.cc0000644000000000000000000000303712316770314020577 0ustar rootroot/* searchMonitor.cc */ #include "osl/search/searchMonitor.h" #include "osl/csa.h" #include #include osl::search::SearchMonitor:: ~SearchMonitor() { } void osl::search::SearchMonitor::newDepth(int) { } void osl::search::SearchMonitor::showPV(int, size_t, double, int, Move, const Move *, const Move *, const bool*, const bool*) { } void osl::search::SearchMonitor::showFailLow(int, size_t, double, int, Move) { } void osl::search::SearchMonitor::rootMove(Move) { } void osl::search::SearchMonitor::rootFirstMove(Move cur) { rootMove(cur); } void osl::search::SearchMonitor::timeInfo(size_t, double) { } void osl::search::SearchMonitor::hashInfo(double) { } void osl::search::SearchMonitor::rootForcedMove(Move) { } void osl::search::SearchMonitor::rootLossByCheckmate() { } void osl::search::SearchMonitor::depthFinishedNormally(int) { } void osl::search::SearchMonitor::searchFinished() { } // void osl::search::CerrMonitor:: showPV(int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool */*threatmate_first*/, const bool */*threatmate_last*/) { std::cerr << " " << csa::show(cur) << " " << std::setw(6) << value << " " << std::setw(2) << last -first << "/" << std::setw(2) << depth << " "; for (int i=0; i std::ostream& osl::search::operator<<(std::ostream& os, DualThreatmateState s) { return os << "+ " << s.status(BLACK) << " - " << s.status(WHITE); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchState2.cc0000644000000000000000000001111012316770314020301 0ustar rootroot/* searchState2.cc */ #include "osl/search/searchState2.h" #include "osl/search/simpleHashRecord.h" #include "osl/search/sacrificeCheck.h" #include "osl/csa.h" #include "osl/misc/milliSeconds.h" #include /* ------------------------------------------------------------------------- */ osl::search:: RecordStack2::RecordStack2() { clear(); } void osl::search:: RecordStack2::clear() { data.clear(); data.push_back(0); } #ifndef MINIMAL void osl::search:: RecordStack2::dump() const { std::cerr << "RecordStack\n"; for (size_t i=0; i osl::search::SearchState2Core::depth_node_count_quiesce; #endif osl::search:: SearchState2Core::SearchState2Core(const NumEffectState& s, checkmate_t& c) : current_state(s), checkmate_searcher(&c), current_path(s.turn()), root_depth(0), stop_tree(false) { setState(s); // initialize shared assert(hasLastRecord()); } osl::search:: SearchState2Core::~SearchState2Core() { } void osl::search:: SearchState2Core::setState(const NumEffectState& s) { if (&root_state != &s) root_state = s; restoreRootState(); try { shared.reset(); shared.reset(new SearchState2Shared()); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of SearchState2Shared failed\n"; } } void osl::search:: SearchState2Core::restoreRootState() { current_state = root_state; current_path = PathEncoding(current_state.turn(), move_history.size()); repetition_counter.clear(); const HashKey key(current_state); repetition_counter.push(key, current_state); move_history.clear(); record_stack.clear(); root_depth = 0; } void osl::search:: SearchState2Core::setHistory(const MoveStack& h) { move_history = h; current_path = PathEncoding(current_path.turn(), h.size()); root_depth = history().size(); } void osl::search:: SearchState2Core::setBigramKillerMove(const BigramKillerMove& killers) { try { shared.reset(); shared.reset(new SearchState2Shared()); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of SearchState2Shared failed\n"; } shared->bigram_killers = killers; } bool osl::search:: SearchState2Core::abort() const { return abort(Move()); } bool osl::search:: SearchState2Core::abort(Move best_move) const { std::cerr << state(); #ifndef MINIMAL history().dump(); const SimpleHashRecord *record = record_stack.lastRecord(); std::cerr << "best move " << csa::show(best_move) << "\n"; std::cerr << "record " << record << "\n"; if (record) { record->dump(std::cerr); } record_stack.dump(); repetition_counter.history().dump(); #endif return false; } void osl::search::SearchState2Core::makePV(PVVector& parent, Move m, PVVector& pv) const { parent.clear(); parent.push_back(m); parent.push_back(pv.begin(), pv.end()); #ifdef DEBUG_PV NumEffectState s = state(); for (Move p: parent) { if (! p.isPass() && ! s.isValidMove(p)) { std::cerr << "best move error " << p << " " << i << "\n"; std::cerr << state(); for (Move q: parent) std::cerr << q << " "; std::cerr << "\n"; ::abort(); break; } ApplyMoveOfTurn::doMove(s, p); } #endif } #ifndef NDEBUG void osl::search:: SearchState2Core::makeMoveHook(Move) { // history().dump(); } #endif /* ------------------------------------------------------------------------- */ osl::search:: SearchState2::SearchState2(const NumEffectState& s, checkmate_t& c) : SearchState2Core(s, c), root_limit(0), cur_limit(0) { } osl::search:: SearchState2::~SearchState2() { } void osl::search:: SearchState2::setState(const NumEffectState& s) { SearchState2Core::setState(s); root_limit = cur_limit = 0; } int osl::search:: SearchState2::countSacrificeCheck2(int history_max) const { return SacrificeCheck::count2(recordHistory(), history(), history_max); } bool osl::search:: SearchState2::abort(Move best_move) const { std::cerr << "cur limit " << cur_limit << " root limit " << root_limit << "\n"; SearchState2Core::abort(best_move); return false; } void osl::search:: SearchState2::checkPointSearchAllMoves() { // debug code can be written here } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceLog.h0000644000000000000000000000152012316770314020405 0ustar rootroot/* quiescenceLog.h */ #ifndef SEARCH_QUIESCENCELOG #define SEARCH_QUIESCENCELOG #include "osl/numEffectState.h" #include namespace osl { namespace search { class QuiescenceRecord; /** * å–りåˆã„探索ã®è¨˜éŒ²ã‚’ã¨ã‚‹. * init ã—ãªã„é™ã‚Šè¨˜éŒ²ã¯æ®‹ã‚‰ãªã„ */ struct QuiescenceLog { static void enter(const SimpleState&); static void pushMove(int depth, Move m, const QuiescenceRecord *r); static void staticValue(int depth, int value); static void node(int depth, int alpha, int beta, int result); static void init(const char *filename); static void close(); static std::ostream *os(); }; } // namespace search } // namespace osl #endif /* SEARCH_QUIESCENCELOG */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/bigramKillerMove.h0000644000000000000000000000231512316770314021055 0ustar rootroot/* bigramKillerMove.h */ #ifndef _BIGRAMKILLERMOVETABLE_H #define _BIGRAMKILLERMOVETABLE_H #include "osl/search/lRUMoves.h" #include "osl/numEffectState.h" #include #include namespace osl { namespace search { /** * ç›¸æ‰‹ã®æŒ‡æ‰‹ã«åŸºã¥ãkiller move */ class BigramKillerMove { private: CArray2d killer_moves; public: BigramKillerMove(); ~BigramKillerMove(); void clear(); void setMove(Move key, Move value) { if (value.isPass()) return; if (key.to() == value.to()) return; // takeback ã¯èª­ã¿ãㆠassert(value.isValid()); assert(key.player() != value.player()); killer_moves[key.to().index()][ptypeOIndex(key.ptypeO())].setMove(value); } const LRUMoves& operator[](Move key) const { return killer_moves[key.to().index()][ptypeOIndex(key.ptypeO())]; } void getMove(const NumEffectState& state, Move last_move, MoveVector& moves) const; void dump() const; }; } // namespace search } // namespace osl #endif /* _BIGRAMKILLERMOVETABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceGenerator.h0000644000000000000000000001502312316770314021615 0ustar rootroot/* quiescenceGenerator.h */ #ifndef OSL_QUIESCENCEGENERATOR_H #define OSL_QUIESCENCEGENERATOR_H #include "osl/move_classifier/shouldPromoteCut.h" #include "osl/search/historyTable.h" #include "osl/move_generator/capture_.h" #include "osl/move_generator/escape_.h" #include "osl/move_generator/promote_.h" #include "osl/move_generator/safeDropMajorPiece.h" #include "osl/move_generator/addEffect8.h" #include "osl/move_generator/additionalLance.h" #include "osl/eval/pieceEval.h" #include "osl/numEffectState.h" #include "osl/container/square8.h" namespace osl { namespace search { /** * QuiescenceSearch ã§ä½¿ã†æŒ‡æ‰‹ç”Ÿæˆ */ template struct QuiescenceGenerator { /** * P ãŒæ•µã® PTYPE ã‚’å–る手を生æˆã™ã‚‹ï¼Ž * @param dont_capture ã“れをå–る手ã¯é™¤ã */ template static void capture(const NumEffectState&, MoveVector& moves, Piece dont_capture); /** * P ãŒæ•µã® target ã‚’å–る手を生æˆã™ã‚‹ï¼Ž */ static void capture(const NumEffectState&, Square target, MoveVector& moves); /** * P ãŒæ•µã® target ã‚’å–る手を最大1手生æˆã™ã‚‹ï¼Ž */ static void capture1(const NumEffectState& state, Square target, MoveVector& moves) { move_generator::GenerateCapture::generate1(P, state, target, moves); } static void promote(const NumEffectState&, PieceMask pins, MoveVector& moves); template static void promote(const NumEffectState&, MoveVector& moves); template static void promoteN(const NumEffectState&, MoveVector& moves, const HistoryTable& table); static void check(const NumEffectState&, PieceMask pins, MoveVector& moves, bool no_liberty=false); static void check(const NumEffectState&, PieceMask pins, bool no_liberty, const Square8& sendoffs, MoveVector& moves); static void escapeKing(const NumEffectState& state, MoveVector& moves); /** * @return existance of safe (in takeback) move */ static bool escapeKingInTakeBack(const NumEffectState& state, MoveVector& moves, bool check_by_lance); static void dropMajorPiece(const NumEffectState& state, MoveVector& moves); static void dropMajorPiece3(const NumEffectState& state, MoveVector& moves, const HistoryTable& table); static void attackMajorPiece(const NumEffectState& state, PieceMask pins, MoveVector& moves); static void escapeAll(const NumEffectState& state, MoveVector& moves); /** * @param escape KING以外ã®é§’ */ static void escapeNormalPiece(const NumEffectState& state, Piece escape, MoveVector& moves, bool add_support_only=false); /** * ç›´å‰ã«æŒ‡æ‰‹ã‹ã‚‰é€ƒã’ã‚‹ */ template static void escapeFromLastMove(const NumEffectState& state, Move last_move, MoveVector& moves); template static void escapeFromLastMoveOtherThanPawn(const NumEffectState& state, Move last_move, MoveVector& moves); /** * @return 利ãã®ãªã„場所ã«ç§»å‹•å¯èƒ½ */ static bool escapeByMoveOnly(const NumEffectState& state, Piece piece, MoveVector& moves); static void attackGoldWithPawn(const NumEffectState& state, PieceMask pins, MoveVector& moves); static void attackWithKnight(const NumEffectState& state, PieceMask pins, Square attack_from, bool has_knight, MoveVector& moves); static void attackSilverWithPawn(const NumEffectState& state, PieceMask pins, MoveVector& moves); static void attackKnightWithPawn(const NumEffectState& state, PieceMask pins, MoveVector& moves); /** * è§’ãŒå‰ã«é€²ã‚€. 覗ã„ã¦æˆã‚’å—ã‘ã«ãã„èª­ã¿æŠœã‘を防ã */ static void advanceBishop(const NumEffectState& state, MoveVector& moves); template static void advanceBishop(const NumEffectState& state, const Square from, MoveVector& moves); static void attackKing8(const NumEffectState& state, PieceMask pins, MoveVector& moves); static void attackToPinned(const NumEffectState& state, PieceMask pins, MoveVector& moves); static void utilizePromoted(const NumEffectState& state, Piece target, MoveVector& moves); static void breakThreatmate(const NumEffectState& state, Move threatmate, PieceMask pins, MoveVector& moves); static void kingWalk(const NumEffectState& state, MoveVector& moves); private: static void attackMajorPieceSecondSelection(bool target_has_support, const MoveVector& src, MoveVector& out); static void attackMajorPieceFirstSelection(const NumEffectState& state, PieceMask pins, const MoveVector& all_moves, MoveVector& moves, MoveVector& expensive_drops); static void attackMajorPieceZerothSelection(const NumEffectState& state, const MoveVector& src, Square target, MoveVector& open_out, MoveVector& out); }; } // namespace search } // namespace osl template inline void osl::search::QuiescenceGenerator

:: capture(const NumEffectState& state, Square target, MoveVector& moves) { move_generator::GenerateCapture::generate(P,state, target, moves); #ifndef NDEBUG for (Move m: moves) assert(! ShouldPromoteCut::canIgnoreMove

(m)); #endif } template template inline void osl::search::QuiescenceGenerator

:: promote(const NumEffectState& state, MoveVector& moves) { move_generator::Promote

::template generatePtype(state, moves); } template template inline void osl::search::QuiescenceGenerator

:: promoteN(const NumEffectState& state, MoveVector& moves, const HistoryTable& table) { MoveVector all; move_generator::Promote

::template generatePtype(state, all); FixedCapacityVector, 16*2> selected; for (Move m: all) { if (state.hasEffectAt(alt(P), m.to())) continue; selected.push_back(std::make_pair(table.value(m), m)); } std::sort(selected.begin(), selected.end()); for (size_t i=0; i namespace osl { namespace search { /** * SimpleHashTable ã®ä¸­ã«è¨˜éŒ²ã™ã‚‹ã‚¨ãƒ³ãƒˆãƒª */ class SimpleHashRecord { public: /** 陿­¢æŽ¢ç´¢ç”¨ */ QuiescenceRecord qrecord; private: MoveLogProb best_move; int upper_bound; int lower_bound; signed short upper_limit; signed short lower_limit; /** CAVEAT: 32bit ã§ã¯ 100万局é¢/ç§’ã§1時間ã¡ã‚‡ã£ã¨è€ƒãˆã‚‹ã¨æº¢ã‚Œã‚‹ */ unsigned int search_nodes; public: SimpleHashRecord() : upper_limit(-1), lower_limit(-1), search_nodes(0) { } void addNodeCount(size_t diff) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif search_nodes += diff; } /** * 値を書ã込む. è©°å°†æ£‹ã‚„åƒæ—¥æ‰‹å¯¾ç­–を想定. */ void setAbsoluteValue(Move best_move, int value, int limit) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif lower_limit = limit; lower_bound = value; upper_limit = limit; upper_bound = value; if (best_move.isNormal()) this->best_move = MoveLogProb(best_move, 100); else this->best_move = MoveLogProb(); } void setBestMove(Move m, int logprob=100) { assert(! m.isInvalid()); // æ™®é€šã®æ›´æ–°ã¯setLowerBoundã§ã€‚ best_move = MoveLogProb(m, logprob); qrecord.best_moves.add(m); } void setAbsoluteValue(MoveLogProb best_move, int value, int limit) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif lower_limit = limit; lower_bound = value; upper_limit = limit; upper_bound = value; this->best_move = best_move; } /** * lowerBound ã®è¨­å®š. * - æ·±ã•優先 * - åŒã˜æ·±ã•ãªã‚‰è‰¯ã„値優先 */ void setLowerBound(Player P, int limit, const MoveLogProb& best_move, int value) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif assert((value % 2) == 0); assert(limit >= 0); if (limit < lower_limit) return; if (best_move.validMove()) this->best_move= best_move; lower_bound = value; lower_limit = limit; if (hasUpperBound(0)) makeConsistent(P); } /** * upperBound ã®è¨­å®š. * - æ·±ã•優先 * - åŒã˜æ·±ã•ãªã‚‰æ‚ªã„値優先 */ void setUpperBound(Player P, int limit, const MoveLogProb& best_move, int value) { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif assert((value % 2) == 0); assert(limit >= 0); if (limit < upper_limit) return; if (best_move.validMove() && (! this->best_move.validMove())) { // best move ã¯upper boundã§ã¯åŸºæœ¬çš„ã«ã¯æ›´æ–°ã—ãªã„ this->best_move= best_move; } upper_bound = value; upper_limit = limit; if (hasLowerBound(0)) makeConsistent(P); } private: /** * 上é™ã¨ä¸‹é™ã«çŸ›ç›¾ãŒã‚ã£ãŸã‚‰èª¿æ•´ã™ã‚‹. * åŒã˜æ·±ã•ã ã£ãŸã‚‰å¾Œã‹ã‚‰æ¥ãŸæ–¹ã‚’優先ã—ãªã„ã¨ï¼Œå†ã€…探索ã®çµæžœã‚’記録ã§ããªã„ * @param PreferLowerBound åŒã˜æ·±ã•ã ã£ãŸã‚‰ lower bound を優先ã™ã‚‹ */ template void makeConsistent(Player P) { assert(hasLowerBound(0) && hasUpperBound(0)); if (! eval::betterThan(P, lower_bound, upper_bound)) return; if ((upper_limit < lower_limit) || (PreferLowerBound && (upper_limit == lower_limit))) { upper_bound = lower_bound; assert((upper_bound % 2) == 0); } else { lower_bound = upper_bound; assert((lower_bound % 2) == 0); } } public: /** upperBound を記録ã—ãŸã¨ãã®limit */ int upperLimit() const { return upper_limit; } /** 手番ã®ãƒ—レイヤã‹ã‚‰ã¿ãŸè©•価値ã®ä¸Šé™ */ int upperBound() const { return upper_bound; } /** lowerBound を記録ã—ãŸã¨ãã®limit */ int lowerLimit() const { return lower_limit; } /** 手番ã®ãƒ—レイヤã‹ã‚‰ã¿ãŸè©•価値ã®ä¸‹é™ */ int lowerBound() const { return lower_bound; } /** 今ã¾ã§ã«è©°å°†æ£‹ã§æŽ¢ã—ãŸãƒŽãƒ¼ãƒ‰æ•° */ int checkmateNodes() const { return qrecord.checkmate_nodes; } int threatmateNodes() const { return qrecord.threatmate_nodes; } const MoveLogProb bestMove() const { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif return best_move; } bool hasUpperBound(int limit) const { return (upperLimit() >= limit); } bool hasLowerBound(int limit) const { return (lowerLimit() >= limit); } bool hasAbsoluteUpperBound(Player p, int limit) const { return (p == BLACK) ? hasUpperBound(limit) : hasLowerBound(limit); } bool hasAbsoluteLowerBound(Player p, int limit) const { return (p == BLACK) ? hasLowerBound(limit) : hasUpperBound(limit); } int absoluteUpperBound(Player p) const { return (p == BLACK) ? upperBound() : lowerBound(); } int absoluteLowerBound(Player p) const { return (p == BLACK) ? lowerBound() : upperBound(); } void resetValue() { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif lower_limit = -1; upper_limit = -1; } /** high fail ã™ã‚‹ã‹ */ template bool hasGreaterLowerBound(int limit, int threshold, int& val) const { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif if ((lowerLimit() < limit) || (EvalTraits

::betterThan(threshold, lowerBound()))) return false; val = lowerBound(); return true; } /** low fail ã™ã‚‹ã‹ */ template bool hasLesserUpperBound(int limit, int threshold, int& val) const { #ifdef OSL_SMP SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif if ((upperLimit() < limit) || (EvalTraits

::betterThan(upperBound(), threshold))) return false; val = upperBound(); return true; } const DualThreatmateState& threatmate() const { return qrecord.threatmate; } DualThreatmateState& threatmate() { return qrecord.threatmate; } void dump(std::ostream&) const; size_t nodeCount() const { return search_nodes; } bool inCheck() const { #ifdef OSL_USE_RACE_DETECTOR SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif return qrecord.threatmate.flags.is_king_in_check; } void setInCheck(bool new_value) { #ifdef OSL_USE_RACE_DETECTOR SCOPED_LOCK_CHAR(lk,qrecord.mutex); #endif qrecord.threatmate.flags.is_king_in_check = new_value; } }; } // namespace search using search::SimpleHashRecord; } // namespace osl #endif /* OSL_SEARCH_SIMPLEHASHRECORD_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/firstMoveThreatmate.h0000644000000000000000000000131412316770314021615 0ustar rootroot/* firstMoveThreatmate.tcc */ #ifndef SEARCH_FIRSTMOVETHREATMATE_H #define SEARCH_FIRSTMOVETHREATMATE_H #include "osl/basic_type.h" namespace osl { namespace search { /** * åˆæ‰‹ã«å¯¾ã—ã¦è©°ã‚ã‚æŽ¢ç´¢ã‚’ã™ã‚‹ã‹ã©ã†ã‹ã‚’判定 */ struct FirstMoveThreatmate { static bool isMember(Move last_move, Square king) { const Ptype captured = last_move.capturePtype(); const Square to = last_move.to(); return ((captured != PTYPE_EMPTY) || (isMajor(last_move.ptype())) || (abs(to.x() - king.x()) + abs(to.y() - king.y()) < 8)); } }; } } #endif /* SEARCH_FIRSTMOVETHREATMATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchRecorder.cc0000644000000000000000000001765412316770314020727 0ustar rootroot/* searchRecorder.cc */ #include "osl/search/searchRecorder.h" #include "osl/search/realizationProbability.h" #include "osl/eval/evalTraits.h" #include "osl/moveLogProb.h" #include "osl/csa.h" #include #include #include #include #ifndef _MSC_VER # include #endif #ifndef MINIMAL const char *checkmateFileName = "currentCheck.csa"; #endif /** 以下を define ã—ãªã„㨠詰将棋ã®çµæžœã‚’å…¨ã¦è¨˜éŒ²ã™ã‚‹ */ #define SELECT_CHECKMATE_LOG /** 以下を定義ã™ã‚‹ã¨è©°å°†æ£‹ã«å…¥ã£ãŸæ™‚ã®å±€é¢ã‚’別ファイルã«ä¿å­˜ã™ã‚‹ */ // #define CHECKMATE_SEARCHER_DEBUG /* ------------------------------------------------------------------------- */ osl::search::CountRecorder::CountRecorder() : node_count(0), quiescence_count(0), checkmate_count(0) { } osl::search::CountRecorder::~CountRecorder() { } void osl::search:: CountRecorder::recordInvalidMoveInTable(const SimpleState& state, const MoveLogProb& move, int limit) const { std::cerr << "?? invalid move in table " << move.move() << " " << move.logProb() << " limit " << limit << "\n" << state; } void osl::search::CountRecorder::resetNodeCount() { node_count = quiescence_count = checkmate_count = 0; } void osl::search:: CountRecorder::finishSearch(Move /*best_move*/, double sec, bool verbose) const { if (! verbose) return; reportCount(std::cerr, sec); } void osl::search:: CountRecorder::reportCount(std::ostream& os) const { os << "#normal : " << nodeCount() << ", "; os << "#quiescence: " << quiescenceCount() << ", "; os << "#checkmate : " << checkmateCount() << "\n"; } void osl::search:: CountRecorder::reportCount(std::ostream& os, double seconds) const { const double total = nodeCount() + quiescenceCount() + checkmateCount(); os << "#total : " << total << std::setprecision(10) << " in " << seconds << " sec., " << total/seconds << " nodes/sec." << std::setprecision(4) << " (quiesce " << 100.0*quiescenceCount()/total << "%," << " checkmate " << 100.0*checkmateCount()/total << "%)\n"; } /* ------------------------------------------------------------------------- */ #ifndef MINIMAL static bool showAllValues = false; struct osl::search::SearchRecorder::Recorder { std::ofstream os; /** ç¾åœ¨ã®æ·±ã•(表示加工用) */ int current_depth; /** 探索を開始ã—ãŸæ™‚点ã§ã®limit */ int initial_limit; int log_margin; Recorder(const char *filename) : os(filename), current_depth(0), initial_limit(0), log_margin(RealizationProbability::TableMove) { } std::ostream& stream() { assert(os); #if 0 os << current_depth << ':'; #endif for (int i=0; i<=current_depth; ++i) os << '*'; os << ' '; return os; } /** 変ãªåå‰ã ã‘ã©è¨˜éŒ²ã‚’å–ã‚‹æ·±ã•ã«åŽã¾ã£ã¦ã„る事を調ã¹ã‚‹ */ bool notSoDeep(int limit) const { return #ifdef SELECT_CHECKMATE_LOG (limit <= initial_limit) // SearchTable::CheckmateSpecialDepth ãŒæ¥ã‚‹ã“ã¨ãŒã‚ã‚‹ && #endif (initial_limit - limit) <= log_margin; } void flush() { #if 1 os << std::flush; #endif } }; osl::search:: SearchRecorder::SearchRecorder(const char *filename) : recorder(new Recorder(filename)) { } osl::search:: SearchRecorder::~SearchRecorder() { } void osl::search:: SearchRecorder::setLogMargin(int margin) { recorder->log_margin = margin; } void osl::search:: SearchRecorder::tryMove(const MoveLogProb& m, int last_f, int limit) const { ++recorder->current_depth; if (recorder->notSoDeep(limit-100)) // 末端ã§ã¯tryMove を無視 { std::ostream& os = stream(); os << "==> " << csa::show(m.move()); os << " " << m.logProb() << "\t" << "last_f: " << last_f << " limit: " << limit << "\n"; recorder->flush(); } } void osl::search:: SearchRecorder::retryMove(const MoveLogProb& m, int last_f, int limit, int retryCount) const { ++recorder->current_depth; if (recorder->notSoDeep(limit)) // å†æŽ¢ç´¢ã¯å¿…ãšè¨˜éŒ²ã—ãªã„ã¨ã‚„ã‚„ã“ã—ã„ { std::ostream& os = stream(); os << "ex" << retryCount << "> " << csa::show(m.move()); os << " " << m.logProb() << "\t" << "last_f: " << last_f << " limit: " << limit << "\n"; recorder->flush(); } } void osl::search:: SearchRecorder::recordValue(const MoveLogProb& m, int val, bool betterMove, int limit) const { if (recorder->notSoDeep(limit) && (showAllValues || betterMove)) { std::ostream& os = stream(); os << "<== " << val << "\t" << csa::show(m.move()); os << "\n"; recorder->flush(); } CountRecorder::recordValue(m,val,betterMove,limit); --recorder->current_depth; } static const char *lowerChar(osl::Player p) { return (p == osl::BLACK) ? "B (lb)>" : "W (lb)<"; } static const char *higherChar(osl::Player p) { return (p == osl::BLACK) ? "B (ub)<" : "W (ub)>"; } void osl::search:: SearchRecorder::tableHitLowerBound(Player p, int val, int last_f, int limit) const { if (recorder->notSoDeep(limit)) { stream() << "==| table answered " << lowerChar(p) << val << " for " << p << " last_f " << last_f << "\n"; recorder->flush(); } } void osl::search:: SearchRecorder::tableHitUpperBound(Player p, int val, int last_f, int limit) const { if (recorder->notSoDeep(limit)) { stream() << "==| table answered " << higherChar(p) << val << " for " << p << " last_f " << last_f << "\n"; recorder->flush(); } } void osl::search:: SearchRecorder::tableStoreLowerBound(Player p, const MoveLogProb& best_move, int val, int limit) const { const Move move = best_move.move(); assert(move.isInvalid() || move.isValidOrPass()); // TODO: lower bound 㯠invalid ã¯ãªã„ã¯ãš? if (recorder->notSoDeep(limit-100)) // 末端ã¯ç„¡è¦– { std::ostream& os = stream(); os << "|== table store " << lowerChar(p) << val << " " << csa::show(move); os << " limit " << limit << "\n"; recorder->flush(); } } void osl::search:: SearchRecorder::tableStoreUpperBound(Player p, const MoveLogProb& best_move, int val, int limit) const { const Move move = best_move.move(); assert(move.isInvalid() || move.isValidOrPass()); if (recorder->notSoDeep(limit-100)) // 末端ã¯ç„¡è¦– { std::ostream& os = stream(); os << "|== table store " << higherChar(p) << val << " " << csa::show(move); os << " limit " << limit << "\n"; recorder->flush(); } } void osl::search:: SearchRecorder::recordTopLevelLowFail(const MoveLogProb& /* best */, int last_f) const { stream() << "low fail, last_f=" << last_f << "\n"; reportCount(stream()); } void osl::search:: SearchRecorder::recordTopLevelHighFail(const MoveLogProb& best_move, int last_f) const { stream() << "high fail, last_f=" << last_f << " " << best_move << "\n"; reportCount(stream()); } void osl::search:: SearchRecorder::startSearch(int limit) const { stream() << "\nnew search: limit " << limit << ", log " << recorder->log_margin << "\n"; recorder->initial_limit = limit; CountRecorder::startSearch(limit); } void osl::search:: SearchRecorder::finishSearch(Move best_move, double sec, bool verbose) const { stream() << "search finished\t" << best_move << "\n"; CountRecorder::finishSearch(best_move, sec, verbose); } void osl::search:: SearchRecorder::gotoCheckmateSearch(const SimpleState& #ifdef CHECKMATE_SEARCHER_DEBUG state #endif , int #ifdef CHECKMATE_SEARCHER_DEBUG nodeLimit #endif ) const { #ifdef CHECKMATE_SEARCHER_DEBUG std::ofstream os(checkmateFileName, std::ios::app); os << state; os << nodeLimit << "\n"; #endif } void osl::search:: SearchRecorder::backFromCheckmateSearch() const { #ifdef CHECKMATE_SEARCHER_DEBUG std::ofstream os(checkmateFileName, std::ios::app); os << "done\n"; #endif } std::ostream& osl::search:: SearchRecorder::stream() const { return recorder->stream(); } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/0000755000000000000000000000000012316770314017275 5ustar rootrootlibosl-0.8.0.orig/full/osl/search/analyzer/logWriter.h0000644000000000000000000000230712316770314021426 0ustar rootroot/* logWriter.h */ #ifndef _LOGWRITER_H #define _LOGWRITER_H #include "osl/basic_type.h" #include namespace osl { class MoveLogProb; namespace search { class SimpleHashRecord; namespace analyzer { /** * 探索ログ log を書ãå‡ºã™æŠ½è±¡ã‚¯ãƒ©ã‚¹. * @see DotWriter * @see OutlineWriter (未定義) */ class LogWriter { public: enum NodeType { NORMAL=0, IMPORTANT=1, ABNORMAL=2, }; LogWriter(); virtual ~LogWriter(); /** * @param important ãƒ¦ãƒ¼ã‚¶ãŒæŒ‡å®šã—ãŸèª­ç­‹ã‚’指定ã™ã‚‹å ´åˆ true */ virtual void showNode(Player turn, const SimpleHashRecord *record, int limit, NodeType type) const = 0; virtual void showNodeQuiescence(Player turn, const SimpleHashRecord *record, int limit, NodeType type) const = 0; virtual void showArc(const SimpleHashRecord *from, const SimpleHashRecord *to, const MoveLogProb& move, bool important) const = 0; virtual void showComment(const char * /*line*/) const {} }; } // namespace analyzer } // namespace search } // namespace osl #endif /* _LOGWRITER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/categoryMoveVector.cc0000644000000000000000000000107512316770314023436 0ustar rootroot/* categoryMoveVector.cc */ #include "osl/search/analyzer/categoryMoveVector.h" osl::search::analyzer:: CategoryMoves::CategoryMoves(const MoveLogProbVector& v, const std::string& n) : moves(v), category(n) { } osl::search::analyzer:: CategoryMoves::~CategoryMoves() { } osl::search::analyzer:: CategoryMoveVector::CategoryMoveVector() { } osl::search::analyzer:: CategoryMoveVector::~CategoryMoveVector() { } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/logWriter.cc0000644000000000000000000000050512316770314021562 0ustar rootroot/* logWriter.cc */ #include "osl/search/analyzer/logWriter.h" osl::search::analyzer::LogWriter:: LogWriter() { } osl::search::analyzer::LogWriter:: ~LogWriter() { } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/categoryMoveVector.h0000644000000000000000000000135512316770314023301 0ustar rootroot// categoryMoveVector.h #ifndef CATEGORYMOVEVECTOR_H #define CATEGORYMOVEVECTOR_H #include "osl/container/moveLogProbVector.h" #include #include namespace osl { namespace search { namespace analyzer { struct CategoryMoves { MoveLogProbVector moves; std::string category; CategoryMoves(const MoveLogProbVector&, const std::string&); ~CategoryMoves(); }; class CategoryMoveVector : public std::forward_list { public: CategoryMoveVector(); ~CategoryMoveVector(); }; } // namespace analyzer } // namespace search } // namespace osl #endif /* CATEGORYMOVEVECTOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/recordSet_.cc0000644000000000000000000000037512316770314021702 0ustar rootroot/* recordSet.cc */ #include "osl/search/analyzer/recordSet_.h" osl::search::analyzer::RecordSet:: RecordSet() { } osl::search::analyzer::RecordSet:: ~RecordSet() { } /* ------------------------------------------------------------------------- */ libosl-0.8.0.orig/full/osl/search/analyzer/dotWriter.h0000644000000000000000000000234312316770314021433 0ustar rootroot/* dotWriter.h */ #ifndef _DOTWRITER_H #define _DOTWRITER_H #include "osl/search/analyzer/logWriter.h" #include namespace osl { namespace hash { class HashKey; } namespace search { class SimpleHashTable; namespace analyzer { class RecordSet; /** * 探索ログ dot (www.graphviz.org) 用を書ã出ã™. */ class DotWriter : public LogWriter { /** * æ—¢ã«æ›¸ã„ãŸãƒŽãƒ¼ãƒ‰ã‚’ä¿å­˜. * CAVEAT: from, 㨠to を両方書ã㨠from -> to ã®ã‚¨ãƒƒã‚¸ã‚‚書ã‹ãªã„ */ std::unique_ptr written; std::ostream& os; public: explicit DotWriter(std::ostream& os); ~DotWriter(); void showNode(Player turn, const SimpleHashRecord *record, int limit, NodeType type) const; void showNodeQuiescence(Player turn, const SimpleHashRecord *record, int limit, NodeType type) const; void showArc(const SimpleHashRecord *from, const SimpleHashRecord *to, const MoveLogProb& move, bool important) const; void showComment(const char *line) const; }; } // namespace analyzer } // namespace search } // namespace osl #endif /* _DOTWRITER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/dotWriter.cc0000644000000000000000000000765012316770314021577 0ustar rootroot/* dotWriter.cc */ #include "osl/search/analyzer/dotWriter.h" #include "osl/search/analyzer/recordSet_.h" #include "osl/search/simpleHashRecord.h" #include "osl/csa.h" #include #include #include #include // #define BOOST_FORMAT_BUG osl::search::analyzer::DotWriter:: DotWriter(std::ostream& o) : written(new RecordSet()), os(o) { os << "digraph OSL_DotWriter {\n"; } osl::search::analyzer::DotWriter:: ~DotWriter() { os << "}\n" << std::flush; } void osl::search::analyzer::DotWriter:: showComment(const char *line) const { os << "// " << line << "\n"; } void osl::search::analyzer::DotWriter:: showNode(Player turn, const SimpleHashRecord *record, int limit, NodeType type) const { const bool black_turn = turn == BLACK; if (written->find(record) != written->end()) return; written->insert(record); assert(record); std::stringstream range; int lower_limit = record->lowerLimit(); int lower_bound = record->lowerBound(); int upper_limit = record->upperLimit(); int upper_bound = record->upperBound(); if (! black_turn) { std::swap(lower_limit, upper_limit); std::swap(lower_bound, upper_bound); } int bound = 0; if (lower_limit >= 0) { ++bound; range << (boost::format("%d(%d)") % lower_bound % lower_limit); } range << '<'; if (upper_limit >= 0) { ++bound; range << (boost::format("%d(%d)") % upper_bound % upper_limit); } const char *color = 0; switch (type) { case IMPORTANT: color = "blue"; break; case ABNORMAL: color = "magenta"; break; default: color = (bound == 2) ? "red" : "black"; } std::stringstream bestmove; bestmove << csa::show(record->bestMove().move()); os << (boost::format("N%x [label=\"l=%d\\n%s\\n%s\",color=%s,shape=box]\n") % record % limit % range.str() % bestmove.str() % color); } // TODO: 鏿‰‹æ¨©å¾Œã« showNode ã¨å…±é€šéƒ¨åˆ†ã‚’ã¾ã¨ã‚ã‚‹ void osl::search::analyzer::DotWriter:: showNodeQuiescence(Player turn, const SimpleHashRecord *record, int limit, NodeType type) const { bool black_turn = (turn == BLACK); if (written->find(record) != written->end()) return; written->insert(record); assert(record); const QuiescenceRecord *qrecord = &record->qrecord; std::stringstream range; int lower_limit = qrecord->lowerDepth(); int lower_bound = qrecord->lowerBound(); int upper_limit = qrecord->upperDepth(); int upper_bound = qrecord->upperBound(); if (! black_turn) { std::swap(lower_limit, upper_limit); std::swap(lower_bound, upper_bound); } int bound = 0; if (lower_limit >= 0) { ++bound; range << (boost::format("%d(%d)") % lower_bound % lower_limit); } range << '<'; if (upper_limit >= 0) { ++bound; range << (boost::format("%d(%d)") % upper_bound % upper_limit); } const char *color = 0; switch (type) { case IMPORTANT: color = "blue"; break; case ABNORMAL: color = "magenta"; break; default: color = (bound == 2) ? "burlywood" : "cyan"; } os << (boost::format("N%x [label=\"l=%d\\n%s\",color=%s,shape=box]\n") % record % limit % range.str() % color); } void osl::search::analyzer::DotWriter:: showArc(const SimpleHashRecord *from, const SimpleHashRecord *to, const MoveLogProb& move, bool important) const { if ((written->find(from) != written->end()) && (written->find(to) != written->end())) return; assert(from); assert(to); std::stringstream move_string; move_string << csa::show(move.move()); const char *color = 0; if (important) color = "blue"; else color = (move.logProb() <= 100) ? "red" : "black"; os << (boost::format("N%x -> N%x [label=\"%s (%d)\", color=%s, style=bold]\n") % from % to % move_string.str() % move.logProb() % color); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/search/analyzer/recordSet_.h0000644000000000000000000000106012316770314021534 0ustar rootroot/* recordSet.h */ #ifndef _SEARCH_RECORDSET_H #define _SEARCH_RECORDSET_H #include namespace osl { namespace search { class SimpleHashRecord; } } namespace osl { namespace search { namespace analyzer { class RecordSet : public std::unordered_set { public: RecordSet(); ~RecordSet(); }; } // namespace analyzer } // namespace search } // namespace osl #endif /* _SEARCH_RECORDSET_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchMonitor.h0000644000000000000000000000250212316770314020435 0ustar rootroot/* searchMonitor.h */ #ifndef OSL_SEARCHMONITOR_H #define OSL_SEARCHMONITOR_H #include "osl/basic_type.h" namespace osl { namespace search { class SearchMonitor { public: virtual ~SearchMonitor(); virtual void newDepth(int depth); virtual void showPV(int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool *threatmate_first, const bool *threatmate_last); virtual void showFailLow(int depth, size_t node_count, double elapsed, int value, Move cur); virtual void rootMove(Move cur); virtual void rootFirstMove(Move cur); virtual void timeInfo(size_t node_count, double elapsed); virtual void hashInfo(double ratio); virtual void rootForcedMove(Move the_move); virtual void rootLossByCheckmate(); virtual void depthFinishedNormally(int depth); virtual void searchFinished(); }; class CerrMonitor : public SearchMonitor { public: void showPV(int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool *threatmate_first, const bool *threatmate_last); }; } using search::SearchMonitor; } #endif /* OSL_SEARCHMONITOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/usiProxy.cc0000644000000000000000000002441012715504335017623 0ustar rootroot#include "osl/search/usiProxy.h" #include "osl/search/interimReport.h" #include "osl/search/searchMonitor.h" #include "osl/search/moveWithComment.h" #include "osl/search/simpleHashTable.h" #include "osl/usi.h" #include #include #include #include #include #include #include #include #include #include #include #include #ifdef _WIN32 # include # include # define pipe(fds) _pipe(fds, 5000, _O_TEXT) #else # include #endif #include #include /* * Not yet supported in Windows. fork() should be replaced by * CreateProcess(). */ struct osl::search::UsiProxy::Proxy { pid_t pid; int pipe_in[2], pipe_out[2]; std::string program; FILE *in, *out; UsiProxy *current; std::atomic_bool quit; Proxy(const std::string& name) : program(name), current(nullptr), quit(false) { #ifndef _WIN32 ::pipe(pipe_in); ::pipe(pipe_out); std::cerr << "new proxy " << program << std::endl; if ( (pid = fork()) == 0 ) { // child if (dup2(pipe_out[0], 0) < 0 || dup2(pipe_in[1], 1) < 0) throw std::runtime_error("error dup2 in child"); close(pipe_in[0]); close(pipe_in[1]); close(pipe_out[0]); close(pipe_out[1]); // close(2); char buf[1024]; // broken basename requring (non-const) char * strcpy(buf, program.c_str()); if (chdir(::dirname(buf))) { std::cerr << "chdir failed " << dirname(buf) << std::endl; throw std::system_error(std::error_code(errno, std::system_category()), "chdir"); } strcpy(buf, program.c_str()); std::string base = std::string("./") + ::basename(buf); /*int err =*/ execlp( base.c_str(), base.c_str(), NULL ); throw std::system_error(std::error_code(errno, std::system_category()), "execlp"); } else { // parent close(pipe_in[1]); close(pipe_out[0]); out = fdopen(pipe_out[1], "w"); in = fdopen(pipe_in[0], "r"); setvbuf(out, NULL, _IONBF, 0); setvbuf(in, NULL, _IONBF, 0); std::thread([=](){ while (!quit) { push(this->readLineInThread()); } fclose(in); }).detach(); writeLine("usi"); while (true) { auto line = readLineMayBlock(); if (line == "usiok") break; if (line == "") throw std::runtime_error("UsiProxy usi failed"); // std::cerr << "< " << line << std::endl; } writeLine("setoption name Threads value " +std::to_string(OslConfig::concurrency())); if (OslConfig::concurrency() == 1) writeLine("setoption name Hash value " +std::to_string(OslConfig::memoryUseLimit()/1024/1024 / (std::thread::hardware_concurrency()*2))); for (auto command: initial_commands) writeLine(command); writeLine("isready"); while (true) { auto line = readLineMayBlock(); if (line == "readyok") break; if (line == "") throw std::runtime_error("UsiProxy isready failed"); std::cerr << "< " << line << std::endl; } } #endif } ~Proxy() { writeLine("quit"); quit = true; std::this_thread::sleep_for(std::chrono::seconds(1)); fclose(out); } void attach(UsiProxy *proxy) { std::lock_guard lk(mutex); if (current != nullptr) throw std::runtime_error("UsiProxy::Proxy::attach"); current = proxy; } void detach(UsiProxy *proxy) { std::lock_guard lk(mutex); if (current != proxy) throw std::runtime_error("UsiProxy::Proxy::detatch"); current = nullptr; } void writeLine(const std::string& msg) { std::cerr << "> " << msg << std::endl; fprintf(out, "%s\n", msg.c_str()); } bool messageAvailable() { std::lock_guard lk(mutex); return queue.size() > 0; } std::string readLineMayBlock() { std::unique_lock lk(mutex); condition.wait(lk, [&](){ return queue.size()>0; }); auto ans = queue.front(); queue.pop(); return *ans; } std::string readLineInTime(milliseconds msec) { std::unique_lock lk(mutex); if (! condition.wait_for(lk, msec, [&](){ return queue.size()>0; })) return ""; // timeout auto ans = queue.front(); queue.pop(); return *ans; } // private std::queue> queue; std::mutex mutex; std::condition_variable condition; std::string readLineInThread() { char buff[2048]; if (quit) return ""; if (fgets(buff, sizeof(buff), in) == NULL) { quit = true; std::cerr << "< (eof)\n"; return ""; } std::string ans = buff; boost::algorithm::trim(ans); if (ans.find("info ") != 0) std::cerr << "< " << ans << std::endl; return ans; } void push(std::string msg) { std::lock_guard lk(mutex); queue.push(std::make_shared(msg)); condition.notify_one(); } }; std::queue> osl::search::UsiProxy::proxy_pool; std::string osl::search::UsiProxy::default_program = OSL_HOME "/../gpsfish_dev/src/gpsfish"; std::vector osl::search::UsiProxy::initial_commands; std::mutex osl::search::UsiProxy::mutex; bool osl::search::UsiProxy::setUp(const std::string& program, const std::vector& commands) { if (program != "" && ! boost::filesystem::exists(program)) throw std::runtime_error("UsiProxy::setUp "+program+" not found"); std::lock_guard lk(mutex); if (program != "") default_program = program; initial_commands = commands; return boost::filesystem::exists(default_program); } osl::search::UsiProxy:: UsiProxy(const NumEffectState& s, checkmate_t& checker, SimpleHashTable *t, CountRecorder&) : root_ignore_moves(nullptr), prediction_for_speculative_search(false) { { std::lock_guard lk(mutex); if (proxy_pool.empty()) proxy_pool.push(std::make_shared(default_program)); proxy = proxy_pool.front(); proxy_pool.pop(); } proxy->attach(this); state = s; if (t->isVerbose()) addMonitor(std::shared_ptr(new CerrMonitor())); } osl::search::UsiProxy:: UsiProxy::UsiProxy(const UsiProxy& src) : SearchTimer(src), FixedEval(src), state(src.state), history(src.history), root_ignore_moves(nullptr), prediction_for_speculative_search(false) { { std::lock_guard lk(mutex); if (proxy_pool.empty()) proxy_pool.push(std::make_shared(default_program)); proxy = proxy_pool.front(); proxy_pool.pop(); } proxy->attach(this); } osl::search::UsiProxy:: ~UsiProxy() { proxy->writeLine("stop"); proxy->detach(this); { std::lock_guard lk(mutex); proxy_pool.push(proxy); } proxy.reset(); } osl::Move osl::search::UsiProxy:: computeBestMoveIteratively(int limit, int step, int initial_limit, size_t node_limit, const TimeAssigned& assign, MoveWithComment *additional_info) { this->setStartTime(clock::now()); this->setTimeAssign(assign); // mismatch: we need the initial state to utilize history std::string position; position.reserve(16+90+10+5*0); position = "position "; position += usi::show(state); position += " moves"; proxy->writeLine(position); if (root_ignore_moves && !root_ignore_moves->empty()) { std::string ignore_moves = "ignore_moves"; for (auto move:*root_ignore_moves) { ignore_moves += " " + usi::show(move); } proxy->writeLine(ignore_moves); } proxy->writeLine("go byoyomi "+std::to_string(assign.standard.count())); milliseconds msec100(100); std::string line; InterimReport report; while (true) { line = proxy->readLineInTime(msec100); if (!report.stopped && line.find("info ") == 0 && report.updateByInfo(line, -1)) { InterimReport info; info.set(state.turn(), report); std::vector pv = toCSA(info.pv.moves); for (const auto& monitor: this->monitors()) monitor->showPV(info.depth_head, info.node_count, info.elapsed, info.pv.score, pv.empty() ? Move() : *pv.begin(), &*pv.begin(), &*pv.begin()+pv.size(), nullptr, nullptr); try { throwIfNoMoreTime(info.node_count); } catch (NoMoreMemory&) { } catch (misc::NoMoreTime&) { } } if (!report.stopped && this->stopping()) { report.stopped = true; proxy->writeLine("stop"); } if (line.find("bestmove ") == 0) break; } if (additional_info) { InterimReport info; info.set(state.turn(), report); additional_info->move = info.pv.empty() ? Move() : usi::strToMove(info.pv.moves[0], state); additional_info->value = info.pv.score; additional_info->moves = toCSA(info.pv.moves); if (additional_info->moves.size() > 0) additional_info->moves.erase(additional_info->moves.begin()); additional_info->root = HashKey(state); additional_info->node_count = info.node_count; additional_info->elapsed = info.elapsed; additional_info->root_limit = info.pv.depth; } for (const auto& monitor:this->monitors()) monitor->searchFinished(); std::vector elements; boost::algorithm::split(elements, line, boost::algorithm::is_any_of(" ")); if (elements.size() < 2 || elements[0] != "bestmove") throw std::logic_error("^unkown usi bestmove "+line); Move best_move = usi::strToMove(elements[1], state); if (root_ignore_moves && root_ignore_moves->isMember(best_move)) return Move(); return best_move; } bool osl::search::UsiProxy:: isReasonableMove(Move move, int pawn_sacrifice) { return true; } void osl::search::UsiProxy:: setRootIgnoreMoves(const MoveVector *rim, bool prediction) { assert(!prediction || rim); root_ignore_moves = rim; prediction_for_speculative_search = prediction; } void osl::search::UsiProxy:: setHistory(const MoveStack& h) { history = h; } std::vector osl::search::UsiProxy::toCSA(const std::vector& pv) const { std::vector ans; NumEffectState work = state; for (auto usi_move:pv) { try { Move move = usi::strToMove(usi_move, work); ans.push_back(move); work.makeMove(move); } catch (std::exception& e) { std::cerr << "UsiProxy::toCSA " << e.what() << std::endl; break; } } return ans; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchTimer.h0000644000000000000000000001232012316770314020065 0ustar rootroot/* hasTimer.h */ #ifndef OSL_SEARCHTIMER_H #define OSL_SEARCHTIMER_H #include "osl/misc/milliSeconds.h" #include "osl/misc/lightMutex.h" #include "osl/oslConfig.h" #include #include namespace osl { namespace search { struct TimeAssigned { milliseconds standard, max; TimeAssigned() : standard(milliseconds::max()), max(milliseconds::max()) { } explicit TimeAssigned(milliseconds assign) : standard(assign), max(assign) { } TimeAssigned(milliseconds s, milliseconds m) : standard(s), max(m) { } }; class SearchMonitor; struct SearchTimerCommon { enum StopReason { NotStopped, NoMoreTime, NoMoreMemory, StopByOutside }; /** 探索開始時刻 */ time_point start_time; /** 探索予定時間 */ TimeAssigned assigned; /** 時間ãŒä½•倿®‹ã£ã¦ã„ãŸã‚‰æ¬¡ã®iteration ã«é€²ã‚€ã‹ */ volatile double next_iteration_coefficient; volatile bool stop_all; volatile StopReason stop_reason; uint64_t node_count_hard_limit; volatile int last_memory_use1000; // work area time_point last_tested; uint64_t next_node_count; double nps; volatile bool stable; std::vector > monitors; typedef LightMutex Mutex; mutable Mutex mutex; SearchTimerCommon() : start_time(clock::now()), next_iteration_coefficient(4.0), stop_all(0), stop_reason(NotStopped), node_count_hard_limit(std::numeric_limits::max()), last_memory_use1000(0), stable(true) { } }; class SearchTimer { std::shared_ptr shared_timer; typedef SearchTimerCommon::Mutex Mutex; public: SearchTimer() : shared_timer(new SearchTimerCommon) {} SearchTimer(const SearchTimer& src) : shared_timer(src.shared_timer) {} virtual ~SearchTimer(); void setTimeAssign(const TimeAssigned& a) { SCOPED_LOCK(lk,shared_timer->mutex); shared_timer->assigned = a; } void setStartTime(time_point start) { SCOPED_LOCK(lk,shared_timer->mutex); shared_timer->start_time = start; shared_timer->next_node_count = 0; shared_timer->nps = 0.0; shared_timer->last_tested = start; shared_timer->stop_all = false; } void setStable(bool new_stable) { shared_timer->stable = new_stable; } bool isStableNow() const { return shared_timer->stable; } bool hasSchedule() const { SCOPED_LOCK(lk,shared_timer->mutex); return shared_timer->assigned.standard < milliseconds::max(); } const TimeAssigned& timeAssigned() const { SCOPED_LOCK(lk,shared_timer->mutex); return shared_timer->assigned; } const time_point startTime() const { SCOPED_LOCK(lk,shared_timer->mutex); return shared_timer->start_time; } double elapsed(time_point now) const { return toSeconds(now - shared_timer->start_time); } double elapsed() const { return elapsed(clock::now()); } void setNextIterationCoefficient(double new_value) { SCOPED_LOCK(lk,shared_timer->mutex); shared_timer->next_iteration_coefficient = new_value; } void setNodeCountHardLimit(uint64_t new_value) { SCOPED_LOCK(lk,shared_timer->mutex); shared_timer->node_count_hard_limit = new_value; } double nextIterationCoefficient() const { SCOPED_LOCK(lk,shared_timer->mutex); return shared_timer->next_iteration_coefficient; } bool stopping() const { return shared_timer->stop_all; } void stopNow() { shared_timer->stop_reason = SearchTimerCommon::StopByOutside; shared_timer->stop_all = true; } SearchTimerCommon::StopReason stopReason() { return shared_timer->stop_reason; } void throwIfNoMoreTime(uint64_t node_count) { SearchTimerCommon& shared = *shared_timer; if (! shared.stop_all) { uint64_t next_node_count; { #ifdef OSL_USE_RACE_DETECTOR SCOPED_LOCK(lk,shared_timer->mutex); #endif next_node_count = shared.next_node_count; } if (next_node_count > node_count || ! hasSchedule()) return; } testAndUpdateNextTimeTest(node_count); } int nodeAffordable() const { const time_point now = clock::now(); #ifdef OSL_USE_RACE_DETECTOR SCOPED_LOCK(lk,shared_timer->mutex); #endif const double nps = shared_timer->nps; const double left = toSeconds(shared_timer->start_time + shared_timer->assigned.max - now); return std::max(0, static_cast(nps * left)); } /** メモリã¨ãƒŽãƒ¼ãƒ‰æ•°ã®é–¢ä¿‚を調整. 探索中ã¯åˆ©ç”¨ä¸å¯ï¼Ž*/ static void adjustMemoryUseLimit(double scale=0.9); void addMonitor(const std::shared_ptr&); bool hasMonitor() const { return ! shared_timer->monitors.empty(); } const std::vector >& monitors() const { return shared_timer->monitors; } int lastMemoryUseRatio1000() const { return shared_timer->last_memory_use1000; } private: void testAndUpdateNextTimeTest(uint64_t node_count); void throwStop(); }; } // namespace search } // namespace osl #endif /* OSL_SEARCHTIMER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceSearch2.cc0000644000000000000000000000211112316770314021306 0ustar rootroot/* quiescenceSearch2.cc */ #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceSearch2.tcc" #include "osl/checkmate/fixedDepthSearcher.tcc" #include "osl/eval/progressEval.h" #include "osl/eval/openMidEndingEval.h" namespace osl { #ifndef MINIMAL template class search::QuiescenceSearch2; template int search::QuiescenceSearch2::searchProbCut(int, int, eval::ProgressEval&, Move); template int search::QuiescenceSearch2::searchProbCut(int, int, eval::ProgressEval&, Move); #endif template class search::QuiescenceSearch2; template int search::QuiescenceSearch2::searchProbCut(int, int, eval::ml::OpenMidEndingEval&, Move); template int search::QuiescenceSearch2::searchProbCut(int, int, eval::ml::OpenMidEndingEval&, Move); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: /* ------------------------------------------------------------------------- */ libosl-0.8.0.orig/full/osl/search/searchState2.h0000644000000000000000000003700712316770314020160 0ustar rootroot/* searchState2.h */ #ifndef OSL_SEARCHSTATE2_H #define OSL_SEARCHSTATE2_H #include "osl/search/killerMoveTable.h" #include "osl/search/bigramKillerMove.h" #include "osl/search/historyTable.h" #include "osl/search/firstMoveThreatmate.h" #include "osl/search/simpleHashRecord.h" #include "osl/checkmate/dualDfpn.h" #include "osl/checkmate/fixedDepthSearcher.h" #include "osl/effect_util/neighboring8Direct.h" #include "osl/numEffectState.h" #include "osl/hashKey.h" #include "osl/repetitionCounter.h" #include "osl/container/moveStack.h" #include namespace osl { namespace search { /** * SimpleHashRecord* ã®stack. * 先頭è¦ç´ ã¯rootã‚’æ„味ã™ã‚‹ã€‚ */ class RecordStack2 { static const int SEARCH_DEPTH_MAX = 64; FixedCapacityVector data; public: RecordStack2(); void clear(); void push(SimpleHashRecord *r) { data.push_back(r); } void pop() { assert(size() > 1); data.pop_back(); } SimpleHashRecord* lastRecord(unsigned int n=0) const { assert(size() > n); return data[size()-1-n]; } SimpleHashRecord* rootRecord() const { assert(! empty()); return data[0]; } void setRootRecord(SimpleHashRecord *root) { data[0] = root; } void setLastRecord(SimpleHashRecord *r) { assert(size() > 0); // 1 for root data[size()-1] = r; } size_t size() const { return data.size(); } bool empty() const { return data.empty(); } bool hasLastRecord(unsigned int n=0) const { return size() > n; } void dump() const; }; class Worker; /** * 並列探索をã™ã‚‹å ´åˆã«å…±æœ‰ã•れるも㮠*/ struct SearchState2Shared : boost::noncopyable { BigramKillerMove bigram_killers; KillerMoveTable killer_moves; HistoryTable history_table; SearchState2Shared(); ~SearchState2Shared(); }; #define search_assert(x) assert(((x) || (SearchState2Core::abort()))) #define search_assert2(x, m) assert(((x) || (SearchState2Core::abort(m)))) struct AlphaBeta2ParallelCommon; /** */ class SearchState2Core #if OSL_WORDSIZE == 32 : public misc::Align16New #endif { friend struct AlphaBeta2ParallelCommon; public: enum { MaxDepth = 64 }; typedef DualDfpn checkmate_t; protected: NumEffectState current_state, root_state; checkmate_t* checkmate_searcher; #ifdef OSL_SMP public: void setCheckmateSearcher(checkmate_t *new_checkmate) { checkmate_searcher = new_checkmate; } private: #endif PathEncoding current_path; MoveStack move_history; int root_depth; protected: RecordStack2 record_stack; RepetitionCounter repetition_counter; std::shared_ptr shared; public: typedef FixedCapacityVector PVVector; protected: CArray pv; enum NodeType { PvNode = 0, AllNode = 1, CutNode = -1, }; CArray node_type; public: /** beta cut in parallel search */ volatile bool stop_tree; #ifndef MINIMAL static CArray depth_node_count_quiesce; #endif SearchState2Core(const NumEffectState& s, checkmate_t& checker); virtual ~SearchState2Core(); int curDepth() const { return history().size() - root_depth; } /** * state ã®ã‚³ãƒ”ーを行ã†. * * this->state ã¯æŽ¢ç´¢çµ‚äº†å¾Œã‚‚ä¿å­˜ã•れるãŒï¼ŒæŽ¢ç´¢ä¸­ã« exception ãŒèµ·ã“る㨠* 破壊ã•れã¦ã„ã‚‹ */ virtual void setState(const NumEffectState& s); void setHistory(const MoveStack& h); bool hasLastRecord(unsigned int n=0) const { return record_stack.hasLastRecord(n); } SimpleHashRecord* lastRecord(unsigned int n=0) { return record_stack.lastRecord(n); } const SimpleHashRecord* lastRecord(unsigned int n=0) const { return record_stack.lastRecord(n); } SimpleHashRecord *rootRecord() { return record_stack.rootRecord(); } void setCurrentRecord(SimpleHashRecord *r) { search_assert((int)record_stack.size() == curDepth()+1); record_stack.setLastRecord(r); } void setRootRecord(SimpleHashRecord *root) { search_assert(record_stack.size() == 1); search_assert(curDepth() == 0); record_stack.setRootRecord(root); } // killer move void setKillerMove(Move best_move) { if (best_move.isPass()) return; shared->killer_moves.setMove(curDepth(), best_move); const Move last_move = lastMove(); if (! last_move.isInvalid()) { search_assert(best_move.player() != last_move.player()); shared->bigram_killers.setMove(last_move, best_move); } } void getBigramKillerMoves(MoveVector& moves) const { shared->bigram_killers.getMove(state(), lastMove(), moves); #ifdef TRI_PLY_BIGRAM_KILLERS if (move_history.hasLastMove(3)) shared->bigram_killers.getMove(state(), lastMove(3), moves); #endif } void getKillerMoves(MoveVector& moves) const { getBigramKillerMoves(moves); shared->killer_moves.getMove(state(), curDepth(), moves); } const BigramKillerMove& bigramKillerMove() const { return shared->bigram_killers; } void setBigramKillerMove(const BigramKillerMove& killers); HistoryTable& historyTable() { return shared->history_table; } const HistoryTable& historyTable() const { return shared->history_table; } // doUndo void pushPass() { const Move pass = Move::PASS(current_state.turn()); current_state.changeTurn(); current_path.pushMove(pass); move_history.push(pass); } void popPass() { const Move pass = Move::PASS(alt(current_state.turn())); current_state.changeTurn(); current_path.popMove(pass); move_history.pop(); } private: /** * ApplyMoveã®å‰ã«è¡Œã†ã“㨠*/ void pushBeforeApply(Move move) { move_history.push(move); record_stack.push(0); assert(curDepth() > 0); node_type[curDepth()] = static_cast(-node_type[curDepth()-1]); } struct Updator { const HashKey& new_hash; SearchState2Core *state; Updator(const HashKey& h, SearchState2Core *s) : new_hash(h), state(s) { } void update() { state->updateRepetitionCounterAfterMove(new_hash); } }; template struct UpdateWrapper : public Updator { Function& function; UpdateWrapper(const HashKey& h, SearchState2Core *s, Function& f) : Updator(h, s), function(f) { } void operator()(Square to) { update(); function(to); } }; friend struct Updator; /** * pushBeforeApply ã®å¾Œï¼ŒApplyMoveã®ä¸­ï¼ŒFunctionを呼ã¶å‰ã«å‘¼ã°ã‚Œã‚‹ */ void updateRepetitionCounterAfterMove(const HashKey& new_hash) { repetition_counter.push(new_hash, current_state); } /** * ApplyMoveã®å¾Œã«è¡Œã†ã“㨠*/ void popAfterApply() { record_stack.pop(); repetition_counter.pop(); move_history.pop(); } #ifndef NDEBUG void makeMoveHook(Move); #endif public: /** * ã¾ã¨ã‚‚ãªdoUndo */ template void doUndoMoveOrPass(const HashKey& new_hash, Move move, Function& f) { pushBeforeApply(move); UpdateWrapper wrapper(new_hash, this, f); current_path.pushMove(move); current_state.makeUnmakeMove(Player2Type

(), move, wrapper); current_path.popMove(move); popAfterApply(); } void makeMove(Move move) // for debug { HashKey new_hash = currentHash().newHashWithMove(move); pushBeforeApply(move); current_state.makeMove(move); updateRepetitionCounterAfterMove(new_hash); } const Move lastMove(int i=1) const { return move_history.lastMove(i); } const MoveStack& history() const { return move_history; } const RecordStack2& recordHistory() const { return record_stack; } const PathEncoding& path() const { return current_path; } const NumEffectState& state() const { return current_state; } const NumEffectState& rootState() const { return root_state; } void restoreRootState(); const checkmate_t& checkmateSearcher() const { return *checkmate_searcher; } const RepetitionCounter& repetitionCounter() const { return repetition_counter; } const HashKey& currentHash() const { return repetition_counter.history().top(); } /** * 軽é‡åŒ–版 doUndo åƒæ—¥æ‰‹æƒ…報や, hash ã‚’æ›´æ–°ã—ãªã„ */ template void doUndoMoveLight(Move move, Function& f) { current_path.pushMove(move); current_state.makeUnmakeMove(Player2Type

(), move, f); current_path.popMove(move); } template bool isLosingState(int node_limit) { search_assert(P == path().turn()); const bool lose = checkmate_searcher->isLosingState

(node_limit, current_state, currentHash(), path(), lastMove()); return lose; } public: template static bool isWinningState(checkmate_t& search, NumEffectState& state, const HashKey& key, PathEncoding path, int node_limit, Move& checkmate_move, Move last_move, bool #ifdef OSL_DFPN_SMP_SEARCH parallel #endif =false ) { assert(P == path.turn()); #ifdef OSL_DFPN_SMP_SEARCH if (parallel) return search.isWinningStateParallel

(node_limit, state, key, path, checkmate_move, last_move); #endif const bool win = search.isWinningState

(node_limit, state, key, path, checkmate_move, last_move); return win; } static bool isWinningState(checkmate_t& search, NumEffectState& state, const HashKey& key, PathEncoding path, int node_limit, Move& checkmate_move, Move last_move, bool parallel=false) { if (state.turn() == BLACK) return isWinningState (search, state, key, path, node_limit, checkmate_move, last_move, parallel); else return isWinningState (search, state, key, path, node_limit, checkmate_move, last_move, parallel); } template bool isWinningState(int node_limit, Move& checkmate_move, bool parallel=false) { search_assert(P == path().turn()); return isWinningState

(*checkmate_searcher, current_state, currentHash(), path(), node_limit, checkmate_move, lastMove(), parallel); } /** FixedDepthSearcher を呼㶠*/ template bool isWinningStateShort(int depth, Move& checkmate_move) { checkmate::FixedDepthSearcher searcher(current_state); const ProofDisproof pdp=searcher.hasCheckmateMove

(depth, checkmate_move); return pdp.isCheckmateSuccess(); } /** * P ã®æ‰‹ç•ªã§Pã®çމã«è©°ã‚ã‚ãŒã‹ã‹ã£ã¦ã„ã‚‹ã‹ã©ã†ã‹ */ template bool isThreatmateState(int node_limit, Move& threatmate_move, bool #ifdef OSL_DFPN_SMP_SEARCH parallel #endif =false) { search_assert(P == path().turn()); current_state.changeTurn(); HashKey threatmate_hash = currentHash(); threatmate_hash.changeTurn(); const PathEncoding threatmate_path(current_state.turn()); const Player Opponent = alt(P); bool threatmate; #ifdef OSL_DFPN_SMP_SEARCH if (parallel) threatmate = checkmate_searcher->template isWinningStateParallel (node_limit, current_state, threatmate_hash, threatmate_path, threatmate_move, Move::PASS(P)); else #endif threatmate = checkmate_searcher->template isWinningState (node_limit, current_state, threatmate_hash, threatmate_path, threatmate_move, Move::PASS(P)); current_state.changeTurn(); return threatmate; } template bool isThreatmateStateShort(int depth, Move& threatmate_move) { search_assert(P == path().turn()); current_state.changeTurn(); const Player Opponent = alt(P); checkmate::FixedDepthSearcher searcher(current_state); const ProofDisproof pdp = searcher.hasCheckmateMove(depth, threatmate_move); current_state.changeTurn(); return pdp.isCheckmateSuccess(); } bool abort() const; virtual bool abort(Move) const; bool tryThreatmate() const { const Move last_move = lastMove(); if (! last_move.isNormal()) return false; const Square king = state().kingSquare(state().turn()); if (curDepth() == 1) return FirstMoveThreatmate::isMember(last_move, king); return Neighboring8Direct::hasEffect (state(), last_move.ptypeO(), last_move.to(), king); } void makePV(Move m) { const int depth = curDepth(); makePV(pv[depth], m, pv[depth+1]); } void initPV() { const int depth = curDepth(); pv[depth].clear(); } void makePV(PVVector& parent, Move m, PVVector& pv) const; /** turn ã®å´ãŒé€£ç¶šçŽ‹æ‰‹ã§è©°ã‚を逃れã¦ã„る回数 */ int #ifdef __GNUC__ __attribute__ ((pure)) #endif countCheckAfterThreatmate(Player turn, int depth=1) const { assert(((depth % 2) && state().turn() == turn) || ((depth % 2) == 0 && state().turn() != turn)); int result = 0; for (int i=depth;; i+=2) { if (! hasLastRecord(i) || ! lastRecord(i)) break; if (lastRecord(i)->qrecord.threatmate.status(turn).status() != ThreatmateState::CHECK_AFTER_THREATMATE) break; ++result; } return result; } int countCheckAfterThreatmateSacrifice(Player turn, int depth=1) const { assert(((depth % 2) && state().turn() == turn) || ((depth % 2) == 0 && state().turn() != turn)); assert(depth > 0); int result = 0; for (int i=depth;; i+=2) { if (! hasLastRecord(i) || ! lastRecord(i)) break; if (lastRecord(i)->qrecord.threatmate.status(turn).status() != ThreatmateState::CHECK_AFTER_THREATMATE) break; if (lastMove(i-1).isCapture()) ++result; } return result; } }; #undef search_assert #undef search_assert2 #define search_assert(x) assert((x) || SearchState2Core::abort()) #define search_assert2(x, m) assert((x) || SearchState2Core::abort(m)) /** * SearchFramework ã®ã†ã¡ï¼Œtemplate parameter ã‚’å«ã¾ãªã„部分. */ class SearchState2 : public SearchState2Core { public: /** å†æŽ¢ç´¢ã‚„ï¼ŒæŒ‡æ‰‹ç”Ÿæˆã§ã‚ˆã‚Šç¢ºçއã®é«˜ã„手ãŒã‚ã£ãŸã¨ãã«ç„¡è¦–ã™ã‚‹ç¯„囲 */ static const int ReSearchLimitMargin = 80; protected: int root_limit; int cur_limit; public: SearchState2(const NumEffectState& s, checkmate_t& checker); virtual ~SearchState2(); void setState(const NumEffectState& s); void setKillerMove(Move best_move) { if (best_move.isPass()) return; SearchState2Core::setKillerMove(best_move); } int curLimit() const { return cur_limit; } bool abort(Move) const; protected: /** * root ã§ limitã‚’é–¾å€¤ã«æŽ¢ç´¢ã‚’å§‹ã‚ã‚‹ã“ã¨ã‚’設定 */ void setRoot(int limit) { root_limit = limit; cur_limit = limit; } void addLimit(int limit) { cur_limit += limit; search_assert(cur_limit >= 0); } void subLimit(int limit) { cur_limit -= limit; search_assert(cur_limit >= 0); } /** çŽ‹æ‰‹ã®æ¨ã¦é§’ã®é€£ç¶šã‚’2ループã¾ã§æ•°ãˆã‚‹ * @param history_max ã“れ以上を逆上らãªã„ */ int countSacrificeCheck2(int history_max) const; /** debug 用途 */ void checkPointSearchAllMoves(); }; } // namespace search } // namespace osl #undef search_assert #undef search_assert2 #endif /* OSL_SEARCHSTATE2_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta2Parallel.h0000644000000000000000000000764312316770314021253 0ustar rootroot/* alphaBeta2Parallel.h */ #ifndef _ALPHABETA2PARALLEL_H #define _ALPHABETA2PARALLEL_H #ifdef OSL_SMP #include "osl/search/alphaBeta2.h" #include "osl/misc/atomicCounter.h" #include #include #include #include #include #define SPLIT_STAT // #define OSL_SMP_NO_SPLIT_ROOT namespace osl { namespace search { // block_id: -1 illegal, 0 not used (master tree), 1- parallel search struct AlphaBeta2ParallelCommon : boost::noncopyable { struct TreeInfoCommon { int thread_id; volatile int nprocs; MoveLogProb best_move; AlphaBeta2Window window; int value; size_t nodes_searched; bool is_root, in_pv; Player turn; }; struct TreeInfo : public TreeInfoCommon { CArray siblings; volatile int parent; MoveLogProbVector moves; volatile int move_index, search_value; int alpha_update, last_alpha_update; volatile bool used; LightMutex lock; TreeInfo() : used(0) { siblings.fill(0); } void set(const TreeInfo& parent, int max_threads) { TreeInfoCommon::operator=(parent); used = true; for (int i=0; i job; CArray checkmate; CArray info; /** job the thread waiting for, maybe obsolete */ CArray waiting; CArray threads; std::mutex lock_smp; std::condition_variable condition_smp; volatile int smp_idle; volatile bool quit; unsigned int parallel_splits; unsigned int max_split_depth, descendant_reject, descendant_test; std::mutex living_threads_lock; std::condition_variable living_threads_condition; volatile int living_threads; int max_threads, max_thread_group; int split_min_limit; int my_id; AtomicCounter parallel_abort; AtomicCounter cancelled_splits; bool started; AlphaBeta2ParallelCommon(); ~AlphaBeta2ParallelCommon(); static checkmate_t*& checkmateSearcher(SearchState2& state) { return state.checkmate_searcher; } void waitAll(); bool isDescendant(int elder, int younger); struct SplitFailed {}; }; template struct AlphaBeta2Parallel : public AlphaBeta2ParallelCommon { struct Worker { AlphaBeta2Parallel *shared; int thread_id; Worker(int tid, AlphaBeta2Parallel *shared); void operator()(); }; typedef AlphaBeta2Tree tree_t; CArray tree; tree_t *master; explicit AlphaBeta2Parallel(tree_t *master); ~AlphaBeta2Parallel(); void threadStart(); void testStop(); void search(int tree_id); void threadWait(int thread_id, int waiting); /** @return true if search finished after successful split, false if split failed */ bool split(tree_t *tree, int tree_id, int thread_id, int max_split); void stopThread(int tree_id); void copyToParent(int parent, int child); /** @return 0 failed, block_id otherwise */ int copyToChild(int parent, int thread_id); int treeId(tree_t *tree); int parentID(int tree_id) { return info[tree_id].parent; } TreeInfo* parent(int tree_id) { return &info[parentID(tree_id)]; } const std::pair nextMove(int tree_id); size_t checkmateCount() const; size_t mainCheckmateCount() const; }; } } #endif /* OSL_SMP */ #endif /* _ALPHABETA2PARALLEL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/sortCaptureMoves.h0000644000000000000000000000140012316770314021141 0ustar rootroot/* sortCaptureMoves.h */ #ifndef SEARCH_SORTCAPTUREMOVES_H #define SEARCH_SORTCAPTUREMOVES_H #include "osl/numEffectState.h" namespace osl { namespace search { /** * 安ã„é§’ã®é †ã«sort ã™ã‚‹. */ struct SortCaptureMoves { /** å–り返ã—を考慮ã™ã‚‹ï¼Ž*/ static void sortByTakeBack(const NumEffectState& state, MoveVector& moves); /** å–ã‚‹é§’ã¯è€ƒãˆãªã„.*/ static void sortByMovingPiece(MoveVector& moves); /** å–ã‚‹é§’ã¯è€ƒãˆãªã„.from ãŒä¸€è‡´ã™ã‚‹æŒ‡æ‰‹å„ªå…ˆ */ static void sortBySpecifiedPiece(MoveVector& moves, Square from); }; } } #endif /* SEARCH_SORTCAPTUREMOVES_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/dominanceCheck.h0000644000000000000000000000256512316770314020524 0ustar rootroot/* dominanceCheck.h */ #ifndef SEARCH_DOMINANCECHECK_H #define SEARCH_DOMINANCECHECK_H #include "osl/hash/hashKeyStack.h" namespace osl { namespace search { struct DominanceCheck { enum Result { NORMAL=0, WIN, LOSE }; /** * é§’æã™ã‚‹ãƒ«ãƒ¼ãƒ—ã®æ¤œå‡º. * @return true ãªã‚‰ç›´å‰ã®æŒ‡æ‰‹ã¯æŒ‡ã—ã¦ã¯ã„ã‘ãªã„ * @param history 今ã¾ã§ã®å±€é¢ * @param next_state 次ã®å±€é¢ */ static Result detect(const HashKeyStack& history, const HashKey& next_state) { const Player player = alt(next_state.turn()); const PieceStand new_stand = next_state.blackStand(); for (size_t i=3; i void osl::search::SortCaptureMoves::sortByMovingPiece(MoveVector& moves) { std::sort(moves.begin(), moves.end(), move_order::CheapPtype()); } namespace osl { namespace search { struct OrderSpecifiedPiece { Square from; explicit OrderSpecifiedPiece(Square f) : from(f) { } bool operator()(Move l, Move r) const { const Square from_l = l.from(); if (from_l == from) return true; const Square from_r = r.from(); if (from_r == from) return false; return move_order::CheapPtype()(l, r); } }; } // anonymous namespace } // namespace osl void osl::search::SortCaptureMoves:: sortBySpecifiedPiece(MoveVector& moves, Square from) { std::sort(moves.begin(), moves.end(), OrderSpecifiedPiece(from)); } void osl::search::SortCaptureMoves:: sortByTakeBack(const NumEffectState& state, MoveVector& moves) { std::sort(moves.begin(), moves.end(), move_order::CaptureEstimation(state)); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/quiescenceLog.cc0000644000000000000000000000272712316770314020555 0ustar rootroot/* quiescenceLog.cc */ #include "osl/search/quiescenceLog.h" #include "osl/search/quiescenceRecord.h" #include #include namespace { std::unique_ptr os; } // anonymous namespace std::ostream* osl::search::QuiescenceLog:: os() { return ::os.get(); } void osl::search::QuiescenceLog:: init(const char *filename) { ::os.reset(new std::ofstream(filename)); } void osl::search::QuiescenceLog:: close() { ::os.reset(); } void osl::search::QuiescenceLog:: enter(const SimpleState& state) { if (os()) { *os() << '*' << "new node\n"; *os() << state; } } void osl::search::QuiescenceLog:: pushMove(int depth, Move move, const QuiescenceRecord *record) { if (os()) { *os() << std::string(2+std::max(0,QSearchTraits::MaxDepth-depth), '*') << move << "\n" << std::flush; if (record) record->dump(*os()); } } void osl::search::QuiescenceLog:: staticValue(int depth, int value) { if (os()) *os() << std::string(2+std::max(0,QSearchTraits::MaxDepth-depth), '*') <<" static " << value << "\n" << std::flush; } void osl::search::QuiescenceLog:: node(int depth, int alpha, int beta, int result) { if (os()) *os() << std::string(1+std::max(0,QSearchTraits::MaxDepth-depth), '*') << alpha << " " << beta << " => " << result << "\n" << std::flush; }; /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/passCounter.h0000644000000000000000000000124412316770314020130 0ustar rootroot/* passCounter.h */ #ifndef SEARCH_PASSCOUNTER_H #define SEARCH_PASSCOUNTER_H namespace osl { namespace search { class PassCounter { CArray counter; public: PassCounter() { counter.fill(0); } void inc(Player moving) { assert(playerToIndex(moving) >= 0); ++counter[moving]; } void dec(Player moving) { --counter[moving]; assert(playerToIndex(moving) >= 0); } bool loopByBothPass() const { return counter[0] && counter[1]; } }; } // namespace search } // namespace osl #endif /* __H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta3.cc0000644000000000000000000007766412316770314017747 0ustar rootroot/* alphaBeta3.cc */ #include "osl/search/alphaBeta3.h" #include "osl/search/searchRecorder.h" #include "osl/search/bigramKillerMove.h" #include "osl/search/killerMoveTable.h" #include "osl/search/simpleHashTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/move_classifier/shouldPromoteCut.h" #include "osl/search/moveWithComment.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/eval/see.h" #include "osl/rating/featureSet.h" #include "osl/rating/ratingEnv.h" #include "osl/move_generator/capture_.h" #include "osl/move_generator/escape_.h" #include "osl/move_generator/promote_.h" #include "osl/move_generator/allMoves.h" #include "osl/move_classifier/directCheck.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_order/captureEstimation.h" #include "osl/move_order/captureSort.h" #include "osl/move_order/cheapPtype.h" #include "osl/csa.h" #include "osl/stat/average.h" #include "osl/stat/histogram.h" #include "osl/repetitionCounter.h" #include #include #include #include #include const int extended_futility_margin = 256*16, futility_margin = 128*16, table_record_limit = 400; const int lmr_fullwidth = 4, lmr_reduce_limit = 200; const bool best_move_extension_enabled = false; const bool futility_pruning_enabled = true; const bool extended_futility_pruning_enabled = true; const bool cut_drop_move_in_frontier_node = true; const bool lmr_enabled = true, lmr_verify_enabled = true; const bool immediate_checkmate_enabled = true; const bool decorate_csa_in_pv = false, show_height_in_pv = false; /* ------------------------------------------------------------------------- */ namespace osl { namespace search { inline Ptype promoteIf(Ptype ptype) { return canPromote(ptype) ? promote(ptype) : ptype; } struct CompactRecord { Move best_move; int value, limit; enum ValueType { Exact, UpperBound, LowerBound }; ValueType type; CompactRecord() : limit(-1000000) { } template bool highFail(int height, int threshold) const { return height <= limit && EvalTraits

::betterThan(value, threshold) && (type == Exact || type == LowerBound); } template bool lowFail(int height, int threshold) const { return height <= limit && EvalTraits

::betterThan(threshold, value) && (type == Exact || type == UpperBound); } }; struct CompactHashTable // todo: open hash { typedef std::unordered_map> table_t; table_t table; mutable int probe_success, probe_fail; CompactHashTable() : probe_success(0), probe_fail(0) { } ~CompactHashTable() { } const CompactRecord probe(const HashKey& key) const { table_t::const_iterator p = table.find(key); if (p != table.end()) { ++probe_success; return p->second; } ++probe_fail; return CompactRecord(); } void store(const HashKey& key, const CompactRecord& value) { table[key] = value; } void clear() { table.clear(); probe_success = probe_fail = 0; } }; } } /* ------------------------------------------------------------------------- */ // TODO: make shared? object namespace { boost::scoped_array tree; osl::search::CompactHashTable table; osl::stat::Average mpn, mpn_cut, last_alpha_update; osl::stat::Histogram alpha_update_type(1,8); osl::search::BigramKillerMove bigram_killers; osl::search::KillerMoveTable killer_moves; int eval_count; int max_node_depth, total_node_count, depth_node_count[osl::search::AlphaBeta3::MaxDepth]; void init_node_count() { max_node_depth = total_node_count = 0; std::fill(depth_node_count, depth_node_count+sizeof(depth_node_count)/sizeof(int), 0); } inline void add_node_count(int depth) { max_node_depth = std::max(max_node_depth, depth); ++depth_node_count[depth]; ++total_node_count; } osl::Player root_player; osl::RepetitionCounter repetition_counter; } /* ------------------------------------------------------------------------- */ osl::search::AlphaBeta3:: AlphaBeta3(const NumEffectState& s, checkmate_t& /*checker*/, SimpleHashTable *t, CountRecorder& r) : state(s), depth(0), recorder(r), table_common(t) { if (! tree) { rating::StandardFeatureSet::instance(); tree.reset(new SearchInfo[MaxDepth]); } } osl::search::AlphaBeta3:: ~AlphaBeta3() { } int osl::search::AlphaBeta3:: evalValue() const { ++eval_count; if ((eval_count % (1<<18) == 0) || stop_by_alarm) if (toSeconds(this->timeAssigned().standard) - this->elapsed() < 0.3 || stop_by_alarm) throw misc::NoMoreTime(); return tree[depth].eval.value(); } osl::Move osl::search::AlphaBeta3:: computeBestMoveIteratively(int limit, int /*step*/, int initial_limit, size_t /*node_limit*/, const TimeAssigned& assign, MoveWithComment */*additional_info*/) { this->setStartTime(clock::now()); this->setTimeAssign(assign); mpn.clear(); mpn_cut.clear(); last_alpha_update.clear(); bigram_killers.clear(); table.clear(); eval_count = 0; init_node_count(); initial_limit = std::min(initial_limit, limit); // todo: iteration Move best_move; double consumed = 0; try { for (int i=0; i<=limit; i+=100) { double new_consumed = this->elapsed(), diff = new_consumed - consumed; consumed = new_consumed; if (table_common->verboseLevel() > 1) std::cerr << i << " sec " << diff << " " << new_consumed << " mpn " << mpn.average() << " " << mpn_cut.average() << " " << last_alpha_update.average() << "\n"; best_move = searchRoot(i); if (hasSchedule()) { const double current_time_left = toSeconds(this->timeAssigned().standard)-this->elapsed(); const double coef = nextIterationCoefficient(); if (current_time_left < new_consumed * coef) { if (table_common->verboseLevel() > 1) std::cerr << "expected timeover\n"; break; } } } } catch (misc::NoMoreTime&) { if (table_common->verboseLevel() > 1) std::cerr << "timeover\n"; } catch (NoMoreMemory&) { if (table_common->verboseLevel() > 1) std::cerr << "memory full\n"; } double new_consumed = this->elapsed(), diff = new_consumed - consumed; consumed = new_consumed; if (table_common->verboseLevel() > 1) { std::cerr << "finish" << " sec " << diff << " " << new_consumed << " mpn " << mpn.average() << " " << mpn_cut.average() << " " << last_alpha_update.average() << "\n"; std::cerr << "table " << table.table.size() << " " << table.probe_success << " " << table.probe_fail << "\n"; recorder.finishSearch(best_move, consumed, table_common->verboseLevel() > 1); // alpha_update_type.show(std::cerr); for (int i=0; i<=max_node_depth/4; ++i) { for (int j=0; j<4; ++j) { const int id = i + (max_node_depth/4)*j; fprintf(stderr, " depth %2d %5.2f%%", id, 100.0*depth_node_count[id] / (double)total_node_count); } fprintf(stderr, "\n"); } } return best_move; } bool osl::search::AlphaBeta3:: isReasonableMove(Move /*move*/, int /*pawn_sacrifice*/) { return true; } void osl::search::AlphaBeta3:: setRootIgnoreMoves(const MoveVector * /*rim*/, bool) { } void osl::search::AlphaBeta3:: setHistory(const MoveStack& /*h*/) { } void osl::search::AlphaBeta3:: showNodeDepth(std::ostream&) { } void osl::search::AlphaBeta3:: clearNodeDepth() { } /* ------------------------------------------------------------------------- */ osl::Move osl::search::AlphaBeta3:: searchRoot(int limit) { depth = 0; SearchInfo& root = tree[0]; root.moved = Move::PASS(alt(state.turn())); root.hash_key = HashKey(state); root.height = limit; root.path = PathEncoding(state.turn(), 0); root.eval = eval_t(state); root.moves.clear(); recorder.resetNodeCount(); root_player = state.turn(); repetition_counter.clear(); repetition_counter.push(root.hash_key, state); #if 1 RatedMoveVector moves; { const rating::StandardFeatureSet& features = rating::StandardFeatureSet::instance(); RatingEnv env; env.make(state); features.generateRating(state, env, 2000, moves); for (const RatedMove& move: moves) root.moves.push_back(move.move()); } #else state.generateLegal(root.moves); #endif Move best_move; const Player turn = state.turn(); int best_value = minusInfty(turn); root.alpha = best_value + eval::delta(turn); root.beta = -minusInfty(turn) - eval::delta(turn); root.node_type = PvNode; CompactRecord record = table.probe(root.hash_key); if (record.best_move.isNormal()) { MoveVector::iterator p =std::find(root.moves.begin(), root.moves.end(), record.best_move); if (p != root.moves.end()) std::swap(*root.moves.begin(), *p); } for (Move move: root.moves) { if (best_move.isNormal()) root.node_type = AllNode; assert(!ShouldPromoteCut::canIgnoreAndNotDrop(move)); if (best_move.isNormal()) continue; const int value = (turn == BLACK) ? makeMoveAndSearch(move, 100) : makeMoveAndSearch(move, 100); if (eval::betterThan(turn, value, best_value)) { root.pv.setPV(move, root, tree[depth+1].pv); if (limit && table_common->verboseLevel()) { std::cerr << " " << csa::show(move) << " " << std::setw(6) << value << " " << std::setw(3) << root.pv.size() << " "; for (size_t i=1; iallocate(root.hash_key, limit); if (record) record->setLowerBound(turn, limit, MoveLogProb(best_move,100), best_value); } } record.best_move = best_move; record.value = best_value; record.type = CompactRecord::Exact; record.limit = root.height; table.store(root.hash_key, record); return best_move; } template struct osl::search::AlphaBeta3::CallSearch { AlphaBeta3 *search; explicit CallSearch(AlphaBeta3 *s) : search(s) {} void operator()(Square) const { search->template presearch

(); } }; template struct osl::search::AlphaBeta3::CallQuiesce { AlphaBeta3 *search; explicit CallQuiesce(AlphaBeta3 *s) : search(s) {} void operator()(Square) const { search->template quiesce(); } }; template int osl::search::AlphaBeta3:: makeMoveAndSearch(Move move, int consume) { ++depth; SearchInfo &node = tree[depth], &parent = tree[depth-1]; node.moved = move; node.hash_key = tree[depth-1].hash_key.newHashWithMove(move); node.path = parent.path; node.height = parent.height - consume; node.alpha = parent.beta; node.beta = parent.alpha; node.node_type = (NodeType)-(parent.node_type); node.eval = parent.eval; node.pv.clear(); node.extended = 0; // åƒæ—¥æ‰‹ç¢ºèª if (0) { const Sennichite next_sennichite = repetition_counter.isAlmostSennichite(node.hash_key); if (node.moved.isNormal() && next_sennichite.isDraw()) return this->drawValue(); if (next_sennichite.hasWinner()) return this->winByFoul(next_sennichite.winner()); } // repetition_counter.push(node.hash_key, state); CallSearch

f(this); node.path.pushMove(move); state.makeUnmakeMove(Player2Type

(), move, f); node.path.popMove(move); // repetition_counter.pop(); --depth; return tree[depth+1].search_value; } inline bool osl::search::AlphaBeta3:: reductionOk() const { const SearchInfo& node = tree[depth]; const Move m = node.moved; if (m.isCaptureOrPromotion()) return false; if (node.in_check || (depth > 0 && tree[depth-1].in_check)) return false; return true; } template void osl::search::AlphaBeta3:: presearch() { SearchInfo& node = tree[depth]; assert(state.turn() == alt(P)); const Player turn = alt(P); if (state.hasEffectAt(turn, state.kingSquare(alt(turn)))) { node.search_value = winByFoul(turn); return; } node.in_check = state.hasEffectAt(alt(turn), state.kingSquare(turn)); node.eval.update(state, node.moved); // heuristic extension #if 0 if (depth > 1 && tree[depth-1].in_check && tree[depth-1].moves.size() == 1) { // one reply const int ext = 50; node.extended += ext; node.height += ext; } #endif if (node.in_check) { const int ext = (node.alpha != node.beta || (depth > 2 && tree[depth-1].moved.ptype() == KING)) ? 100 : 100; node.extended += ext; node.height += ext; } else if (depth > 1 && node.moved.to() == tree[depth-1].moved.to() && ! node.moved.isPass()) { const int ext = (node.alpha != node.beta || tree[depth-1].moved.isCapture()) ? 50 : 25; node.extended += ext; node.height += ext; } // null move pruning if (node.moved.isPass()) { // need verify? const int ext = (node.height >= 500) ? -200 : -100; node.height += ext; node.extended = ext; } // null window search const int org_alpha = node.alpha, org_height = node.height; const NodeType org_node_type = node.node_type; const bool pv_in_pvs = node.node_type == CutNode && node.alpha != node.beta; int lmr_reduce = 0; if (pv_in_pvs) node.alpha = node.beta; if (node.alpha == node.beta) { if (lmr_enabled && ! node.extended && reductionOk() && (!pv_in_pvs || node.height >= lmr_reduce_limit+100) && depth > 0) { if (pv_in_pvs) lmr_reduce = tree[depth-1].moves_tried / lmr_fullwidth * 50; else lmr_reduce = tree[depth-1].moves_tried / lmr_fullwidth * 75; lmr_reduce = std::min(400, lmr_reduce); node.height -= lmr_reduce; if (pv_in_pvs && node.height < lmr_reduce_limit) node.height = lmr_reduce_limit; } search(); if (EvalTraits

::betterThan(node.beta, node.search_value)) // note: beta cut for opponent return; node.height = org_height; node.alpha = org_alpha; node.node_type = org_node_type; // verification search not in pv if (! pv_in_pvs) { if (lmr_verify_enabled && lmr_reduce) { node.height -= lmr_reduce/2; if (lmr_reduce >= 100 || node.height >= 400) search(); } return; } node.node_type = PvNode; } // now node is pv assert(node.node_type == PvNode); if (node.height >= table_record_limit) { CompactRecord record = table.probe(node.hash_key); // iid if hash-move is not available if (! record.best_move.isNormal()) { const int height = node.height; for (int i=200; i+100(); node.alpha = org_alpha; node.node_type = PvNode; } node.height = height; } } // main search const bool best_move_extension_candidate = best_move_extension_enabled && root_player == P && node.height >= 150 && node.extended < 50; const bool skip_main_search = best_move_extension_candidate && pv_in_pvs; if (! skip_main_search) search(); // best move ext --- ? if (best_move_extension_candidate && EvalTraits

::betterThan(node.search_value, node.beta)) // alpha value update for P { node.node_type = PvNode; node.alpha = org_alpha; const int ext = 50; node.height += ext; node.extended += ext; search(); } } template void osl::search::AlphaBeta3:: search() { using namespace move_classifier; add_node_count(depth); SearchInfo& node = tree[depth]; assert(state.turn() == P); recorder.addNodeCount(); if (node.height < 0) { quiesceRoot

(); return; } CompactRecord record = node.height >= table_record_limit ? table.probe(node.hash_key) : CompactRecord(); if (node.alpha == node.beta) { if (record.highFail

(node.height, node.beta)) { node.search_value = record.value; return; } if (record.lowFail

(node.height, node.alpha)) { node.search_value = record.value; return; } } const bool frontier_node = futility_pruning_enabled && node.height < 100; const bool extended_frontier_node = (! frontier_node) && extended_futility_pruning_enabled && node.height < 200; const bool in_pv = node.alpha != node.beta; node.move_type = Initial; node.moves_tried = 0; const int initial_value = minusInfty(P)+depth*EvalTraits

::delta*2; int best_value = initial_value, last_alpha_update=0; if (EvalTraits

::betterThan(best_value, node.alpha)) { node.alpha = best_value + EvalTraits

::delta; if (EvalTraits

::betterThan(best_value, node.beta)) { node.search_value = best_value; return; } } const int initial_alpha = node.alpha; if (record.best_move.isNormal()) { const Move move = record.best_move; int value = makeMoveAndSearch

(move, 100); if (EvalTraits

::betterThan(value, best_value)) { best_value = value; if (EvalTraits

::betterThan(value, node.alpha)) { if (in_pv) node.pv.setPV(move, node, tree[depth+1].pv); node.alpha = value + EvalTraits

::delta; last_alpha_update = node.moves_tried+1; alpha_update_type.add(node.move_type); if (EvalTraits

::betterThan(value, node.beta)) { mpn_cut.add(node.moves_tried+1); goto done; } } } node.moves_tried++; } if (immediate_checkmate_enabled && ! node.in_check && (frontier_node || extended_futility_pruning_enabled) && ImmediateCheckmate::hasCheckmateMove

(state)) { node.search_value = winByCheckmate(P); return; } for (Move move=nextMove

(); !move.isInvalid(); move=nextMove

(), node.moves_tried++) { if (node.moves_tried == 1) node.node_type = AllNode; if (move == record.best_move) continue; if (! node.in_check && node.node_type != PvNode) { if (frontier_node && node.move_type > Pass) { const int futility = evalValue() + (move.capturePtype() ? eval_t::captureValue(move.capturePtypeO()) : 0) + futility_margin*EvalTraits

::delta; if (EvalTraits

::betterThan(best_value, futility) && (!tree[depth-1].in_check || !PlayerMoveAdaptor::isMember(state,move))) continue; } else if (extended_frontier_node && node.move_type > Killer) { const int futility_base = evalValue()+ extended_futility_margin*EvalTraits

::delta; if ((move.capturePtype() && EvalTraits

::betterThan(best_value, futility_base+node.eval.captureValue(move.capturePtypeO()))) || EvalTraits

::betterThan(best_value, futility_base+See::see(state, move))) if (!tree[depth-1].in_check || !PlayerMoveAdaptor::isMember(state,move)) continue; } } int value = makeMoveAndSearch

(move, 100); if (EvalTraits

::betterThan(value, best_value)) { best_value = value; record.best_move = move; if (EvalTraits

::betterThan(value, node.alpha)) { if (in_pv) node.pv.setPV(move, node, tree[depth+1].pv); node.alpha = value + EvalTraits

::delta; last_alpha_update = node.moves_tried+1; alpha_update_type.add(node.move_type); if (EvalTraits

::betterThan(value, node.beta)) { mpn_cut.add(node.moves_tried+1); goto done; } } } } mpn.add(node.moves_tried); if (last_alpha_update) ::last_alpha_update.add(last_alpha_update); done: if (last_alpha_update && node.move_type > Killer) { bigram_killers.setMove(node.moved, record.best_move); killer_moves.setMove(depth, record.best_move); // history_table.setMove(depth, record.best_move); } if (node.height >= table_record_limit) { record.value = best_value; record.limit = node.height; if (EvalTraits

::betterThan(initial_alpha, best_value)) record.type = CompactRecord::UpperBound; else if (EvalTraits

::betterThan(node.beta, best_value)) record.type = CompactRecord::Exact; else record.type = CompactRecord::LowerBound; table.store(node.hash_key, record); } node.search_value = best_value; } template osl::Move osl::search::AlphaBeta3::nextMove() { SearchInfo& node = tree[depth]; switch (node.move_type) { case Initial: node.move_index = 0; node.moves.clear(); if (node.in_check) { move_generator::GenerateEscape

:: generate(state,state.kingPiece

(),node.moves); node.move_type = KingEscape; // fall through } // fall through case KingEscape: if (! node.moves.empty()) { if (node.move_index < node.moves.size()) return node.moves[node.move_index++]; return Move(); } node.move_type = Pass; // fall through node.move_index = 0; case Pass: if (node.move_index++ == 0 && node.node_type != PvNode && !node.in_check) return Move::PASS(P); node.move_type = TakeBack; // fall through node.move_index = 0; if (node.moved.isNormal()) { move_generator::GenerateCapture::generate(P,state, node.moved.to(), node.moves); // move_order::MoveSorter::sort(node.moves, move_order::CheapPtype()); } case TakeBack: if (node.move_index == 0 && node.moves.size()) return node.moves[node.move_index++]; node.move_type = Capture; // fall through node.move_index = 0; generateCapture

(state, node); case Capture: if (node.move_index < node.moves.size()) return node.moves[node.move_index++]; node.move_type = Killer; // fall through node.move_index = 0; node.moves.clear(); bigram_killers.getMove(state, node.moved, node.moves); killer_moves.getMove(state, depth, node.moves); case Killer: if (node.move_index < node.moves.size()) return node.moves[node.move_index++]; node.move_type = CaptureAll; // fall through node.move_index = 0; generateCaptureAll

(state, node); case CaptureAll: if (node.move_index < node.moves.size()) return node.moves[node.move_index++]; node.move_type = All; // fall through node.move_index = 0; generateAllMoves

(state, tree[depth-1], node); case All: if (node.move_index < node.moves.size()) return node.moves[node.move_index++]; } return Move(); } template void osl::search::AlphaBeta3:: generateAllMoves(const NumEffectState& state, const SearchInfo& parent, SearchInfo& node) { node.moves.clear(); if (cut_drop_move_in_frontier_node && ! parent.in_check && ! node.in_check && node.node_type != PvNode) { if ((futility_pruning_enabled && node.height < 100) || (extended_futility_pruning_enabled && node.height < 200 && EvalTraits

::betterThan(node.alpha, node.eval.value() + extended_futility_margin*EvalTraits

::delta))) { // generation considering futility pruning GenerateAllMoves::generateOnBoard

(state, node.moves); } } #if 1 # if 1 if (node.alpha != node.beta || node.height >= 800) { RatedMoveVector moves; const rating::StandardFeatureSet& features = rating::StandardFeatureSet::instance(); RatingEnv env; env.make(state); features.generateRating(state, env, 2000, moves); for (const RatedMove& move: moves) if (move.move().isDrop() || ! seePlusLight

(state, move.move())) node.moves.push_back(move.move()); return; } # endif GenerateAllMoves::generate

(state, node.moves); if (node.alpha != node.beta || node.height > 300) std::sort(node.moves.begin(), node.moves.end(), move_order::CaptureEstimation(state)); #endif } template void osl::search::AlphaBeta3:: generateCapture(const NumEffectState& state, SearchInfo& node) { node.moves.clear(); MoveVector all; for (size_t i=0; i+1()) continue; move_generator::GenerateCapture::generate(P,state, p.square(), store); } for (Move move: all) { if (See::see(state, move) > 0) { node.moves.push_back(move); } } if (! node.moves.empty()) return; } // promote all.clear(); move_generator::Promote

::generate(state, all); for (Move move: all) { if (See::see(state, move) > 0) { node.moves.push_back(move); } } if (! node.moves.empty()) return; // pawn all.clear(); { move_action::Store store(all); for (int j=Ptype_Table.getIndexMin(PAWN); j()) continue; move_generator::GenerateCapture::generate(P,state, p.square(), store); } } for (Move move: all) { if (See::see(state, move) > 0) { node.moves.push_back(move); } } } template inline bool osl::search::AlphaBeta3:: seePlusLight(const NumEffectState& state, Move m) { assert(P == m.player()); assert(P == state.turn()); assert(! m.isDrop()); if (state.countEffect(P, m.to()) > state.countEffect(P, m.to())) return true; return eval::Ptype_Eval_Table.value(m.capturePtype()) >= eval::Ptype_Eval_Table.value(m.oldPtype()); } template void osl::search::AlphaBeta3:: generateCaptureAll(const NumEffectState& state, SearchInfo& node) { node.moves.clear(); MoveVector all; { move_action::Store store(all); for (size_t i=0; i+1()) continue; move_generator::GenerateCapture::generate(P,state, p.square(), store); } } move_generator::Promote

::generateMoves(state, store); for (int j=PtypeTraits::indexMin; j::indexLimit; ++j) { const Piece p = state.pieceOf(j); if (! p.isOnBoardByOwner()) continue; move_generator::GenerateCapture::generate(P,state, p.square(), store); } } for (Move move: all) if (seePlusLight

(state, move)) node.moves.push_back(move); std::sort(node.moves.begin(), node.moves.end(), move_order::CaptureEstimation(state)); } template void osl::search::AlphaBeta3:: quiesceRoot() { SearchInfo& node = tree[depth]; assert(! state.hasEffectAt(P, state.kingSquare(alt(P)))); assert(node.in_check == state.hasEffectAt(alt(P), state.kingSquare(P))); node.search_value = evalValue(); const int static_value = node.search_value; int best_value = static_value; if (node.in_check) { node.moves.clear(); move_generator::GenerateEscape

:: generate(state,state.kingPiece

(),node.moves); best_value = threatmatePenalty(P)+depth*EvalTraits

::delta*2; for (Move move: node.moves) { int value = makeMoveAndQuiesce

(move); if (EvalTraits

::betterThan(value, best_value)) { best_value = value; if (EvalTraits

::betterThan(value, node.alpha)) { if (node.node_type == PvNode) node.pv.setPV(move, node, tree[depth+1].pv); node.alpha = value + EvalTraits

::delta; if (EvalTraits

::betterThan(value, node.beta)) goto done; } } } goto done; } // end of in check if (EvalTraits

::betterThan(best_value, node.beta)) goto done; if (immediate_checkmate_enabled && ImmediateCheckmate::hasCheckmateMove

(state)) { node.search_value = winByCheckmate(P); return; } for (Ptype ptype: PieceStand::order) { const int expected = static_value + node.eval.captureValue(newPtypeO(alt(P), promoteIf(ptype))); if (EvalTraits

::betterThan(node.alpha, expected)) break; for (int j=Ptype_Table.getIndexMin(ptype); j()) continue; node.moves.clear(); move_generator::GenerateCapture::generate(P,state, p.square(), node.moves); for (Move move: node.moves) { if (See::see(state, move) < 0) continue; int value = makeMoveAndQuiesce

(move); if (EvalTraits

::betterThan(value, best_value)) { best_value = value; if (EvalTraits

::betterThan(value, node.alpha)) { if (node.node_type == PvNode) node.pv.setPV(move, node, tree[depth+1].pv); node.alpha = value + EvalTraits

::delta; if (EvalTraits

::betterThan(value, node.beta)) goto done; } } } } } done: node.search_value = best_value; } template int osl::search::AlphaBeta3:: makeMoveAndQuiesce(Move move) { ++depth; tree[depth] = tree[depth-1]; tree[depth].moved = move; tree[depth].hash_key = tree[depth-1].hash_key.newHashWithMove(move); tree[depth].height -= 1; std::swap(tree[depth].alpha, tree[depth].beta); tree[depth].pv.clear(); CallQuiesce

f(this); tree[depth].path.pushMove(move); state.makeUnmakeMove(move, f); tree[depth].path.popMove(move); --depth; return tree[depth+1].search_value; } template void osl::search::AlphaBeta3:: quiesce() { add_node_count(depth); assert(state.turn() == P); recorder.addQuiescenceCount(); SearchInfo& node = tree[depth]; if (state.hasEffectAt(P, state.kingSquare(alt(P)))) { node.search_value = winByFoul(P); return; } node.eval.update(state, node.moved); node.in_check = state.hasEffectAt(alt(P), state.kingSquare(P)); const int static_value = evalValue(); int best_value = static_value; if (node.in_check) { node.moves.clear(); move_generator::GenerateEscape

:: generate(state,state.kingPiece

(),node.moves); best_value = threatmatePenalty(P)+depth*EvalTraits

::delta*2; for (Move move: node.moves) { int value = makeMoveAndQuiesce

(move); if (EvalTraits

::betterThan(value, best_value)) { best_value = value; if (EvalTraits

::betterThan(value, node.alpha)) { node.alpha = value + EvalTraits

::delta; if (EvalTraits

::betterThan(value, node.beta)) goto done; } } } goto done; } // end of in check // leaf if (EvalTraits

::betterThan(best_value, node.beta)) goto done; if (immediate_checkmate_enabled && node.alpha != node.beta && ImmediateCheckmate::hasCheckmateMove

(state)) { node.search_value = winByCheckmate(P); return; } for (size_t i=0; i::betterThan(node.alpha, expected)) break; for (int j=Ptype_Table.getIndexMin(ptype); j()) continue; node.moves.clear(); move_generator::GenerateCapture::generate(P,state, p.square(), node.moves); for (size_t k=0; k::delta; if (EvalTraits

::betterThan(value, best_value)) { if (node.node_type == PvNode) node.pv.setPV(move, node, tree[depth+1].pv); best_value = value; if (i < 6 || EvalTraits

::betterThan(value, node.beta)) goto done; } } } } done: node.search_value = best_value; } /* ------------------------------------------------------------------------- */ osl::search::AlphaBeta3:: SearchInfo::SearchInfo() : eval((NumEffectState(SimpleState(HIRATE)))), pv() { } void osl::search::AlphaBeta3:: PVVector::setPV(Move m, const SearchInfo& node, const PVVector& child) { clear(); const PVInfo info = { m, node.height, node.in_check, }; push_back(info); push_back(child.begin(), child.end()); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchWindow.h0000644000000000000000000001015112316770314020254 0ustar rootroot/* searchWindow.h */ #ifndef _SEARCHWINDOW_H #define _SEARCHWINDOW_H #include "osl/search/simpleHashRecord.h" #include "osl/eval/evalTraits.h" namespace osl { namespace search { enum TableHit { NO_HIT=0, LOWER_HIT, UPPER_HIT }; struct AlphaBetaWindow { int alpha_value, beta_value; explicit AlphaBetaWindow(int a, int b) : alpha_value(a), beta_value(b) { assert(a % 2); assert(b % 2); } int& alpha() { return alpha_value; } int& beta() { return beta_value; } int alpha() const { return alpha_value; } int beta() const { return beta_value; } const AlphaBetaWindow flipPlayer() const { return AlphaBetaWindow(beta(), alpha()); } bool isConsistent(Player P) const { return eval::notLessThan(P, beta(), alpha()); } bool null() const { return alpha() == beta(); } void dump() const; }; template struct AlphaBetaWindowUtil { typedef typename EvalBase::eval_t eval_t; /** * NullWindow ã®å ´åˆã¨é•ã£ã¦ window ã‚’ç‹­ã出æ¥ã‚‹ã“ã¨ãŒã‚る. */ template static TableHit isOutOfWindow(const SimpleHashRecord& record, int limit, AlphaBetaWindow& w, int& val, const Recorder& recorder) { #ifdef __APPLE__ int table_value=0; #else int table_value; #endif if (record.template hasGreaterLowerBound

(limit, w.alpha(), table_value)) { assert(eval::isConsistentValue(table_value)); w.alpha() = table_value + EvalTraits

::delta; if (EvalTraits

::betterThan(table_value, w.beta())) { recorder.tableHitLowerBound(P, table_value, w.beta(), limit); val = table_value; return LOWER_HIT; } } if (record.template hasLesserUpperBound

(limit, w.beta(), table_value)) { assert(eval::isConsistentValue(table_value)); w.beta() = table_value - EvalTraits

::delta; if (EvalTraits

::betterThan(w.alpha(), table_value)) { recorder.tableHitUpperBound(P, table_value, w.alpha(), limit); val = table_value; return UPPER_HIT; } } return NO_HIT; } }; struct NullWindow { int value; explicit NullWindow(int v) :value(v) { } int& alpha() { return value; } int& beta() { return value; } int alpha() const { return value; } int beta() const { return value; } bool isConsistent(Player) const { return true; } void dump() const; }; template struct NullWindowUtil { typedef typename EvalBase::eval_t eval_t; /** * Record ã¨æ¯”ã¹ã¦ cut ã§ãã‚‹ã‹ã©ã†ã‹ã‚’判定ã™ã‚‹. * @return cut ã§ãã‚‹ã‹ã©ã†ã‹ * @param val cut 出æ¥ã‚‹å ´åˆã¯ upper/lower bound ãŒå…¥ã‚‹ * @param best_move_extension 真ã®å ´åˆï¼Œwindow ã‚’è¶Šãˆã¦ã„ã¦ã‚‚ * ã‹ãªã‚Šæ·±ã読んã çµæžœã§ãªã„㨠cut ã—ãªã„.一度åŒã˜æ·±ã•ã§æŽ¢ç´¢ã—ãŸæ‰‹ã‚’, * ã“れã‹ã‚‰èª­ã‚€æ‰‹ã®ç¢ºçŽ‡ã‚’é«˜ãã¨ã‚‹ã“ã¨ã§å»¶é•·ã™ã‚‹æ™‚ã«ä½¿ç”¨ã™ã‚‹ãŸã‚ */ template static TableHit isOutOfWindow(const SimpleHashRecord& record, int limit, NullWindow w, int& val, const Recorder& recorder) { const int lookUpLimit = (best_move_extension ? limit + 200 : limit); #ifdef __APPLE__ int table_value=0; #else int table_value; #endif if (record.template hasGreaterLowerBound

(lookUpLimit, w.beta(), table_value)) { assert(eval::isConsistentValue(table_value)); recorder.tableHitLowerBound(P, table_value, w.beta(), limit); val = table_value; return LOWER_HIT; } if (record.template hasLesserUpperBound

(lookUpLimit, w.alpha(), table_value)) { assert(eval::isConsistentValue(table_value)); recorder.tableHitUpperBound(P, table_value, w.alpha(), limit); val = table_value; return UPPER_HIT; } return NO_HIT; } }; } // namespace search } // namespace osl #endif /* _SEARCHWINDOW_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveScore.cc0000644000000000000000000001235512316770314017727 0ustar rootroot/* moveScore.cc */ #include "osl/search/moveScore.h" #include "osl/move_generator/capture_.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/escape_.h" #include "osl/move_generator/escape_.tcc" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/move_generator/addEffectWithEffect.tcc" #include "osl/move_generator/capture_.h" #include "osl/move_generator/capture_.tcc" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/allMoves.tcc" #include "osl/move_generator/drop.h" #include "osl/move_generator/drop.tcc" #include #include osl::search::MoveScore* osl::search::MoveScore:: sortPositive(MoveScore *first, MoveScore *last) { MoveScore *p=first-1, *q=last; while (p != q) { while (++p != q && p->score > 0) ; if (p != q) { while (--q != p && q->score <= 0) ; std::swap(*p, *q); } } std::stable_sort(first, p, std::greater()); return p; } namespace osl { namespace search { struct Store{ MoveScore* out; Store(MoveScore* o) :out(o) {} void simpleMove(Square /*from*/,Square /*to*/,Ptype /*ptype*/, bool /*isPromote*/,Player /*p*/,Move move){ (*out++).move = move; } void unknownMove(Square /*from*/,Square /*to*/,Piece /*p1*/,Ptype /*ptype*/,bool /*isPromote*/,Player /*p*/,Move move) { (*out++).move = move; } void dropMove(Square /*to*/,Ptype /*ptype*/,Player /*p*/,Move move) { (*out++).move = move; } // old interfaces void simpleMove(Square from,Square to,Ptype ptype, bool isPromote,Player p) { simpleMove(from,to,ptype,isPromote,p, Move(from,to,ptype,PTYPE_EMPTY,isPromote,p)); } void unknownMove(Square from,Square to,Piece captured, Ptype ptype,bool isPromote,Player p) { unknownMove(from,to,captured,ptype,isPromote,p, Move(from,to,ptype,captured.ptype(),isPromote,p)); } void dropMove(Square to,Ptype ptype,Player p) { dropMove(to,ptype,p, Move(to,ptype,p)); } }; struct NoCaptureStore{ MoveScore* out; NoCaptureStore(MoveScore* o) :out(o) {} void simpleMove(Square /*from*/,Square /*to*/,Ptype /*ptype*/, bool /*isPromote*/,Player /*p*/,Move move){ (*out++).move = move; } void unknownMove(Square /*from*/,Square /*to*/,Piece p1,Ptype /*ptype*/,bool /*isPromote*/,Player /*p*/,Move move) { if(p1.isEmpty()) (*out++).move = move; } void dropMove(Square /*to*/,Ptype /*ptype*/,Player /*p*/,Move move) { (*out++).move = move; } // old interfaces void simpleMove(Square from,Square to,Ptype ptype, bool isPromote,Player p) { (*out++).move = Move(from,to,ptype,PTYPE_EMPTY,isPromote,p); } void unknownMove(Square from,Square to,Piece captured, Ptype ptype,bool isPromote,Player p) { if(captured.isEmpty()) (*out++).move = Move(from,to,ptype,captured.ptype(),isPromote,p); } void dropMove(Square to,Ptype ptype,Player p) { (*out++).move = Move(to,ptype,p); } }; } } template osl::search::MoveScore* osl::search::MoveScore:: generateCapture(const NumEffectState& state, MoveScore *out) { Store store(out); for(int num=0;num()) move_generator::Capture::generate

(state,p.square(),store); } return store.out; } osl::search::MoveScore* osl::search::MoveScore:: generateCapture(const NumEffectState& state, MoveScore *out) { if (state.turn() == BLACK) return generateCapture(state, out); else return generateCapture(state, out); } osl::search::MoveScore* osl::search::MoveScore:: generateNoCapture(const NumEffectState& state, MoveScore *out) { NoCaptureStore store(out); if (state.turn() == BLACK) move_generator::AllMoves::generate(state,store); else move_generator::AllMoves::generate(state,store); return store.out; } osl::search::MoveScore* osl::search::MoveScore:: generateAll(const NumEffectState& state, MoveScore *out) { Store store(out); if (state.turn() == BLACK) move_generator::AllMoves::generate(state,store); else move_generator::AllMoves::generate(state,store); return store.out; } osl::search::MoveScore* osl::search::MoveScore:: generateCheckNoCapture(const NumEffectState& state, MoveScore *out) { const Square king = state.kingSquare(alt(state.turn())); NoCaptureStore store(out); if (state.turn() == BLACK) move_generator::AddEffectWithEffect:: generate(state,king,store); else move_generator::AddEffectWithEffect:: generate(state,king,store); return store.out; } osl::search::MoveScore* osl::search::MoveScore:: generateKingEscape(const NumEffectState& state, MoveScore *out) { Store store(out); if (state.turn() == BLACK) move_generator::Escape::generateKingEscape (state,store); else move_generator::Escape::generateKingEscape (state,store); return store.out; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta4.cc0000644000000000000000000000170612316770314017730 0ustar rootroot/* alphaBeta4.cc */ #include "osl/search/alphaBeta4.h" #include "osl/search/searchRecorder.h" osl::search4::AlphaBeta4:: AlphaBeta4(const NumEffectState& /*state*/, checkmate_t& /*checkmate*/, SimpleHashTable */*table*/, CountRecorder& /*recorder*/) { } osl::search4::AlphaBeta4:: ~AlphaBeta4() { } osl::Move osl::search4::AlphaBeta4:: computeBestMoveIteratively(int /*limit*/, int /*step*/, int /*initial_limit*/, size_t /*node_limit*/, const TimeAssigned& assign, MoveWithComment */*additional_info*/) { this->setStartTime(clock::now()); this->setTimeAssign(assign); return Move(); } bool osl::search4::AlphaBeta4:: isReasonableMove(Move /*move*/, int /*pawn_sacrifice*/) { return true; } void osl::search4::AlphaBeta4:: setRootIgnoreMoves(const MoveVector * /*rim*/, bool) { } void osl::search4::AlphaBeta4:: setHistory(const MoveStack& /*h*/) { } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveStackRejections.cc0000644000000000000000000003215712316770314021751 0ustar rootroot/* moveStackRejections.cc */ #include "osl/search/moveStackRejections.h" #include "osl/misc/lightMutex.h" #include "osl/eval/evalTraits.h" #include "osl/oslConfig.h" #include std::ostream& osl::search::operator<<(std::ostream& os,osl::search::OnBoardElement const& mp) { return os << "[" << mp.pos() << "," << mp.ptypeO() << "]"; } std::ostream& osl::search::operator<<(std::ostream& os,osl::search::StandElements const& mp) { os << "["; for(int ptypeIndex=8;ptypeIndex<=15;ptypeIndex++) os << (int)mp.v.c8[ptypeIndex-osl::PTYPE_BASIC_MIN] << ","; return os << "]"; } void osl::search::StateElements:: addMyBoard(osl::Square pos,osl::PtypeO ptypeO) { short posPtypeO=OnBoardElement::makePosPtypeO(pos,ptypeO); for(size_t i=0;i bool osl::search::StateElements:: validSimpleMove(osl::NumEffectState const& state, osl::search::OnBoardElement const& fromElement, osl::search::OnBoardElement const& toElement,Move lastMove) const { Square from=fromElement.pos(), to=toElement.pos(); PtypeO fromPtypeO=fromElement.ptypeO(), toPtypeO=toElement.ptypeO(); if(fromPtypeO!=toPtypeO && (fromPtypeO!=unpromote(toPtypeO) || (!from.canPromote

() && !to.canPromote

()))) return false; EffectContent effect=Ptype_Table.getEffect(fromPtypeO,from,to); if(!effect.hasEffect()) return false; if(effect.hasUnblockableEffect()) return true; Offset o=effect.offset(); Square moveTo=lastMove.to(),moveFrom=lastMove.from(); Square pos=from+o; for (;; pos+=o) { if(pos==to) return true; if(pos==moveTo) return false; if(!state.pieceAt(pos).isEmpty()){ if(pos==moveFrom){ for (pos+=o;; pos+=o) { if(pos==to) return true; if(pos==moveTo) return false; if(!state.pieceAt(pos).isEmpty()){ break; } } } break; } } return false; } template bool osl::search::StateElements:: validCaptureMove(osl::NumEffectState const& state, osl::search::OnBoardElement const& fromElement, osl::search::OnBoardElement const& toElement, osl::search::OnBoardElement const& captureElement, osl::Move lastMove) const { Square to=toElement.pos(); if(to!=captureElement.pos()) return false; Square from=fromElement.pos(); PtypeO fromPtypeO=fromElement.ptypeO(), toPtypeO=toElement.ptypeO(); if(fromPtypeO!=toPtypeO && (fromPtypeO!=unpromote(toPtypeO) || (!from.canPromote

() && !to.canPromote

()))) return false; EffectContent effect=Ptype_Table.getEffect(fromPtypeO,from,to); if(!effect.hasEffect()) return false; if(effect.hasUnblockableEffect()) return true; Offset o=effect.offset(); Square moveTo=lastMove.to(),moveFrom=lastMove.from(); Square pos=from+o; for (;; pos+=o) { if(pos==to) return true; if(pos==moveTo) return false; if(!state.pieceAt(pos).isEmpty()){ if(pos==moveFrom){ for (pos+=o;; pos+=o) { if(pos==to) return true; if(pos==moveTo) return false; if(!state.pieceAt(pos).isEmpty()){ break; } } } break; } } return false; } /** * rejectable patterns * 0 - sennichite (or piece losing loop) * myPlus 1 myMinus 1 - my simple move * myPlus 1 myMinus 1 opMinus 1 - my capture move * myPlus 1 - my drop move * opPlus 1 opMinus 1 - op simple move * opPlus 1 opMinus 1 myPlus 1 - op capture move * opMinus 1 - op drop move */ template bool osl::search::StateElements::canReject(osl::NumEffectState const& state,bool mayRejectSennichite,bool isRootMove,Move lastMove,Move actualMove) const { const Player altP=alt(P); switch(myOnboardPlus.size()){ case 0: switch(opOnboardPlus.size()){ case 1: // myPlus=0, opPlus=1 if(opOnboardMinus.size()==1 && myOnboardMinus.size()==0){ // op simple move if(validSimpleMove(state,opOnboardPlus[0],opOnboardMinus[0],lastMove)){ if(!mayRejectSennichite && stand.isZero()){ return false; } return stand.geZero(); } } return false; case 0: // myPlus=0, opPlus=0 if(opOnboardMinus.size()==1){ if(myOnboardMinus.size()==0){ StandElements localStand(stand); // op drop move Ptype ptype=getPtype(opOnboardMinus[0].ptypeO()); if(!isPromoted(ptype)){ localStand.sub(ptype); if(!mayRejectSennichite && localStand.isZero()){ return false; } return localStand.geZero(); } } } else{ // pass moves (including piece loosing cases) if(opOnboardMinus.size()==0 && myOnboardMinus.size()==0){ if(isRootMove) return stand.gtZero(); else return stand.geZero(); } } return false; default: return false; } case 1: // myPlus=1 switch(myOnboardMinus.size()){ case 1: // myPlus=1, myMinus=1 switch(opOnboardMinus.size()){ case 1: // myPlus=1, myMinus=1, opMinus=1 if(opOnboardPlus.size()==0){ // my capture move if(validCaptureMove

(state,myOnboardMinus[0],myOnboardPlus[0],opOnboardMinus[0],lastMove)) { StandElements localStand(stand); Ptype capturePtype=unpromote(getPtype(opOnboardMinus[0].ptypeO())); // altPã«é–¢ã—ã¦æ¸›ã‚Šã™ãŽãŸåˆ†ã‚’増やã™? // 相手ã«å–ã£ã¦æ¸›ã£ã¦ã„ã‚‹ã¯ãšãªã®ã§ï¼Œãれをキャンセルã™ã‚‹ localStand.add(capturePtype); if(localStand.isZero()){ assert(actualMove.player()==P); if(!mayRejectSennichite && actualMove.ptypeO()==myOnboardPlus[0].ptypeO() && actualMove.from()==myOnboardMinus[0].pos() && actualMove.to()==myOnboardPlus[0].pos()) return false; return true; } return localStand.geZero(); } } return false; case 0: // myPlus=1, myMinus=1, opMinus=0 if(opOnboardPlus.size()==0){ // my simple move if(validSimpleMove

(state,myOnboardMinus[0],myOnboardPlus[0],lastMove)){ if(stand.isZero()){ assert(actualMove.player()==P); if(!mayRejectSennichite && actualMove.ptypeO()==myOnboardPlus[0].ptypeO() && actualMove.from()==myOnboardMinus[0].pos() && actualMove.to()==myOnboardPlus[0].pos()) return false; return true; } return stand.geZero(); } } return false; } case 0: // myPlus=1, myMinus=0 if(opOnboardPlus.size()==1){ if(opOnboardMinus.size()==1){ if(validCaptureMove(state,opOnboardPlus[0],opOnboardMinus[0],myOnboardPlus[0],lastMove)) { StandElements localStand(stand); Ptype capturePtype=unpromote(getPtype(myOnboardPlus[0].ptypeO())); // 次ã®moveを実行ã™ã‚‹ã¨ç›¸æ‰‹ã«å–ã£ã¦ã¯å¢—ãˆã‚‹ï¼Ž localStand.add(capturePtype); if(!mayRejectSennichite && localStand.isZero()){ return false; } return localStand.geZero(); } } else return false; } else if(opOnboardPlus.size()==0 && opOnboardMinus.size()==0 && !isPromoted(myOnboardPlus[0].ptypeO()) ){ // my drop move StandElements localStand(stand); localStand.sub(getPtype(myOnboardPlus[0].ptypeO())); if(localStand.isZero()){ if(!mayRejectSennichite && actualMove.ptypeO()==myOnboardPlus[0].ptypeO() && actualMove.isDrop() && actualMove.to()==myOnboardPlus[0].pos()) return false; return true; } return localStand.geZero(); } } default: return false; } } std::ostream& osl::search::operator<<(std::ostream& os,osl::search::StateElements const& mps) { { os << "[ MyOnboardPlus("; for(size_t i=0;i check,hit; ProbeCounter(){} void incCheck(int d){ #ifdef OSL_USE_RACE_DETECTOR osl::LightMutex::scoped_lock lk(mutex); #endif check[d]++; } void incHit(int d){ #ifdef OSL_USE_RACE_DETECTOR osl::LightMutex::scoped_lock lk(mutex); #endif hit[d]++; } ~ProbeCounter(){ for(int i=0;i<1024;i++){ if(check[i]!=0){ std::cerr << i << " : " << hit[i] << "/" << check[i] << std::endl; } } } }; ProbeCounter probeCounter; #endif template bool osl::search::MoveStackRejections:: probe(osl::NumEffectState const& state,osl::container::MoveStack const& history,int ply,osl::Move const& m,int alpha,int checkCountOfAltP) { StateElements elements; elements.addMyMove(m); assert(m.player()==P); bool existNormal=false; for(int i=1;icheckCountOfAltP*2-1); if(elements.stand.isZero()){ if(mayRejectSennichite) return true; } else if(elements.stand.geZero()) return true; } Move m2=history.lastMove(i+1); if(m2.isNormal()){ assert(m2.player()==P); elements.addMyMove(m2); existNormal=true; } else if(m2.isInvalid()) return false; #ifdef SHOW_PROBE_COUNTER probeCounter.incCheck(i); #endif // i==1 -- checkCount=1 // i==3 -- checkCount=2 bool mayRejectSennichite=osl::eval::notLessThan(P,alpha,0) && (i>checkCountOfAltP*2-1); bool isRootMove=(i == ply-1); if( existNormal && elements.canReject

(state,mayRejectSennichite,isRootMove,m,m2) ){ #ifdef SHOW_PROBE_COUNTER probeCounter.incHit(i); #endif return true; } } return false; } namespace osl { namespace search { template bool MoveStackRejections::probe( osl::NumEffectState const& state,osl::container::MoveStack const& history,int ply,osl::Move const& m,int alpha, int checkCountOfAltP); template bool MoveStackRejections::probe( osl::NumEffectState const& state,osl::container::MoveStack const& history,int ply,osl::Move const& m,int alpha,int checkCountOfAltP); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/usiReporter.h0000644000000000000000000000440412316770314020146 0ustar rootroot/* usiReporter.h */ #ifndef OSL_USIREPORTER_H #define OSL_USIREPORTER_H #include "osl/search/searchMonitor.h" #include "osl/misc/milliSeconds.h" #include #include namespace osl { namespace search { struct UsiReporter { static void newDepth(std::ostream& os, int depth); static void showPV(std::ostream& os, int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, bool ignore_silent=false); static void showPVExtended(std::ostream& os, int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool *threatmate_first, const bool *threatmate_last); static void rootMove(std::ostream& os, Move cur, bool allow_frequent_display=false); static void timeInfo(std::ostream& os, size_t node_count, double elapsed); static void hashInfo(std::ostream& os, double ratio); }; class UsiMonitor : public SearchMonitor { Move last_root_move; std::string deferred; double silent_period; bool extended; time_point depth0; std::ostream& os; boost::asio::ip::udp::socket *udp_socket; boost::asio::ip::udp::endpoint *udp_endpoint; std::string client_id; public: UsiMonitor(bool extended, std::ostream& os, double silent=0.5); ~UsiMonitor(); void setUdpLogging(std::string& udp_client_id, boost::asio::ip::udp::socket *, boost::asio::ip::udp::endpoint *); void newDepth(int depth); void showPV(int depth, size_t node_count, double elapsed, int value, Move cur, const Move *first, const Move *last, const bool *threatmate_first, const bool *threatmate_last); void showFailLow(int depth, size_t node_count, double elapsed, int value, Move cur); void rootMove(Move cur); void rootFirstMove(Move cur); void timeInfo(size_t node_count, double elapsed); void hashInfo(double ratio); void rootForcedMove(Move the_move); void rootLossByCheckmate(); void searchFinished(); private: void showDeferred(bool forced=false); }; } using search::UsiMonitor; } #endif /* OSL_USIREPORTER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/sacrificeCheck.h0000644000000000000000000000234012316770314020506 0ustar rootroot/* sacrificeCheck.h */ #ifndef OSL_SACRIFICECHECK_H #define OSL_SACRIFICECHECK_H #include "osl/search/simpleHashRecord.h" #include "osl/container/moveStack.h" namespace osl { namespace search { struct SacrificeCheck { template static int count2(const RecordStack& record_stack, const MoveStack& history, int history_max) { int i=1; while (history.hasLastMove(i+1) && (i+1 <= history_max)) { // 王手回é¿ã§é§’å¾— assert(record_stack.hasLastRecord(i)); const SimpleHashRecord *last_record = record_stack.lastRecord(i); if ((! last_record) || (! last_record->inCheck())) break; const Move last_move = history.lastMove(i); if (! last_move.isCapture()) break; if (static_cast(record_stack.size()) <= i) break; // ãŸã ã§å–られãŸçŽ‹æ‰‹ const Move last_last_move = history.lastMove(i+1); if ((last_last_move.to() != last_move.to()) || (last_last_move.isCapture()) || (unpromote(last_last_move.ptype()) == PAWN)) break; i+=2; } return i/2; } }; } // namespace search } // namespace osl #endif /* OSL_SACRIFICECHECK_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/breakThreatmate.cc0000644000000000000000000002447312316770314021074 0ustar rootroot/* breakThreatmate.cc */ #include "osl/search/breakThreatmate.h" #include "osl/container/moveLogProbVector.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/move_generator/capture_.h" #include "osl/move_generator/pieceOnBoard.h" #include "osl/move_generator/escape_.h" #include "osl/bits/king8Info.h" void osl::search:: BreakThreatmate::generateBreakDrop(int limit, const NumEffectState& state, Square to, int default_prob, MoveLogProbVector& out) { const Player Turn = state.turn(); default_prob = std::max(default_prob, 150); if (state.hasPieceOnStand(Turn)) { if (! state.isPawnMaskSet(Turn, to.x()) && Ptype_Table.canDropTo(Turn, PAWN, to) && limit >= default_prob-100) out.push_back(MoveLogProb(Move(to, PAWN, Turn), default_prob-100)); } if (state.hasPieceOnStand(Turn) && Ptype_Table.canDropTo(Turn, LANCE, to) && limit >= default_prob-50) out.push_back(MoveLogProb(Move(to, LANCE, Turn), default_prob-50)); if (default_prob > limit) return; if (state.hasPieceOnStand(Turn) && Ptype_Table.canDropTo(Turn, KNIGHT, to)) out.push_back(MoveLogProb(Move(to, KNIGHT, Turn), default_prob)); if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(to, SILVER, Turn), default_prob)); if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(to, GOLD, Turn), default_prob)); if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(to, BISHOP, Turn), default_prob)); if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(to, ROOK, Turn), default_prob)); } void osl::search::BreakThreatmate::findBlockLong(const NumEffectState& state, Move threatmate_move, MoveVector& out) { const Player Turn = alt(threatmate_move.player()); const Piece my_king = state.kingPiece(Turn); const Square target = threatmate_move.to(); out.clear(); move_action::Store store(out); // block additional if (! threatmate_move.isDrop() && threatmate_move.oldPtype() != KNIGHT) { const Offset step = Board_Table.getShortOffsetNotKnight(Offset32(threatmate_move.from(), target)); Square p=threatmate_move.from()+step; Piece piece=state.pieceAt(p); for (; piece.isEmpty(); p+=step, piece=state.pieceAt(p)) ; if (piece.isPiece() && piece.owner() == alt(Turn) && state.hasEffectByPiece(piece, threatmate_move.from())) { if (Turn == BLACK) move_generator::Escape::generateBlocking (state, my_king, threatmate_move.from(), piece.square(), store); else move_generator::Escape::generateBlocking (state, my_king, threatmate_move.from(), piece.square(), store); } } // block long { mask_t attack = state.longEffectAt(target, alt(Turn)); while (attack.any()) { static_assert(PtypeFuns::indexNum == PtypeFuns::indexNum, ""); static_assert(PtypeFuns::indexNum == PtypeFuns::indexNum, ""); const int num = (attack.takeOneBit()+((PtypeFuns::indexNum)<<5)); if (Turn == BLACK) move_generator::Escape::generateBlocking (state, my_king, target, state.pieceOf(num).square(), store); else move_generator::Escape::generateBlocking (state, my_king, target, state.pieceOf(num).square(), store); } } } void osl::search::BreakThreatmate:: generateAddEffect(int limit, const NumEffectState& state, Square target, const MoveVector& all_moves, MoveLogProbVector& out) { const Player Turn = state.turn(); const int max_prob = state.king8Info(state.turn()).liberty() ? limit : 100; for (Move move: all_moves) { const Ptype ptype = move.ptype(); if (ptype == KING) continue; // KING_WALK will generate if (! move.isDrop()) { if (isMajor(ptype) && state.hasEffectByPiece(state.pieceOnBoard(move.from()), target)) continue; // already have effect } const Square to = move.to(); const int me = state.countEffect(Turn, to) + (move.isDrop() ? 1 : 0); const int op = state.countEffect(alt(Turn), to); int prob = (move.isDrop() ? 100 : 100); // delay drop if (move.isCapture()) { prob -= 50; } else { if (isMajor(ptype) || ((ptype == GOLD || ptype == SILVER) && (to.x() == 1 || to.x() == 9))) { prob += 50; } if (! ((me >= 2) || (op == 0))) { prob += 300; } } prob = std::min(prob, max_prob); if (prob <= limit) out.push_back(MoveLogProb(move, prob)); } } // yoshiki's suggestion é§’å–り 50, 普通 100, é§’æ¨ã¦ 400 void osl::search::BreakThreatmate:: generate(int limit, const NumEffectState& state, Move threatmate_move, MoveLogProbVector& out) { assert(threatmate_move.isNormal()); const Player Turn = state.turn(); MoveVector all_moves; assert(threatmate_move.isNormal()); const Square target = threatmate_move.to(); move_generator::GenerateAddEffectWithEffect::generate (Turn, state, target, all_moves); generateAddEffect(limit, state, target, all_moves, out); if (threatmate_move.isDrop()) { const int drop_prob = (state.hasEffectAt(alt(Turn), target) ? 400 : 100); generateBreakDrop(limit, state, target, drop_prob, out); } else { // not drop const Square from = threatmate_move.from(); const Offset offset = Board_Table.getShortOffsetNotKnight(Offset32(target, from)); if (! offset.zero()) { for (Square to = from + offset; to != target; to += offset) { assert(to.isOnBoard()); assert(state.pieceOnBoard(to) == Piece::EMPTY()); const int drop_prob = (state.hasEffectAt(Turn, to) ? 100 : 400); generateBreakDrop(limit, state, to, drop_prob, out); const int move_prob = (state.hasMultipleEffectAt(Turn, to) ? 100 : 400); if (move_prob > limit) continue; all_moves.clear(); move_generator::GenerateCapture::generate (Turn, state, to, all_moves); for (Move move: all_moves) { out.push_back(MoveLogProb(move, move_prob)); } } } } const Piece my_king = state.kingPiece(Turn); if (my_king.square() != target+Board_Table.getShortOffset(Offset32(my_king.square(),target))) { const checkmate::King8Info king8info = state.king8Info(Turn); unsigned int drop_candidate = king8info.dropCandidate(); if (drop_candidate) { const int d = misc::BitOp::bsf(drop_candidate); const Square to = my_king.square() + Board_Table.getOffset(Turn, static_cast(d)); if (to != target) { all_moves.clear(); move_generator::GenerateAddEffectWithEffect::generate (Turn, state, to, all_moves); generateAddEffect(limit, state, to, all_moves, out); } } } // king walk const int king_prob = 100; if (king_prob <= limit) { all_moves.clear(); { GeneratePieceOnBoard::generate(Turn, state, my_king, all_moves); } for (Move move: all_moves) { if (state.hasEffectAt(alt(Turn), move.to())) continue; out.push_back(MoveLogProb(move, king_prob)); } } // open king road const Square center = my_king.square(); generateOpenRoad(limit, state, center + DirectionTraits::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits

    ::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits
    ::blackOffset(), out); generateOpenRoad(limit, state, center + DirectionTraits::blackOffset(), out); // block findBlockLong(state, threatmate_move, all_moves); if (! all_moves.empty()) { Ptype cheapest = PTYPE_EMPTY; if (state.hasPieceOnStand(Turn)) cheapest = PAWN; else if (state.hasPieceOnStand(Turn)) cheapest = LANCE; else if (state.hasPieceOnStand(Turn)) cheapest = KNIGHT; int added = 0; Move chuai_reserve; for (Move m: all_moves) { const int d = state.countEffect(Turn, m.to()) + m.isDrop(); const int a = state.countEffect(alt(Turn), m.to()); if (d == 1 || (m.ptype() != cheapest && cheapest != PTYPE_EMPTY && Ptype_Table.canDropTo(Turn, cheapest, m.to()) && (cheapest != PAWN || ! state.isPawnMaskSet(m.player(), m.to().x())))) continue; if (a >= d) { if (! chuai_reserve.isNormal()) chuai_reserve = m; continue; } const int prob = 150+added*50; if (prob > limit) break; out.push_back(MoveLogProb(m, prob)); } if (added == 0 && chuai_reserve.isNormal() && limit >= 250) { out.push_back(MoveLogProb(chuai_reserve, 250)); if (chuai_reserve.isDrop() && chuai_reserve.ptype() == KNIGHT && 300 <= limit) { if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(chuai_reserve.to(),SILVER,Turn), 300)); else if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(chuai_reserve.to(),GOLD,Turn), 300)); else if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(chuai_reserve.to(),BISHOP,Turn), 300)); else if (state.hasPieceOnStand(Turn)) out.push_back(MoveLogProb(Move(chuai_reserve.to(),ROOK,Turn), 300)); } } } } void osl::search::BreakThreatmate:: generateOpenRoad(int limit, const NumEffectState& state, Square from, MoveLogProbVector& out) { const Piece target = state.pieceAt(from); if (! target.isPiece()) return; const Player Turn = state.turn(); if (target.owner() != Turn) return; const int capture_prob = 50; const int default_prob = 100; const int sacrifice_prob = 400; if (limit < capture_prob) return; MoveVector moves; GeneratePieceOnBoard::generate(Turn, state, target, moves); for (Move move: moves) { const bool capture = move.isCapture(); const bool sacrifice = state.hasEffectAt(alt(Turn), move.to()); const int prob = capture ? capture_prob : (sacrifice ? sacrifice_prob : default_prob); if (prob <= limit) out.push_back(MoveLogProb(move, prob)); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/usiProxy.h0000644000000000000000000000457212521114240017457 0ustar rootroot/* alphaBeta4.h */ #ifndef OSL_SEARCH_USIPROXY_H #define OSL_SEARCH_USIPROXY_H #include "osl/numEffectState.h" #include "osl/search/searchTimer.h" #include "osl/search/fixedEval.h" #include "osl/eval/openMidEndingEval.h" #include "osl/container/moveStack.h" #include "osl/checkmate/dualDfpn.h" #include #include namespace osl { namespace search { struct MoveWithComment; struct SimpleHashTable; struct CountRecorder; class UsiProxy : public SearchTimer, FixedEval { NumEffectState state; MoveStack history; const MoveVector *root_ignore_moves; // acquaintance bool prediction_for_speculative_search; struct Proxy; std::shared_ptr proxy; static std::mutex mutex; static std::queue> proxy_pool; static std::string default_program; static std::vector initial_commands; public: /** * Regits a USI program. * * @param program path to a usi program. * (default $OSL_HOME/../gpsfish_dev/src/gpsfish) * @param initial_commands commands to send at start up * @return true if an appropriate program exists; otherwise, false */ static bool setUp(const std::string& program="", const std::vector& initial_commands={}); static std::string getProgram() { return default_program; } // interface required for game_playing::SearchPlayer typedef DualDfpn checkmate_t; typedef eval::ml::OpenMidEndingEval eval_t; UsiProxy(const NumEffectState& s, checkmate_t& checker, SimpleHashTable *t, CountRecorder&); UsiProxy(const UsiProxy&); UsiProxy& operator=(const UsiProxy&) = delete; ~UsiProxy(); Move computeBestMoveIteratively (int limit, int step, int initial_limit=600, size_t node_limit=1600000, const TimeAssigned& assign=TimeAssigned(milliseconds(60*1000)), MoveWithComment *additional_info=0); bool isReasonableMove(Move move, int pawn_sacrifice=1); void setRootIgnoreMoves(const MoveVector *rim, bool); void setHistory(const MoveStack& h); void enableMultiPV(unsigned int) {} std::vector toCSA(const std::vector&) const; }; } } #endif /* OSL_SEARCH_ALPHABETA4_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/searchBase.h0000644000000000000000000000642412316770314017667 0ustar rootroot/* searchBase.h */ #ifndef OSL_SEARCHBASE_H #define OSL_SEARCHBASE_H #include "osl/search/searchRecorder.h" #include "osl/search/searchTable.h" #include "osl/search/realizationProbability.h" #include "osl/search/simpleHashRecord.h" #include "osl/search/searchWindow.h" #include "osl/search/fixedEval.h" #include "osl/hash/hashCollision.h" #include "osl/hashKey.h" #include "osl/numEffectState.h" #include namespace osl { namespace search { class SimpleHashTable; /** * MTDF 㨠SearchFramework ã«å…±é€šã® * å°ç‰©ã®ãƒ¡ã‚½ãƒƒãƒ‰. */ template struct SearchBase : protected FixedEval { // types typedef Eval eval_t; typedef Probabilities Probabilities_t; protected: Recorder& recorder; Table *table; // acquaintance public: SearchBase(Recorder& r, Table *t) : recorder(r), table(t) { assert(table); assert(winThreshold(BLACK) > eval_t::infty()); } virtual ~SearchBase() {} virtual bool abort(Move) const { return false; } /** * ãƒ†ãƒ¼ãƒ–ãƒ«ã®æŒ‡æ‰‹ã®æ­£ã—ã•を確ã‹ã‚ã‚‹ * * ã¤ã„ã§ã«å®Ÿç¾ç¢ºçއã®ãƒã‚§ãƒƒã‚¯ã‚‚ã™ã‚‹ * HashKey ã®conflict ãŒã‚ã‚‹ã¨table ã‹ã‚‰ç‰½ã„㟠move ãŒä¸æ­£ã§ã‚ã‚‹ã“ã¨ãŒã‚ã‚‹ * conflict ã§ turn ã®é•ã„ãŒã‚る㨠isAlmostValidMove ã§ã¯ãƒã‚§ãƒƒã‚¯ã§ããªã„ * ã“ã¨ã«æ³¨æ„ */ bool validTableMove(const NumEffectState& state, const MoveLogProb& move, int limit) const { if ((limit < move.logProb()) || (! move.validMove())) return false; if (! move.isNormal()) return false; const bool valid = ((move.player() == state.turn()) && state.isAlmostValidMove(move.move())); if (! valid) { // 本æ¥ã“ã“ã«æ¥ã¦ã¯ã„ã‘ãªã„ recorder.recordInvalidMoveInTable(state, move, limit); throw hash::HashCollision(); } return valid; } private: void recordCheckmateResult(Player P, SimpleHashRecord *record, int val, Move move) const { assert(isWinValue(P,val) || isWinValue(alt(P),val)); const int limit = SearchTable::CheckmateSpecialDepth; const MoveLogProb best_move(move, 101); recorder.tableStoreLowerBound(P, best_move, val, limit); recorder.tableStoreUpperBound(P, best_move, val, limit); record->setAbsoluteValue(best_move.move(), val, SearchTable::CheckmateSpecialDepth); } public: /** 詰将棋ã®è¦‹ã¤ã‘ãŸå‹ */ void recordWinByCheckmate(Player P, SimpleHashRecord *record, Move check_move) const { assert(record); recordCheckmateResult(P, record, winByCheckmate(P), check_move); } /** 詰将棋ã®è¦‹ã¤ã‘ãŸæ•— */ void recordLoseByCheckmate(Player P, SimpleHashRecord *record) const { assert(record); recordCheckmateResult(P, record, winByCheckmate(alt(P)), Move::INVALID()); } using FixedEval::isWinValue; using FixedEval::winByCheckmate; using FixedEval::winByFoul; using FixedEval::winByLoop; using FixedEval::minusInfty; using FixedEval::drawValue; }; } // namespace search } // namespace osl #endif /* OSL_SEARCHBASE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/timeControl.cc0000644000000000000000000000155312316770314020262 0ustar rootroot/* timeControl.cc */ #include "osl/search/timeControl.h" int osl::search::TimeControl:: secondsForThisMove(int totalSeconds) { if (totalSeconds < 90) return 1; if (totalSeconds < 2*60) return 4; if (totalSeconds < 3*60) return 8; if (totalSeconds < 4*60) return 15; if (totalSeconds < 6*60) return 22; if (totalSeconds < 8*60) return 30; if (totalSeconds < 10*60) return 42; if (totalSeconds < 12*60) return 55; if (totalSeconds < 25*60) return 67; if (totalSeconds < 40*60) return 90; if (totalSeconds < 60*60) // 1h return 135; if (totalSeconds < 90*60) // 1.5h return 197; if (totalSeconds < 2*60*60) // 2h return 270; return 600; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/generalSimpleHashTable.tcc0000644000000000000000000001037512316770314022514 0ustar rootroot/* generalSimpleHashTable.cc */ #include "osl/search/generalSimpleHashTable.h" #include "osl/hashKey.h" #include "osl/config.h" #ifdef OSL_SMP # include "osl/misc/lightMutex.h" # include #endif #include template struct osl::container::GeneralSimpleHashTable::Table { typedef std::unordered_map> table_t; typedef typename table_t::const_iterator const_iterator; #ifdef OSL_SMP typedef osl::misc::LightMutex Mutex; static const unsigned int DIVSIZE=16; CArray mutex; #else static const unsigned int DIVSIZE=1; #endif CArray tables; /** icc ã®hash_map ãŒcapacity ã‚’æŒã£ã¦ã„ãªã‹ã£ãŸæ°—ãŒã™ã‚‹ã®ã§è‡ªåˆ†ã§æŒã¤ */ const size_t capacity; int num_cache_hit, num_record_after_full; Table(size_t c) : capacity(c), num_cache_hit(0), num_record_after_full(0) { } ~Table() { } void clear() { for(size_t i=0;isecond; } static int keyToIndex(const HashKey& key) { unsigned long val=key.signature(); return (val>>24)%DIVSIZE; } public: Record *find(const HashKey& key) { int i=keyToIndex(key); #if (defined OSL_SMP) && (! defined USE_TBB_HASH) SCOPED_LOCK(lk,mutex[i]); #endif return findInLock(key,i); } Record *allocate(const HashKey& key) { const int i=keyToIndex(key); #if (defined OSL_SMP) && (! defined USE_TBB_HASH) SCOPED_LOCK(lk,mutex[i]); #endif const size_t current_size = tables[i].size(); if (current_size < capacity/DIVSIZE) { Record *record = &tables[i].operator[](key); #ifndef OSL_USE_RACE_DETECTOR if (current_size == tables[i].size()) ++num_cache_hit; #endif return record; } // サイズを増やã•ãªã„よã†ã«æŽ¢ã™ Record *result = findInLock(key,i); if ((result == 0) && capacity) { #ifdef OSL_SMP if (capacity > 10000) std::cerr << "table full " << size() << " " << capacity << "\n"; // SMP環境ã§ã¯å…¨ã¦ã®threadã«æŠ•ã’ã‚‹å¿…è¦ãŒã‚ã‚‹ ++num_record_after_full; throw TableFull(); #else if (num_record_after_full++ == 0) throw TableFull(); #endif } return result; } }; template osl::container::GeneralSimpleHashTable:: GeneralSimpleHashTable(size_t capacity) : table(new Table(capacity)) { } template osl::container::GeneralSimpleHashTable:: ~GeneralSimpleHashTable() { } template void osl::container::GeneralSimpleHashTable:: clear() { table->clear(); } template Record * osl::container::GeneralSimpleHashTable:: allocate(const HashKey& key) { return table->allocate(key); } template Record * osl::container::GeneralSimpleHashTable:: find(const HashKey& key) { return table->find(key); } template const Record * osl::container::GeneralSimpleHashTable:: find(const HashKey& key) const { return table->find(key); } template size_t osl::container::GeneralSimpleHashTable:: size() const { return table->size(); } template size_t osl::container::GeneralSimpleHashTable:: capacity() const { return table->capacity; } template int osl::container::GeneralSimpleHashTable:: numCacheHit() const { return table->num_cache_hit; } template int osl::container::GeneralSimpleHashTable:: numRecordAfterFull() const { return table->num_record_after_full; } template int osl::container::GeneralSimpleHashTable:: divSize() const { return Table::DIVSIZE; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/alphaBeta2.cc0000644000000000000000000024147312335610142017726 0ustar rootroot/* alphaBeta2.cc */ #include "osl/search/alphaBeta2.h" #ifdef OSL_SMP # include "osl/search/alphaBeta2Parallel.h" #endif #include "osl/search/simpleHashRecord.h" #include "osl/search/simpleHashTable.h" #include "osl/search/dominanceCheck.h" #include "osl/search/moveGenerator.h" #include "osl/search/realizationProbability.h" #include "osl/search/quiescenceSearch2.h" #include "osl/search/realizationProbability.h" #include "osl/search/moveWithComment.h" #include "osl/search/moveStackRejections.h" #include "osl/search/searchMonitor.h" #include "osl/search/usiReporter.h" #include "osl/search/limitToCheckCount.h" #include "osl/eval/see.h" #include "osl/eval/pieceEval.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/checkmate/fixedDepthSearcher.tcc" #include "osl/csa.h" #include "osl/record/ki2.h" #include "osl/record/kanjiCode.h" #include "osl/move_classifier/pawnDropCheckmate.h" #include "osl/move_classifier/check_.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/additionalEffect.h" #include "osl/misc/eucToLang.h" #include "osl/stat/ratio.h" #include "osl/enterKing.h" #include #include #include #ifdef _WIN32 #include #include #endif #define search_assert(x, m) assert((x) || SearchState2::abort(m)) typedef osl::search::RealizationProbability Probabilities_t; #ifdef CHECKMATE_COUNT static size_t root_checkmate = 0, checkmate_before = 0, checkmate_after = 0, count_threatmate = 0, quiesce_checkmate=0; #endif // #define EXPERIMENTAL_QUIESCE /* ------------------------------------------------------------------------- */ void osl::search::AlphaBeta2SharedRoot:: showLastPv(int limit) const { for (int i=last_pv.size()-1; i>=0 && last_pv[i].depth == limit; --i) { std::cerr << last_pv[i].eval << ' '; for (size_t j=0; j osl::CArray osl::search::AlphaBeta2Tree::depth_node_count; #endif template osl::search::AlphaBeta2Tree:: AlphaBeta2Tree(const NumEffectState& s, checkmate_t& c, SimpleHashTable *t, CountRecorder& r) : SearchBase(r, t), SearchState2(s, c), AlphaBeta2Common(s), node_count(0), shared_root(new AlphaBeta2SharedRoot) { #ifdef OSL_SMP for (int i=0; i<4; ++i) { try { shared.reset(new AlphaBeta2Parallel(this)); break; } catch (std::bad_alloc&) { std::cerr << "panic " << i << " allocation of AlphaBeta2Parallel failed\n"; #ifdef _WIN32 std::this_thread::sleep_for(std::chrono::seconds(1)); #else sleep(1); #endif } } #endif } template osl::search::AlphaBeta2Tree:: AlphaBeta2Tree(const AlphaBeta2Tree& src, AlphaBeta2Parallel *) : SearchBase(src), SearchState2(src), SearchTimer(src), AlphaBeta2Common(src), node_count(0), shared(src.shared), shared_root(src.shared_root) { for (PVVector& p: pv) p.clear(); } template osl::search::AlphaBeta2Tree:: ~AlphaBeta2Tree() { for (MoveGenerator *p: generators) dealloc(p); #ifdef OSL_SMP if (shared && shared.use_count() == 1) shared.reset(); #endif } template osl::search::MoveGenerator * osl::search::AlphaBeta2Tree::alloc() { try { return new MoveGenerator; } catch (std::bad_alloc&) { std::cerr << "panic. allocation of MoveGenerator failed\n"; throw TableFull(); // stop search anyway } return 0; } template void osl::search::AlphaBeta2Tree::dealloc(MoveGenerator *p) { delete p; } template osl::search::MoveGenerator& osl::search::AlphaBeta2Tree::makeGenerator() { const size_t cur_depth = this->curDepth(); while (generators.size() <= cur_depth) generators.push_back(0); if (generators[cur_depth] == 0) generators[cur_depth] = alloc(); return *generators[cur_depth]; } /* ------------------------------------------------------------------------- */ /* Methods for alpha beta search */ /* ------------------------------------------------------------------------- */ template template int osl::search::AlphaBeta2Tree:: alphaBetaSearchAfterMove(const MoveLogProb& moved, Window w, bool in_pv) { assert(w.alpha(P) % 2); assert(w.beta(P) % 2); assert(alt(P) == state().turn()); assert(P == moved.player()); assert(eval::notLessThan(P, w.beta(P), w.alpha(P))); // PãŒæŒ‡ã—ãŸå¾Œã§Pã®çŽ‹ã«åˆ©ããŒã‚ã‚‹ => ç›´å‰ã®æ‰‹ãŒéžåˆæ³•手 if (state().inCheck(P)) { return this->minusInfty(P); } this->eval.update(state(), moved.move()); const Player Turn = alt(P); const size_t previous_node_count = nodeCount(); pv[this->curDepth()].clear(); int result; // å±€é¢è¡¨ãŒåˆ©ç”¨ä¸å¯èƒ½ã®å ´åˆã«ã“ã®é–¢æ•°ã¨å­å­«ã§åˆ©ç”¨ã™ã‚‹record // TODO: class ã« max_depth ã ã‘æŒãŸã›ã‚‹ã¹ã std::unique_ptr record_if_unavailable; int alloc_limit = curLimit(), memory1000 = lastMemoryUseRatio1000(); const SimpleHashRecord *parent = hasLastRecord(1) ? lastRecord(1) : 0; const uint64_t table_use = this->table->memoryUse(); if (table_use*8 > OslConfig::memoryUseLimit() && memory1000 > 300 && (root_limit >= 1600 || memory1000 > 500) && ! in_pv && ! state().inCheck() && (!parent||! parent->inCheck())) { if (table_use*6 > OslConfig::memoryUseLimit()) alloc_limit -= std::max(root_limit - 1400, 200); else alloc_limit -= std::max((root_limit - 1400)*3/4, 0); if (memory1000 > 900) alloc_limit -= 400; else if (root_limit >= 1600 && memory1000 > 800) alloc_limit -= 200; else if (root_limit >= 1600 && memory1000 > 700) alloc_limit -= 100; alloc_limit = std::max(0, alloc_limit); } SimpleHashRecord *record = this->table->allocate(currentHash(), alloc_limit); const bool has_table_record = record; if (! record) { record_if_unavailable.reset(new SimpleHashRecord()); record = record_if_unavailable.get(); // memorize ã—ã¦ã¯ã„ã‘ãªã„ } setCurrentRecord(record); record->setInCheck(state().inCheck()); #if 0 // harmful now if (pass_count.loopByBothPass()) { return quiesce(w); } #endif ++node_count; int consumption = moved.logProb(); // hash ã®æ‰‹ãŒãªã„å ´åˆã®iid if (in_pv && (! record->bestMove().isNormal())) { assert(node_type[this->curDepth()] == PvNode); for (int limit = curLimit() - 200+1; limit > consumption+200; limit -= 200) { searchAllMoves(moved.move(), limit, record, w); if (! record->bestMove().validMove()) { Move quiesce_best = record->qrecord.bestMove(); if (quiesce_best.isNormal()) record->setBestMove(quiesce_best, 200); } } } if (! in_pv) { // null window search if (node_type[this->curDepth()] == PvNode) node_type[this->curDepth()] = AllNode; result = searchAllMoves (moved.move(), consumption, record, Window(w.alpha(P), w.alpha(P))); } else { // normal search assert(node_type[this->curDepth()] == PvNode); result = searchAllMoves(moved.move(), consumption, record, w); } bool extended = false; // extension if the alpha value is updated if (eval::betterThan(P, result, w.alpha(P))) { const SimpleHashRecord *parent = lastRecord(1); int consumption_here = consumption+1; const int re_search = 100; if (! w.null() && (! in_pv || consumption > re_search)) consumption_here = std::min(consumption, re_search); else if (consumption > re_search && (record->threatmate().status(P).status() == ThreatmateState::CHECK_AFTER_THREATMATE || record->threatmate().mayHaveCheckmate(P))) consumption_here = re_search; else if (consumption > 150 && ((parent && parent->inCheck()) || state().hasEffectAt(P, state().kingSquare(alt(P))))) consumption_here = 150; if (consumption_here <= consumption) { node_type[this->curDepth()] = PvNode; extended = true; ext_limit.add(consumption - consumption_here); result = searchAllMoves(moved.move(), consumption_here, record, w); } } ext.add(extended); if (has_table_record) record->addNodeCount(nodeCount() - previous_node_count); return result; } template template int osl::search::AlphaBeta2Tree:: searchAllMoves(Move m, int limit_consumption, SimpleHashRecord *record, Window w) { if (! w.null()) assert(node_type[this->curDepth()] == PvNode); const Player P = alt(Turn); this->recorder.tryMove(MoveLogProb(m, limit_consumption), w.alpha(P), curLimit()); subLimit(limit_consumption); const int result = searchAllMoves(record, w); addLimit(limit_consumption); this->recorder.recordValue(MoveLogProb(m, limit_consumption), result,eval::betterThan(P, result, w.alpha(P)), curLimit()); return result; } template template void osl::search::AlphaBeta2Tree:: testThreatmate(SimpleHashRecord *record, bool in_pv) { if ((! record->inCheck()) && (! (record && record->threatmate().isThreatmate(P))) && (in_pv || (this->curDepth() > 0 && this->node_type[this->curDepth()-1] != CutNode)) && tryThreatmate()) { int threatmate_limit = 0; const SimpleHashRecord *parent = lastRecord(1); size_t node_count = record->nodeCount(); if (parent) node_count = std::max(node_count, parent->nodeCount()/32); threatmate_limit = 4500-this->curDepth()*1000; int threatmate_max = 0; if ((node_count >= 1000 && this->recorder.checkmateRatio() < 0.5) || (node_count >= 200 && (state().king8Info(P).libertyCount() == 0 || state().king8Info(P).dropCandidate() || state().king8Info(P).template hasMoveCandidate(state())))) threatmate_max = 100; threatmate_limit = std::max(threatmate_limit, threatmate_max); if (! in_pv) threatmate_limit /= 2; if (root_limit < 800) threatmate_limit /= 2; #ifdef EXPERIMENTAL_QUIESCE if (curLimit() <= 400) threatmate_limit = 1; else if (curLimit() <= 500) threatmate_limit /= 16; else if (curLimit() <= 600) threatmate_limit /= 4; #endif if (curLimit() >= this->table->minimumRecordLimit()) { threatmate_limit = record->qrecord.threatmateNodesLeft(threatmate_limit); } else { threatmate_limit /= 2; // for safety against multiple calls } Move threatmate_move; this->recorder.gotoCheckmateSearch(state(), threatmate_limit); #ifdef CHECKMATE_COUNT size_t count = checkmateSearcher().totalNodeCount(); #endif bool threatmate = isThreatmateState

    (threatmate_limit, threatmate_move); #ifdef CHECKMATE_COUNT count_threatmate += checkmateSearcher().totalNodeCount() - count; #endif if (threatmate_limit > 100) { updateCheckmateCount(); testStop(); } this->recorder.backFromCheckmateSearch(); if (!threatmate && threatmate_limit == 0 && record->qrecord.threatmateNodesLeft(2)) { threatmate = isThreatmateStateShort

    (2, threatmate_move); } if (threatmate) { record->threatmate().setThreatmate(P, threatmate_move); } } } template template bool osl::search::AlphaBeta2Tree:: tryCheckmate(SimpleHashRecord *record, bool in_pv, Move& checkmate_move) { int checkmate_limit = 1; if (! in_pv) { const SimpleHashRecord *parent = lastRecord(1); if (! (record->threatmate().mayHaveCheckmate(alt(P)) || (parent && parent->threatmate().maybeThreatmate(alt(P))))) return false; // simulation only } if (in_pv && root_limit >= 500+this->rootLimitBias()) { int depth = this->curDepth(); if (root_limit >= 700+this->rootLimitBias() && depth <= 3) { if (/*record_memorize &&*/ depth <= 1) checkmate_limit = checkmate::limitToCheckCount(3500); else if (/* record_memorize &&*/ depth == 2) checkmate_limit = 1000; else if (/* record_memorize &&*/ depth == 3) checkmate_limit = 200; } else if (((root_limit - curLimit()) <= 500) || (depth <= 5)) { assert(static_cast(curLimit()) < 4096); checkmate_limit = checkmate::limitToCheckCount(std::max(0,curLimit()-200-this->rootLimitBias())); } const SimpleHashRecord *parent = lastRecord(1); if (record->threatmate().mayHaveCheckmate(alt(P)) || (parent && parent->threatmate().maybeThreatmate(alt(P)))) checkmate_limit += std::max(100, checkmate_limit); else checkmate_limit = std::min((long)record->nodeCount()/2, (long)checkmate_limit); if (root_limit < 800) checkmate_limit /= 2; } if (curLimit() >= this->table->minimumRecordLimit()) { // 詰将棋ã¯ã‚る程度深ã•ãŒå¢—ãˆãŸã¨ãã ã‘呼㶠checkmate_limit = record->qrecord.checkmateNodesLeft(checkmate_limit); if (checkmate_limit <= 0) return false; } else { checkmate_limit /= 2; // for safety against multiple calls } // 相手を詰ã¾ã™ã“ã¨ã‚’考ãˆã‚‹ #ifdef CHECKMATE_COUNT size_t count = checkmateSearcher().totalNodeCount(); #endif this->recorder.gotoCheckmateSearch(state(), checkmate_limit); const bool win = isWinningState

    (checkmate_limit, checkmate_move); if (checkmate_limit > 100) updateCheckmateCount(); this->recorder.backFromCheckmateSearch(); #ifdef CHECKMATE_COUNT checkmate_before += checkmateSearcher().totalNodeCount() - count; #endif if (this->root_limit >= 1600 && checkmate_limit >= 100) this->checkmate_searcher->runGC(this->table->isVerbose(), lastMemoryUseRatio1000()); return win; } template template bool osl::search::AlphaBeta2Tree:: tryCheckmateAgain(SimpleHashRecord *record, Move& checkmate_move, int node_count, int best_value) { int checkmate_limit = 1; if (record->threatmate().maybeThreatmate(P)) { if (EvalTraits

    ::betterThan(this->eval.captureValue(newPtypeO(P,KING)), best_value)) checkmate_limit = node_count / 2; // ã“ã®å±€é¢ã¯å¿…æ­» or 詰将棋以外ã®alt(P)ã®å‹ else checkmate_limit = node_count / 8; checkmate_limit += 100; if (this->recorder.checkmateRatio() < 0.5) { int checkmate_importance_wrt_root = this->recorder.searchNodeCount()/2 + this->recorder.checkmateCount()/8; for (int i=0; icurDepth(); ++i) { if (this->in_pv[i]) checkmate_importance_wrt_root = checkmate_importance_wrt_root*7/8; else checkmate_importance_wrt_root /= 7; } checkmate_limit = std::max(checkmate_limit, checkmate_importance_wrt_root); } } else if (record->threatmate().mayHaveCheckmate(alt(P))) { checkmate_limit = countCheckAfterThreatmate(alt(P),2)*320 + 100; #ifdef MORE_CHECKMATE_IF_CAPTURE_MAJOR if (lastMove().isNormal() && isMajorNonPieceOK(lastMove().capturePtype()) && ! state().hasEffectAt(P, lastMove().to())) checkmate_limit += 20000; #endif } if (curDepth() == 1 && hasLastRecord(1)) { const SimpleHashRecord *parent = lastRecord(1); // root if (parent->inCheck() || parent->threatmate().maybeThreatmate(alt(P))) checkmate_limit = std::max(checkmate_limit, (int)parent->nodeCount()/2+parent->checkmateNodes()); } // adjustment by time int checkmate_afford = this->nodeAffordable(); #ifdef OSL_SMP checkmate_afford *= 1.5 / shared->max_threads; #endif if (checkmate_limit > 100 && checkmate_limit > checkmate_afford) { #ifndef NDEBUG if (checkmate_afford > 0 && toSeconds(this->timeAssigned().standard) >= 10.0) std::cerr << "adjust checkmate near timeover " << checkmate_limit << " => " << checkmate_afford << "\n"; #endif checkmate_limit = checkmate_afford; } if (true /*record_memorize*/) checkmate_limit = record->qrecord.checkmateNodesLeft(checkmate_limit); #ifdef CHECKMATE_COUNT size_t count = checkmateSearcher().totalNodeCount(); #endif this->recorder.gotoCheckmateSearch(state(), checkmate_limit); const bool win = isWinningState

    (checkmate_limit, checkmate_move); if (checkmate_limit > 100) updateCheckmateCount(); this->recorder.backFromCheckmateSearch(); #ifdef CHECKMATE_COUNT checkmate_after += checkmateSearcher().totalNodeCount() - count; #endif if (this->root_limit >= 1600 && checkmate_limit >= 100) this->checkmate_searcher->runGC(this->table->isVerbose(), lastMemoryUseRatio1000()); return win; } template bool osl::search:: AlphaBeta2Tree::tryPass(SimpleHashRecord *record, Player P) const { return ! record->inCheck() && ! record->threatmate().maybeThreatmate(P); } template template const osl::MoveLogProb osl::search:: AlphaBeta2Tree::nextMove() { MoveGenerator& generator = makeGenerator(); SimpleHashRecord *record = lastRecord(); switch (this->move_type[this->curDepth()]) { case common_t::HASH: { if (curLimit() < this->leafLimit()) { this->move_type[this->curDepth()] = common_t::FINISH; break; } this->move_type[this->curDepth()] = common_t::TACTICAL; MoveLogProb best_move_in_table = record->bestMove(); assert(curLimit() > 0); generator.init(curLimit(), record, this->eval, state(), node_type[this->curDepth()] != CutNode, best_move_in_table.move()); if (best_move_in_table.validMove() && this->validTableMove(state(), best_move_in_table, curLimit())) { if (this->in_pv[this->curDepth()] || best_move_in_table.move().capturePtype()) best_move_in_table.setLogProbAtMost(RealizationProbability::TableMove); else best_move_in_table.setLogProbAtMost(state().inCheck() ? 120 : 150); return best_move_in_table; } } // fall through // TODO: 打歩詰ã‚ã¯ã“ã“ã§ãƒã‚§ãƒƒã‚¯ã™ã‚‹ã¨æ—©ãㆠcase common_t::TACTICAL: { MoveLogProb m = generator.nextTacticalMove

    (*this); if (m.validMove()) return m; // fall through this->move_type[this->curDepth()] = common_t::KILLER; this->killers[this->curDepth()].clear(); if ((! record->inCheck()) && ! record->threatmate().maybeThreatmate(P) && (curLimit() >= 300)) { MoveVector killer_moves; // TODO: 効率化 getKillerMoves(killer_moves); for (Move move: killer_moves) { assert(this->killers[this->curDepth()].size() < this->killers[this->curDepth()].capacity()); this->killers[this->curDepth()].push_back(move); } std::reverse(this->killers[this->curDepth()].begin(), this->killers[this->curDepth()].end()); } } case common_t::KILLER: { typename common_t::killer_t& killers = this->killers[this->curDepth()]; if (! killers.empty()) { Move m = killers[killers.size()-1]; killers.pop_back(); return MoveLogProb(m, 300); } // fall through this->move_type[this->curDepth()] = common_t::PASS; } case common_t::PASS: assert(record->inCheck() == state().inCheck()); this->move_type[this->curDepth()] = common_t::ALL; if (tryPass(record, P)) { const int pass_consumption = (curLimit() >= 800) ? 300 : 200; return MoveLogProb(Move::PASS(P), pass_consumption); } // TODO: pass ã®å¾Œã®æœ€å–„手 // fall through case common_t::ALL: { MoveLogProb m = generator.nextMove

    (*this); if (m.validMove()) return m; this->move_type[this->curDepth()] = common_t::FINISH; } default: assert(this->move_type[this->curDepth()] == common_t::FINISH); } return MoveLogProb(); } template template int osl::search::AlphaBeta2Tree:: searchAllMoves(SimpleHashRecord *record, Window w) { #ifndef NDEBUG checkPointSearchAllMoves(); #endif assert(P == state().turn()); search_assert(w.isConsistent(), lastMove()); assert(curLimit() >= 0); assert(hasLastRecord(1)); const SimpleHashRecord *parent = lastRecord(1); #ifndef DONT_USE_CHECKMATE const int node_count_at_beginning = nodeCount(); #endif #if (! defined OSL_USE_RACE_DETECTOR) && (! defined MINIMAL) depth_node_count[this->curDepth()]++; #endif this->move_type[this->curDepth()] = common_t::INITIAL; const bool in_pv = this->in_pv[this->curDepth()] = ! w.null(); // テーブルã«ã‚る値を調ã¹ã‚‹ if (record) { if (in_pv) { if (record->hasLowerBound(SearchTable::HistorySpecialDepth)) { int lower_bound = record->lowerBound(); if (this->isWinValue(P, lower_bound) || (record->hasUpperBound(SearchTable::HistorySpecialDepth) && record->upperBound() == lower_bound)) return lower_bound; } if (record->hasUpperBound(SearchTable::HistorySpecialDepth)) { int upper_bound = record->upperBound(); if (this->isWinValue(alt(P), upper_bound)) return upper_bound; } } else { // ! in_pv int table_value = 0; if (record->hasGreaterLowerBound

    (curLimit(), w.alpha(P), table_value)) { assert(eval::isConsistentValue(table_value)); w.alpha(P) = table_value + EvalTraits

    ::delta; if (EvalTraits

    ::betterThan(table_value, w.beta(P))) { this->recorder.tableHitLowerBound(P, table_value, w.beta(P), curLimit()); return table_value; } } if (record->hasLesserUpperBound

    (curLimit(), w.beta(P), table_value)) { assert(eval::isConsistentValue(table_value)); w.beta(P) = table_value - EvalTraits

    ::delta; if (EvalTraits

    ::betterThan(w.alpha(P), table_value)) { this->recorder.tableHitUpperBound(P, table_value, w.alpha(P), curLimit()); return table_value; } } } Move checkmate_move=Move::INVALID(); if ((!record->inCheck()) && record->qrecord.checkmateNodesLeft(1) && isWinningStateShort

    (2, checkmate_move)) { this->recordWinByCheckmate(P, record, checkmate_move); return this->winByCheckmate(P); } #ifndef DONT_USE_CHECKMATE assert(record); // try simulation or simple checkmate search int additional_limit = 0; // simulation only if (parent && parent->threatmate().maybeThreatmate(alt(P))) { additional_limit = std::max(100, parent->qrecord.threatmateNodes()/8); additional_limit = record->qrecord.checkmateNodesLeft(additional_limit); } this->recorder.gotoCheckmateSearch(state(), additional_limit); const bool win = isWinningState

    (additional_limit, checkmate_move); updateCheckmateCount(); this->recorder.backFromCheckmateSearch(); if (win) { assert(checkmate_move.isValid()); this->recordWinByCheckmate(P, record, checkmate_move); return this->winByCheckmate(P); } #endif } search_assert(w.isConsistent(), lastMove()); const int initial_alpha = w.alpha(P); #ifndef DONT_USE_CHECKMATE // è©°ã‚ã‚を考ãˆã‚‹ testThreatmate

    (record, in_pv); #endif // 探索å‰ã« ThreatmateState を設定 record->qrecord.updateThreatmate(P, (parent ? &(parent->threatmate()) : 0), state().inCheck()); MoveLogProb best_move; // invalidated int best_value = this->minusInfty(P); int tried_moves = 0; int alpha_update = 0; int last_alpha_update = 0; #if (defined OSL_SMP) int last_smp_idle = 0; # if (! defined OSL_SMP_NO_SPLIT_INTERNAL) # if (! defined NDEBUG) bool already_split = false; # endif # endif #endif // the first move MoveLogProb m = nextMove

    (); ++tried_moves; if (! m.validMove() || m.logProb() > curLimit()) { goto move_generation_failure; } #if (defined OSL_SMP) && (! defined OSL_SMP_NO_SPLIT_INTERNAL) int first_move_node; #endif { #if (defined OSL_SMP) && (! defined OSL_SMP_NO_SPLIT_INTERNAL) const int previous_node_count = nodeCount(); #endif assert(eval::betterThan(P, w.alpha(P), best_value)); const int result = alphaBetaSearch

    (m, w, in_pv); if (eval::betterThan(P, result, best_value)) { best_value = result; best_move = m; if (eval::betterThan(P, best_value, w.alpha(P))) { w.alpha(P) = result + EvalTraits

    ::delta;; assert(best_move.validMove()); ++alpha_update; last_alpha_update = 1; if (eval::betterThan(P, result, w.beta(P))) { mpn_cut.add(tried_moves); if (this->move_type[this->curDepth()] >= common_t::ALL) { setKillerMove(best_move.move()); if (best_move.isNormal() && ! best_move.move().isCapture()) { const int d = (curLimit()+200)/100; this->historyTable().add(best_move.move(), d*d); } } assert(best_move.validMove()); assert(! this->isWinValue(alt(P), best_value)); goto register_table; } else { if (in_pv) makePV(m.move()); } } } #if (defined OSL_SMP) && (! defined OSL_SMP_NO_SPLIT_INTERNAL) first_move_node = nodeCount() - previous_node_count; #endif } testStop(); #ifndef DONT_USE_CHECKMATE if (in_pv) { Move checkmate_move; if (tryCheckmate

    (record, in_pv, checkmate_move)) { assert(checkmate_move.isValid()); best_value= this->winByCheckmate(P); this->recordWinByCheckmate(P, record, checkmate_move); return best_value; } } #endif search_assert(w.isConsistent(), lastMove()); if (curLimit() < this->leafLimit()) goto move_generation_failure; while (true) { #if (defined OSL_SMP) && (! defined OSL_SMP_NO_SPLIT_INTERNAL) const bool prefer_split = shared && curLimit() >= shared->split_min_limit && (curLimit() >= 600+this->rootLimitBias() // || (curLimit() >= 400 && this->curDepth() < 2) || (first_move_node >= 30000)); try { if (prefer_split) { int cur_smp_idle; { # ifdef OSL_USE_RACE_DETECTOR std::lock_guard lk(shared->lock_smp); #endif cur_smp_idle = shared->smp_idle; } if (cur_smp_idle > last_smp_idle) { last_smp_idle = cur_smp_idle; assert(! already_split); # if (! defined NDEBUG) already_split = true; # endif if (examineMovesOther

    (w, best_move, best_value, tried_moves, alpha_update, last_alpha_update)) { assert(best_move.validMove()); assert(best_move.player() == P); if (this->move_type[this->curDepth()] >= common_t::ALL) { setKillerMove(best_move.move()); if (best_move.isNormal() && ! best_move.move().isCapture()) { const int d = (curLimit()+200)/100; this->historyTable().add(best_move.move(), d*d); } } mpn_cut.add(tried_moves); goto register_table; } goto all_moves_done; } } } catch(AlphaBeta2ParallelCommon::SplitFailed&) { # if (! defined NDEBUG) already_split = false; # endif // fall through } #endif MoveLogProb m = nextMove

    (); if (! m.validMove()) break; ++tried_moves; assert(eval::betterThan(P, w.alpha(P), best_value)); const int result = alphaBetaSearch

    (m, w, in_pv && ! best_move.validMove()); if (eval::betterThan(P, result, best_value)) { best_value = result; best_move = m; if (eval::betterThan(P, best_value, w.alpha(P))) { w.alpha(P) = result + EvalTraits

    ::delta;; assert(best_move.validMove()); ++alpha_update; last_alpha_update = tried_moves; if (eval::betterThan(P, result, w.beta(P))) { assert(best_move.validMove()); if (this->move_type[this->curDepth()] >= common_t::ALL) { setKillerMove(best_move.move()); if (best_move.isNormal() && ! best_move.move().isCapture()) { const int d = (curLimit()+200)/100; this->historyTable().add(best_move.move(), d*d); } } mpn_cut.add(tried_moves); goto register_table; } else { if (in_pv) makePV(m.move()); } } } } #if (defined OSL_SMP) && (! defined OSL_SMP_NO_SPLIT_INTERNAL) all_moves_done: #endif if (tried_moves == 1 && tryPass(record, P)) { // goto quiescence search if tried move is only null move goto move_generation_failure; } mpn.add(tried_moves); if (alpha_update) { this->alpha_update.add(alpha_update); this->last_alpha_update.add(last_alpha_update); } // å®£è¨€å‹ if (((this->curDepth() % 2) == 0 || OslConfig::usiMode()) && EnterKing::canDeclareWin

    (state())) { best_value = this->brinkmatePenalty(alt(P), std::max(1,16-this->curDepth())*256) + this->eval.value(); record->setAbsoluteValue(Move::DeclareWin(), best_value, SearchTable::CheckmateSpecialDepth); return best_value; } if (record) { // ã‚‚ã†ä¸€åº¦ï¼Œç›¸æ‰‹ã‚’è©°ã¾ã™ã“ã¨ã‚’考ãˆã‚‹ #ifndef DONT_USE_CHECKMATE Move checkmate_move=Move::INVALID(); if (tryCheckmateAgain

    (record, checkmate_move, nodeCount() - node_count_at_beginning, best_value)) { assert(checkmate_move.isValid()); best_value= this->winByCheckmate(P); this->recordWinByCheckmate(P, record, checkmate_move); return best_value; } #endif } register_table: assert(best_value == this->minusInfty(P) || best_move.validMove()); assert(eval::isConsistentValue(best_value)); if (this->isWinValue(alt(P), best_value)) { // TODO: ç›´å‰ã®ç€æ‰‹ãŒ(ã‚„ã‘ãã)王手ã®é€£ç¶šã ã£ãŸå ´åˆ // å¿…æ­»ã§ã¯ãªãã¦è©°æ‰±ã„ã®æ–¹ãŒè‰¯ã„å¯èƒ½æ€§ã¯ã‚ã‚‹ best_value = this->brinkmatePenalty(P, std::max(1,16-this->curDepth())*256) + this->eval.value(); // (ã“ã®æ·±ã•ã§ã¯)上é™==ä¸‹é™ record->setAbsoluteValue(best_move, best_value, curLimit()); return best_value; } else if (EvalTraits

    ::betterThan(w.alpha(P), initial_alpha)) { if (best_move.validMove()) { assert(best_value % 2 == 0); record->setLowerBound(P, curLimit(), best_move, best_value); } } if (EvalTraits

    ::betterThan(w.beta(P), best_value)) { if (best_move.validMove()) record->setUpperBound(P, curLimit(), best_move, best_value); } return best_value; move_generation_failure: pv[this->curDepth()].clear(); // 手を生æˆã§ããªã‹ã£ãŸ // limit ㌠200 未満ã ã£ãŸå ´åˆã¨ï¼Œä»¥ä¸Šã ã£ãŸãŒ move generator ㌠limit ä»¥ä¸‹ã®æ‰‹ã‚’生æˆã§ããªã‹ã£ãŸå ´åˆã“ã“ã«æ¥ã‚‹ best_value = quiesce

    (w); if (record) { if (EvalTraits

    ::betterThan(best_value, initial_alpha)) { if (EvalTraits

    ::betterThan(w.beta(P), best_value)) { record->setAbsoluteValue(MoveLogProb(), best_value, curLimit()); } else { record->setLowerBound(P, curLimit(), MoveLogProb(), best_value); } } else { assert(EvalTraits

    ::betterThan(w.beta(P), best_value)); record->setUpperBound(P, curLimit(), MoveLogProb(), best_value); } } assert(eval::isConsistentValue(best_value)); return best_value; } template template int osl::search::AlphaBeta2Tree:: quiesce(Window w) { #ifdef EXPERIMENTAL_QUIESCE return quiesceExp

    (w); #else return quiesceStable

    (w); #endif } template template int osl::search::AlphaBeta2Tree:: quiesceStable(Window w) { testStop(); initPV(); typedef QuiescenceSearch2 qsearcher_t; qsearcher_t qs(*this, *this->table); Move last_move = lastMove(); if (last_move.isInvalid()) last_move = Move::PASS(alt(P)); assert(w.alpha(P) % 2); assert(w.beta(P) % 2); #ifdef CHECKMATE_COUNT size_t count = checkmateSearcher().totalNodeCount(); #endif const int result = qs.template search

    (w.alpha(P), w.beta(P), this->eval, last_move, 4); node_count += qs.nodeCount(); this->recorder.addQuiescenceCount(qs.nodeCount()); #ifdef CHECKMATE_COUNT quiesce_checkmate += checkmateSearcher().totalNodeCount() - count; #endif assert(result % 2 == 0); return result; } template template int osl::search::AlphaBeta2Tree:: quiesceExp(Window w) { testStop(); SimpleHashRecord *record = lastRecord(); assert(record); Move best_move; const int qdepth = 4; const int previous_node_count = nodeCount(); int result = quiesceRoot

    (w, qdepth, best_move, record->threatmate()); const size_t qnode = nodeCount() - previous_node_count; this->recorder.addQuiescenceCount(qnode); record->qrecord.setLowerBound(qdepth, result, best_move); return result; } template template struct osl::search::AlphaBeta2Tree::NextQMove { AlphaBeta2Tree *searcher; Window window; const int depth; int *result; DualThreatmateState threatmate; NextQMove(AlphaBeta2Tree *s, Window w, int d, int *r, DualThreatmateState t) : searcher(s), window(w), depth(d), result(r), threatmate(t) { } void operator()(Square /*last_to*/) { searcher->eval.update(searcher->state(), searcher->lastMove()); *result = searcher->quiesce

    (window, depth, threatmate); } }; template template bool osl::search::AlphaBeta2Tree:: quiesceWithMove(Move move, Window& w, int depth_left, Move& best_move, int& best_value, const DualThreatmateState& threatmate) { // TODO: futility margin const bool in_pv = ! w.null(); int result; typedef NextQMove next_t; next_t helper(this, w, depth_left, &result, threatmate); const HashKey new_hash = currentHash().newHashWithMove(move); const eval_t old_eval = this->eval; doUndoMoveOrPass(new_hash, move, helper); this->eval = old_eval; if (eval::betterThan(P, result, best_value)) { best_value = result; best_move = move; if (eval::betterThan(P, best_value, w.alpha(P))) { w.alpha(P) = result + EvalTraits

    ::delta; if (in_pv) makePV(best_move); if (eval::betterThan(P, result, w.beta(P))) { return true; } } } return false; } template template int osl::search::AlphaBeta2Tree:: quiesceRoot(Window w, int depth_left, Move& best_move, DualThreatmateState threatmate) { assert(! state().inCheck(alt(P))); initPV(); // depth_node_count_quiesce[this->curDepth()]++; // ++node_count; SimpleHashRecord& record = *lastRecord(); assert(record.inCheck() == state().inCheck()); assert(depth_left > 0); int best_value = this->minusInfty(P); // stand pat if (! record.inCheck()) { if (! threatmate.maybeThreatmate(P)) { best_value = this->eval.value(); } else { const int value = this->eval.value() + this->threatmatePenalty(P); best_value = EvalTraits

    ::max(best_value, value); } best_move = Move::PASS(P); if (EvalTraits

    ::betterThan(best_value, w.alpha(P))) { if (EvalTraits

    ::betterThan(best_value, w.beta(P))) return best_value; w.alpha(P) = best_value + EvalTraits

    ::delta; } } Move prev_best = record.qrecord.bestMove(); MoveGenerator& generator = makeGenerator(); generator.init(200, &record, this->eval, state(), w.alpha(P) == w.beta(P), prev_best, true); int tried_moves = 0; // previous 最善手を試㙠if (prev_best.isNormal()) { ++tried_moves; if (quiesceWithMove

    (prev_best, w, depth_left-1, best_move, best_value, threatmate)) goto finish; } // captures or king escape for (MoveLogProb m = generator.nextTacticalMove

    (*this); m.validMove(); m = generator.nextTacticalMove

    (*this)) { ++tried_moves; if (quiesceWithMove

    (m.move(), w, depth_left-1, best_move, best_value, threatmate)) goto finish; } for (MoveLogProb m = generator.nextMove

    (*this); m.validMove(); m = generator.nextMove

    (*this)) { ++tried_moves; if (quiesceWithMove

    (m.move(), w, depth_left-1, best_move, best_value, threatmate)) goto finish; } // pawn drop foul? if (record.inCheck()) { if (tried_moves == 0) { if (lastMove().isNormal() && lastMove().ptype() == PAWN && lastMove().isDrop()) return this->winByFoul(P); return this->winByCheckmate(alt(P)); } goto finish; } finish: return best_value; } template template int osl::search::AlphaBeta2Tree:: quiesce(Window w, int depth_left, DualThreatmateState parent_threatmate) { if (state().inCheck(alt(P))) { return this->minusInfty(alt(P)); } initPV(); #ifndef MINIMAL depth_node_count_quiesce[this->curDepth()]++; #endif ++node_count; SimpleHashRecord record; record.setInCheck(state().inCheck()); DualThreatmateState threatmate; threatmate.updateInLock(P, &parent_threatmate, record.inCheck()); int best_value = this->minusInfty(P); // TODO: 玉ã®å›žã‚Šã®takebackå»¶é•· if (depth_left <= 0) { if (record.inCheck()) { if (lastMove().isCapture()) depth_left +=2; else depth_left = 0; } else if (threatmate.maybeThreatmate(P)) { if (threatmate.mayHaveCheckmate(alt(P))) { Move checkmate_move; bool win = isWinningState

    (10, checkmate_move); if (win) return this->winByCheckmate(P); } return this->eval.value() + this->threatmatePenalty(P); } else { if (threatmate.mayHaveCheckmate(alt(P))) return this->eval.value() + this->threatmatePenalty(alt(P)); if (ImmediateCheckmate::hasCheckmateMove

    (state())) return this->winByCheckmate(P); if (ImmediateCheckmate::hasCheckmateMove(state())) return this->eval.value() + this->threatmatePenalty(P); return this->eval.value(); } } if (! record.inCheck()) { if (ImmediateCheckmate::hasCheckmateMove

    (state())) { return this->winByCheckmate(P); } } if (threatmate.mayHaveCheckmate(alt(P))) { Move checkmate_move; bool win = isWinningState

    (10, checkmate_move); if (win) return this->winByCheckmate(P); } MoveGenerator& generator = makeGenerator(); generator.init(200, &record, this->eval, state(), w.alpha(P) == w.beta(P), Move(), true); int tried_moves = 0; Move best_move; // stand pat if (! record.inCheck()) { if (! threatmate.maybeThreatmate(P)) { best_value = this->eval.value(); } else { const int value = this->eval.value() + this->threatmatePenalty(P); best_value = EvalTraits

    ::max(best_value, value); } best_move = Move::PASS(P); if (EvalTraits

    ::betterThan(best_value, w.alpha(P))) { if (EvalTraits

    ::betterThan(best_value, w.beta(P))) return best_value; w.alpha(P) = best_value + EvalTraits

    ::delta; } } // captures or king escape for (MoveLogProb m = generator.nextTacticalMove

    (*this); m.validMove(); m = generator.nextTacticalMove

    (*this)) { ++tried_moves; if (quiesceWithMove

    (m.move(), w, depth_left-1, best_move, best_value, threatmate)) goto finish; } for (MoveLogProb m = generator.nextMove

    (*this); m.validMove(); m = generator.nextMove

    (*this)) { ++tried_moves; if (quiesceWithMove

    (m.move(), w, depth_left-1, best_move, best_value, threatmate)) goto finish; } // pawn drop foul? if (record.inCheck()) { if (tried_moves == 0) { if (lastMove().ptype() == PAWN && lastMove().isDrop()) return this->winByFoul(P); return this->winByCheckmate(alt(P)); } goto finish; } finish: return best_value; } template void osl::search::AlphaBeta2Tree::updateCheckmateCount() { #ifdef OSL_SMP if (shared) { const size_t new_count = shared->checkmateCount(); this->recorder.setCheckmateCount(new_count); return; } #endif this->recorder.setCheckmateCount (checkmateSearcher().totalNodeCount()); } template int osl::search::AlphaBeta2Tree:: rootAlpha(Player P, int last_value, Progress16 progress) { int pawns = 3; if (eval::betterThan(P, last_value, eval_t::captureValue(newPtypeO(alt(P),KING)))) { pawns = 10; } else if (progress.value() <= 1) { pawns = 3; } else if (progress.value() <= 7) { pawns = 4; } else if (progress.value() <= 9) { pawns = 5; } else if (progress.value() <= 10) { pawns = 6; } else { pawns = 7; } const int width = eval_t::captureValue(newPtypeO(alt(P),PAWN))*pawns/2; return last_value - width - eval::delta(P); } template int osl::search::AlphaBeta2Tree:: stableThreshold(Player P, int last_value) { int pawns = 3; if (eval::betterThan(P, last_value, eval_t::captureValue(newPtypeO(alt(P),KING)))) pawns = 10; else if (eval::betterThan(P, eval_t::captureValue(newPtypeO(alt(P),PAWN))*2, last_value) && eval::betterThan(P, last_value, eval_t::captureValue(newPtypeO(P,PAWN))*2)) pawns = 2; const int width = eval_t::captureValue(newPtypeO(alt(P),PAWN))*pawns/2; return last_value - width - eval::delta(P); } namespace osl { namespace { void find_threatmate(const SimpleHashTable& table, HashKey key, const search::SearchState2::PVVector& pv, CArray& threatmate) { for (size_t i=0; ithreatmate().isThreatmate(key.turn()); } } } } template void osl::search::AlphaBeta2Tree:: updateRootPV(Player P, std::ostream& os, int result, Move m) { std::lock_guard lk(OslConfig::lock_io); this->makePV(m); const int last_root_value = shared_root->root_values_for_iteration.size() ? shared_root->root_values_for_iteration.back() : 0; const int threshold = stableThreshold(P, last_root_value); bool new_stable = eval::betterThan(P, result, threshold); shared_root->last_root_value_update = result; if (new_stable && m != shared_root->last_root_move && (See::see(state(), m) < -eval::Ptype_Eval_Table.value(KNIGHT)*2 || eval::betterThan(P, result, eval_t::captureValue(newPtypeO(alt(P),KING))))) { new_stable = false; } if (new_stable && shared_root->root_values_for_iteration.size() > 1) { const int last_root_value2 = shared_root->root_values_for_iteration[shared_root->root_values_for_iteration.size()-2]; const int threshold2 = stableThreshold(P, last_root_value2); if (eval::betterThan(P, threshold2, result) && eval::betterThan(P, last_root_value2, last_root_value)) new_stable = false; } this->shared_root->last_pv.push_back(RootPV(root_limit, pv[0], result)); this->setStable(new_stable); #ifndef GPSONE if (this->hasMonitor() && !this->prediction_for_speculative_search) { const double scale = OslConfig::usiOutputPawnValue()*2.0 / eval_t::captureValue(newPtypeO(alt(P),PAWN)); CArray threatmate = {{ 0 }}; find_threatmate(*this->table, currentHash(), pv[0], threatmate); for (const auto& monitor: this->monitors()) monitor->showPV(root_limit/200, this->recorder.allNodeCount(), this->elapsed(), static_cast(result*scale), m, &*pv[0].begin(), &*pv[0].end(), &threatmate[0], &threatmate[0]+pv[0].size()); } #endif if (this->table->isVerbose()) { showPV(os, result, m, new_stable ? ' ' : '*'); } } template void osl::search::AlphaBeta2Tree:: addMultiPV(Player P, int result, Move m) { std::lock_guard lk(OslConfig::lock_io); this->makePV(m); this->shared_root->last_pv.push_back(RootPV(root_limit, pv[0], result)); std::swap(*this->shared_root->last_pv.rbegin(), *(this->shared_root->last_pv.rbegin()+1)); if (this->hasMonitor() && !this->prediction_for_speculative_search) { const double scale = OslConfig::usiOutputPawnValue()*2.0 / eval_t::captureValue(newPtypeO(alt(P),PAWN)); CArray threatmate = {{ 0 }}; find_threatmate(*this->table, currentHash(), pv[0], threatmate); for (const auto& monitor:this->monitors()) monitor->showPV(root_limit/200, this->recorder.allNodeCount(), this->elapsed(), static_cast(result*scale), m, &*pv[0].begin(), &*pv[0].end(), &threatmate[0], &threatmate[0]+pv[0].size()); } if (this->table->isVerbose()) { showPV(std::cerr, result, m, '&'); } } template void osl::search::AlphaBeta2Tree:: showFailLow(int result, Move m) const { if (this->root_ignore_moves) std::cerr << "[" << this->root_ignore_moves->size() << "] "; std::cerr << " <" << std::setfill(' ') << std::setw(5) << static_cast(result*200.0/this->eval.captureValue(newPtypeO(WHITE,PAWN))) << " " << csa::show(m) << "\n"; } template void osl::search::AlphaBeta2Tree:: showPV(std::ostream& os, int result, Move m, char stable_char) const { assert(m.isNormal()); // do not pass at root if (this->root_ignore_moves) os << "[" << this->root_ignore_moves->size() << "] "; os << stable_char; os << " " << std::setfill(' ') << std::setw(5) << static_cast(result*200.0/this->eval.captureValue(newPtypeO(WHITE,PAWN))) << " "; for (Move m: pv[0]) { os << csa::show(m); } const double elapsed = this->elapsed(); if (elapsed > 1.0) os << " (" << elapsed << "s, " << OslConfig::memoryUseRatio()*100.0 << "%)"; os << std::endl; #ifndef MINIMAL #ifndef _WIN32 if (! OslConfig::usiMode()) { NumEffectState state = this->state(); std::string str; str.reserve(200); str = " "; for (size_t i=0; itable->find(HashKey(state)); if (record && record->threatmate().isThreatmate(state.turn())) str += "(" K_TSUMERO ")"; } std::string converted = misc::eucToLang(str); if (! converted.empty()) os << converted << std::endl; } #endif #endif #ifdef DEBUG_PV NumEffectState s = state(); for (size_t i=0; i template struct osl::search::AlphaBeta2Tree::NextMove { AlphaBeta2Tree *searcher; const MoveLogProb& moved; Window window; int *result; bool in_pv; NextMove(AlphaBeta2Tree *s, const MoveLogProb& md, Window w, int *r, bool p) : searcher(s), moved(md), window(w), result(r), in_pv(p) { assert(P == md.player()); } void operator()(Square /*last_to*/) { #ifndef NDEBUG const int cur_limit = searcher->curLimit(); #endif *result = searcher->alphaBetaSearchAfterMove

    (moved, window, in_pv); assert(cur_limit == searcher->curLimit() || searcher->SearchState2Core::abort()); } }; template template int osl::search::AlphaBeta2Tree:: alphaBetaSearch(const MoveLogProb& search_move, Window w, bool in_pv) { assert(w.alpha(P) % 2); assert(w.beta(P) % 2); const Move move = search_move.move(); assert(P == move.player()); assert(P == state().turn()); assert(eval::notLessThan(P, w.beta(P), w.alpha(P))); testStop(); pv[curDepth()+1].clear(); // TODO: more efficient way to find foul if (! move.isPass() ){ if(MoveStackRejections::probe

    (state(),history(),curDepth(),move,w.alpha(P),repetitionCounter().checkCount(alt(P)))){ return this->winByLoop(alt(P)); } if (move_classifier::MoveAdaptor > ::isMember(state(), move)) return this->winByFoul(alt(P)); } const HashKey new_hash = currentHash().newHashWithMove(move); assert(P == move.player()); if (move.isPass()) this->pass_count.inc(P); // åƒæ—¥æ‰‹ç¢ºèª if (! this->pass_count.loopByBothPass()) { const Sennichite next_sennichite = repetition_counter.isAlmostSennichite(new_hash); if (next_sennichite.isDraw()) return this->drawValue(); if (next_sennichite.hasWinner()) return this->winByFoul(next_sennichite.winner()); assert(next_sennichite.isNormal()); } if (! move.isPass()) { // å„ªè¶Šé–¢ä¿‚ç¢ºèª const DominanceCheck::Result has_dominance = DominanceCheck::detect(repetition_counter.history(), new_hash); if (has_dominance == DominanceCheck::LOSE) return this->winByLoop(alt(P)); if (has_dominance == DominanceCheck::WIN) return this->winByLoop(P); // 連続王手駒æ¨ã¦ if (! move.isCapture()) { const int sacrifice_count = countSacrificeCheck2(this->curDepth()); if (sacrifice_count == 2) { // 3å›žç›®ã¯æŒ‡ã•ãªã„ const Square to = move.to(); int offence = state().countEffect(P, to) + (move.isDrop() ? 1 : 0); const int deffense = state().hasEffectAt(alt(P), to); // max1 if (offence <= deffense) offence += AdditionalEffect::count2(state(), to, P); if (offence <= deffense) { return this->winByLoop(alt(P)); } } } } // 探索 int result; NextMove

    helper(this, search_move, w, &result, in_pv); this->recorder.addNodeCount(); const eval_t old_eval = this->eval; doUndoMoveOrPass >(new_hash, move, helper); this->eval = old_eval; if (move.isPass()) this->pass_count.dec(P); return result; } template template void osl::search::AlphaBeta2Tree:: examineMovesRoot(const MoveLogProbVector& moves, size_t i, Window window, MoveLogProb& best_move, int& best_value) { for (;i 8 && moves.size() > i+1) { int smp_idle; { # ifdef OSL_USE_RACE_DETECTOR std::lock_guard lk(shared->lock_smp); # endif smp_idle = shared->smp_idle; } if (smp_idle) { try { examineMovesRootPar

    (moves, i, window, best_move, best_value); break; } catch (AlphaBeta2ParallelCommon::SplitFailed&) { } } } #endif const MoveLogProb& m = moves[i]; #ifndef GPSONE if (this->elapsed() > 1.0) { std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->rootMove(m.move()); } if (this->multi_pv) { int width = this->multi_pv*this->eval.captureValue(newPtypeO(P, PAWN))/200; if (width % 2 == 0) width -= EvalTraits

    ::delta; window.alpha(P) = best_value + width; } #endif const int result = alphaBetaSearch

    (m, window, false); if (eval::betterThan(P, result, best_value)) { window.alpha(P) = result + EvalTraits

    ::delta; best_move = m; best_value = result; updateRootPV(P, std::cerr, result, m.move()); if (eval::betterThan(P, result, window.beta(P))) { assert(! this->isWinValue(alt(P), result)); break; } } #ifndef GPSONE else if (this->multi_pv && eval::betterThan(P, result, window.alpha(P))) { addMultiPV(P, result, m.move()); } #endif if (this->root_limit >= 1600) this->checkmate_searcher->runGC(this->table->isVerbose(), lastMemoryUseRatio1000()); } } /* ------------------------------------------------------------------------- */ template osl::search::AlphaBeta2:: AlphaBeta2(const NumEffectState& s, checkmate_t& c, SimpleHashTable *t, CountRecorder& r) : AlphaBeta2Tree(s, c, t, r) { MoveGenerator::initOnce(); } template osl::search::AlphaBeta2:: ~AlphaBeta2() { } template typename osl::search::AlphaBeta2::PVCheckmateStatus osl::search::AlphaBeta2:: findCheckmateInPV(int verify_node, CArray& king_in_threat) { king_in_threat.fill(false); if (this->shared_root->last_pv.empty()) return PVStable; const SearchState2::PVVector& pv = this->shared_root->last_pv.back().pv; NumEffectState state = this->state(); PathEncoding path = this->path(); PVCheckmateStatus found = PVStable; SearchState2::checkmate_t *checkmate_searcher = this->checkmate_searcher; if (this->node_count < verify_node*pv.size()) verify_node = this->node_count/(pv.size()+1)/4; for (size_t i=0; icheckmate_searcher->runGC(this->table->isVerbose(), this->lastMemoryUseRatio1000()); assert(pv[i].isPass() || state.isValidMove(pv[i])); if (! pv[i].isPass() && ! state.isValidMove(pv[i])) { std::cerr << "pv error " << pv[i] << "\n" << state; return PVStable; } state.makeMove(pv[i]); path.pushMove(pv[i]); if (state.inCheck()) continue; const HashKey key(state); SimpleHashRecord *record = this->table->allocate(key, 2000); if (! record) break; Move checkmate_move, threatmate_move; const bool old_win = this->isWinningState (*checkmate_searcher, state, key, path, 0, checkmate_move, pv[i]); if (! old_win) { const bool new_win = this->isWinningState (*checkmate_searcher, state, key, path, verify_node, checkmate_move, pv[i], true); if (new_win) { found = PVCheckmate; this->recordWinByCheckmate(state.turn(), record, checkmate_move); king_in_threat[alt(state.turn())] = true; if (this->table->isVerbose()) std::cerr << " pv checkmate " << csa::show(pv[i]) << "(" << i << ")\n"; } } state.changeTurn(); const Player T = state.turn(); const bool old_threatmate_in_record = record->threatmate().isThreatmate(alt(T)); const bool old_threatmate = this->isWinningState (*checkmate_searcher, state, HashKey(state), PathEncoding(T), 1, threatmate_move, Move::PASS(alt(T))); if (! old_threatmate) { const bool new_threatmate = this->isWinningState (*checkmate_searcher, state, HashKey(state), PathEncoding(T), verify_node, threatmate_move, Move::PASS(alt(T)), this->root_limit >= 1000 + this->rootLimitBias()); if (new_threatmate) { record->threatmate().setThreatmate(alt(T), threatmate_move); king_in_threat[alt(T)] = true; if (! old_threatmate_in_record) found = PVThreatmate; else if (found == PVStable) found = PVThreatmateNotRecord; if (this->table->isVerbose()) std::cerr << " pv threatmate " << csa::show(pv[i]) << "(" << i << ")\n"; } } state.changeTurn(); } this->checkmate_searcher->runGC(this->table->isVerbose(), this->lastMemoryUseRatio1000()); this->updateCheckmateCount(); return found; } template int osl::search::AlphaBeta2:: alphaBetaSearchRoot(MoveLogProb& best_move, int limit) { const Player Turn = this->state().turn(); Window root_window = this->fullWindow(Turn); return alphaBetaSearchRoot(root_window, best_move, limit); } template osl::Move osl::search::AlphaBeta2:: computeBestMoveIteratively(int limit, const int step, int initial_limit, size_t node_limit, const TimeAssigned& assign, MoveWithComment *additional_info) { this->setStartTime(clock::now()); this->setTimeAssign(assign); if (this->table->verboseLevel() > 2) { const time_t now = time(0); char ctime_buf[64]; std::cerr << "AlphaBeta2 " << ctime_r(&now, ctime_buf); } if (this->table->isVerbose()) { std::cerr << " time assign/max " << toSeconds(this->timeAssigned().standard) << "/" << toSeconds(this->timeAssigned().max) << " multipv " << this->multi_pv << " iteration " << this->nextIterationCoefficient() << " mem " << std::fixed << std::setprecision(2) << OslConfig::memoryUseRatio()*100.0 << "%"; std::cerr << "\n"; } initial_limit = std::min(initial_limit, limit); this->recorder.resetNodeCount(); double last_iteration_consumed = 0; double total_consumed = 0; int limit_iterative = initial_limit; Move last_best_move = Move::INVALID(); this->shared_root->last_pv.clear(); #ifdef OSL_SMP # ifdef SPLIT_STAT if (this->shared) { this->shared->parallel_splits = 0; this->shared->cancelled_splits.setValue(0); this->shared->parallel_abort.setValue(0); } # endif #endif try { if (this->table->verboseLevel() > 1) { MoveVector moves; this->state().generateLegal(moves); for (Move move: moves) { HashKey key = this->currentHash().newHashWithMove(move); const SimpleHashRecord *record = this->table->find(key); if (! record || record->lowerLimit() < SearchTable::HistorySpecialDepth) continue; std::cerr << "prebound value " << csa::show(move) << " " << record->lowerBound() << " " << record->upperBound() << "\n"; } } MoveLogProb search_move; this->shared_root->root_values.push_back(alphaBetaSearchRoot(search_move, 0)); this->shared_root->last_root_move = search_move.move(); this->shared_root->best_move_for_iteration.push_back(search_move.move()); if (this->table->verboseLevel() > 1) std::cerr << "=> quiesce " << csa::show(search_move.move()) << "\n"; while (limit_iterative < limit && ! this->stopping()) { if (this->table->verboseLevel() > 1) std::cerr << "=> iteration " << limit_iterative << " (" << last_iteration_consumed << ", " << total_consumed << " sec)" << " mem " << OslConfig::memoryUseRatio()*100.0 << "%\n"; this->recorder.startSearch(limit_iterative); const int previous_node_count = this->nodeCount(); try { for (int i=0; i<8; ++i) { this->shared_root->root_values.push_back(alphaBetaSearchRoot(search_move, limit_iterative+this->rootLimitBias())); this->shared_root->last_root_move = search_move.move(); last_best_move = search_move.move(); if (this->stopping()) break; PVCheckmateStatus need_more_verify = PVStable; CArray king_in_threat; int verify_node_limit = limit <= (1200 + this->rootLimitBias()) ? 10000 : 40000; if (toSeconds(this->timeAssigned().standard) < 20) verify_node_limit /= 4; #ifdef DONT_USE_CHECKMATE break; #endif need_more_verify = findCheckmateInPV(verify_node_limit, king_in_threat); if (need_more_verify == PVStable || (i > 0 && need_more_verify == PVThreatmateNotRecord)) break; if (this->isStableNow()) this->setStable(i > 0 && king_in_threat[this->state().turn()] == false); } } catch (...) { last_iteration_consumed = this->elapsed() - total_consumed; total_consumed += last_iteration_consumed; this->updateCheckmateCount(); this->recorder.finishSearch(search_move.move(), total_consumed, this->table->verboseLevel()); throw; } last_iteration_consumed = this->elapsed() - total_consumed; total_consumed += last_iteration_consumed; this->shared_root->best_move_for_iteration.push_back(last_best_move); this->shared_root->root_values_for_iteration.push_back (this->shared_root->root_values.back()); this->updateCheckmateCount(); if (this->table->verboseLevel() > 2) { std::cerr << "<= " << csa::show(search_move.move()); std::cerr << std::setprecision(4) << " mpn " << this->mpn.average() << " cut " << this->mpn_cut.average() << " alpha " << this->alpha_update.average() << " last " << this->last_alpha_update.average() << " ext " << 100.0*this->ext.average() << "%" << " ext_limit " << this->ext_limit.average() << " mem " << OslConfig::memoryUseRatio()*100.0; #ifdef OSL_SMP # ifdef SPLIT_STAT if (this->shared) { std::cerr << " split " << this->shared->parallel_splits << " cancel " << this->shared->cancelled_splits.value() << " abort " << this->shared->parallel_abort.value(); } # endif #endif std::cerr << "\n"; } bool time_over = false; if (this->hasSchedule()) { const double elapsed = this->elapsed(); const double current_time_left = toSeconds(this->timeAssigned().standard) - elapsed; double coef = this->nextIterationCoefficient(); if (! this->isStableNow()) coef = std::min(0.5, coef); else { const int same_best_moves = this->shared_root->sameBestMoves(); if (same_best_moves == 0) { if (this->table->verboseLevel() > 2 && coef > 0.75) std::cerr << "info: " << coef << " -> 0.75 by bestmove update\n"; coef = std::min(0.75, coef); } else if (same_best_moves >= 3) { const Move last_move = this->lastMove(); if (last_move.isNormal() && last_best_move.isNormal() && last_move.to() == last_best_move.to() && isMajor(last_best_move.capturePtype()) && isMajorNonPieceOK(last_move.capturePtype())) { if (coef < 5.0 && this->table->verboseLevel() > 2) std::cerr << "info: " << coef << " -> 5.0 by takeback major piece\n"; coef = std::max(5.0, coef); } } } if (current_time_left < last_iteration_consumed * coef) time_over = true; if (! time_over) { SimpleHashRecord *record = this->table->find(this->currentHash()); if (record) { record->addNodeCount(this->nodeCount() - previous_node_count); } } } bool node_limit_over = (this->recorder.nodeCount() *4 > node_limit); this->recorder.finishSearch(search_move.move(), total_consumed, (time_over || node_limit_over) && this->table->verboseLevel()); if (time_over || node_limit_over || this->stopping()) { if (this->table->isVerbose()) { const char *reason = "other reason"; if (this->stopReason() == SearchTimerCommon::NoMoreMemory) reason = "memory full"; else if (time_over || this->stopReason() == SearchTimerCommon::NoMoreTime) reason = "time"; else if (node_limit_over) reason = "node count"; else if (this->stopReason() == SearchTimerCommon::StopByOutside) reason = "outside"; std::cerr << "iteration stop at " << limit_iterative << " by " << reason << "\n"; } goto finish; } this->testStop(); limit_iterative += step; } if (this->table->verboseLevel() > 1) std::cerr << "=> final iteration " << limit_iterative << " (" << last_iteration_consumed << ", " << total_consumed << " sec)" << " mem " << OslConfig::memoryUseRatio()*100.0 << "%\n"; while (true) { this->recorder.startSearch(limit); try { for (int i=0; i<8; ++i) { this->shared_root->root_values.push_back(alphaBetaSearchRoot(search_move, limit+this->rootLimitBias())); this->shared_root->last_root_move = search_move.move(); last_best_move = search_move.move(); if (this->stopping()) break; PVCheckmateStatus need_more_verify = PVStable; CArray king_in_threat; int verify_node_limit = limit <= (1200 + this->rootLimitBias()) ? 10000 : 40000; if (toSeconds(this->timeAssigned().standard) < 20) verify_node_limit /= 4; #ifdef DONT_USE_CHECKMATE break; #endif need_more_verify = findCheckmateInPV(verify_node_limit, king_in_threat); if (need_more_verify == PVStable || (i > 0 && need_more_verify == PVThreatmateNotRecord)) break; if (this->isStableNow()) this->setStable(i > 0 && king_in_threat[this->state().turn()] == false); } } catch (...) { last_iteration_consumed = this->elapsed() - total_consumed; total_consumed += last_iteration_consumed; this->updateCheckmateCount(); this->recorder.finishSearch(search_move.move(), total_consumed, this->table->verboseLevel()); throw; } last_iteration_consumed = this->elapsed() - total_consumed; total_consumed += last_iteration_consumed; this->updateCheckmateCount(); this->recorder.finishSearch(search_move.move(), total_consumed, this->table->verboseLevel()); this->shared_root->best_move_for_iteration.push_back(last_best_move); this->shared_root->root_values_for_iteration.push_back (this->shared_root->root_values.back()); if (last_best_move.isNormal()) break; this->testStop(); // ã»ã£ã¦ãŠãã¨æŠ•äº† if (limit >= 2000 || this->root_ignore_moves) break; limit += 200; if (this->table->isVerbose()) std::cerr << " extend limit to " << limit << " before resign\n"; } } catch (std::exception& e) { if (! OslConfig::usiMode()) std::cerr << "std exception " << e.what() << "\n"; } catch (...) { std::cerr << "unknown exception\n"; #ifndef NDEBUG throw; #endif } finish: if (this->table->verboseLevel() > 1) { std::cerr << "<= " << csa::show(last_best_move); std::cerr << std::setprecision(4) << " mpn " << this->mpn.average() << " cut " << this->mpn_cut.average() << " alpha " << this->alpha_update.average() << " last " << this->last_alpha_update.average() << " ext " << this->ext.average() << " ext_limit " << this->ext_limit.average() << " mem " << OslConfig::memoryUseRatio()*100.0; #ifdef OSL_SMP # ifdef SPLIT_STAT if (this->shared) { std::cerr << " split " << this->shared->parallel_splits << " cancel " << this->shared->cancelled_splits.value() << " abort " << this->shared->parallel_abort.value(); } # endif #endif std::cerr << "\n"; } if (additional_info) { additional_info->node_count = this->nodeCount(); additional_info->elapsed = this->elapsed(); additional_info->moves.clear(); additional_info->root_limit = this->root_limit; } if (additional_info && this->shared_root->root_values.size() > 1) { // last_root_value[0] is for quiesce assert(last_best_move == this->shared_root->last_root_move); additional_info->move = last_best_move; const double scale = 200.0/this->eval.captureValue(newPtypeO(WHITE,PAWN)); additional_info->value = static_cast(this->shared_root->last_root_value_update * scale); if (!this->shared_root->last_pv.empty()) { for (size_t i=1; ishared_root->last_pv.back().pv.size(); ++i) { additional_info->moves.push_back(this->shared_root->last_pv.back().pv[i]); } } } #ifndef GPSONE { std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->searchFinished(); } #endif return last_best_move; } template template int osl::search::AlphaBeta2:: alphaBetaSearchRoot(Window window, MoveLogProb& best_move, int limit) { #ifndef GPSONE { std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->newDepth(limit/200); } #endif assert(P == this->state().turn()); assert(window.alpha(P) % 2); assert(window.beta(P) % 2); setRoot(limit); assert(this->curDepth() == 0); this->node_type[this->curDepth()] = base_t::PvNode; this->checkmate_searcher->setRootPlayer(P); #ifdef OSL_SMP if (this->shared) this->shared->threadStart(); #endif // ã¾ãšãƒ†ãƒ¼ãƒ–ルを牽ã SimpleHashRecord *record_in_table = this->table->allocate(this->currentHash(), limit); SimpleHashRecord *record = record_in_table; std::unique_ptr record_if_not_allocated; if (! record) { record_if_not_allocated.reset(new SimpleHashRecord()); record = record_if_not_allocated.get(); } assert(record); this->setRootRecord(record); assert(this->rootRecord() == record); assert(this->hasLastRecord() && this->lastRecord() == record); record->setInCheck(this->state().inCheck()); if (limit == 0) { int result = this->template quiesce

    (fullWindow(P)); best_move = MoveLogProb(record->qrecord.bestMove(), 100); if (this->root_ignore_moves && this->root_ignore_moves->isMember(best_move.move())) best_move = MoveLogProb(); #ifndef GPSONE else if (this->hasMonitor() && !this->prediction_for_speculative_search) { const double scale = OslConfig::usiOutputPawnValue()*2.0 / this->eval.captureValue(newPtypeO(alt(P),PAWN)); std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->showPV(1, this->recorder.allNodeCount(), this->elapsed(), static_cast(result*scale), best_move.move(), 0, 0, 0, 0); } #endif return result; } if (record_in_table) { int table_value = 0; const MoveLogProb m = record_in_table->bestMove(); if (! m.isNormal()) record_in_table->resetValue(); else if (record->hasGreaterLowerBound

    (this->curLimit(), window.beta(P), table_value)) { if (! this->root_ignore_moves || ! this->root_ignore_moves->isMember(m.move())) { best_move = m; return table_value; } } } // gather all moves MoveLogProbVector moves; MoveGenerator& generator = this->makeGenerator(); const MoveLogProb last_best_move = record->bestMove(); { MoveLogProbVector raw_moves; assert(this->curLimit() > 0); const Move hash_move = last_best_move.isNormal() ? last_best_move.move() : record->qrecord.bestMove(); generator.init(this->curLimit()+200, record, this->eval, this->state(), true, hash_move); if (last_best_move.isNormal()) raw_moves.push_back(last_best_move); else if (record->qrecord.bestMove().isNormal()) raw_moves.push_back(MoveLogProb(record->qrecord.bestMove(), 100)); generator.generateAll

    (*this, raw_moves); // clean up losing moves for (size_t i=0; i 0 && m == hash_move) continue; const HashKey key = this->currentHash().newHashWithMove(m); const SimpleHashRecord *record = this->table->find(key); assert(this->state().isValidMove(m)); if (record) { if (record->hasUpperBound(SearchTable::HistorySpecialDepth) && this->isWinValue(alt(P), record->upperBound())) continue; } if (this->root_ignore_moves && this->root_ignore_moves->isMember(m)) continue; if (! m.isDrop() && m.ptype() != KING && move_classifier::KingOpenMove

    ::isMember(this->state(), m.ptype(), m.from(), m.to())) continue; if (move_classifier::MoveAdaptor > ::isMember(this->state(), m)) continue; raw_moves[i].setLogProbAtMost(limit); moves.push_back(raw_moves[i]); } } if (! OslConfig::searchExactValueInOneReply()) { if (moves.size() == 1 || (moves.size() == 2 && moves[0].move() == moves[1].move())) { best_move = moves[0]; #ifndef GPSONE if (this->hasMonitor() && !this->prediction_for_speculative_search) { std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->rootForcedMove(best_move.move()); } #endif return 0; // XXX } } #ifndef DONT_USE_CHECKMATE // 詰将棋を呼んã§ã¿ã‚‹ root ã§ã¯æ²¢å±±å‘¼ã‚“ã§ã‚‚å•題ãªã„ int checkmate_node = 0; if (! this->prediction_for_speculative_search) { int checkmate_max = 30000*std::max(limit - 300 - this->rootLimitBias(), 0)/100; if (limit >= 1000 + this->rootLimitBias()) checkmate_max = std::min(400000, 60000*(limit - 800 - this->rootLimitBias())/100); if (toSeconds(this->timeAssigned().standard) < 20) { checkmate_node /= 4; if (toSeconds(this->timeAssigned().standard) < 10) checkmate_node /= 2; } checkmate_node = record->qrecord.checkmateNodesLeft(checkmate_max); #ifdef CHECKMATE_COUNT std::cerr << "limit " << limit << " checkmate " << checkmate_node << "\n"; #endif } if (checkmate_node > 0) { const bool my_king_in_check = this->state().hasEffectAt(alt(P),this->state().kingSquare(P)); if (my_king_in_check) { // 相手ã‹ã‚‰çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ã‚‹ this->recorder.gotoCheckmateSearch(this->state(), checkmate_node/8); const bool lose = this->template isLosingState

    (checkmate_node/8); this->recorder.backFromCheckmateSearch(); this->updateCheckmateCount(); if (lose) { best_move = MoveLogProb(Move::INVALID(),100); this->recordLoseByCheckmate(P, record); this->shared_root->last_pv.clear(); this->shared_root->last_root_move = Move(); this->shared_root->last_root_value_update = this->winByCheckmate(alt(P)); #ifndef GPSONE std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->rootLossByCheckmate(); #endif return this->winByCheckmate(alt(P)); } } // è©°ã¾ã•れãªã‘れã°ï¼Œç›¸æ‰‹ã‚’è©°ã¾ã™ã“ã¨ã‚’考ãˆã‚‹ { Move checkmate_move; #ifdef CHECKMATE_COUNT size_t count = this->checkmateSearcher().totalNodeCount(); #endif this->recorder.gotoCheckmateSearch(this->state(), checkmate_node); const bool win = this->template isWinningState

    (checkmate_node, checkmate_move, limit >= 1000 + this->rootLimitBias()); this->recorder.backFromCheckmateSearch(); this->updateCheckmateCount(); #ifdef CHECKMATE_COUNT root_checkmate += this->checkmateSearcher().totalNodeCount() - count; #endif if (win) { best_move = MoveLogProb(checkmate_move,100); this->recordWinByCheckmate(P, record, checkmate_move); this->shared_root->last_pv.clear(); this->shared_root->last_root_move = checkmate_move; this->shared_root->last_root_value_update = this->winByCheckmate(P); this->pv[1].clear(); this->updateRootPV(P, std::cerr, this->winByCheckmate(P), checkmate_move); return this->winByCheckmate(P); } } // è©°ã‚ã‚を考ãˆã‚‹ if ((! my_king_in_check) && (! (record->threatmate().isThreatmate(P)))) { Move threatmate_move; #ifdef CHECKMATE_COUNT size_t count = this->checkmateSearcher().totalNodeCount(); #endif this->recorder.gotoCheckmateSearch(this->state(), checkmate_node); const bool threatmate = this->template isThreatmateState

    (checkmate_node, threatmate_move, limit >= 1000 + this->rootLimitBias()); #ifdef CHECKMATE_COUNT root_checkmate += this->checkmateSearcher().totalNodeCount() - count; #endif this->recorder.backFromCheckmateSearch(); this->updateCheckmateCount(); if (threatmate) { if (record) record->threatmate().setThreatmate(P, threatmate_move); if (this->table->verboseLevel() > 1) std::cerr << " root threatmate " << threatmate_move << "\n"; } for (Ptype ptype: PieceStand::order) { this->testStop(); if (! this->state().hasPieceOnStand(P, ptype)) continue; NumEffectState state(this->state().emulateHandPiece(P, alt(P), ptype)); state.setTurn(alt(P)); Move hand_move; this->template isWinningState (*this->checkmate_searcher, state, HashKey(state), PathEncoding(alt(P)), checkmate_node, hand_move, Move::PASS(P), limit >= 1000 + this->rootLimitBias()); } } this->testStop(); } this->checkmate_searcher->runGC(this->table->isVerbose(), this->lastMemoryUseRatio1000()); #endif const int ValueNone = window.alpha(P) - EvalTraits

    ::delta; int best_value = ValueNone; try { // first move size_t i=0; if (limit >= 1000 && ! moves.empty() && window == fullWindow(P)) { // try aspiration window if we have sufficient limit const int root_alpha = this->rootAlpha(P, this->shared_root->root_values.size() ? this->shared_root->root_values.back() : 0, this->eval.progress16()); if (EvalTraits

    ::betterThan(root_alpha, window.alpha(P))) { const Window window_copy = window; window.alpha(P) = root_alpha; #ifndef GPSONE { std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->rootFirstMove(moves[0].move()); } #endif const int result = this->template alphaBetaSearch

    (moves[0], window, true); if (EvalTraits

    ::betterThan(result, root_alpha)) { window.alpha(P) = result + EvalTraits

    ::delta; best_move = moves[0]; best_value = result; this->updateRootPV(P, std::cerr, result, moves[0].move()); ++i; } else { if (this->table->isVerbose()) this->showFailLow(result, moves[0].move()); #ifndef GPSONE if (this->hasMonitor() && !this->prediction_for_speculative_search) { const double scale = OslConfig::usiOutputPawnValue()*2.0 / this->eval.captureValue(newPtypeO(alt(P),PAWN)); for (const auto& monitor:this->monitors()) monitor->showFailLow(this->root_limit/200, this->recorder.allNodeCount(), this->elapsed(),static_cast(result*scale), moves[0].move()); } #endif this->setStable(false); window = window_copy; } this->checkmate_searcher->runGC(this->table->isVerbose(), this->lastMemoryUseRatio1000()); } } for (; i lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->rootMove(m.move()); } #endif const int result = this->template alphaBetaSearch

    (m, window, true); if (eval::betterThan(P, result, best_value)) { window.alpha(P) = result + EvalTraits

    ::delta; best_move = m; best_value = result; this->updateRootPV(P, std::cerr, result, m.move()); if (eval::betterThan(P, result, window.beta(P))) { assert(! this->isWinValue(alt(P), result)); } } else if (result == ValueNone) this->setStable(false); this->checkmate_searcher->runGC(this->table->isVerbose(), this->lastMemoryUseRatio1000()); } // other moves if (! eval::betterThan(P, window.alpha(P), window.beta(P))) { this->template examineMovesRoot

    (moves, i, window, best_move, best_value); } if (best_move.isNormal()) { if (best_value != ValueNone) { assert(! this->shared_root->last_pv.empty()); assert(best_move.move() == this->shared_root->last_pv.back().pv[0]); } } #ifndef GPSONE { std::lock_guard lk(OslConfig::lock_io); for (const auto& monitor:this->monitors()) monitor->depthFinishedNormally(limit/200); } #endif } catch (std::runtime_error& e) { if (this->table->isVerbose()) std::cerr << e.what() << "\n"; assert(best_value % 2 == 0); this->stopNow(); this->restoreRootState(); if (best_value != ValueNone) record->setLowerBound(P, this->curLimit(), best_move, best_value); if (best_move.validMove() && best_move.move() != last_best_move.move()) { if (this->table->verboseLevel() > 1) { std::cerr << "! use better move than the last best move\n"; if (best_value != ValueNone) { assert(! this->shared_root->last_pv.empty() && ! this->shared_root->last_pv.back().pv.empty()); assert(best_move.move() == this->shared_root->last_pv.back().pv[0]); } } } else { #ifdef OSL_SMP if (this->shared) this->shared->waitAll(); #endif throw; } } assert(best_value % 2 == 0); if (best_value != ValueNone) record->setLowerBound(P, this->curLimit(), best_move, best_value); #ifdef OSL_SMP if (this->shared) this->shared->waitAll(); #endif #ifndef GPSONE if (best_value == ValueNone && this->hasMonitor() && !this->prediction_for_speculative_search) { const double scale = OslConfig::usiOutputPawnValue()*2.0 / this->eval.captureValue(newPtypeO(alt(P),PAWN)); const int value = this->winByCheckmate(alt(P)); for (const auto& monitor:this->monitors()) monitor->showPV(limit/200, this->recorder.allNodeCount(), this->elapsed(), static_cast(value*scale), Move::INVALID(), 0, 0, 0, 0); } #endif return best_value; } template void osl::search::AlphaBeta2::setRoot(int limit) { SearchState2::setRoot(limit); SimpleHashRecord *record = this->table->allocate(this->currentHash(), std::max(1000,limit)); assert(record); this->setRootRecord(record); this->move_type[this->curDepth()] = base_t::INITIAL; } template void osl::search::AlphaBeta2::makeMove(Move move) { assert(this->state().isValidMove(move)); SearchState2::makeMove(move); this->eval.update(this->state(), move); SimpleHashRecord *record = this->table->allocate(this->currentHash(), this->curLimit()); assert(record); this->move_type[this->curDepth()] = base_t::INITIAL; record->setInCheck(this->state().inCheck()); this->setCurrentRecord(record); } template bool osl::search::AlphaBeta2:: isReasonableMove(Move /*move*/, int /*pawn_sacrifice*/) { return true; } template void osl::search::AlphaBeta2:: showNodeDepth(std::ostream& os) { #ifndef MINIMAL int max_depth=0; for (int i=base_t::MaxDepth-1; i>=0; --i) { if (base_t::depth_node_count[i] || base_t::depth_node_count_quiesce[i]) { max_depth = i; break; } } int max_count=0; for (int i=0; i<=max_depth; i+=2) { max_count = std::max(max_count, base_t::depth_node_count[i]+base_t::depth_node_count_quiesce[i]); } int unit = std::max(max_count/79, 100); for (int i=0; i<=max_depth; i+=2) { os << std::setw(3) << i << " " << std::string(base_t::depth_node_count[i]/unit, '*') << std::string(base_t::depth_node_count_quiesce[i]/unit, '+') << std::endl; } # ifdef CHECKMATE_COUNT std::cerr << "checkmate root " << root_checkmate << " quiesce " << quiesce_checkmate << "\nnormal before " << checkmate_before << " after " << checkmate_after << " threatmate " << count_threatmate << "\n"; # endif #endif } template void osl::search::AlphaBeta2:: clearNodeDepth() { #ifndef MINIMAL base_t::depth_node_count.fill(0); base_t::depth_node_count_quiesce.fill(0); #endif } namespace osl { namespace search { #ifndef MINIMAL template class AlphaBeta2; template class AlphaBeta2Tree; template void AlphaBeta2Tree::examineMovesRoot(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); template void AlphaBeta2Tree::examineMovesRoot(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); #endif template class AlphaBeta2; template class AlphaBeta2Tree; template void AlphaBeta2Tree::examineMovesRoot(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); template void AlphaBeta2Tree::examineMovesRoot(const MoveLogProbVector&, size_t, Window, MoveLogProb&, int&); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/interimReport.cc0000644000000000000000000001513112316770314020623 0ustar rootroot/* interimReport.cc */ #include "interimReport.h" #include #include #include #include #include #include #include #include #include std::function osl::search::InterimReport::info = [](std::string){}; std::function osl::search::InterimReport::warn = [](std::string){}; std::function osl::search::InterimReport::error = [](std::string){}; osl::search::InterimReport:: InterimReport(int o) : owner(o), depth_head(0), node_count(0), elapsed(0.0), stopped(false), aborted(false), last_message_ignored(false) { } osl::search::InterimReport:: ~InterimReport() { } void osl::search::InterimReport:: finished(const std::string& line) { assert(line.find("checkmate ") == 0 || line.find("bestmove ") == 0); result_line = line; if (node_count == 0 && pv.score == 0 && line.find("checkmate ") != 0) { info("$ finish without info, owner "+std::to_string(owner)+" "+line); if (line == "bestmove resign") { pv.score = -usi_win_value; pv.clear(); pv.push_back("resign"); } else if (line == "bestmove win") { pv.score = usi_win_value; pv.clear(); pv.push_back("win"); } else { error("$ unexpected finish without info, owner "+std::to_string(owner) +" "+line); } } } bool osl::search::InterimReport:: updateByInfo(const std::string& line, int id) { const bool overwrite = id < 0; const bool verbose = false; if (verbose) std::cerr << "$ " << line << "\n"; bool important = false; std::istringstream is(line); std::string key, value; int64_t int_value; is >> key; assert(key == "info"); bool same_best_move = false, same_score = false, better_score = false, has_score = false, enter_new_depth = false; int new_score = 0; std::vector new_pv; while (is >> key) { if (key == "depth") { is >> int_value; if (! (overwrite || (is && int_value >= depth_head))) info("$depth decreased "+std::to_string(id)+" "+line); enter_new_depth = (int_value > pv.depth); depth_head = int_value; } else if (key == "time") { is >> int_value; assert(is && int_value > elapsed*1000-100); if (int_value == 0) int_value = 1; elapsed = int_value / 1000.0; } else if (key == "nodes") { is >> int_value; if (int_value < node_count) error("$node count decreased " + std::to_string(int_value) + ' ' + std::to_string(node_count) + " in " + line); assert(is && int_value >= node_count); node_count = int_value; } else if (key == "pv") { if (getline(is, value)) { std::string prev_best = pv.empty() ? "" : pv[0]; boost::algorithm::trim(value); boost::algorithm::trim_left(value); boost::algorithm::split(new_pv, value, boost::algorithm::is_any_of(" ")); same_best_move = !new_pv.empty() && (prev_best == new_pv[0]); } else if (! new_pv.empty()) { error("$warn empty pv: " + line); } } else if (key == "score") { is >> key >> int_value; assert(is); if (key == "cp") { has_score = true; better_score = (int_value > pv.score); // negamax at this point same_score = (pv.score == int_value); new_score = int_value; } } else if (key == "seldepth" || key == "multipv" || key.find("currmove") == 0 || key == "hashfull" || key == "nps" || key == "cpuload") { is >> value; // ignore assert(is); } else if (key == "string") { getline(is, value); last_string = value; if (last_string == " loss by checkmate") { pv.score = -usi_win_value; pv.clear(); pv.push_back("resign"); important = true; } else { // warn("$warn string not supported yet " + line); // todo? important = true; } } else { error("$warn unknown info key " + key + " in " + line); assert(0); } } if (enter_new_depth || better_score || same_best_move || overwrite) { if (has_score && ! new_pv.empty() && ! pv.empty() && ! same_best_move) { alternatives[pv[0]] = pv; } if (has_score) { pv.depth = depth_head; pv.score = new_score; pv.elapsed = elapsed; important = true; } if (! new_pv.empty()) { pv.depth = depth_head; pv.moves.swap(new_pv); pv.elapsed = elapsed; important = true; } } else if (has_score && !new_pv.empty()) { // info("subpv from "+std::to_string(id)+ " " + line); PVInfo& data = alternatives[new_pv[0]]; data.depth = depth_head; data.score = new_score; data.moves = new_pv; data.elapsed = elapsed; } // gpsfish sometimes reaches depth 100 within 0.3ms in case of easy win, // reporting the same move and value if (depth_head > 20 && same_best_move && same_score && abs(pv.score) > 1000) { if (! last_message_ignored) { info("$ignored repeated massages from " +std::to_string(id) + " " + std::to_string(pv.score)); last_message_ignored = true; } return false; } if (important) last_message_ignored = false; return important; } std::string osl::search::InterimReport:: composeInfo(bool negate_score) const { std::ostringstream msg; msg << "info"; int dh = depth_head, pd = pv.depth; if (std::max(dh, pd) > 0) msg << " depth " << std::max(dh, pd); if (elapsed > 0.0) msg << " time " << static_cast(elapsed*1000); msg << " score cp " << (negate_score ? -pv.score : pv.score); if (node_count > 0) { msg << " nodes " << node_count; if (elapsed > 0.0) msg << " nps " << static_cast(node_count/elapsed); } if (! pv.empty()) msg << " pv " << joinPV(); return msg.str(); } std::string osl::search::InterimReport:: joinPV() const { return boost::algorithm::join_if (pv.moves, " ", [](std::string s){ return !boost::algorithm::starts_with (s, "ignore_moves"); }); } std::string osl::search::InterimReport:: makeSearchResult() const { std::string result = "bestmove "; if (pv.empty()) return result + "resign"; if (pv[0].find("ignore_moves") == 0) return result + pv[1]; return result + pv[0]; } void osl::search::InterimReport:: set(osl::Player turn, const InterimReport& src) { if (this == &src) return; *this = src; pv.score *= sign(turn); for (pv_table::value_type& v: alternatives) { v.second.score *= sign(turn); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/search/moveWithComment.h0000644000000000000000000000134412316770314020750 0ustar rootroot/* moveWithComment.h */ #ifndef _MOVEWITHCOMMENT_H #define _MOVEWITHCOMMENT_H #include "osl/basic_type.h" #include "osl/hashKey.h" #include namespace osl { namespace search { struct MoveWithComment { Move move; int value; std::vector moves; HashKey root; uint64_t node_count; double elapsed; int root_limit; explicit MoveWithComment(Move m=Move::INVALID(), int v=0) : move(m), value(v), node_count(0), elapsed(0), root_limit(0) { } ~MoveWithComment(); }; } // namespace search using search::MoveWithComment; } // namespace osl #endif /* _MOVEWITHCOMMENT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/0000755000000000000000000000000012316770314016474 5ustar rootrootlibosl-0.8.0.orig/full/osl/effect_util/effectUtil.h0000644000000000000000000000157512316770314020747 0ustar rootroot#ifndef _EFFECTUTIL_H #define _EFFECTUTIL_H #include "osl/numEffectState.h" #include "osl/container.h" #include #include namespace osl { namespace effect_util { /** * EffectState を活用ã™ã‚‹ãŸã‚ã®ãƒ¡ã‚½ãƒƒãƒ‰ * NumSimpleEffect ãªã©ã®å…¬é–‹ã‚¤ãƒ³ã‚¿ãƒ¼ãƒ•ェース㧠* 使ã£ã¦æ›¸ã‘るコード */ struct EffectUtil { /** * state ã® position ã« ptypeo ãŒã‚ã£ãŸå ´åˆã‚’仮定ã—ã¦ï¼Œè„…å¨ã‚’outã«é›†ã‚ã‚‹ */ template static void findThreat(const NumEffectState& state, Square position, PtypeO ptypeo, PieceVector& out); template struct FindThreat; struct SafeCapture; }; } // namespace effect_util using effect_util::EffectUtil; } // namespace osl #endif /* _EFFECTUTIL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/virtualPin.h0000644000000000000000000000235112316770314021003 0ustar rootroot/* virtualPin.h */ #ifndef _VIRTUALPIN_H #define _VIRTUALPIN_H #include "osl/numEffectState.h" namespace osl { namespace effect_util { class VirtualPin { private: template static bool findDirection(const SimpleState& state, Square target, Player defense, const PieceMask& remove) { const Offset diff = Board_Table.getOffset(defense, DIR); Piece p; for (p=state.nextPiece(target, diff);;p=state.nextPiece(p.square(), diff)) { if (! p.isPiece()) return false; if (! remove.test(p.number())) break; } assert(p.isPiece()); if (p.owner() == defense) return false; return (Ptype_Table.getMoveMask(p.ptype()) & DirectionTraits::longDir>::mask); } public: /** remove ãŒå…¨ã¦å‹•ã㨠defenseã®çŽ‰ã«æ”»ã‚æ–¹ã®åйããŒç™ºç”Ÿã™ã‚‹ã‹ã€‚*/ static bool find(const NumEffectState& state, Player defense, const PieceMask& remove); static bool find(const NumEffectState& state, Player defense, Square target) { return find(state, defense, state.effectSetAt(target)); } }; } using effect_util::VirtualPin; } #endif /* _VIRTUALPIN_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/pin.h0000644000000000000000000002230012316770314017430 0ustar rootroot/* pin.h */ #ifndef _PIN_H #define _PIN_H #include "osl/numEffectState.h" #include "osl/bits/pieceMask.h" namespace osl { namespace effect_util { class PinOrOpen { private: /** * é§’ã‹ã‚‰8è¿‘å‚をサーãƒã—ã¦ã„ã£ã¦ï¼Œãã®æ–¹å‘ã®åˆ©ããŒã‚ã‚‹ã‹? */ template static void findDirectionStep(const NumEffectState& state, Square target, PieceMask& pins, PieceMask const& onBoard) { const Offset offset = DirectionTraits

    ::blackOffset(); Square pos=target-offset; int num; while(Piece::isEmptyNum(num=state.pieceAt(pos).number())) pos-=offset; if(Piece::isEdgeNum(num)) return; int num1=state.longEffectNumTable()[num][DIR]; if(Piece::isPieceNum(num1) && onBoard.test(num1)){ pins.set(num); } } public: template static PieceMask makeStep(const NumEffectState& state, Square target) { PieceMask pins; PieceMask mask=state.piecesOnBoard(alt(Defense)); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); findDirectionStep(state,target,pins,mask); return pins; } static PieceMask makeStep(const NumEffectState& state, Square target, Player defense) { if(defense==BLACK) return makeStep(state,target); else return makeStep(state,target); } static PieceMask make(const NumEffectState& state,Player defense) { return makeStep(state,state.kingSquare(),defense); } }; /** * 素抜ããŒã‚ã‚‹ãŸã‚å‹•ã‘ãªã„駒を求ã‚ã‚‹. * TODO: 差分計算ã§é«˜é€Ÿã«æ›´æ–°ã™ã‚‹ */ class Pin { private: template static void findDirection(const SimpleState& state, Square target, Player defense, PieceMask& pins) { const Offset diff = Board_Table.getOffset(defense, DIR); const Piece pin = state.nextPiece(target, diff); if(!pin.isOnBoardByOwner(defense)) return; const Piece attack_piece = state.nextPiece(pin.square(), diff); if(!attack_piece.isOnBoardByOwner(alt(defense))) return; if (Ptype_Table.getMoveMask(attack_piece.ptype()) & DirectionTraits::longDir>::mask) pins.set(pin.number()); } /** * targetã«ã¯defenseã®KINGãŒã‚ã‚‹ã¨ã„ã†å‰æ * Pã¯defense * targetã«defenseã®lanceãŒã‚ã‚‹ã¨åƒã‹ãªã„. */ template static void findLance(const NumEffectState& state, Square target, PieceMask& pins) { assert(target==state.kingSquare

    ()); const Offset diff = DirectionPlayerTraits::offset(); Square pos = target+diff; Piece pin; while ((pin=state.pieceAt(pos)) == Piece::EMPTY()) pos += diff; if (! pin.isOnBoardByOwner

    () ) return; NumBitmapEffect effect=state.effectSetAt(pos); mask_t mask=(effect.getMask(1)&mask_t::makeDirect(PtypeFuns::indexMask<<8)); if(mask.any()){ pins.set(pin.number()); } } public: /** * 8æ–¹å‘計算ã™ã‚‹æ–¹æ³• * @see make, makeByPiece */ static PieceMask makeNaive(const SimpleState& state, Square target, Player defense); private: static bool hasEffectWithOffset(const SimpleState& state, Piece attack_piece, Piece pin, Offset diff) { const Piece attack_piece2 = state.nextPiece(pin.square(), diff); return attack_piece == attack_piece2; } static bool hasEffectWithOffset(const NumEffectState& state, Piece attack_piece, Piece pin, Offset) { return state.hasEffectByPiece(attack_piece, pin.square()); } static void findOffset(const NumEffectState& state, Piece attack_piece, Square target, Player defense, Offset diff, PieceMask& pins) { const Piece pin = state.nextPiece(target, diff); assert(pin.isPiece()); if (pin.owner() != defense) return; if (! hasEffectWithOffset(state, attack_piece, pin, diff)) return; pins.set(pin.number()); } template static void findPtype(const NumEffectState& state, Square target, Player attack, Player defense, PieceMask& result) { static_assert((PTYPE == ROOK) || (PTYPE == BISHOP), "ptype"); const PtypeO attack_ptypeo = newPtypeO(attack, PTYPE); for (int i=PtypeTraits::indexMin; i < PtypeTraits::indexLimit; ++i) { const Piece attack_piece = state.pieceOf(i); if (attack_piece.isOnBoardByOwner(attack)) { const Square attack_position = attack_piece.square(); const Offset32 diff(attack_position, target); const EffectContent effect = Ptype_Table.getEffect(attack_ptypeo, diff); if (!effect.hasBlockableEffect()) // 利ãã¯ã‚ã‚‹ã‹ continue; const Offset offset = effect.offset(); #if 0 if (offset.zero()) // 隣ã«ã„ã‚‹å ´åˆ: pin ã¯ãªã„ continue; #endif findOffset(state, attack_piece, target, defense, offset, result); } } } public: /** * 飛車角ã¯é§’ã®ä½ç½®ã‹ã‚‰åˆ¤æ–­ã™ã‚‹è¨ˆç®—方法. * @see make, makeNaive */ static PieceMask makeByPiece(const NumEffectState& state, Square target, Player defense); /** * 飛車角ã¯é§’ã®ä½ç½®ã‹ã‚‰åˆ¤æ–­, KINGã«ç‰¹åŒ– * @see make, makeNaive */ static PieceMask makeByPieceKing(const NumEffectState& state, Square target, Player defense); /** * é§’ã‹ã‚‰8è¿‘å‚をサーãƒã—ã¦ã„ã£ã¦ï¼Œãã®æ–¹å‘ã®åˆ©ããŒã‚ã‚‹ã‹? */ template static void findDirectionStep(const NumEffectState& state, Square target, PieceMask& pins) { const Offset offset = DirectionTraits

    ::blackOffset(); Square pos=target-offset; int num; while(Piece::isEmptyNum(num=state.pieceAt(pos).number())) pos-=offset; if(Piece::isEdgeNum(num)) return; if(Defense==BLACK){ if(!state.pieceAt(pos).pieceIsBlack()) return; } else{ if(state.pieceAt(pos).pieceIsBlack()) return; } int num1=state.longEffectNumTable()[num][DIR]; if(!Piece::isPieceNum(num1)) return; if(Defense==BLACK){ if(!state.pieceOf(num1).pieceIsBlack()) pins.set(num); } else{ if(state.pieceOf(num1).pieceIsBlack()) pins.set(num); } } template static PieceMask makeStep(const NumEffectState& state, Square target) { PieceMask pins; findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); findDirectionStep(state,target,pins); return pins; } static PieceMask makeStep(const NumEffectState& state, Square target, Player defense) { if(defense==BLACK) return makeStep(state,target); else return makeStep(state,target); } template static PieceMask makeStep1(const NumEffectState& state, Square target) { PieceMask pins=PinOrOpen::makeStep(state,target);; pins &= state.piecesOnBoard(Defense); return pins; } static PieceMask makeStep1(const NumEffectState& state, Square target, Player defense) { if(defense==BLACK) return makeStep1(state,target); else return makeStep1(state,target); } /** * pin ã•れã¦ã„る駒を計算ã™ã‚‹ * @param target 守るマス * @param defense pin ã•れã¦ã„ã‚‹é§’ã®æ‰€æœ‰è€… * @see makeByPiece, makeNaive */ static PieceMask make(const NumEffectState& state, Square target, Player defense) { return makeByPiece(state, target, defense); } /** * defense ã®çŽ‹ã‚’å®ˆã‚‹ãŸã‚ã« pin ã•れã¦ã„る駒を計算ã™ã‚‹ */ static PieceMask make(const NumEffectState& state, Player defense) { return makeByPiece(state, defense); } static PieceMask makeNaive(const SimpleState& state, Player defense) { return makeNaive(state, state.kingSquare(defense), defense); } static PieceMask makeByPiece(const NumEffectState& state, Player defense) { return makeByPieceKing(state, state.kingSquare(defense), defense); } /** * defense ã®çŽ‹ã«ã¤ã„㦠pin ã•れã¦ã„る駒を計算ã™ã‚‹ */ static int count(const NumEffectState& state, Player defense) { const PieceMask pins = make(state, defense); return pins.countBit(); } static int count(const NumEffectState& state, Square target, Player defense) { const PieceMask pins = make(state, target, defense); return pins.countBit(); } }; } // namespace effect_util } // namespace osl #endif /* _PIN_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/effectUtil.cc0000644000000000000000000000073012316770314021075 0ustar rootroot/* effectUtil.cc */ #include "osl/effect_util/effectUtil.h" #include "osl/effect_util/effectUtil.tcc" #include "osl/eval/openMidEndingEval.h" #include "osl/numEffectState.tcc" #ifndef DFPNSTATONE namespace osl { template void EffectUtil::findThreat( const NumEffectState& state, Square position, PtypeO ptypeo, PieceVector& out); } #endif // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/virtualPin.cc0000644000000000000000000000151012316770314021135 0ustar rootroot/* virtualPin.cc */ #include "osl/effect_util/virtualPin.h" bool osl::effect_util:: VirtualPin::find(const NumEffectState& state, Player defense, const PieceMask& remove) { const Square target = state.kingSquare(defense); return findDirection
      (state, target, defense, remove) || findDirection(state, target, defense, remove) || findDirection(state, target, defense, remove) || findDirection(state, target, defense, remove) || findDirection(state, target, defense, remove) || findDirection
      (state, target, defense, remove) || findDirection(state, target, defense, remove) || findDirection(state, target, defense, remove); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/pin.cc0000644000000000000000000000337412316770314017600 0ustar rootroot/* pin.cc */ #include "osl/effect_util/pin.h" #ifndef MINIMAL osl::PieceMask osl::effect_util:: Pin::makeNaive(const SimpleState& state, Square target, Player defense) { assert(target.isOnBoard()); PieceMask result; findDirection
        (state, target, defense, result); findDirection(state, target, defense, result); findDirection(state, target, defense, result); findDirection(state, target, defense, result); findDirection(state, target, defense, result); findDirection
        (state, target, defense, result); findDirection(state, target, defense, result); findDirection(state, target, defense, result); return result; } osl::PieceMask osl::effect_util:: Pin::makeByPiece(const NumEffectState& state, Square target, Player defense) { assert(target.isOnBoard()); const Player attack = alt(defense); PieceMask result; // 香車 findDirection(state, target, defense, result); // 飛車 è§’ findPtype(state, target, attack, defense, result); findPtype(state, target, attack, defense, result); return result; } osl::PieceMask osl::effect_util:: Pin::makeByPieceKing(const NumEffectState& state, Square target, Player defense) { assert(target.isOnBoard()); const Player attack = alt(defense); PieceMask result; // 香車 if(defense==BLACK){ findLance(state, target, result); } else{ findLance(state, target, result); } // 飛車 è§’ findPtype(state, target, attack, defense, result); findPtype(state, target, attack, defense, result); return result; } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/effect_util/effectUtil.tcc0000644000000000000000000000337512316770314021271 0ustar rootroot#ifndef _EFFECTUTIL_TCC #define _EFFECTUTIL_TCC #include "osl/effect_util/effectUtil.h" template struct osl::effect_util::EffectUtil::FindThreat { const NumEffectState& state; Player target; int attacker_value; PieceVector& supported, & unsupported; FindThreat(const NumEffectState& st, Player t, int a, PieceVector& s, PieceVector& u) : state(st), target(t), attacker_value(a), supported(s), unsupported(u) { } void operator()(Square pos) { const Piece cur = state.pieceOnBoard(pos); assert(cur.isPiece()); if (cur.owner() != target) return; if (state.hasEffectAt(target, pos)) { if (abs(EvalT::captureValue(cur.ptypeO())) > attacker_value) supported.push_back(cur); } else { unsupported.push_back(cur); } } }; template void osl::EffectUtil:: findThreat(const NumEffectState& state, Square position, PtypeO ptypeo, PieceVector& out) { PieceVector supported, unsupported; const int attacker_value = abs(EvalT::captureValue(ptypeo)); FindThreat f(state, alt(getOwner(ptypeo)), attacker_value, supported, unsupported); state.forEachEffectOfPtypeO, false> (position, ptypeo, f); unsupported.sortByPtype(); supported.sortByPtype(); PieceVector::iterator u=unsupported.begin(), s=supported.begin(); if (u!=unsupported.end()) { while ((s!=supported.end()) && ((abs(EvalT::captureValue(s->ptypeO())) - attacker_value) > abs(EvalT::captureValue(u->ptypeO())))) { out.push_back(*s); ++s; } } out.push_back(u, unsupported.end()); out.push_back(s, supported.end()); } #endif /* _EFFECTUTIL_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/0000755000000000000000000000000012521114240016623 5ustar rootrootlibosl-0.8.0.orig/full/osl/game_playing/cuiClient.cc0000644000000000000000000000247412316770314021074 0ustar rootroot/* cuiClient.cc */ #include "osl/game_playing/cuiClient.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/csaLogger.h" #include "osl/search/moveWithComment.h" osl::game_playing:: CuiClient::CuiClient(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l, std::istream& i, std::ostream& o) : GameManager(black, white, l), is(i), os(o), stop_by_outside(0) { } osl::game_playing:: CuiClient::~CuiClient() { } void osl::game_playing:: CuiClient::run(const char *black, const char *white) { logger->init(black, white, state->state()); run(); } void osl::game_playing:: CuiClient::run() { try { logger->writeComment("game start"); while (1) { while (! isComputer(state->state().turn())) { while (readAndProcessCommand()) ; } int seconds=0; MoveWithComment best_move; if (! stop_by_outside) { best_move = computeMove(seconds); } else { best_move = MoveWithComment(Move::INVALID()); logger->writeComment("forced resign"); } processComputerMove(best_move, seconds); } } catch (EndGame&) { logger->writeComment("game end"); } return; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/winCountTracer.h0000644000000000000000000000226012316770314021757 0ustar rootroot/* winCountTracer.h */ #ifndef GAME_PLAYING_WINCOUNTTRACER_H #define GAME_PLAYING_WINCOUNTTRACER_H #include "osl/game_playing/openingBookTracer.h" #include namespace osl { namespace book { class WinCountBook; } namespace game_playing { /** * WinCountBookã®è¿½è·¡ */ class WinCountTracer : public OpeningBookTracer { public: typedef book::WinCountBook WinCountBook; private: WinCountBook& book; int state_index; Player turn; int randomness; bool verbose; std::stack state_stack; public: /* @param randomness ゼロ以外ã®å ´åˆï¼Œæœ€è‰¯ã§ãªã„手も確率的ã«é¸æŠž */ explicit WinCountTracer(WinCountBook&, int randomness=0, bool verbose=false); WinCountTracer(const WinCountTracer&); OpeningBookTracer* clone() const; void update(Move); const Move selectMove() const; int stateIndex() const { return state_index; } bool isOutOfBook() const; void popMove(); }; } // namespace game_playing } // namespace osl #endif /* _WINCOUNTTRACER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/openingBookTracer.cc0000644000000000000000000000127412316770314022565 0ustar rootroot/* openingBookTracer.cc */ #include "osl/game_playing/openingBookTracer.h" osl::game_playing:: OpeningBookTracer::~OpeningBookTracer() { } /* ------------------------------------------------------------------------- */ osl::game_playing:: NullBook::~NullBook() { } void osl::game_playing:: NullBook::update(Move) { } const osl::Move osl::game_playing:: NullBook::selectMove() const { return Move::INVALID(); } bool osl::game_playing:: NullBook::isOutOfBook() const { return true; } void osl::game_playing:: NullBook::popMove() { } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/weightTracer.h0000644000000000000000000000416412316770314021445 0ustar rootroot/* winCountTracer.h */ #ifndef GAME_PLAYING_WEIGHTTRACER_H #define GAME_PLAYING_WEIGHTTRACER_H #include "osl/game_playing/openingBookTracer.h" #include "osl/book/openingBook.h" #include namespace osl { namespace book { class WeightedBook; } namespace game_playing { /** * WeightedBookã®è¿½è·¡ */ class WeightTracer : public OpeningBookTracer { public: typedef book::WeightedBook WeightedBook; protected: WeightedBook& book; int state_index, start_index; Player turn; std::stack state_stack; const osl::Move selectMoveAtRandom(const std::vector& moves) const; const int weight_coef_for_the_initial_move; const int weight_coef; public: explicit WeightTracer(WeightedBook&, bool verbose=false, const int weight_coef_for_the_initial_move = 16, const int weight_coef = 10); WeightTracer(const WeightTracer&); OpeningBookTracer* clone() const; void update(Move); const Move selectMove() const; int stateIndex() const { return state_index; } bool isOutOfBook() const; void popMove(); }; class DeterminateWeightTracer : public WeightTracer { /**< select a move from topn moves */ const int topn; public: explicit DeterminateWeightTracer(WeightedBook& book, bool verbose=false, const int topn=1, const int weight_coef_for_the_initial_move = 16, const int weight_coef = 10) : WeightTracer(book, verbose, weight_coef_for_the_initial_move, weight_coef), topn(topn) {} DeterminateWeightTracer(const DeterminateWeightTracer& copy) : WeightTracer(copy), topn(copy.getTopn()) {} OpeningBookTracer* clone() const; const Move selectMove() const; int getTopn() const {return topn;} }; } // namespace game_playing } // namespace osl #endif // GAME_PLAYING_WEIGHTTRACER_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/speculativeModel.h0000644000000000000000000000215412316770314022317 0ustar rootroot/* speculativeModel.h */ #ifndef OSL_SPECULATIVEMODEL_H #define OSL_SPECULATIVEMODEL_H #include "osl/game_playing/computerPlayer.h" #include "osl/search/searchTimer.h" namespace osl { namespace game_playing { class SearchPlayer; /** * ç›¸æ‰‹ã®æ‰‹ã®äºˆæ¸¬1ã¤ã«ã¤ã1thread */ class SpeculativeModel { public: virtual ~SpeculativeModel(); virtual void setMaxThreads(int); virtual void startSpeculative(const std::shared_ptr state, const SearchPlayer& main_player)=0; virtual void stopOtherThan(Move)=0; virtual void stopAll()=0; virtual const HashKey searchState() const=0; /** * @param byoyomi 対局æ¡ä»¶ã‚’ä¼ãˆã‚‹ãŸã‚ã«åˆ©ç”¨ */ virtual const MoveWithComment waitResult(Move last_move, search::TimeAssigned, SearchPlayer& main_player, int byoyomi)=0; virtual void selectBestMoveCleanUp()=0; void clearResource(); }; } // game_playing } // osl #endif /* OSL_SPECULATIVEMODEL_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/gnuShogiClient.cc0000644000000000000000000001123312316770314022070 0ustar rootroot/* gnuShogiClient.cc */ #include "osl/game_playing/gnuShogiClient.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/csaLogger.h" #include "osl/game_playing/csaStopwatch.h" #include "osl/search/moveWithComment.h" #include "osl/usi.h" #include "osl/sennichite.h" #include #include osl::game_playing:: GnuShogiClient::GnuShogiClient(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l, std::istream& is, std::ostream& os) : CuiClient(black, white, l, is, os) { } osl::game_playing:: GnuShogiClient::~GnuShogiClient() { } bool osl::game_playing:: GnuShogiClient::readAndProcessCommand() { CsaStopwatch timer; std::string line; std::getline(is, line); const long op_think_time = timer.read(); if (! is) { logger->inputError("(stream not available)"); throw EndGame(); } if (line == "quit" || line == "exit") throw GnuShogiQuit(); if (line == "undo") { logger->popMove(); popMove(); return false; } if (line == "force") { setComputerPlayer(BLACK, false); setComputerPlayer(WHITE, false); logger->breakGame(); return false; } if (line == "black") { setComputerPlayer(BLACK, true); setComputerPlayer(WHITE, false); return true; } if (line == "white") { setComputerPlayer(BLACK, false); setComputerPlayer(WHITE, true); return true; } if (line == "go") { const Player turn = state->state().turn(); if (! isComputer(turn)) { setComputerPlayer(turn, true); setComputerPlayer(alt(turn), false); } return false; } if (line == "new" || line == "beep" || line == "random") return false; // XXX if (line.find("time") == 0 || line.find("otime") == 0) { if (line.find("time") == 0) { std::istringstream ss(line); std::string dummy; int time; ss >> dummy >> time; setTimeLeft(time/100, time/100); } std::cerr << line << "\n"; return false; } if (line.find("help") == 0) { std::cerr << " 2g7f move a piece from 2g to 2f\n" " P*2d drop a pawn to 2d\n" " undo undo the last move\n" " force human plays both colors\n" " black/white set computer's color\n" " exit/quit exit program\n"; return true; } if (line.size() < 4) goto ignore; if (isdigit(line[0]) || line[1] == '*') // FIXME { const Move op_move=psn::strToMove(line, state->state()); if (state->isIllegal(op_move)) { os << "Illegal move\n"; logger->inputError(line.c_str()); return true; } const Sennichite result = pushMove(MoveWithComment(op_move), op_think_time); if (! result.isNormal()) { if (result == Sennichite::BLACK_LOSE()) os << "White mates!\n"; else if (result == Sennichite::WHITE_LOSE()) os << "Black mates!\n"; else os << "Black mates!\n"; // does xshogi know draw? setComputerPlayer(BLACK, false); setComputerPlayer(WHITE, false); logger->endByRepetition(result); throw EndGame(); } const int chess_moves = state->chessMoves(); os << chess_moves << ". " << psn::show(op_move) << " " << (time_keeper.timeLeft(op_move.player()) - op_think_time)*100 << std::endl << std::flush; return false; } ignore: std::cerr << line << "\n"; std::string comment = "ignored line " + line; logger->writeComment(comment.c_str()); return false; } void osl::game_playing:: GnuShogiClient::processComputerMove(const MoveWithComment& selected, int my_think_time) { const Move best_move = selected.move; const Player turn = state->state().turn(); if ((! best_move.isNormal()) || (state->isIllegal(best_move))) { os << ((alt(turn) == BLACK) ? "Black" : "White") << " mates!\n"; logger->resign(turn); setComputerPlayer(BLACK, false); setComputerPlayer(WHITE, false); throw EndGame(); } const int chess_moves = state->chessMoves(); os << chess_moves << ". ... " << psn::show(best_move) << " " << (time_keeper.timeLeft(turn) - my_think_time)*100 << std::endl << std::flush; const Sennichite result = pushMove(selected, my_think_time); if (! result.isNormal()) { if (result == Sennichite::BLACK_LOSE()) os << "White mates!\n"; else if (result == Sennichite::WHITE_LOSE()) os << "Black mates!\n"; else os << "Black mates!\n"; // does xshogi know draw? setComputerPlayer(BLACK, false); setComputerPlayer(WHITE, false); logger->endByRepetition(result); throw EndGame(); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/computerPlayer.cc0000644000000000000000000000377512316770314022175 0ustar rootroot/* computerPlayer.cc */ #include "osl/game_playing/computerPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/openingBookTracer.h" #include "osl/random.h" osl::game_playing:: ComputerPlayer::~ComputerPlayer() { } bool osl::game_playing:: ComputerPlayer::isReasonableMove(const GameState&, Move, int) { return true; } void osl::game_playing:: ComputerPlayer::allowSpeculativeSearch(bool value) { speculative_search_allowed = value; } void osl::game_playing:: ComputerPlayer::setInitialState(const NumEffectState&) { } bool osl::game_playing:: ComputerPlayer::stopSearchNow() { return true; } void osl::game_playing:: ComputerPlayer::setRootIgnoreMoves(const MoveVector */*rim*/, bool) { } /* ------------------------------------------------------------------------- */ osl::game_playing:: ComputerPlayerSelectBestMoveInTime::~ComputerPlayerSelectBestMoveInTime() { } /* ------------------------------------------------------------------------- */ osl::game_playing:: ResignPlayer::~ResignPlayer() { } void osl::game_playing:: ResignPlayer::pushMove(Move) { } void osl::game_playing:: ResignPlayer::popMove() { } const osl::search::MoveWithComment osl::game_playing:: ResignPlayer::selectBestMove(const GameState&, int, int, int) { return MoveWithComment(Move::INVALID()); } /* ------------------------------------------------------------------------- */ osl::game_playing:: RandomPlayer::~RandomPlayer() { } void osl::game_playing:: RandomPlayer::pushMove(Move) { } void osl::game_playing:: RandomPlayer::popMove() { } const osl::search::MoveWithComment osl::game_playing:: RandomPlayer::selectBestMove(const GameState& state, int, int, int) { MoveVector moves; state.state().generateLegal(moves); if (moves.empty()) return MoveWithComment(Move::INVALID()); return MoveWithComment(moves[time_seeded_random() % moves.size()]); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/usiResponse.cc0000644000000000000000000001431412316770314021470 0ustar rootroot/* usiResponse.cc */ #include "osl/game_playing/usiResponse.h" #include "osl/game_playing/gameState.h" #include "osl/move_probability/featureSet.h" #include "osl/rating/ratingEnv.h" #include "osl/rating/featureSet.h" #include "osl/progress.h" #include "osl/sennichite.h" #include "osl/csa.h" #include "osl/usi.h" #ifndef MINIMAL # include "osl/record/ki2.h" #endif #include #include osl::game_playing:: UsiResponse::UsiResponse(const UsiState& u, bool n, bool v) : usi_state(u), new_move_probability(n), verbose(v) { } osl::game_playing:: UsiResponse::~UsiResponse() { } osl::MoveVector osl::game_playing:: UsiResponse::generateGoodMoves() { GameState state(usi_state.initial_state); for (Move m: usi_state.moves) state.pushMove(m); MoveVector normal_or_win_or_draw, loss; state.generateNotLosingMoves(normal_or_win_or_draw, loss); if (verbose && ! loss.empty()) { std::cerr << " removed losing move "; for (Move m: loss) std::cerr << csa::show(m); std::cerr << "\n"; } return normal_or_win_or_draw; } void osl::game_playing:: UsiResponse::genmoveProbability(int limit, MoveLogProbVector& out) { GameState gstate(usi_state.initial_state); for (Move m: usi_state.moves) gstate.pushMove(m); const NumEffectState& state= gstate.state(); const MoveStack& history = gstate.moveHistory(); progress::ml::NewProgress progress(state); MoveLogProbVector moves; if (new_move_probability) { const move_probability::StandardFeatureSet& feature_set = move_probability::StandardFeatureSet::instance(); Move threatmate = move_probability::StateInfo::findShortThreatmate (state, history.lastMove()); move_probability::StateInfo info(state, progress.progress16(), history, threatmate); feature_set.generateLogProb(info, moves); } else { const rating::StandardFeatureSet& feature_set = rating::StandardFeatureSet::instance(); rating::RatingEnv env; env.history = history; env.make(state, state.pin(state.turn()), state.pin(alt(state.turn())), progress.progress16()); feature_set.generateLogProb(state, env, limit, moves); } for (size_t i=1; i moves; std::istringstream is(moves_str); std::string s; while (is >> s) { const Move move = usi::strToMove(s, state); moves.push_back(move); state.makeMove(move); } assert(!moves.empty()); Move last_move; if (! usi_state.moves.empty()) { last_move = usi_state.moves.back(); } out = "ki2moves "; out += ki2::show(&*moves.begin(), &*moves.end(), current, last_move); } /** * Outputs the number of moves and the last move in the ki2 format. */ void osl::game_playing:: UsiResponse::ki2currentinfo(const NumEffectState& current, std::string& out) { Move last_last_move, last_move; if (1 <= usi_state.moves.size()) { last_move = usi_state.moves.back(); } if (2 <= usi_state.moves.size()) { last_last_move = usi_state.moves[usi_state.moves.size()-2]; } if (last_move.isValid()) { out = "ki2currentinfo "; out += std::to_string(usi_state.moves.size()); out += " "; out += ki2::show(last_move, current, last_last_move); } else { out = "ki2currentinfo"; } } #endif void osl::game_playing:: UsiResponse::isValidPosition(const std::string& line, std::string& out) { out = "invalid"; if (line.find("position") == 0) { try { NumEffectState initial_state; std::vector moves; usi::parse(line.substr(8), initial_state, moves); out = "valid"; } catch (std::exception& e) { // fall through } } } bool osl::game_playing:: UsiResponse::hasImmediateResponse(const std::string& command, std::string& out) { if (command.find("genmove_probability") == 0) { int limit = 2000, value; std::istringstream is(command.substr(strlen("genmove_probability"))); if (is >> value) limit = value; genmoveProbability(limit, out); return true; } if (command.find("genmove") == 0) { genmove(out); return true; } const NumEffectState state = usi_state.currentState(); if (command.find("csashow") == 0) { csashow(state, out); return true; } if (command.find("csamove ") == 0) { csamove(state, command.substr(8), out); return true; } #ifndef MINIMAL if (command.find("ki2moves ") == 0) { ki2moves(state, command.substr(9), out); return true; } if (command.find("ki2currentinfo") == 0) { ki2currentinfo(state, out); return true; } #endif if (command.find("isvalidposition ") == 0) { isValidPosition(command.substr(16), out); return true; } if (command.find("echo ") == 0) { out = command.substr(5); return true; } return false; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/historyToTable.cc0000644000000000000000000001266612316770314022135 0ustar rootroot/* historyToTable.cc */ #include "osl/game_playing/historyToTable.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/pvHistory.h" #include "osl/search/hashRejections.h" #include "osl/hash/hashKeyStack.h" #include "osl/repetitionCounter.h" #include "osl/search/simpleHashTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/container/moveStack.h" #include "osl/csa.h" #include const int osl::game_playing::HistoryToTable::LIMIT = osl::search::SearchTable::HistorySpecialDepth; void osl::game_playing:: HistoryToTable::adjustDominance(const HashKey& key, search::SimpleHashTable& table, int black_win, int white_win, const Move& good_move) { const PieceStand black_stand = key.pieceStand(); const Player turn = key.turn(); for (Ptype ptype: PieceStand::order) { if (black_stand.get(ptype)) { // white win dominance PieceStand new_stand = black_stand; new_stand.sub(ptype); HashKey new_key = key; new_key.setPieceStand(new_stand); SimpleHashRecord *record = table.allocate(new_key, LIMIT); if (record) { const Move record_move = (turn == WHITE) ? good_move : Move::INVALID(); record->setAbsoluteValue(record_move, white_win, LIMIT); record->qrecord.setHistoryValue(record_move, white_win); } } if (black_stand.canAdd(ptype)) { // black win dominance // TODO: // - 加ãˆã‚‹æŒé§’ãŒã‚ã‚‹ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯ã¯æœ¬å½“ã¯ç›¤é¢ã‚’見る必è¦ãŒã‚ã‚‹ // - good_move ãŒvalid ã§ã‚ã‚‹ã“ã¨ã® assert を入れる PieceStand new_stand = black_stand; new_stand.add(ptype); HashKey new_key = key; new_key.setPieceStand(new_stand); SimpleHashRecord *record = table.allocate(new_key, LIMIT); if (record) { const Move record_move = (turn == BLACK) ? good_move : Move::INVALID(); record->setAbsoluteValue(record_move, black_win, LIMIT); record->qrecord.setHistoryValue(record_move, black_win); } } } } void osl::game_playing:: HistoryToTable::adjustTable(const GameState& state, SimpleHashTable& table, int black_win, int draw, int white_win) { const RepetitionCounter& counter = state.counter(); // å„ªè¶Šé–¢ä¿‚ã‚ˆã‚Šåƒæ—¥æ‰‹ãŒå„ªå…ˆ // åƒæ—¥æ‰‹ã¯æ–°ã—ã„å±€é¢å„ªå…ˆ HashKeyStack history = state.hashHistory(); // copy MoveStack move_history = state.moveHistory(); move_history.push(Move::INVALID()); assert(move_history.size() == history.size()); HashKeyStack reverse_history; while (! history.empty()) { const HashKey key = history.top(); history.pop(); assert(move_history.hasLastMove()); const Move last_move = move_history.lastMove(); move_history.pop(); if (key != HashKey(state.state())) // keep current state clean reverse_history.push(key); // set dominance adjustDominance(key, table, black_win, white_win, last_move); } while (! reverse_history.empty()) { // set repetition const HashKey key = reverse_history.top(); reverse_history.pop(); SimpleHashRecord *record = table.allocate(key, LIMIT); const std::pair result = counter.distanceToSennichite(key); if (result.first.isDraw()) { record->setAbsoluteValue(Move::INVALID(), draw*result.second, LIMIT); record->qrecord.setHistoryValue(draw*result.second); } else { assert(result.first.hasWinner()); const int value = (result.first.winner() == BLACK) ? black_win : white_win; record->setAbsoluteValue(Move::INVALID(), value, LIMIT); record->qrecord.setHistoryValue(value); } } } void osl::game_playing:: HistoryToTable::setPV(const PVHistory& pv_history, const GameState& gstate, search::SimpleHashTable& table) { const Player Turn = gstate.state().turn(); NumEffectState state(gstate.initialState()); MoveStack history = gstate.moveHistory(); HashKey key(state); for (int i=history.size(); i>0; --i) { const Move m = history.lastMove(i); if (! m.isNormal() || ! state.isValidMove(m)) { std::cerr << "setPV failed " << i << " " << m << "\n" << state; #ifndef NDEBUG for (int j=history.size(); j>0; --j) std::cerr << history.lastMove(j) << " "; std::cerr << std::endl; #endif return; } const MoveWithComment& pv = pv_history[(history.size()-i) % pv_history.size()]; if (pv.root == key && state.turn() == Turn && !pv.moves.empty()) { if (table.isVerbose()) { std::cerr << "setPV " << csa::show(m) << " "; for (Move p: pv.moves) std::cerr << csa::show(p); std::cerr << "\n"; } if (! pv.move.isNormal() || ! state.isValidMove(pv.move)) { std::cerr << "setPV failed (corrupt pv) " << pv.move << "\n"; } else { NumEffectState state_copy = state; state_copy.makeMove(pv.move); HashKey cur = key.newHashWithMove(pv.move); for (Move move: pv.moves) { SimpleHashRecord *record = table.allocate(cur, 1000); if (record) { if (move == Move::PASS(state_copy.turn()) // pass is allowed here || state_copy.isValidMove(move)) { record->setBestMove(move); } else { std::cerr << "setPV failed (corrupt pv) " << i << " " << move << "\n"; break; } } state_copy.makeMove(move); cur = cur.newHashWithMove(move); } } } key = key.newHashWithMove(m); state.makeMove(m); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/speculativeModel.cc0000644000000000000000000000053512316770314022456 0ustar rootroot/* speculativeModel.cc */ #include "osl/game_playing/speculativeModel.h" osl::game_playing:: SpeculativeModel::~SpeculativeModel() { } void osl::game_playing:: SpeculativeModel::setMaxThreads(int) { } void osl::game_playing:: SpeculativeModel::clearResource() { } /* ------------------------------------------------------------------------- */ libosl-0.8.0.orig/full/osl/game_playing/weightTracer.cc0000644000000000000000000001270212335610142021571 0ustar rootroot/* weightTracer.cc */ #include "osl/game_playing/weightTracer.h" #include "osl/game_playing/openingBookTracer.h" #include "osl/book/openingBook.h" #include "osl/csa.h" #include "osl/random.h" #include #include #include #ifdef _WIN32 #include #endif osl::game_playing:: WeightTracer::WeightTracer(WeightedBook& b, bool v, const int weight_coef_for_the_initial_move, const int weight_coef) : book(b), state_index(b.startState()), start_index(b.startState()), turn(BLACK), weight_coef_for_the_initial_move(weight_coef_for_the_initial_move), weight_coef(weight_coef) { verbose = v; } osl::game_playing:: WeightTracer::WeightTracer(const WeightTracer& copy) : OpeningBookTracer(copy), book(copy.book), state_index(copy.state_index), start_index(copy.start_index), turn(copy.turn), state_stack(copy.state_stack), weight_coef_for_the_initial_move(copy.weight_coef_for_the_initial_move), weight_coef(copy.weight_coef) { } osl::game_playing::OpeningBookTracer* osl::game_playing:: WeightTracer::clone() const { return new WeightTracer(*this); } void osl::game_playing:: WeightTracer::update(Move move) { if (verbose) { std::cerr << "WeightTracer " << " Move: " << csa::show(move) << " "; const time_t now = time(0); char ctime_buf[64]; std::cerr << ctime_r(&now, ctime_buf) << std::endl; } state_stack.push(state_index); assert(move.player() == turn); turn = alt(turn); if (! isOutOfBook()) { const std::vector& moves = book.moves(state_index); for (size_t i=0; i" << state_index << "\n"; return; } } if (verbose) std::cerr << "book: end" << "\n"; } state_index = -1; } void osl::game_playing:: WeightTracer::popMove() { state_index = state_stack.top(); state_stack.pop(); turn = alt(turn); if (verbose) std::cerr << "WeightTracer " << this << " pop: " << turn << std::endl; } bool osl::game_playing:: WeightTracer::isOutOfBook() const { return state_index < 0; } const osl::Move osl::game_playing:: WeightTracer::selectMoveAtRandom(const std::vector& moves) const { if (verbose) std::cerr << "book " << moves.size() << " candidates\n" << std::endl; int max_weight_index = 0; int max_weight = 0; int sum = 0; for (size_t i=0; i= 0) { if (verbose) { const int weight = moves[maxIndex].weight; std::cerr << "book " << 100.0*weight/sum << '%'; if (weight != max_weight) std::cerr << " (c.f. " << 100.0*max_weight/sum << " " << csa::show(moves[max_weight_index].move) << ")"; std::cerr << std::endl; } return moves[maxIndex].move; } return Move::INVALID(); } const osl::Move osl::game_playing:: WeightTracer::selectMove() const { const std::vector raw_moves = book.moves(state_index); std::vector moves; int max_weight = 0; for (size_t i=0; i moves = book.moves(state_index); const int original_size = moves.size(); std::sort(moves.begin(), moves.end(), osl::book::WMoveSort()); /* * Select top_n moves. * - WMoves with the same weight are included in the result. * The size of the result vector might be greater than topn. * - Zero-weighed WMoves are exluded. The size of the result vector * might be less than topn. */ int top = topn; std::vector::iterator it = moves.begin(); for (/*none*/; it != moves.end() && top > 0; ++it) { if (it->weight == 0) break; if (it->weight != boost::next(it)->weight) top -= 1; } moves.erase(it, moves.end()); if (verbose) { std::cerr << "book: there remain " << moves.size() << " candidates of " << original_size << " moves\n"; } if (moves.empty()) return Move::INVALID(); return selectMoveAtRandom(moves); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/computerPlayer.h0000644000000000000000000000467712316770314022041 0ustar rootroot/* computerPlayer.h */ #ifndef GAME_PLAYING_COMPUTERPLAYER_H #define GAME_PLAYING_COMPUTERPLAYER_H #include "osl/search/moveWithComment.h" #include "osl/numEffectState.h" namespace osl { namespace container { class MoveVector; } namespace search { struct TimeAssigned; } namespace game_playing { class GameState; class ComputerPlayer { protected: bool speculative_search_allowed; public: ComputerPlayer() : speculative_search_allowed(false) { } virtual ~ComputerPlayer(); /** new ã—ãŸã‚‚ã®ã‚’返㙠*/ virtual ComputerPlayer* clone() const = 0; virtual void pushMove(Move m)=0; virtual void popMove()=0; /** @return success to stop */ virtual bool isReasonableMove(const GameState&, Move move, int pawn_sacrifice); /** * @param seconds 残りæŒã¡æ™‚é–“ */ virtual const MoveWithComment selectBestMove(const GameState&, int seconds, int elapsed, int byoyomi)=0; virtual void setInitialState(const NumEffectState&); /** * ç›¸æ‰‹æ™‚é–“ã®æŽ¢ç´¢ã‚’è¨±å¯ã™ã‚‹ (GameManager ãŒæ“作) */ virtual void allowSpeculativeSearch(bool value); /** 探索をã¨ã‚ã‚‹ */ virtual bool stopSearchNow(); virtual void setRootIgnoreMoves(const MoveVector *rim, bool prediction); }; class ComputerPlayerSelectBestMoveInTime { public: virtual ~ComputerPlayerSelectBestMoveInTime(); virtual const MoveWithComment selectBestMoveInTime(const GameState&, const search::TimeAssigned&)=0; }; /** * å¸¸ã«æŠ•äº†ã™ã‚‹ */ class ResignPlayer : public ComputerPlayer { public: ~ResignPlayer(); ComputerPlayer* clone() const { return new ResignPlayer(); } void pushMove(Move m); void popMove(); const MoveWithComment selectBestMove(const GameState&, int, int, int); }; /** * åˆæ³•æ‰‹ã‚’ãƒ©ãƒ³ãƒ€ãƒ ã«æŒ‡ã™ */ class RandomPlayer : public ComputerPlayer { public: ComputerPlayer* clone() const { return new RandomPlayer(); } ~RandomPlayer(); void pushMove(Move m); void popMove(); const MoveWithComment selectBestMove(const GameState&, int, int, int); }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_COMPUTERPLAYER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/searchPlayer.h0000644000000000000000000001264612316770314021443 0ustar rootroot#ifndef GAME_PLAYING_SEARCHPLAYER_H #define GAME_PLAYING_SEARCHPLAYER_H #include "osl/game_playing/computerPlayer.h" #include "osl/search/searchTimer.h" #include "osl/misc/milliSeconds.h" namespace osl { namespace misc { class RealTime; } namespace search { class CountRecorder; class SimpleHashTable; struct TimeAssigned; class SearchMonitor; } namespace checkmate { class DualDfpn; } namespace game_playing { struct Config; bool operator==(const Config& l, const Config& r); struct PVHistory; /** * MtdfPlayer 㨠AlphaBetaPlayer ã®å…±é€šéƒ¨åˆ† */ class SearchPlayer : public ComputerPlayer, public ComputerPlayerSelectBestMoveInTime { public: struct NtesukiThread; struct Config { int limit; size_t node_limit; size_t table_size; int table_record_limit; int initial_limit; int deepening_step; size_t total_checkmate_limit; int verbose; /** SearchBase::next_iteration_coefficient ã«è¨­å®šã™ã‚‹ã‚‚ã® */ double next_iteration_coefficient; /** åƒæ—¥æ‰‹ã«å¯¾ã™ã‚‹ãƒœãƒ¼ãƒŠã‚¹/ãƒšãƒŠãƒ«ãƒ†ã‚£ã®æ­©ã®ç›¸å¯¾å€¤. -2ãªã‚‰1æ­©æã—ã¦ã‚‚é¿ã‘ã‚‹ */ double draw_coef; bool save_pv; uint64_t node_count_hard_limit; /** 最善手以外も探索ã™ã‚‹å¹… */ int multi_pv_width; std::vector > monitors; Config(); friend bool operator==(const Config& l, const Config& r); }; protected: Config config; std::shared_ptr table_ptr; std::shared_ptr checkmate_ptr; std::unique_ptr recorder_ptr; volatile bool searching; std::unique_ptr searcher; /** 探索ã«å…¥ã‚‹å‰ã«æ­¢ã‚ã‚‹ */ volatile bool plan_stop; const MoveVector *root_ignore_moves; // acquaintance bool prediction_for_speculative_search; std::unique_ptr pv_history; int almost_resign_count; public: SearchPlayer(); SearchPlayer(const SearchPlayer&); ~SearchPlayer(); void setDepthLimit(int limit, int initial_limit, int deepening_step); void setNodeLimit(size_t node_limit); void setNodeCountHardLimit(size_t node_limit); void setTableLimit(size_t size, int record_limit); void setVerbose(int verbose=1); void setDrawCoef(double new_value) { config.draw_coef = new_value; } void setNextIterationCoefficient(double new_value); double nextIterationCoefficient() const { return config.next_iteration_coefficient; } void enableSavePV(bool enable=true) { config.save_pv = enable; } void enableMultiPV(int width) { config.multi_pv_width = width; } void addMonitor(const std::shared_ptr&); /** 所有権移転 */ void resetRecorder(search::CountRecorder *new_recorder); void pushMove(Move m); void popMove(); /** * other ã®å±€é¢è¡¨ã¨å–り替ãˆã‚‹ */ void swapTable(SearchPlayer& other); const search::SimpleHashTable* table() const { return table_ptr.get(); } const search::CountRecorder& recorder() const { return *recorder_ptr; } bool stopSearchNow(); bool canStopSearch(); // 呼出をçœç•¥ã•れãªã„よã†å¿µã®ç‚º const ã§ãªãã—㟠/** * searchWithSecondsForThisMove を呼ã³å‡ºã™ */ const MoveWithComment selectBestMove(const GameState&, int limit, int elapsed, int byoyomi); const MoveWithComment selectBestMoveInTime(const GameState&, const search::TimeAssigned&); static const search::TimeAssigned assignTime(const GameState& state, int limit, int elapsed, int byoyomi, int verbose); const search::TimeAssigned assignTime(const GameState& state, int limit, int elapsed, int byoyomi) const; void saveSearchResult(const GameState&, const MoveWithComment&); protected: template ComputerPlayer* cloneIt(const Searcher&) const; /** @return time consumed in milliseconds */ const milliseconds setUpTable(const GameState&, int pawn_value); template const MoveWithComment search(const GameState&, const search::TimeAssigned&); template bool isReasonableMoveBySearch(Searcher&, Move move, int pawn_sacrifice); template static int pawnValue(); template static int pawnValueOfTurn(Player turn); const search::TimeAssigned adjust(const search::TimeAssigned& org, const milliseconds& elapsed); public: virtual const MoveWithComment searchWithSecondsForThisMove(const GameState&, const search::TimeAssigned&)=0; void setRootIgnoreMoves(const MoveVector *rim, bool prediction) { root_ignore_moves = rim; prediction_for_speculative_search = prediction; } const Config& getConfig() const { return config; } static int secondsForThisMove(const GameState& state, int limit, int elapsed, int byoyomi, int verboseness); int secondsForThisMove(const GameState& state, int limit, int elapsed, int byoyomi) const; void setTimeAssign(const search::TimeAssigned& new_assign); const time_point startTime() const; }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_SEARCHPLAYER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/alphaBetaPlayer.h0000644000000000000000000000461712316770314022056 0ustar rootroot/* alphaBetaPlayer.h */ #ifndef GAMEPLAYING_ALPHABETAPLAYER_H #define GAMEPLAYING_ALPHABETAPLAYER_H #include "osl/game_playing/searchPlayer.h" namespace osl { namespace search { struct AlphaBeta2SharedRoot; } namespace game_playing { class AlphaBeta2ProgressEvalPlayer : public SearchPlayer { public: AlphaBeta2ProgressEvalPlayer(); ~AlphaBeta2ProgressEvalPlayer(); ComputerPlayer* clone() const; const MoveWithComment searchWithSecondsForThisMove(const GameState&, const search::TimeAssigned&); bool isReasonableMove(const GameState&, Move move, int pawn_sacrifice); }; class AlphaBeta2OpenMidEndingEvalPlayer : public SearchPlayer { public: AlphaBeta2OpenMidEndingEvalPlayer(); ~AlphaBeta2OpenMidEndingEvalPlayer(); ComputerPlayer* clone() const; const MoveWithComment searchWithSecondsForThisMove(const GameState&, const search::TimeAssigned&); bool isReasonableMove(const GameState&, Move move, int pawn_sacrifice); const MoveWithComment analyzeWithSeconds(const GameState& gs, const search::TimeAssigned& org, search::AlphaBeta2SharedRoot& out); }; class AlphaBeta3OpenMidEndingEvalPlayer : public SearchPlayer { public: AlphaBeta3OpenMidEndingEvalPlayer(); ~AlphaBeta3OpenMidEndingEvalPlayer(); ComputerPlayer* clone() const; const MoveWithComment searchWithSecondsForThisMove(const GameState&, const search::TimeAssigned&); bool isReasonableMove(const GameState&, Move move, int pawn_sacrifice); }; class AlphaBeta4Player : public SearchPlayer { public: AlphaBeta4Player(); ~AlphaBeta4Player(); ComputerPlayer* clone() const; const MoveWithComment searchWithSecondsForThisMove(const GameState&, const search::TimeAssigned&); bool isReasonableMove(const GameState&, Move move, int pawn_sacrifice); }; class UsiProxyPlayer : public SearchPlayer { public: UsiProxyPlayer(); ~UsiProxyPlayer(); ComputerPlayer* clone() const; const MoveWithComment searchWithSecondsForThisMove(const GameState&, const search::TimeAssigned&); bool isReasonableMove(const GameState&, Move move, int pawn_sacrifice); }; } // namespace game_playing } // namespace osl #endif /* GAMEPLAYING_ALPHABETAPLAYER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/timeKeeper.h0000644000000000000000000000137212316770314021105 0ustar rootroot/* timeKeeper.h */ #ifndef GAME_PLAYING_TIMEKEEPER_H #define GAME_PLAYING_TIMEKEEPER_H #include "osl/basic_type.h" #include namespace osl { namespace game_playing { class TimeKeeper { struct Stack; std::unique_ptr seconds; public: TimeKeeper(); TimeKeeper(int black_time, int white_time); ~TimeKeeper(); void reset(int black_time, int white_time); void pushMove(Player, int seconds); void popMove(); int timeLeft(Player) const; int timeElapsed(Player) const; int timeLimit(Player) const; }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_TIMEKEEPER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/searchPlayer.tcc0000644000000000000000000000774112316770314021765 0ustar rootroot/* searchPlayer.tcc */ #ifndef GAMEPLAYING_SEARCHPLAYER_TCC #define GAMEPLAYING_SEARCHPLAYER_TCC #include "osl/game_playing/searchPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/pvHistory.h" #include "osl/search/searchState2.h" #include "osl/eval/evalTraits.h" #include "osl/container/moveStack.h" #ifdef USE_NTESUKI # include "osl/ntesuki/ntesukiSearcher.h" # include "osl/ntesuki/ntesukiMoveGenerator.h" #endif #include #include #ifdef USE_NTESUKI struct osl::game_playing::SearchPlayer::NtesukiThread { explicit NtesukiThread(Move& next_move, volatile bool *thread_finished, volatile bool *stop_flag, NumEffectState state); void operator()(); Move& next_move; volatile bool *thread_finished; volatile bool *stop_flag; NumEffectState state; }; #endif template osl::game_playing::ComputerPlayer* osl::game_playing:: SearchPlayer::cloneIt(const Searcher& copy) const { return new Searcher(copy); } template int osl::game_playing:: SearchPlayer::pawnValue() { typedef typename Searcher::eval_t eval_t; return abs(eval_t::captureValue(newPtypeO(BLACK,PAWN)))/2; } template int osl::game_playing:: SearchPlayer::pawnValueOfTurn(Player turn) { return pawnValue() * eval::delta(turn); } template const osl::search::MoveWithComment osl::game_playing:: SearchPlayer::search(const GameState& state, const search::TimeAssigned& msec) { Searcher& searcher = dynamic_cast(*this->searcher); searcher.setRootIgnoreMoves(root_ignore_moves, prediction_for_speculative_search); typedef typename Searcher::eval_t eval_t; if (! eval_t::initialized()) throw std::runtime_error("evaluation function not initialized"); const MoveStack& history = state.moveHistory(); #ifdef USE_NTESUKI volatile bool ntesuki_thread_finished; volatile bool stop_ntesuki; Move ntesuki_next_move = Move::INVALID(); NtesukiThread thread(ntesuki_next_move, &ntesuki_thread_finished, &stop_ntesuki, state.state()); boost::thread ntesuki_thread(thread); #endif searcher.setHistory(history); searcher.enableMultiPV(config.multi_pv_width); for (const std::shared_ptr& m: config.monitors) searcher.addMonitor(m); int deepening_step_for_this_move = config.deepening_step; if (msec.standard < milliseconds::max()) { if (toSeconds(msec.standard) < 10.0) deepening_step_for_this_move = std::min(100, config.deepening_step); } searcher.setNextIterationCoefficient(config.next_iteration_coefficient); searcher.setNodeCountHardLimit(config.node_count_hard_limit); MoveWithComment best_move; best_move.root = HashKey(state.state()); if (plan_stop) return best_move; searching = true; best_move.move = searcher.computeBestMoveIteratively(config.limit, deepening_step_for_this_move, config.initial_limit, config.node_limit, msec, &best_move); searching = false; #ifdef USE_NTESUKI if (ntesuki_thread_finished) { if (ntesuki_next_move.isNormal()) { return ntesuki_next_move; } else { //ntesuki_finished } } else { //force_finish stop_ntesuki = true; ntesuki_thread.join(); } #endif saveSearchResult(state, best_move); static const int resign_value = OslConfig::resignThreshold(); if (! state.state().inCheck() && best_move.move.isNormal() && best_move.value*sign(state.state().turn()) < -resign_value) { ++almost_resign_count; if (almost_resign_count >= 3) best_move.move = Move(); } else { almost_resign_count = 0; } return best_move; } template bool osl::game_playing:: SearchPlayer::isReasonableMoveBySearch(Searcher& searcher, Move move, int pawn_sacrifice) { return searcher.isReasonableMove(move, pawn_sacrifice); } #endif /* GAMEPLAYING_SEARCHPLAYER_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/openingBookTracer.h0000644000000000000000000000261212316770314022424 0ustar rootroot/* openingBookTracer.h */ #ifndef _OPENINGBOOKTRACER_H #define _OPENINGBOOKTRACER_H #include "osl/basic_type.h" namespace osl { namespace game_playing { /** * 定跡ã®è¿½è·¡ */ class OpeningBookTracer { protected: bool verbose; public: OpeningBookTracer() : verbose(false) {} virtual ~OpeningBookTracer(); /** new ã—ãŸã‚‚ã®ã‚’返㙠*/ virtual OpeningBookTracer* clone() const = 0; /** 指ã—ãŸæ‰‹ã«å¯¾å¿œã—ã¦çŠ¶æ…‹ã‚’æ›´æ–°ã™ã‚‹ï¼Ž */ virtual void update(Move)=0; /** * è‰¯ã„æ‰‹ã‚’探ã™ï¼ŽçŠ¶æ…‹ã¯æ›´æ–°ã—ãªã„. * @return 定跡をã¯ãšã‚ŒãŸã‚‰ Move::INVALID() */ virtual const Move selectMove() const=0; virtual bool isOutOfBook() const=0; /** * 一手å‰ã®çŠ¶æ…‹ã«æˆ»ã™ */ virtual void popMove()=0; bool isVerbose() const { return verbose; } }; /** * 定跡無㗠*/ class NullBook : public OpeningBookTracer { public: ~NullBook(); OpeningBookTracer* clone() const { return new NullBook(); } void update(Move); const Move selectMove() const; bool isOutOfBook() const; void popMove(); }; } // namespace game_playing } // namespace osl #endif /* _OPENINGBOOKTRACER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/searchPlayer.cc0000644000000000000000000002767212316770314021606 0ustar rootroot/* searchPlayer.cc */ #include "osl/game_playing/searchPlayer.h" #include "osl/game_playing/searchPlayer.tcc" #include "osl/game_playing/historyToTable.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/pvHistory.h" #include "osl/search/searchRecorder.h" #include "osl/search/simpleHashRecord.h" #include "osl/search/simpleHashTable.h" #include "osl/search/timeControl.h" #include "osl/search/searchTimer.h" #include "osl/search/fixedEval.h" #include "osl/search/bigramKillerMove.h" #include "osl/enterKing.h" #include "osl/progress/effect5x3.h" #include "osl/container/moveStack.h" #include "osl/hash/hashRandom.h" #include #include #include osl::game_playing::SearchPlayer:: Config::Config() : limit(1200), node_limit(800000), table_size(10000), table_record_limit(0), initial_limit(600), deepening_step(200), verbose(0), next_iteration_coefficient(3), draw_coef(0), save_pv(true), node_count_hard_limit(std::numeric_limits::max()), multi_pv_width(0) { } bool osl::game_playing::operator==(const SearchPlayer::Config& l, const SearchPlayer::Config& r) { return (l.limit == r.limit) && (l.node_limit == r.node_limit) && (l.table_size == r.table_size) && (l.table_record_limit == r.table_record_limit) && (l.initial_limit == r.initial_limit) && (l.deepening_step == r.deepening_step) && (l.verbose == r.verbose) && (l.next_iteration_coefficient == r.next_iteration_coefficient) && (l.draw_coef == r.draw_coef); } osl::game_playing:: SearchPlayer::SearchPlayer() : recorder_ptr(new CountRecorder()), searching(0), plan_stop(false), root_ignore_moves(0), prediction_for_speculative_search(0), pv_history(new PVHistory) { } osl::game_playing:: SearchPlayer::SearchPlayer(const SearchPlayer& copy) : ComputerPlayer(copy), ComputerPlayerSelectBestMoveInTime(copy), config(copy.config), recorder_ptr(new CountRecorder()), searching(0), plan_stop(false), root_ignore_moves(0), prediction_for_speculative_search(0), pv_history(new PVHistory(*copy.pv_history)), almost_resign_count(0) { } osl::game_playing:: SearchPlayer::~SearchPlayer() { } void osl::game_playing:: SearchPlayer::swapTable(SearchPlayer& other) { table_ptr.swap(other.table_ptr); } bool osl::game_playing:: SearchPlayer::canStopSearch() { return searching; } bool osl::game_playing:: SearchPlayer::stopSearchNow() { plan_stop = true; if (! searching) { std::cerr << "SearchPlayer not searching "; const time_t now = time(0); char ctime_buf[64]; std::cerr << ctime_r(&now, ctime_buf); return false; } searcher->stopNow(); return true; } void osl::game_playing:: SearchPlayer::resetRecorder(search::CountRecorder *new_recorder) { recorder_ptr.reset(new_recorder); } const osl::search::TimeAssigned osl::game_playing:: SearchPlayer::adjust(const search::TimeAssigned& org, const milliseconds& consumed) { if (consumed < org.standard/8) return search::TimeAssigned(org.standard - consumed, org.max - consumed); // spent too much seconds in preparation search::SearchTimer::adjustMemoryUseLimit(0.9); return search::TimeAssigned(std::min(org.standard - org.standard/8, org.max - consumed), org.max - consumed); } const osl::milliseconds osl::game_playing:: SearchPlayer::setUpTable(const GameState& gs, int pawn_value) { const time_point started = clock::now(); time_t t = time(0); char ctime_buf[64]; if (table_ptr.get() && table_ptr->verboseLevel() > 2) { std::cerr << "setUpTable " << ctime_r(&t, ctime_buf) << std::flush; } // release cherkmate_ptr first checkmate_ptr.reset(); const int black_win = search::FixedEval::winByLoop(BLACK); const int white_win = search::FixedEval::winByLoop(WHITE); if (table_ptr.get()) { table_ptr->clear(); } else { try { table_ptr.reset(new SimpleHashTable(config.table_size, config.table_record_limit, config.verbose)); } catch (std::bad_alloc&) { std::cerr << "\atable allocation failed, try agaian" << std::endl; table_ptr.reset(new SimpleHashTable(config.table_size, config.table_record_limit, config.verbose)); } } table_ptr->setVerbose(config.verbose); HistoryToTable::adjustTable(gs, *table_ptr, black_win, config.draw_coef*pawn_value, white_win); if (config.save_pv) HistoryToTable::setPV(*pv_history, gs, *table_ptr); try { checkmate_ptr.reset(new DualDfpn()); } catch (std::bad_alloc&) { std::cerr << "\acheckmate allocation failed, try agaian" << std::endl; checkmate_ptr.reset(new DualDfpn()); } checkmate_ptr->writeRootHistory(gs.counter(), gs.moveHistory(), gs.state(), gs.state().turn()); if (table_ptr->verboseLevel() > 2) { t = time(0); std::cerr << "setup done in " << toSeconds(clock::now() - started) << " sec. " << ctime_r(&t, ctime_buf) << std::flush; } #ifndef MINIMAL if (OslConfig::evalRandom()) HashRandom::setUp(1.0*OslConfig::evalRandom()*pawn_value/100); #endif return duration_cast(clock::now() - started); } void osl::game_playing:: SearchPlayer::setDepthLimit(int l, int il, int ds) { config.limit = l; config.initial_limit = il; config.deepening_step = ds; } void osl::game_playing:: SearchPlayer::setNodeLimit(size_t nl) { config.node_limit = nl; } void osl::game_playing:: SearchPlayer::setNodeCountHardLimit(size_t nl) { config.node_count_hard_limit = nl; } void osl::game_playing:: SearchPlayer::setTableLimit(size_t size, int record_limit) { config.table_size = size; config.table_record_limit = record_limit; table_ptr.reset(); } void osl::game_playing:: SearchPlayer::setVerbose(int v) { config.verbose = v; if (table_ptr) table_ptr->setVerbose(v); } void osl::game_playing:: SearchPlayer::setNextIterationCoefficient(double new_value) { config.next_iteration_coefficient = new_value; if (searcher) searcher->setNextIterationCoefficient(new_value); } void osl::game_playing:: SearchPlayer::addMonitor(const std::shared_ptr& m) { config.monitors.push_back(m); } void osl::game_playing:: SearchPlayer::pushMove(Move /*move*/) { checkmate_ptr.reset(); if (speculative_search_allowed) table_ptr.reset(); } void osl::game_playing:: SearchPlayer::popMove() { checkmate_ptr.reset(); if (speculative_search_allowed) table_ptr.reset(); } int osl::game_playing:: SearchPlayer::secondsForThisMove(const GameState& state, int time_limit, int elapsed, int byoyomi) const { return secondsForThisMove(state, time_limit, elapsed, byoyomi, table_ptr.get() ? table_ptr->verboseLevel() : 0); } int osl::game_playing:: SearchPlayer::secondsForThisMove(const GameState& state, int time_limit, int elapsed, int byoyomi, int verboseness) { if (byoyomi < 0) return -1; // ç„¡é™ if (time_limit - elapsed < byoyomi) return byoyomi; const int time_limit_org = time_limit; const int moves = state.moveHistory().size(); if (byoyomi == 0) { // 330手指ã›ã‚‹ã‚ˆã†ã«ã™ã‚‹ // http://www32.ocn.ne.jp/~yss/csa14rep.html // 90ç§’ã‹ã‚‰1秒将棋ã«å…¥ã‚‹ã®ã§240ã§è‰¯ã„ (330-90) time_limit -= std::max(0, (240 - moves)); } const int time_left = time_limit - elapsed; if (time_left <= 1) return 1; int seconds_for_this_move = search::TimeControl::secondsForThisMove(time_left); // Think more if book leads us to near endgame const progress::Effect5x3 progress(state.state()); if (time_left >= 600*time_limit_org/1500) { if ((progress.progress16().value() >= 15) && ((progress.progress16(BLACK).value() >= 13) || (progress.progress16(WHITE).value() >= 13))) { if (verboseness) std::cerr << " time control endgame ext\n"; return seconds_for_this_move*2; } } if (byoyomi == 0 || time_left >= byoyomi*60) { // do not think too much in opening if (progress.progress16().value() == 0) { if (verboseness) std::cerr << " time control progress0 limit " << 25*time_limit_org/1500 << "\n"; return std::min(std::max(1, 25*time_limit_org/1500), seconds_for_this_move); } if (progress.progress16().value() <= 3 && moves <= 40) { if (verboseness) std::cerr << " time control progress4 limit " << 38*time_limit_org/1500 << "\n"; return std::min(std::max(1, 38*time_limit_org/1500), seconds_for_this_move); } } // others seconds_for_this_move += byoyomi; if (byoyomi >= 10 && time_left >= byoyomi*2) seconds_for_this_move += byoyomi/2; return seconds_for_this_move; } const osl::search::TimeAssigned osl::game_playing:: SearchPlayer::assignTime(const GameState& state, int limit, int elapsed, int byoyomi) const { return assignTime(state, limit, elapsed, byoyomi, table_ptr.get() ? table_ptr->verboseLevel() : 0); } const osl::search::TimeAssigned osl::game_playing:: SearchPlayer::assignTime(const GameState& state, int limit, int elapsed, int byoyomi, int verboseness) { const int seconds_for_this_move = secondsForThisMove(state, limit, elapsed, byoyomi, verboseness); const int seconds_max = (byoyomi && (limit - elapsed) < byoyomi) ? seconds_for_this_move : std::min(seconds_for_this_move*5, std::max(seconds_for_this_move, (limit-elapsed)/2)); return search::TimeAssigned(milliseconds(seconds_for_this_move*1000), milliseconds(seconds_max*1000)); } const osl::search::MoveWithComment osl::game_playing:: SearchPlayer::selectBestMove(const GameState& state, int limit, int elapsed, int byoyomi) { return selectBestMoveInTime(state, assignTime(state, limit, elapsed, byoyomi)); } const osl::search::MoveWithComment osl::game_playing:: SearchPlayer::selectBestMoveInTime(const GameState& state, const search::TimeAssigned& msec) { if (EnterKing::canDeclareWin(state.state())) return MoveWithComment(Move::DeclareWin()); if (msec.standard == msec.max && config.next_iteration_coefficient > 1.0) setNextIterationCoefficient(1.0); return searchWithSecondsForThisMove(state, msec); } void osl::game_playing:: SearchPlayer::saveSearchResult(const GameState& state, const MoveWithComment& best_move) { (*pv_history)[state.moveHistory().size() % pv_history->size()] = best_move; } void osl::game_playing:: SearchPlayer::setTimeAssign(const search::TimeAssigned& new_assign) { if (searcher) { searcher->setTimeAssign(new_assign); } } const osl::time_point osl::game_playing:: SearchPlayer::startTime() const { if (searcher) { return searcher->startTime(); } return time_point(); } #ifdef USE_NTESUKI osl::game_playing::SearchPlayer:: NtesukiThread::NtesukiThread(Move& next_move, volatile bool *thread_finished, volatile bool *stop_flag, NumEffectState state) : next_move(next_move), thread_finished(thread_finished), stop_flag(stop_flag), state(state) { } void osl::game_playing::SearchPlayer:: NtesukiThread::operator()() { std::cerr << "start ntesuki search\n"; *thread_finished = false; const Player P = state.turn(); const HashKey key = osl::HashKey::calcHash(state);; std::unique_ptr gam(new osl::ntesuki::GetAttackMoves()); std::unique_ptr gdm(new osl::ntesuki::GetDefenseMoves()); osl::ntesuki::NtesukiSearcher searcher(state, gam.get(), gdm.get(), 500000u, stop_flag, true, 2); try { int ntesuki_num = searcher.searchSlow(P, 10000000); if (-1 != ntesuki_num) { const osl::ntesuki::PdNtesukiTable& table = searcher.getTableSlow(P); const osl::ntesuki::PdNtesukiRecord *record = table.find(key); next_move = record->getBestMove(ntesuki_num).move(); } } catch (ntesuki::ReadNodeLimit& e) { } catch (ntesuki::TableFull& e) { } catch (std::runtime_error& e) { std::cerr << e.what() << "\n"; } std::cerr << "end ntesuki search\n"; *thread_finished = true; } #endif /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/recordTracer.cc0000644000000000000000000000367312316770314021576 0ustar rootroot/* recordTracer.cc */ #include "osl/game_playing/recordTracer.h" #include "osl/record/kisen.h" #include "osl/csa.h" #include osl::game_playing:: RecordTracer::RecordTracer(const std::vector& m, bool v) : moves(m), verbose(v) { state_index.push(moves.empty() ? -1 : 0); if (verbose && (! moves.empty())) std::cerr << "book: expect " << csa::show(moves[0]) << "\n"; } osl::game_playing:: RecordTracer::RecordTracer(const RecordTracer& copy) : OpeningBookTracer(copy), moves(copy.moves), state_index(copy.state_index), verbose(copy.verbose) { } osl::game_playing:: RecordTracer::~RecordTracer() { } osl::game_playing::OpeningBookTracer* osl::game_playing:: RecordTracer::clone() const { return new RecordTracer(*this); } void osl::game_playing:: RecordTracer::update(Move move) { if ((! isOutOfBook()) && (move == moves.at(stateIndex()))) { const size_t next_index = stateIndex()+1; if (next_index < moves.size()) { state_index.push(next_index); if (verbose) std::cerr << "book: expect " << csa::show(moves[next_index]) << "\n"; return; } } state_index.push(-1); } const osl::Move osl::game_playing:: RecordTracer::selectMove() const { if (isOutOfBook()) return Move::INVALID(); return moves.at(stateIndex()); } bool osl::game_playing:: RecordTracer::isOutOfBook() const { return stateIndex() < 0; } void osl::game_playing:: RecordTracer::popMove() { state_index.pop(); } const osl::game_playing::RecordTracer osl::game_playing:: RecordTracer::kisenRecord(const char *filename, int id, unsigned int num_moves, bool verbose) { KisenFile kisen(filename); std::vector moves = kisen.moves(id); if (moves.size() > num_moves) moves.resize(num_moves); return RecordTracer(moves, verbose); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaClient.cc0000644000000000000000000001240512335610142021046 0ustar rootroot/* csaClient.cc */ #include "osl/game_playing/csaClient.h" #include "osl/game_playing/gnuShogiClient.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/csaLogger.h" #include "osl/game_playing/csaStopwatch.h" #include "osl/search/moveWithComment.h" #include "osl/csa.h" #include "osl/container/moveStack.h" #include "osl/sennichite.h" #include #ifdef _WIN32 #include #include #endif osl::game_playing:: CsaClient::CsaClient(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l, std::istream& is, std::ostream& os) : CuiClient(black, white, l, is, os), show_move_with_comment(false), silent(false), line(128,' ') { setComputerPlayer(WHITE, true); } osl::game_playing:: CsaClient::~CsaClient() { } bool osl::game_playing:: CsaClient::readAndProcessCommand() { char ctime_buf[64]; if (! silent) { std::cerr << "\nCsaClient start waiting "; const time_t now = time(0); std::cerr << ctime_r(&now, ctime_buf) << state->state() << "TIME[" << time_keeper.timeElapsed(BLACK) << ":" << time_keeper.timeElapsed(WHITE) << "] "; const MoveStack& history = state->moveHistory(); const std::vector& eval_history = state->evalStack(); for (int i=1; i<=8 && history.hasLastMove(i); ++i) { std::cerr << "(" << history.size() - i + 1 << ")" << csa::show(history.lastMove(i)); if (i-1 < (int)eval_history.size() && eval_history[eval_history.size()-i]) std::cerr << "<" << eval_history[eval_history.size()-i] << ">"; std::cerr << " "; } std::cerr << std::endl << std::endl; } CsaStopwatch timer; std::getline(is, line); if (! silent) { std::cerr << "\nCsaClient read " << line << " "; const time_t now = time(0); std::cerr << ctime_r(&now, ctime_buf) << std::endl; } const long op_think_time = timer.read(); if (! is) { const char *message = "istream error (maybe closed)"; std::cerr << message << std::endl; logger->writeComment(message); throw EndGame(); } if (line == "%TORYO") { logger->resign(state->state().turn()); throw EndGame(); } // TODO: %MATTA, %CHUDAN try { const Move op_move=csa::strToMove(line, state->state()); const GameState::MoveType illegal_move = state->isIllegal(op_move); if (illegal_move) { std::cerr << "illegal move: " << line << "\n"; logger->inputError(line.c_str()); if (illegal_move == GameState::PAWN_DROP_FOUL) logger->writeComment("pawn drop foul"); else if (illegal_move == GameState::UNSAFE_KING) logger->writeComment("unsafe king"); else if (illegal_move == GameState::OTHER_INVALID) logger->writeComment("other illegal move"); os << "%CHUDAN" << std::endl; throw EndGame(); } const Sennichite result = pushMove(MoveWithComment(op_move), op_think_time); if (! result.isNormal()) { os << "%SENNICHITE" << std::endl; logger->endByRepetition(result); throw EndGame(); } if (! silent) { std::cerr << state->state() << "TIME[" << time_keeper.timeElapsed(BLACK) << ":" << time_keeper.timeElapsed(WHITE) << "] "; const MoveStack& history = state->moveHistory(); const std::vector& eval_history = state->evalStack(); for (int i=1; i<=8 && history.hasLastMove(i); ++i) { std::cerr << "(" << history.size() - i + 1 << ")" << csa::show(history.lastMove(i)); if (i-1 < (int)eval_history.size() && eval_history[eval_history.size()-i]) std::cerr << "<" << eval_history[eval_history.size()-i] << "> "; std::cerr << " "; } std::cerr << std::endl << std::endl; } } catch (csa::CsaIOError&) { std::cerr << "bad input: " << line << "\n"; logger->inputError(line.c_str()); throw EndGame(); } return false; } void osl::game_playing:: CsaClient::setShowMoveWithComment(bool value) { show_move_with_comment = value; } void osl::game_playing:: CsaClient::processComputerMove(const MoveWithComment& selected, int my_think_time) { static std::string reserved="+7776FU"; const Move best_move = selected.move; if ((! best_move.isNormal()) || (state->isIllegal(best_move))) { if (best_move == Move::DeclareWin()) { os << "%KACHI\n"; logger->endByDeclaration(state->state().turn()); } else { if (best_move.isNormal()) { std::cerr << "error: prefer resign to playing illegal move " << best_move << " code " << state->isIllegal(best_move) << "\n"; logger->writeComment("error: prefer abort to playing illegal move"); abort(); } os << "%TORYO\n"; logger->resign(state->state().turn()); } throw EndGame(); } os << csa::show(best_move, reserved); if (show_move_with_comment && (! selected.moves.empty() || selected.value != 0)) { os << ",'* " << selected.value; for (Move move: selected.moves) { os << " "; os << csa::show(move, reserved); } } os << std::endl << std::flush; assert(isComputer(state->state().turn())); const Sennichite result = pushMove(selected, my_think_time); if (! result.isNormal()) { logger->endByRepetition(result); throw EndGame(); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/speculativeAllMoves.cc0000644000000000000000000003211512316770314023137 0ustar rootroot/* speculativeAllMoves.cc */ #include "osl/game_playing/speculativeAllMoves.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/searchPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/search/timeControl.h" #include "osl/search/searchRecorder.h" #include "osl/search/simpleHashTable.h" #include "osl/search/usiReporter.h" #include "osl/misc/milliSeconds.h" #include "osl/csa.h" #include "osl/sennichite.h" #include "osl/misc/lightMutex.h" #include #include #include #include #ifndef _MSC_VER # include #endif osl::game_playing::SpeculativeAllMoves:: ResultVector::ResultVector() { } osl::game_playing::SpeculativeAllMoves:: ResultVector::~ResultVector() { } void osl::game_playing::SpeculativeAllMoves::ResultVector:: add(Move prediction, const MoveWithComment& result) { SCOPED_LOCK(lk,mutex); data.push_back(std::make_pair(prediction, result)); } const osl::search::MoveWithComment* osl::game_playing::SpeculativeAllMoves::ResultVector:: find(Move prediction) const { SCOPED_LOCK(lk,mutex); for (const vector_t::value_type& v: data) { if (v.first == prediction) return &v.second; } return 0; } void osl::game_playing::SpeculativeAllMoves::ResultVector:: clear() { SCOPED_LOCK(lk,mutex); data.clear(); } void osl::game_playing::SpeculativeAllMoves::ResultVector:: show(std::ostream& os) const { SCOPED_LOCK(lk,mutex); for (size_t i=0; i" << csa::show(data[i].second.move); } os << std::endl; } /* ------------------------------------------------------------------------- */ struct osl::game_playing::SpeculativeAllMoves::SearchAllMoves::StatusLock { volatile Status& status; std::mutex& mutex; std::condition_variable *condition; const Status in, out; StatusLock(volatile Status *s, std::mutex *m, std::condition_variable* c, Status i, Status o) : status(*s), mutex(*m), condition(c), in(i), out(o) { std::lock_guard lk(mutex); status = in; condition->notify_all(); } StatusLock(volatile Status *s, std::mutex *m, Status i) : status(*s), mutex(*m), condition(0), in(i), out(*s) { std::lock_guard lk(mutex); status = in; } ~StatusLock() { status = out; if (condition) condition->notify_all(); } }; struct osl::game_playing::SpeculativeAllMoves::SearchAllMoves::Generator { GameState& state; SearchPlayer& player; MoveVector tried_moves; volatile Status& status; std::mutex& mutex; int index, seconds; bool has_byoyomi; Generator(GameState& s, SearchPlayer& p, SearchAllMoves& parent, int sec, bool byoyomi) : state(s), player(p), status(parent.status), mutex(parent.mutex), index(-1), seconds(sec), has_byoyomi(byoyomi) { } Move pickUpMove() { try { MoveWithComment result; { StatusLock lk(&status, &mutex, PREDICTION2); player.setRootIgnoreMoves(&tried_moves, true); player.setVerbose(0); const int sec = std::max(1, has_byoyomi ? seconds/10 : seconds/7); result = player.selectBestMove(state, 0, 0, sec); player.setRootIgnoreMoves(0, false); player.setVerbose(1); } #ifndef NDEBUG if (result.move.isNormal()) { std::cerr << "search prediction "; std::cerr << csa::show(result.move); std::cerr << "\n"; } #endif return result.move; } catch (std::exception& e) { std::cerr << "Generator::bestMove " << e.what() << "\n"; } return Move::INVALID(); } const Move nextMove() { const Move move = pickUpMove(); if (! move.isNormal()) { std::cerr << "finish\n"; return Move::INVALID(); } tried_moves.push_back(move); return move; } }; osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::SearchAllMoves(ResultVector& r) : results(r), next_iteration_coefficient(1.0), current_move(Move::INVALID()), status(INITIAL), seconds(-1), stop_flag(false) { } osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::~SearchAllMoves() { } void osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::setUp(const GameState& main_state, const SearchPlayer& main_player, int standard_seconds, bool has_byoyomi) { player.reset(); next_iteration_coefficient = main_player.nextIterationCoefficient(); try { player.reset(dynamic_cast(main_player.clone())); player->setVerbose(1); player->setNextIterationCoefficient(std::max(1.0, next_iteration_coefficient/2)); state = main_state.clone(); generator.reset(new Generator(*state, *player, *this, standard_seconds, has_byoyomi)); seconds = standard_seconds; if (has_byoyomi) seconds += std::min(30, standard_seconds/2); } catch (std::exception& e) { player.reset(); std::cerr << "setUp " << e.what() << "\n"; throw; } } void osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::run() { StatusLock lk(&status, &mutex, &condition, RUNNING, FINISHED); if (! player) return; while (true) { std::this_thread::yield(); // test whether opponent's move has arrived if (stop_flag) return; Move prediction; { StatusLock lk(&status, &mutex, PREDICTION1); prediction = generator->nextMove(); } if (! prediction.isNormal()) return; if (stop_flag) return; const MoveWithComment result = testMove(prediction); results.add(prediction, result); if (! stop_flag) results.show(std::cerr); } } const osl::search::MoveWithComment osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::testMove(Move predicted_move) { StatusLock lk(&status, &mutex, SEARCH1); { std::lock_guard lk(mutex); current_move = predicted_move; } assert(state); state->pushMove(predicted_move); assert(player); player->pushMove(predicted_move); MoveWithComment result(Move::INVALID()); std::cerr << "\nprediction (" << seconds << ") " << csa::show(predicted_move) << " "; const time_t now = time(0); char ctime_buf[64]; std::cerr << ctime_r(&now, ctime_buf); try { StatusLock lk(&status, &mutex, SEARCH2); if (seconds <= 0) seconds = 120; const milliseconds msec(seconds*1000); result = player->searchWithSecondsForThisMove(*state, search::TimeAssigned(msec, msec*5)); } catch (std::exception& e) { // TODO table full ã¯clear? std::cerr << "error in speculative thread " << e.what() << "\n"; stop_flag = true; } catch (...) { std::cerr << "error in speculative thread\n"; stop_flag = true; } state->popMove(); player->popMove(); { std::lock_guard lk(mutex); current_move = Move::INVALID(); } return result; } void osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::stopOtherThan(Move the_move) { stop_flag = true; if (currentMove() != the_move) stopNow(); else { #ifndef NDEBUG std::cerr << "match " << csa::show(the_move) << "\n"; #endif #ifndef GPSONE if (OslConfig::usiMode()) OslConfig::setUsiSilent(false); #endif assert(player); player->setNextIterationCoefficient(next_iteration_coefficient); player->setVerbose(2); } } void osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::stopNow() { stop_flag = true; waitRunning(); if (player && status != FINISHED) { std::cerr << "stopNow " << status << "\n"; const bool success = player->stopSearchNow(); if (! success) std::cerr << "stop search failed\n"; } } void osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::waitRunning() { std::unique_lock lk(mutex); while (status == INITIAL) { condition.wait(lk); if (!player) return; } } void osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::setTimeAssign(const search::TimeAssigned& new_assign) { if (player && status != FINISHED) { waitRunning(); player->setTimeAssign(new_assign); } } const osl::time_point osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::startTime() { if (player && status != FINISHED) { waitRunning(); return player->startTime(); } return time_point(); } const osl::Move osl::game_playing::SpeculativeAllMoves:: SearchAllMoves::currentMove() const { std::lock_guard lk(mutex); return current_move; } /* ------------------------------------------------------------------------- */ struct osl::game_playing::SpeculativeAllMoves::Runner { SpeculativeAllMoves *parent; Runner(SpeculativeAllMoves *p) : parent(p) { } void #ifdef __GNUC__ # ifdef _WIN32 __attribute__((noinline)) __attribute__((force_align_arg_pointer)) # endif #endif operator()() { parent->searcher->run(); } }; osl::game_playing::SpeculativeAllMoves:: SpeculativeAllMoves() : results(new ResultVector()), last_search_seconds(-1), has_byoyomi(false), allowed(true) { } osl::game_playing:: SpeculativeAllMoves::~SpeculativeAllMoves() { stopAll(); selectBestMoveCleanUp(); } void osl::game_playing::SpeculativeAllMoves:: startSpeculative(const std::shared_ptr state, const SearchPlayer& main_player) { std::lock_guard lk(mutex); if (! allowed) return; try { search_state = HashKey(state->state()); results->clear(); searcher.reset(new SearchAllMoves(*results)); searcher->setUp(*state, main_player, last_search_seconds, has_byoyomi); thread.reset(new std::thread(Runner(this))); } catch (std::exception& e) { std::cerr << "startSpeculative " << e.what(); searcher.reset(); } } void osl::game_playing::SpeculativeAllMoves:: clearResource() { std::lock_guard lk(mutex); assert(! thread); searcher.reset(); } void osl::game_playing::SpeculativeAllMoves:: stopOtherThan(Move the_move) { std::lock_guard lk(mutex); if (searcher) searcher->stopOtherThan(the_move); } void osl::game_playing::SpeculativeAllMoves:: stopAll() { std::lock_guard lk(mutex); if (searcher) searcher->stopNow(); } const osl::search::MoveWithComment osl::game_playing::SpeculativeAllMoves:: waitResult(Move last_move, search::TimeAssigned wait_for, SearchPlayer& main_player, int byoyomi) { { std::lock_guard lk(mutex); if (! allowed || ! searcher) return MoveWithComment(Move::INVALID()); } last_search_seconds = (int)ceil(toSeconds(wait_for.standard)); has_byoyomi = (byoyomi > 0); const time_t start_time = time(0); const time_point start_time_msec = clock::now(); assert(last_move.isNormal()); const MoveWithComment *result = 0; bool stop_now = false; if (searcher->currentMove() != last_move) { stop_now = true; wait_for = search::TimeAssigned(milliseconds(0)); } // const time_t standard_time = start_time + ceil(wait_for.standard.toSeconds()); const time_t stop_time = start_time + static_cast(ceil(toSeconds(wait_for.max))); const time_point started = searcher->startTime(); const bool already_finished = searcher->isFinished(); if (! already_finished) { char ctime_buf[64]; std::cerr << "wait for (" << toSeconds(wait_for.standard) << "/" << toSeconds(wait_for.max) << ") " << ctime_r(&stop_time, ctime_buf); const milliseconds diff = duration_cast(start_time_msec - started); wait_for.standard = wait_for.standard + diff; wait_for.max = wait_for.max + diff; searcher->setTimeAssign(wait_for); } { int wait_count = 0; while (true) { const bool now_finished = searcher->isFinished(); if ((result = results->find(last_move))) { #ifndef GPSONE if (wait_count == 0 && OslConfig::usiMode()) { search::UsiReporter::showPV(std::cout, result->root_limit/200, result->node_count, result->elapsed, last_move.player() == BLACK ? -result->value : result->value, result->move, &*result->moves.begin(), &*result->moves.end(), true); } #endif break; } assert(searcher); if (now_finished) return MoveWithComment(Move::INVALID()); if (stop_now && ++wait_count > 60) { std::cerr << "error stop now failed for 60 times\n"; abort(); } if (! stop_now) { time_t now = time(0); stop_now = now >= stop_time; } if (stop_now) { searcher->stopNow(); } std::unique_lock lk(searcher->mutex); auto const timeout= std::chrono::steady_clock::now() +((wait_count <= 10) ? std::chrono::milliseconds(1000) : std::chrono::milliseconds(2000)); searcher->condition.wait_until(lk, timeout); } } if (! searcher->isFinished()) searcher->stopNow(); if (result->move.isNormal()) { SearchPlayer *player = searcher->currentPlayer(); if (player) main_player.swapTable(*player); } return *result; } void osl::game_playing::SpeculativeAllMoves:: selectBestMoveCleanUp() { if (! thread) return; { std::lock_guard lk(mutex); if (searcher && ! searcher->isFinished()) searcher->stopNow(); } thread->join(); thread.reset(); if (searcher) searcher.reset(); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/winCountTracer.cc0000644000000000000000000000533212316770314022120 0ustar rootroot/* winCountTracer.cc */ #include "osl/game_playing/winCountTracer.h" #include "osl/game_playing/openingBookTracer.h" #include "osl/book/openingBook.h" #include "osl/random.h" #include osl::game_playing:: WinCountTracer::WinCountTracer(WinCountBook& b, int r, bool v) : book(b), state_index(0), turn(BLACK), randomness(r), verbose(v) { if (randomness < 0) randomness = 0; } osl::game_playing:: WinCountTracer::WinCountTracer(const WinCountTracer& copy) : OpeningBookTracer(copy), book(copy.book), state_index(copy.state_index), turn(copy.turn), randomness(copy.randomness), verbose(copy.verbose), state_stack(copy.state_stack) { } osl::game_playing::OpeningBookTracer* osl::game_playing:: WinCountTracer::clone() const { return new WinCountTracer(*this); } void osl::game_playing:: WinCountTracer::update(Move move) { state_stack.push(state_index); assert(move.player() == turn); turn = alt(turn); if (! isOutOfBook()) { const std::vector& moves = book.moves(state_index); for (size_t i=0; i" << state_index << "\n"; return; } } if (verbose) std::cerr << "book: end" << "\n"; } state_index = -1; } void osl::game_playing:: WinCountTracer::popMove() { state_index = state_stack.top(); state_stack.pop(); turn = alt(turn); } bool osl::game_playing:: WinCountTracer::isOutOfBook() const { return state_index < 0; } const osl::Move osl::game_playing:: WinCountTracer::selectMove() const { assert(randomness >= 0); int maxWin = -1, maxIndex = -1; std::vector moves = book.moves(state_index); for (size_t index=0; index= maxWin + randomness) { maxWin=winNum; maxIndex=index; } } else { if (loseNum >= maxWin + randomness) { maxWin=winNum; maxIndex=index; } } } if (verbose) std::cerr << std::endl; if (maxIndex >= 0) return moves[maxIndex].move; return Move::INVALID(); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaLogger.cc0000644000000000000000000000605512335610142021053 0ustar rootroot/* csaLogger.cc */ #include "osl/game_playing/csaLogger.h" #include "osl/game_playing/timeKeeper.h" #include "osl/search/moveWithComment.h" #include "osl/numEffectState.h" #include "osl/csa.h" #include "osl/sennichite.h" #include #ifdef _WIN32 #include #include #endif osl::game_playing:: CsaLogger::CsaLogger(std::ostream& os) : output(os) { } osl::game_playing:: CsaLogger::~CsaLogger() { } void osl::game_playing:: CsaLogger::init(const char *black, const char *white, const SimpleState& state) { output << "N+" << black << std::endl << "N-" << white << std::endl; output << state << std::flush; writeCurrentDate(); } void osl::game_playing:: CsaLogger::pushMove(const Move& move, int seconds) { output << csa::show(move) << std::endl << "T" << seconds << std::endl << std::flush; } void osl::game_playing:: CsaLogger::pushMove(const MoveWithComment& move, int seconds) { pushMove(move.move, seconds); if (! move.moves.empty()) { output << "'** " << move.value; for (Move m: move.moves) { output << " " << csa::show(m); } output << std::endl << std::flush; } } void osl::game_playing:: CsaLogger::popMove() { writeLine("%MATTA"); // csa ã®%MATTA ã¯2手戻ã™ã®ã§æ„味ãŒé•ã†? } void osl::game_playing:: CsaLogger::showTimeLeft(const TimeKeeper& keeper) { output << "'time left " << keeper.timeLeft(BLACK) << " " << keeper.timeLeft(WHITE) << std::endl << std::flush; } void osl::game_playing:: CsaLogger::writeLine(const char *line) { output << line << std::endl << std::flush; } void osl::game_playing:: CsaLogger::writeComment(const char *comment) { output << "'" << comment << std::endl << std::flush; } void osl::game_playing:: CsaLogger::writeCurrentDate() { char ctime_buf[64]; const time_t t = time(0); output << "'" << ctime_r(&t, ctime_buf); // ctime returns string with "\n" } void osl::game_playing:: CsaLogger::resign(Player resigned) { output << "%TORYO" << std::endl; writeWinner(alt(resigned)); writeCurrentDate(); } void osl::game_playing:: CsaLogger::inputError(const char *message) { output << "'!!! input error: " << message << std::endl << std::flush; } void osl::game_playing:: CsaLogger::breakGame() { output << "%CHUDAN" << std::endl << std::flush; } void osl::game_playing:: CsaLogger::endByRepetition(const Sennichite& result) { output << "%SENNICHITE" << std::endl; output << "'" << result << std::endl << std::flush; assert(! result.isNormal()); if (result.hasWinner()) writeWinner(result.winner()); else writeComment("draw"); writeCurrentDate(); } void osl::game_playing:: CsaLogger::endByDeclaration(Player declarer) { output << "%KACHI" << std::endl; output << "'declared by " << declarer << std::endl << std::flush; writeCurrentDate(); } void osl::game_playing:: CsaLogger::writeWinner(Player winner) { output << "'" << winner << " win" << std::endl << std::flush; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/gnuShogiClient.h0000644000000000000000000000135612316770314021737 0ustar rootroot/* gnuShogiClient.h */ #ifndef GAMEPLAYING_GNUSHOGICLIENT_H #define GAMEPLAYING_GNUSHOGICLIENT_H #include "osl/game_playing/cuiClient.h" namespace osl { namespace game_playing { struct GnuShogiQuit {}; class GnuShogiClient : public CuiClient { public: GnuShogiClient(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l, std::istream&, std::ostream&); ~GnuShogiClient(); private: bool readAndProcessCommand(); void processComputerMove(const search::MoveWithComment&, int seconds); void preComputeNextMove(); }; } // namespace game_playing } // namespace osl #endif /* _GNUSHOGICLIENT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/usiResponse.h0000644000000000000000000000253212316770314021331 0ustar rootroot/* usiResponse.h */ #ifndef OSL_USIRESPONSE_H #define OSL_USIRESPONSE_H #include "osl/game_playing/usiState.h" #include "osl/numEffectState.h" #include "osl/container/moveLogProbVector.h" #include namespace osl { namespace game_playing { struct UsiState; class UsiResponse { const UsiState& usi_state; const bool new_move_probability, verbose; public: UsiResponse(const UsiState&, bool new_move_probability, bool verbose); ~UsiResponse(); bool hasImmediateResponse(const std::string& command, std::string& out); void genmoveProbability(int limit, MoveLogProbVector& out); private: MoveVector generateGoodMoves(); void genmoveProbability(int limit, std::string& out); void genmove(std::string& out); void csashow(const NumEffectState& state, std::string& out); void csamove(const NumEffectState& state, const std::string& str, std::string& out); void ki2moves(const NumEffectState& current, const std::string& moves_str, std::string& out); void ki2currentinfo(const NumEffectState& current, std::string& out); void isValidPosition(const std::string& line, std::string& out); }; } using game_playing::UsiResponse; } #endif /* OSL_USIRESPONSE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/bookPlayer.h0000644000000000000000000000322212316770314021116 0ustar rootroot/* bookPlayer.h */ #ifndef GAME_PLAYING_BOOKPLAYER_H #define GAME_PLAYING_BOOKPLAYER_H #include "osl/game_playing/computerPlayer.h" namespace osl { namespace game_playing { class OpeningBookTracer; /** * 定跡ãŒã‚ã‚‹é–“ã¯å®šè·¡ã‚’使ã†ComputerPlayer */ class BookPlayer : public ComputerPlayer, public ComputerPlayerSelectBestMoveInTime { std::unique_ptr book; std::unique_ptr searcher; int book_limit; int current_moves; bool valid_initial_position; public: /** 所有権移転: new ã—ãŸã‚‚ã®ã‚’渡ã™ã“㨠*/ BookPlayer(OpeningBookTracer*, ComputerPlayer*); ~BookPlayer(); ComputerPlayer* clone() const; /** 何手ã¾ã§å®šè·¡ã‚’使ã†ã‹ã‚’設定. -1 ãªã‚‰ç„¡é™å¤§ */ void setBookLimit(int new_limit); void setInitialState(const NumEffectState&); void pushMove(Move m); void popMove(); const MoveWithComment selectBestMove(const GameState&, int seconds, int elapsed, int byoyomi); const MoveWithComment selectBestMoveInTime(const GameState&, const search::TimeAssigned&); bool bookAvailable() const; // delegations ... void allowSpeculativeSearch(bool value); virtual bool stopSearchNow(); /** 注æ„: 定跡ã«é–¢ã—ã¦ã¯æŒ‡å®šã¯ç„¡åй */ void setRootIgnoreMoves(const MoveVector *rim, bool prediction); private: const Move moveByBook(const GameState& state); }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_BOOKPLAYER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaStopwatch.h0000644000000000000000000000115012316770314021450 0ustar rootroot/* csaStopwatch.h */ #ifndef GAME_PLAYING_CSASTOPWATCH_H #define GAME_PLAYING_CSASTOPWATCH_H #include "osl/misc/milliSeconds.h" #include namespace osl { namespace game_playing { class CsaStopwatch { time_point start; public: CsaStopwatch() : start(clock::now()) { } int read() { double elapsed = elapsedSeconds(start); int ret = (int)floor(elapsed); return std::max(1, ret); } }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_CSASTOPWATCH_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaTime.h0000644000000000000000000000241112316770314020373 0ustar rootroot#ifndef OSL_CSA_TIME_H #define OSL_CSA_TIME_H #include "osl/misc/milliSeconds.h" #include #include namespace osl { namespace game_playing { class CsaTime { time_point start, opmove, mymove; long mytimeleft, optimeleft; public: explicit CsaTime(long timeleft) : mytimeleft(timeleft), optimeleft(timeleft) { mymove = opmove = start = clock::now(); } CsaTime(long myTimeLeft, long opTimeLeft) : mytimeleft(myTimeLeft), optimeleft(opTimeLeft) { mymove = opmove = start = clock::now(); } long makeOpMove() { opmove = clock::now(); long ret = (long)floor(toSeconds(opmove - mymove)); if (ret == 0) { ret = 1; } optimeleft -= ret; return ret; } long makeMyMove() { mymove = clock::now(); long ret = (long)floor(toSeconds(mymove - opmove)); if(ret == 0) { ret = 1; } mytimeleft -= ret; return ret; } long getMyLeft() const { return mytimeleft; } long getOpLeft() const { return optimeleft; } const std::string getStart() const; static const std::string curruntTime(); }; } // namespace game_playing } // namespace osl #endif // OSL_CSA_TIME // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/usiState.h0000644000000000000000000000157312316770314020617 0ustar rootroot/* usiState.h */ #ifndef OSL_USISTATE_H #define OSL_USISTATE_H #include "osl/numEffectState.h" #include namespace osl { namespace game_playing { struct UsiState { NumEffectState initial_state; std::vector moves; volatile bool aborted; UsiState(); ~UsiState(); void reset(const NumEffectState&, const std::vector&); void parseUsi(const std::string&); void openFile(std::string); bool isSuccessorOf(const UsiState& parent); const NumEffectState currentState() const; const std::string usiString() const; const std::string usiBoard() const; void parseIgnoreMoves(const std::string& line, MoveVector& ignore_moves) const; }; } using game_playing::UsiState; } #endif /* OSL_USISTATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/gameManager.h0000644000000000000000000000351412316770314021217 0ustar rootroot/* gameManager.h */ #ifndef GAMEPLAYING_GAMEMANAGER_H #define GAMEPLAYING_GAMEMANAGER_H #include "osl/game_playing/timeKeeper.h" #include "osl/container.h" namespace osl { class Sennichite; namespace search { struct MoveWithComment; } namespace game_playing { class GameState; class CsaLogger; class ComputerPlayer; class GameManager { protected: CArray players; CArray computers; std::unique_ptr state; std::unique_ptr logger; TimeKeeper time_keeper; private: int byoyomi; ComputerPlayer *player(Player turn) const { return players[turn]; } public: struct EndGame {}; /** * @param black, white 0 ã®å ´åˆï¼Œãã®æ‰‹ç•ªã‚’コンピュータã«ã§ããªã„ * @param logger 所有権移転.new ã—ãŸã‚‚ã®ã‚’渡㙠*/ GameManager(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *logger); virtual ~GameManager(); void load(const char *csa_filename, bool verbose=false); void setTimeLeft(int black_time, int white_time); void setByoyomi(int seconds) { byoyomi = seconds; } void resetLogger(CsaLogger *l); void setComputerPlayer(Player turn, bool is_computer); bool isComputer(Player turn) const { return computers[turn] && player(turn); } /** * @param consumed 消費時間を返㙠*/ const search::MoveWithComment computeMove(int& consumed); int eval(Player turn, Move m); protected: const Sennichite pushMove(const search::MoveWithComment&, int seconds); void popMove(); }; } // namespace game_playing } // namespace osl #endif /* _GAMEMANAGER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaTime.cc0000644000000000000000000000150212316770314020531 0ustar rootroot/* csa_time.cc */ #include "osl/game_playing/csaTime.h" #include const std::string osl::game_playing::CsaTime:: getStart() const { std::string result(128,'\0'); int sec = start.time_since_epoch().count()/1000; #ifdef _MSC_VER _snprintf(&result[0], result.size(), "%d", sec); #else snprintf(&result[0], result.size(), "%d", sec); #endif return result; } const std::string osl:: game_playing::CsaTime::curruntTime() { std::string result(128,'\0'); int sec = clock::now().time_since_epoch().count()/1000; #ifdef _MSC_VER _snprintf(&result[0], result.size(), "%d", sec); #else snprintf(&result[0], result.size(), "%d", sec); #endif return result; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/speculativeAllMoves.h0000644000000000000000000000740612316770314023006 0ustar rootroot/* speculativeAllMoves.h */ #ifndef OSL_SPECULATIVEALLMOVES_H #define OSL_SPECULATIVEALLMOVES_H #include "osl/game_playing/computerPlayer.h" #include "osl/game_playing/speculativeModel.h" #include "osl/misc/lightMutex.h" #include "osl/misc/milliSeconds.h" #include #include namespace osl { namespace misc { class RealTime; } namespace search { struct TimeAssigned; } namespace game_playing { class SearchPlayer; /** * 1threadã§å…¨ã¦ã®æ‰‹ã‚’é †ç•ªã«æŠ•æ©Ÿçš„æŽ¢ç´¢ã‚’ã™ã‚‹ */ class SpeculativeAllMoves : public SpeculativeModel { public: class SearchAllMoves; class ResultVector; private: std::shared_ptr searcher; std::unique_ptr thread; std::unique_ptr results; std::mutex mutex; int last_search_seconds; bool has_byoyomi; bool allowed; HashKey search_state; public: SpeculativeAllMoves(); ~SpeculativeAllMoves(); void startSpeculative(const std::shared_ptr state, const SearchPlayer& main_player); void stopOtherThan(Move); void stopAll(); void setMaxThreads(int new_max_threads) { std::lock_guard lk(mutex); allowed = (new_max_threads > 0); } const MoveWithComment waitResult(Move last_move, search::TimeAssigned wait_for, SearchPlayer& main_player, int byoyomi); void selectBestMoveCleanUp(); void clearResource(); const HashKey searchState() const { return search_state; } private: struct Runner; }; class SpeculativeAllMoves::ResultVector { typedef FixedCapacityVector,Move::MaxUniqMoves> vector_t; vector_t data; typedef LightMutex Mutex; mutable Mutex mutex; public: ResultVector(); ~ResultVector(); void add(Move prediction, const MoveWithComment& result); const MoveWithComment* find(Move prediction) const; void clear(); void show(std::ostream&) const; }; /** * 指手を生æˆã—ï¼Œçµæžœã‚’resultsã«ãŸã‚る. * run を別threadã§å‹•ã‹ã™ã“ã¨ã‚’想定ã—ã¦ã„ã‚‹ãŒï¼Œé€æ¬¡ã§ã‚‚ãƒ†ã‚¹ãƒˆå¯ */ class SpeculativeAllMoves::SearchAllMoves { public: enum Status { INITIAL, RUNNING, PREDICTION1, PREDICTION2, SEARCH1, SEARCH2, FINISHED }; struct Generator; friend struct Generator; friend class SpeculativeAllMoves; private: std::shared_ptr state; std::shared_ptr player; std::unique_ptr generator; SpeculativeAllMoves::ResultVector& results; double next_iteration_coefficient; Move current_move; volatile Status status; int seconds; typedef std::mutex Mutex; mutable Mutex mutex; std::condition_variable condition; /** true ãªã‚‰æ¬¡ã®äºˆæƒ³æŽ¢ç´¢ã«ã¯ã„らãªã„ */ volatile bool stop_flag; public: explicit SearchAllMoves(SpeculativeAllMoves::ResultVector&); ~SearchAllMoves(); void setUp(const GameState&, const SearchPlayer&, int standard_seconds, bool has_byoyomi); void run(); void stopNow(); void stopOtherThan(Move); void waitRunning(); bool isFinished() const { return status == FINISHED; } void setTimeAssign(const search::TimeAssigned&); const time_point startTime(); const Move currentMove() const; SearchPlayer* currentPlayer() { return player.get(); } private: const MoveWithComment testMove(Move); struct StatusLock; }; } // game_playing } // osl #endif /* OSL_SPECULATIVEALLMOVES_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/threadForEachMove.h0000644000000000000000000000227212316770314022341 0ustar rootroot/* threadForEachMove.h */ #ifndef OSL_THREADFOREACHMOVE_H #define OSL_THREADFOREACHMOVE_H #include "osl/game_playing/computerPlayer.h" #include "osl/game_playing/speculativeModel.h" namespace osl { namespace game_playing { class SearchPlayer; /** * ç›¸æ‰‹ã®æ‰‹ã®äºˆæ¸¬1ã¤ã«ã¤ã1thread */ class ThreadForEachMove : public SpeculativeModel { struct SpeculativeThread; std::unique_ptr speculative_thread0; std::unique_ptr speculative_thread1; int max_threads; public: explicit ThreadForEachMove(int max_threads=1); ~ThreadForEachMove(); void setMaxThreads(int new_max_threads) { max_threads = new_max_threads; } void startSpeculative(const std::shared_ptr state, const SearchPlayer& main_player); void stopOtherThan(Move); void stopAll(); const MoveWithComment waitResult(Move last_move, int wait_for, SearchPlayer& main_player, int); void selectBestMoveCleanUp(); }; } // game_playing } // osl #endif /* OSL_THREADFOREACHMOVE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/speculativeSearchPlayer.cc0000644000000000000000000001070412316770314023777 0ustar rootroot/* speculativeSearchPlayer.cc */ #include "osl/game_playing/speculativeSearchPlayer.h" #include "osl/game_playing/speculativeAllMoves.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/searchPlayer.h" #include "osl/hash/hashKeyStack.h" #include "osl/container/moveStack.h" #include "osl/sennichite.h" #include #include #ifndef _MSC_VER # include #endif osl::game_playing::SpeculativeSearchPlayer:: SpeculativeSearchPlayer(Player my_turn, SearchPlayer *player) : main_player(player), speculative(new SpeculativeAllMoves()), my_turn(my_turn) { } osl::game_playing:: SpeculativeSearchPlayer::~SpeculativeSearchPlayer() { } osl::game_playing::ComputerPlayer* osl::game_playing::SpeculativeSearchPlayer::clone() const { return new SpeculativeSearchPlayer(my_turn, dynamic_cast(main_player->clone())); } void osl::game_playing::SpeculativeSearchPlayer:: setMaxThreads(int new_max_threads) { speculative->setMaxThreads(new_max_threads); } void osl::game_playing::SpeculativeSearchPlayer:: pushMove(Move m) { main_player->pushMove(m); if (m.player() == my_turn) { if (previous_state.get() && speculative_search_allowed) { #ifndef GPSONE if (OslConfig::usiMode()) OslConfig::setUsiSilent(true); #endif try { previous_state->pushMove(m); speculative->startSpeculative(previous_state, *main_player); } catch (std::exception& e) { std::cerr << e.what() << " in SpeculativeSearchPlayer::pushMove\n"; speculative->clearResource(); } previous_state.reset(); } } else { if (speculative_search_allowed) speculative->stopOtherThan(m); } } void osl::game_playing::SpeculativeSearchPlayer:: popMove() { main_player->popMove(); previous_state.reset(); speculative->stopAll(); } bool osl::game_playing::SpeculativeSearchPlayer:: stopSearchNow() { return main_player->stopSearchNow(); } osl::search::TimeAssigned osl::game_playing::SpeculativeSearchPlayer:: standardSearchSeconds(const GameState& state, int limit, int elapsed, int byoyomi) const { search::TimeAssigned result = main_player->assignTime(state, limit, elapsed, byoyomi); if (result.standard > milliseconds(2000)) { result.standard = result.standard - milliseconds(500); result.max = result.max - milliseconds(500); } return result; } const osl::search::MoveWithComment osl::game_playing::SpeculativeSearchPlayer:: selectBestMove(const GameState& state, int limit, int elapsed, int byoyomi) { if (elapsed > limit) elapsed = limit; const time_t start_time = time(0); MoveWithComment result = MoveWithComment(Move::INVALID()); const Move last_move = state.moveHistory().lastMove(); const HashKey search_key(speculative->searchState()); const HashKey now_key(last_move.isNormal() ? state.hashHistory().top(1) : HashKey()); const bool consistent = (search_key == now_key); const search::TimeAssigned wait_for = consistent ? standardSearchSeconds(state, limit, elapsed, byoyomi) : search::TimeAssigned(milliseconds(0)); if (last_move.isNormal()) result = speculative->waitResult(last_move, wait_for, *main_player, byoyomi); const time_t now = time(0); char ctime_buf[64]; if (! consistent && result.move.isNormal()) std::cerr << "note: the current position differs from the one which previous prediction search ran on\n"; if (result.move.isNormal() && consistent) { #ifdef DEBUG_SPECULATIVE_EXECUTION std::cerr << "returned " << csa::show(result.move) << " " << ctime_r(&now, ctime_buf); #endif selectBestMoveCleanUp(state); main_player->saveSearchResult(state, result); return result; } std::cerr << "search again " << ctime_r(&now, ctime_buf); selectBestMoveCleanUp(state); #ifndef GPSONE if (OslConfig::usiMode()) OslConfig::setUsiSilent(false); #endif const int consumed = (now - start_time); if (byoyomi && (limit <= elapsed+consumed)) byoyomi = std::max(1, byoyomi - (elapsed+consumed-limit)); result = main_player->selectBestMove(state, limit, std::min(limit-1, elapsed+consumed), byoyomi); return result; } void osl::game_playing::SpeculativeSearchPlayer:: selectBestMoveCleanUp(const GameState& state) { try { previous_state = state.clone(); } catch (std::exception& e) { std::cerr << e.what() << std::endl; previous_state.reset(); } speculative->selectBestMoveCleanUp(); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/usiState.cc0000644000000000000000000000512212316770314020747 0ustar rootroot/* usiState.cc */ #include "osl/game_playing/usiState.h" #include "osl/record/ki2.h" #include "osl/record/kakinoki.h" #include "osl/record/csaRecord.h" #include "osl/usi.h" #include #include osl::game_playing:: UsiState::UsiState() : aborted(false) { } osl::game_playing:: UsiState::~UsiState() { } void osl::game_playing:: UsiState::reset(const NumEffectState& i, const std::vector& m) { initial_state = i; moves = m; aborted = false; } bool osl::game_playing:: UsiState::isSuccessorOf(const UsiState& parent) { return ! aborted && ! parent.aborted && initial_state == parent.initial_state && moves.size() == parent.moves.size()+1 && std::equal(parent.moves.begin(), parent.moves.end(), moves.begin()); } const osl::NumEffectState osl::game_playing:: UsiState::currentState() const { NumEffectState state(initial_state); for (Move m: moves) state.makeMove(m); return state; } void osl::game_playing:: UsiState::parseUsi(const std::string& line) { assert(line.find("position") == 0); usi::parse(line.substr(8), initial_state, moves); } void osl::game_playing:: UsiState::openFile(std::string filename) { boost::algorithm::trim(filename); boost::algorithm::trim_left(filename); Record record; #ifndef MINIMAL if (boost::algorithm::iends_with(filename, ".ki2")) { const Ki2File ki2(filename); record = ki2.load(); } else if (boost::algorithm::iends_with(filename, ".kif")) { const KakinokiFile kif(filename); record = kif.load(); } else #endif { const CsaFile csa(filename.c_str()); record = csa.load(); } initial_state = record.initialState(); moves = record.moves(); } const std::string osl::game_playing:: UsiState::usiString() const { std::string ret; ret.reserve(16+90+10+5*moves.size()); ret = "position "; ret += usi::show(initial_state); ret += " moves"; for (Move move: moves) { ret += " "; ret += usi::show(move); } return ret; } const std::string osl::game_playing:: UsiState::usiBoard() const { std::string ret = "position "; ret += usi::show(currentState()); return ret; } void osl::game_playing:: UsiState::parseIgnoreMoves(const std::string& line, MoveVector& ignore_moves) const { assert(line.find("ignore_moves") == 0); std::istringstream is(line); std::string word; is >> word; NumEffectState state(currentState()); ignore_moves.clear(); while (is >> word) { ignore_moves.push_back(usi::strToMove(word, state)); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaClient.h0000644000000000000000000000154112316770314020716 0ustar rootroot/* csaClient.h */ #ifndef GAME_PLAYING_CSACLIENT_H #define GAME_PLAYING_CSACLIENT_H #include "osl/game_playing/cuiClient.h" #include namespace osl { namespace game_playing { class CsaClient : public CuiClient { bool show_move_with_comment; bool silent; std::string line; public: CsaClient(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l, std::istream&, std::ostream&); ~CsaClient(); void setShowMoveWithComment(bool value=true); void setSilent(bool new_value=true) { silent = new_value; } private: bool readAndProcessCommand(); void processComputerMove(const search::MoveWithComment&, int seconds); }; } // namespace game_playing } // namespace osl #endif /* _CSACLIENT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/cuiClient.h0000644000000000000000000000175512316770314020737 0ustar rootroot/* cuiClient.h */ #ifndef GAME_PLAYING_CUICLIENT_H #define GAME_PLAYING_CUICLIENT_H #include "osl/game_playing/gameManager.h" namespace osl { namespace game_playing { class CuiClient : public GameManager { protected: std::istream& is; std::ostream& os; private: /** non-zero value forces resign */ volatile int stop_by_outside; public: CuiClient(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l, std::istream&, std::ostream&); ~CuiClient(); void run(const char *black, const char *white); void run(); volatile int *stopFlag() { return &stop_by_outside; } protected: /** @return read next command immediately */ virtual bool readAndProcessCommand()=0; virtual void processComputerMove(const search::MoveWithComment&, int seconds)=0; }; } // namespace game_playing } // namespace osl #endif /* _CUICLIENT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/timeKeeper.cc0000644000000000000000000000320112316770314021234 0ustar rootroot/* timeKeeper.cc */ #include "osl/game_playing/timeKeeper.h" #include struct osl::game_playing::TimeKeeper::Stack : public std::vector > { }; osl::game_playing:: TimeKeeper::TimeKeeper() : seconds(new Stack()) { reset(1500, 1500); // default: 25 min } osl::game_playing:: TimeKeeper::TimeKeeper(int black_time, int white_time) : seconds(new Stack()) { reset(black_time, white_time); } osl::game_playing:: TimeKeeper::~TimeKeeper() { } void osl::game_playing:: TimeKeeper::reset(int black_time, int white_time) { seconds->clear(); seconds->push_back(std::make_pair(black_time, white_time)); } void osl::game_playing:: TimeKeeper::pushMove(Player turn, int consumed) { std::pair time_left = seconds->back(); if (turn == BLACK) time_left.first -= consumed; else time_left.second -= consumed; seconds->push_back(time_left); } void osl::game_playing:: TimeKeeper::popMove() { assert(! seconds->empty()); seconds->pop_back(); } int osl::game_playing:: TimeKeeper::timeLeft(Player player) const { const std::pair& time_left = seconds->back(); return (player == BLACK) ? time_left.first : time_left.second; } int osl::game_playing:: TimeKeeper::timeElapsed(Player player) const { return timeLimit(player) - timeLeft(player); } int osl::game_playing:: TimeKeeper::timeLimit(Player player) const { const std::pair& time_left = seconds->front(); return (player == BLACK) ? time_left.first : time_left.second; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/gameState.cc0000644000000000000000000001223312316770314021061 0ustar rootroot/* gameState.cc */ #include "osl/game_playing/gameState.h" #include "osl/game_playing/openingBookTracer.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/search/moveStackRejections.h" #include "osl/move_classifier/pawnDropCheckmate.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/effect_util/effectUtil.h" #include "osl/state/historyState.h" #include "osl/hash/hashKeyStack.h" #include "osl/container/moveStack.h" #include "osl/repetitionCounter.h" #include "osl/sennichite.h" #include "osl/enterKing.h" struct osl::game_playing::GameState::State #if OSL_WORDSIZE == 32 : public osl::misc::Align16New #endif { HistoryState state; RepetitionCounter counter; MoveStack move_history; std::vector eval_stack; State(const SimpleState& initial_state) : state(initial_state), counter(state.state()) { move_history.reserve(1024); } }; osl::game_playing:: GameState::GameState(const SimpleState& initial_state) : stack(new State(initial_state)) { } osl::game_playing:: GameState::GameState(const State& src) : stack(new State(src)) // clone { } osl::game_playing:: GameState::~GameState() { } const osl::Sennichite osl::game_playing:: GameState::pushMove(Move m, int eval) { stack->move_history.push(m); const Sennichite result = stack->counter.isSennichite(state(), m); stack->counter.push(state(), m); stack->state.makeMove(m); stack->eval_stack.push_back(eval); return result; } osl::game_playing::GameState::MoveType osl::game_playing:: GameState::isIllegal(Move m) const { if (! state().isValidMove(m, false)) return OTHER_INVALID; typedef move_classifier::PlayerMoveAdaptor PawnDropCheckmate_t; if (PawnDropCheckmate_t::isMember(state(), m)) return PAWN_DROP_FOUL; stack->state.makeMove(m); const bool unsafe_king = state().inCheck(alt(state().turn())); stack->state.unmakeMove(); if (unsafe_king) return UNSAFE_KING; return VALID; } const osl::Move osl::game_playing:: GameState::popMove() { const Move result = stack->move_history.lastMove(); assert(canPopMove()); stack->move_history.pop(); stack->counter.pop(); stack->state.unmakeMove(); stack->eval_stack.pop_back(); return result; } const osl::NumEffectState& osl::game_playing:: GameState::state() const { return stack->state.state(); } int osl::game_playing:: GameState::moves() const { return stack->move_history.size(); } const osl::MoveStack& osl::game_playing:: GameState::moveHistory() const { return stack->move_history; } const osl::hash::HashKeyStack& osl::game_playing:: GameState::hashHistory() const { return stack->counter.history(); } const osl::RepetitionCounter& osl::game_playing:: GameState::counter() const { return stack->counter; } bool osl::game_playing:: GameState::canPopMove() const { return ! stack->state.empty(); } const std::shared_ptr osl::game_playing:: GameState::clone() const { std::shared_ptr result(new GameState(*stack)); return result; } const osl::SimpleState& osl::game_playing:: GameState::initialState() const { return stack->state.initialState(); } const std::vector& osl::game_playing:: GameState::evalStack() const { return stack->eval_stack; } void osl::game_playing:: GameState::generateMoves(MoveVector& normal, MoveVector& win, MoveVector& draw, MoveVector& loss) const { MoveVector all; state().generateLegal(all); NumEffectState copy; const HashKey key(state()); for (Move m: all) { if (isIllegal(m) != VALID) { loss.push_back(m); continue; } const Sennichite result = counter().isAlmostSennichite(key.newMakeMove(m)); if (! result.isNormal()) { if (! result.hasWinner()) draw.push_back(m); else { if (result.winner() == alt(state().turn())) loss.push_back(m); else win.push_back(m); } continue; } if (rejectByStack(m)) { loss.push_back(m); continue; } copy.copyFrom(state()); copy.makeMove(m); if (! copy.inCheck()) { if (checkmate::ImmediateCheckmate::hasCheckmateMove(copy.turn(), copy) || EnterKing::canDeclareWin(copy)) { loss.push_back(m); continue; } } normal.push_back(m); } } void osl::game_playing:: GameState::generateNotLosingMoves(MoveVector& normal_or_win_or_draw, MoveVector& loss) const { MoveVector win, draw; generateMoves(normal_or_win_or_draw, win, draw, loss); normal_or_win_or_draw.push_back(win.begin(), win.end()); normal_or_win_or_draw.push_back(draw.begin(), draw.end()); } bool osl::game_playing:: GameState::rejectByStack(Move move) const { const int max_depth = 8; if (move.player() == BLACK) return search::MoveStackRejections::probe (state(), moveHistory(), std::min(max_depth,moves()), move, 0, counter().checkCount(alt(move.player()))); else return search::MoveStackRejections::probe (state(), moveHistory(), std::min(max_depth,moves()), move, 0, counter().checkCount(alt(move.player()))); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/speculativeSearchPlayer.h0000644000000000000000000000253512316770314023644 0ustar rootroot/* speculativeSearchPlayer.h */ #ifndef OSL_SPECULATIVESEARCHPLAYER_H #define OSL_SPECULATIVESEARCHPLAYER_H #include "osl/game_playing/computerPlayer.h" #include "osl/game_playing/speculativeModel.h" namespace osl { namespace game_playing { class SearchPlayer; class SpeculativeModel; /** * ç›¸æ‰‹æ™‚é–“ä¸­ã«æŽ¢ç´¢ */ class SpeculativeSearchPlayer : public ComputerPlayer { std::unique_ptr main_player; std::shared_ptr previous_state; std::unique_ptr speculative; Player my_turn; public: /** 所有権移転 */ SpeculativeSearchPlayer(Player my_turn, SearchPlayer *); ~SpeculativeSearchPlayer(); ComputerPlayer* clone() const; void pushMove(Move m); void popMove(); bool stopSearchNow(); /** ThreadForEachMove ã®ã¿ã«æœ‰åй */ void setMaxThreads(int new_max_threads); const MoveWithComment selectBestMove(const GameState&, int limit, int elapsed, int byoyomi); search::TimeAssigned standardSearchSeconds(const GameState&, int limit, int elapsed, int byoyomi) const; private: void selectBestMoveCleanUp(const GameState& state); }; } // game_playing } // osl #endif /* OSL_SPECULATIVESEARCHPLAYER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/gameState.h0000644000000000000000000000353712316770314020732 0ustar rootroot/* gameState.h */ #ifndef OSL_GAMESTATE_H #define OSL_GAMESTATE_H #include "osl/numEffectState.h" #include namespace osl { class Sennichite; class RepetitionCounter; namespace container { class MoveStack; } namespace hash { class HashKeyStack; } namespace game_playing { /** * State ã¨åƒæ—¥æ‰‹çŠ¶æ…‹ãªã©ã‚’ä¸€å…ƒç®¡ç† */ class GameState { private: struct State; std::unique_ptr stack; explicit GameState(const State& src); public: explicit GameState(const SimpleState& initial_state); ~GameState(); enum MoveType { VALID, PAWN_DROP_FOUL, UNSAFE_KING, OTHER_INVALID }; MoveType isIllegal(Move m) const; const Sennichite pushMove(Move m, int eval=0); const Move popMove(); bool canPopMove() const; const NumEffectState& state() const; const RepetitionCounter& counter() const; const container::MoveStack& moveHistory() const; const hash::HashKeyStack& hashHistory() const; int moves() const; int chessMoves() const { return moves() / 2 + 1; } const SimpleState& initialState() const; /** * GameState ã®ã‚³ãƒ”ーを作る. * ç¾åœ¨ã®å±€é¢ã‚’åˆæœŸå±€é¢ã¨ã—ã¦æ‰±ã†ãŸã‚, * pushMoveã—ãªã„é™ã‚ŠpopMoveã¯ã§ããªã„ */ const std::shared_ptr clone() const; const std::vector& evalStack() const; void generateNotLosingMoves(MoveVector& normal_or_win_or_draw, MoveVector& loss) const; void generateMoves(MoveVector& normal_moves, MoveVector& win, MoveVector& draw, MoveVector& loss) const; bool rejectByStack(Move move) const; }; } // namespace game_playing } // namespace osl #endif /* OSL_GAMESTATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/gameManager.cc0000644000000000000000000000657712316770314021371 0ustar rootroot/* gameManager.cc */ #include "osl/game_playing/gameManager.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/computerPlayer.h" #include "osl/game_playing/csaLogger.h" #include "osl/game_playing/csaStopwatch.h" #include "osl/record/csaRecord.h" #include "osl/sennichite.h" #include osl::game_playing:: GameManager::GameManager(ComputerPlayer *black, ComputerPlayer *white, CsaLogger *l) : state(new GameState(SimpleState(HIRATE))), logger(l), byoyomi(0) { players[BLACK] = black; players[WHITE] = white; computers[BLACK] = false; computers[WHITE] = false; } osl::game_playing:: GameManager::~GameManager() { } void osl::game_playing:: GameManager::setComputerPlayer(Player turn, bool is_computer) { computers[turn] = is_computer; if (players[turn]) players[turn]->allowSpeculativeSearch(is_computer); } void osl::game_playing:: GameManager::resetLogger(CsaLogger *l) { logger.reset(l); } void osl::game_playing:: GameManager::setTimeLeft(int black_time, int white_time) { time_keeper.reset(black_time, white_time); } void osl::game_playing:: GameManager::load(const char *csa_filename, bool verbose) { if (state->moves()) { std::cerr << "GameManager: game already started, load failure\n"; return; } if (verbose) std::cerr << "loading " << csa_filename << "\n"; CsaFile csa_file(csa_filename); state.reset(new GameState(csa_file.initialState())); logger->init(csa_file.load().player[BLACK].c_str(), csa_file.load().player[WHITE].c_str(), state->state()); if (player(BLACK)) player(BLACK)->setInitialState(state->state()); if (player(WHITE)) player(WHITE)->setInitialState(state->state()); std::vector moves; std::vector times; csa_file.load().load(moves, times); assert(moves.size() == times.size()); for (size_t i=0; istate().isValidMove(moves[i])) || (! pushMove(MoveWithComment(moves[i]), times[i]).isNormal())) { std::cerr << "invalid move " << i << " " << moves[i] << "\n"; break; } } } const osl::search::MoveWithComment osl::game_playing:: GameManager::computeMove(int& consumed) { const Player turn = state->state().turn(); CsaStopwatch timer; const MoveWithComment best_move = player(turn)->selectBestMove(*state, time_keeper.timeLimit(turn), time_keeper.timeElapsed(turn), byoyomi); consumed = timer.read(); return best_move; } const osl::Sennichite osl::game_playing:: GameManager::pushMove(const MoveWithComment& move, int seconds) { assert(state->state().isValidMove(move.move)); time_keeper.pushMove(move.move.player(), seconds); logger->pushMove(move, seconds); logger->showTimeLeft(time_keeper); const Sennichite result = state->pushMove(move.move, move.value); if (player(BLACK)) player(BLACK)->pushMove(move.move); if (player(WHITE)) player(WHITE)->pushMove(move.move); return result; } void osl::game_playing:: GameManager::popMove() { time_keeper.popMove(); logger->popMove(); logger->showTimeLeft(time_keeper); state->popMove(); if (player(BLACK)) player(BLACK)->popMove(); if (player(WHITE)) player(WHITE)->popMove(); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/recordTracer.h0000644000000000000000000000220012316770314021421 0ustar rootroot/* recordTracer.h */ #ifndef GAME_PLAYING_RECORDTRACER_H #define GAME_PLAYING_RECORDTRACER_H #include "osl/game_playing/openingBookTracer.h" #include #include namespace osl { namespace game_playing { /** * vectorã®è¿½è·¡ */ class RecordTracer : public OpeningBookTracer { public: typedef std::vector moves_t; private: const moves_t moves; std::stack state_index; bool verbose; public: explicit RecordTracer(const moves_t& moves, bool verbose=false); RecordTracer(const RecordTracer&); ~RecordTracer(); OpeningBookTracer* clone() const; void update(Move); const Move selectMove() const; int stateIndex() const { return state_index.top(); } bool isOutOfBook() const; void popMove(); static const RecordTracer kisenRecord(const char *filename, int id, unsigned int num_moves, bool verbose); }; } // namespace game_playing } // namespace osl #endif /* _RECORDTRACER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/alphaBetaPlayer.cc0000644000000000000000000001722012521114240022172 0ustar rootroot/* alphaBetaPlayer.cc */ #include "osl/game_playing/alphaBetaPlayer.h" #include "osl/game_playing/searchPlayer.tcc" #include "osl/search/alphaBeta2.h" #include "osl/search/alphaBeta3.h" #include "osl/search/alphaBeta4.h" #include "osl/search/usiProxy.h" #include "osl/search/simpleHashTable.h" #include "osl/eval/progressEval.h" #include "osl/eval/pieceEval.h" #include #ifndef MINIMAL osl::game_playing:: AlphaBeta2ProgressEvalPlayer::AlphaBeta2ProgressEvalPlayer() { } osl::game_playing:: AlphaBeta2ProgressEvalPlayer::~AlphaBeta2ProgressEvalPlayer() { } osl::game_playing::ComputerPlayer* osl::game_playing:: AlphaBeta2ProgressEvalPlayer::clone() const { return cloneIt(*this); } const osl::search::MoveWithComment osl::game_playing:: AlphaBeta2ProgressEvalPlayer::searchWithSecondsForThisMove(const GameState& gs, const search::TimeAssigned& org) { const milliseconds consumed = setUpTable(gs, pawnValueOfTurn(gs.state().turn())); const search::TimeAssigned msec(adjust(org, consumed)); searcher.reset(); try { searcher.reset(new AlphaBeta2ProgressEval(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr)); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of AlphaBeta2 failed\n"; } return SearchPlayer::search(gs, msec); } bool osl::game_playing:: AlphaBeta2ProgressEvalPlayer::isReasonableMove(const GameState& gs, Move move, int pawn_sacrifice) { setUpTable(gs, pawnValueOfTurn(gs.state().turn())); AlphaBeta2ProgressEval searcher(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr); return SearchPlayer::isReasonableMoveBySearch(searcher, move, pawn_sacrifice); } #endif /* ------------------------------------------------------------------------- */ osl::game_playing:: AlphaBeta2OpenMidEndingEvalPlayer::AlphaBeta2OpenMidEndingEvalPlayer() { } osl::game_playing:: AlphaBeta2OpenMidEndingEvalPlayer::~AlphaBeta2OpenMidEndingEvalPlayer() { } osl::game_playing::ComputerPlayer* osl::game_playing:: AlphaBeta2OpenMidEndingEvalPlayer::clone() const { return cloneIt(*this); } const osl::search::MoveWithComment osl::game_playing:: AlphaBeta2OpenMidEndingEvalPlayer::searchWithSecondsForThisMove(const GameState& gs, const search::TimeAssigned& org) { const milliseconds consumed = setUpTable(gs, pawnValueOfTurn(gs.state().turn())); const search::TimeAssigned msec(adjust(org, consumed)); searcher.reset(); try { searcher.reset(new AlphaBeta2OpenMidEndingEval(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr)); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of AlphaBeta2 failed\n"; } return SearchPlayer::search(gs, msec); } const osl::search::MoveWithComment osl::game_playing:: AlphaBeta2OpenMidEndingEvalPlayer::analyzeWithSeconds(const GameState& gs, const search::TimeAssigned& org, search::AlphaBeta2SharedRoot& out) { const search::MoveWithComment result = searchWithSecondsForThisMove(gs, org); out = dynamic_cast(*searcher).sharedRootInfo(); return result; } bool osl::game_playing:: AlphaBeta2OpenMidEndingEvalPlayer::isReasonableMove(const GameState& gs, Move move, int pawn_sacrifice) { setUpTable(gs, pawnValueOfTurn(gs.state().turn())); AlphaBeta2OpenMidEndingEval searcher(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr); return SearchPlayer::isReasonableMoveBySearch(searcher, move, pawn_sacrifice); } /* ------------------------------------------------------------------------- */ #ifndef MINIMAL osl::game_playing:: AlphaBeta3OpenMidEndingEvalPlayer::AlphaBeta3OpenMidEndingEvalPlayer() { } osl::game_playing:: AlphaBeta3OpenMidEndingEvalPlayer::~AlphaBeta3OpenMidEndingEvalPlayer() { } osl::game_playing::ComputerPlayer* osl::game_playing:: AlphaBeta3OpenMidEndingEvalPlayer::clone() const { return cloneIt(*this); } const osl::search::MoveWithComment osl::game_playing:: AlphaBeta3OpenMidEndingEvalPlayer::searchWithSecondsForThisMove(const GameState& gs, const search::TimeAssigned& org) { const milliseconds consumed = setUpTable(gs, pawnValueOfTurn(gs.state().turn())); const search::TimeAssigned msec(adjust(org, consumed)); searcher.reset(); try { searcher.reset(new AlphaBeta3(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr)); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of AlphaBeta3 failed\n"; } return SearchPlayer::search(gs, msec); } bool osl::game_playing:: AlphaBeta3OpenMidEndingEvalPlayer::isReasonableMove(const GameState& gs, Move move, int pawn_sacrifice) { setUpTable(gs, pawnValueOfTurn(gs.state().turn())); AlphaBeta3 searcher(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr); return SearchPlayer::isReasonableMoveBySearch(searcher, move, pawn_sacrifice); } #endif /* ------------------------------------------------------------------------- */ osl::game_playing:: AlphaBeta4Player::AlphaBeta4Player() { } osl::game_playing:: AlphaBeta4Player::~AlphaBeta4Player() { } osl::game_playing::ComputerPlayer* osl::game_playing:: AlphaBeta4Player::clone() const { return cloneIt(*this); } const osl::search::MoveWithComment osl::game_playing:: AlphaBeta4Player::searchWithSecondsForThisMove(const GameState& gs, const search::TimeAssigned& org) { const milliseconds consumed = setUpTable(gs, pawnValueOfTurn(gs.state().turn())); const search::TimeAssigned msec(adjust(org, consumed)); searcher.reset(); try { searcher.reset(new AlphaBeta4(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr)); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of AlphaBeta4 failed\n"; } return SearchPlayer::search(gs, msec); } bool osl::game_playing:: AlphaBeta4Player::isReasonableMove(const GameState& gs, Move move, int pawn_sacrifice) { setUpTable(gs, pawnValueOfTurn(gs.state().turn())); AlphaBeta4 searcher(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr); return SearchPlayer::isReasonableMoveBySearch(searcher, move, pawn_sacrifice); } /* ------------------------------------------------------------------------- */ osl::game_playing:: UsiProxyPlayer::UsiProxyPlayer() { } osl::game_playing:: UsiProxyPlayer::~UsiProxyPlayer() { } osl::game_playing::ComputerPlayer* osl::game_playing:: UsiProxyPlayer::clone() const { return cloneIt(*this); } const osl::search::MoveWithComment osl::game_playing:: UsiProxyPlayer::searchWithSecondsForThisMove(const GameState& gs, const search::TimeAssigned& org) { using search::UsiProxy; const milliseconds consumed = setUpTable(gs, pawnValueOfTurn(gs.state().turn())); const search::TimeAssigned msec(adjust(org, consumed)); searcher.reset(); try { searcher.reset(new UsiProxy(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr)); } catch (std::bad_alloc&) { std::cerr << "panic. allocation of UsiProxy failed\n"; } return SearchPlayer::search(gs, msec); } bool osl::game_playing:: UsiProxyPlayer::isReasonableMove(const GameState& gs, Move move, int pawn_sacrifice) { setUpTable(gs, pawnValueOfTurn(gs.state().turn())); search::UsiProxy searcher(gs.state(), *checkmate_ptr, table_ptr.get(), *recorder_ptr); return SearchPlayer::isReasonableMoveBySearch(searcher, move, pawn_sacrifice); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/historyToTable.h0000644000000000000000000000223312316770314021764 0ustar rootroot/* historyToTable.h */ #ifndef GAME_PLAYING_HISTORYTOTABLE_H #define GAME_PLAYING_HISTORYTOTABLE_H namespace osl { class Move; namespace hash { class HashKey; } namespace search { class SimpleHashTable; class HashRejections; } namespace game_playing { class GameState; struct PVHistory; struct HistoryToTable { /** table ã«æ›¸ã込む深㕠*/ static const int LIMIT; /** * key ã®å±€é¢ã®æŒé§’ã®å¢—減ã•ã›ãŸå±€é¢ã‚’記録 */ static void adjustDominance(const hash::HashKey& key, search::SimpleHashTable& table, int black_win, int white_win, const Move& good_move); /** * table ã«åƒæ—¥æ‰‹æƒ…報,水平線対策情報を記録 */ static void adjustTable(const GameState&, search::SimpleHashTable& table, int black_win, int draw, int white_win); static void setPV(const PVHistory&, const GameState&, search::SimpleHashTable& table); }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_HISTORYTOTABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/pvHistory.h0000644000000000000000000000054112316770314021017 0ustar rootroot/* pvHistory.h */ #ifndef _PVHISTORY_H #define _PVHISTORY_H #include "osl/search/moveWithComment.h" #include "osl/container.h" namespace osl { namespace game_playing { struct PVHistory : public CArray { }; } } #endif /* _PVHISTORY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/bookPlayer.cc0000644000000000000000000000622112316770314021256 0ustar rootroot/* bookPlayer.cc */ #include "osl/game_playing/bookPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/openingBookTracer.h" #include "osl/book/compactBoard.h" #include "osl/container/moveStack.h" #include #include osl::game_playing:: BookPlayer:: BookPlayer(OpeningBookTracer *b, ComputerPlayer *s) : book(b), searcher(s), book_limit(-1), current_moves(0), valid_initial_position(true) { } osl::game_playing:: BookPlayer::~BookPlayer() { } osl::game_playing::ComputerPlayer* osl::game_playing:: BookPlayer::clone() const { return new BookPlayer(book->clone(), searcher->clone()); } void osl::game_playing:: BookPlayer::setBookLimit(int new_limit) { book_limit = new_limit; } void osl::game_playing:: BookPlayer::setInitialState(const NumEffectState& state) { SimpleState usual(HIRATE); valid_initial_position = (book::CompactBoard(state) == book::CompactBoard(usual)); if (book->isVerbose() && !valid_initial_position) std::cerr << "book: end" << "\n"; } void osl::game_playing:: BookPlayer::pushMove(Move m) { ++current_moves; if (valid_initial_position) book->update(m); searcher->pushMove(m); } void osl::game_playing:: BookPlayer::popMove() { --current_moves; if (valid_initial_position) book->popMove(); searcher->popMove(); } bool osl::game_playing:: BookPlayer::bookAvailable() const { return valid_initial_position && (! book->isOutOfBook()) && (book_limit < 0 || current_moves < book_limit); } const osl::Move osl::game_playing:: BookPlayer::moveByBook(const GameState& state) { if (bookAvailable()) { const Move best_move = book->selectMove(); if (best_move.isNormal() && (! state.isIllegal(best_move))) return best_move; } return Move::INVALID(); } const osl::search::MoveWithComment osl::game_playing:: BookPlayer::selectBestMove(const GameState& state, int limit, int elapsed, int byoyomi) { const Move move = moveByBook(state); if (move.isNormal()) return MoveWithComment(move); return searcher->selectBestMove(state, limit, elapsed, byoyomi); } const osl::search::MoveWithComment osl::game_playing:: BookPlayer::selectBestMoveInTime(const GameState& state, const search::TimeAssigned& msec) { const Move move = moveByBook(state); if (move.isNormal()) return MoveWithComment(move); if (ComputerPlayerSelectBestMoveInTime *p = dynamic_cast(searcher.get())) return p->selectBestMoveInTime(state, msec); throw std::runtime_error("type error in BookPlayer::selectBestMoveInTime"); } void osl::game_playing:: BookPlayer::allowSpeculativeSearch(bool value) { ComputerPlayer::allowSpeculativeSearch(value); searcher->allowSpeculativeSearch(value); } void osl::game_playing:: BookPlayer::setRootIgnoreMoves(const MoveVector *rim, bool prediction) { ComputerPlayer::setRootIgnoreMoves(rim, prediction); searcher->setRootIgnoreMoves(rim, prediction); } bool osl::game_playing:: BookPlayer::stopSearchNow() { return searcher->stopSearchNow(); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/osl/game_playing/csaLogger.h0000644000000000000000000000247112316770314020722 0ustar rootroot/* csaLogger.h */ #ifndef GAME_PLAYING_CSALOGGER_H #define GAME_PLAYING_CSALOGGER_H #include "osl/basic_type.h" #include namespace osl { class Move; class Sennichite; namespace state { class SimpleState; } namespace search { struct MoveWithComment; } namespace game_playing { class TimeKeeper; /** * 棋譜ã®è¨˜éŒ² */ class CsaLogger { std::ostream& output; public: explicit CsaLogger(std::ostream& os); ~CsaLogger(); void init(const char *black, const char *white, const SimpleState& state); void pushMove(const Move& move, int seconds); void pushMove(const search::MoveWithComment& move, int seconds); void popMove(); void showTimeLeft(const TimeKeeper&); void writeComment(const char *comment); void resign(Player resigned); void inputError(const char *); void breakGame(); void endByRepetition(const Sennichite&); void endByDeclaration(Player declarer); private: void writeLine(const char *line); void writeWinner(Player winner); void writeCurrentDate(); }; } // namespace game_playing } // namespace osl #endif /* GAME_PLAYING_CSALOGGER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/test/0000755000000000000000000000000012316770314014365 5ustar rootrootlibosl-0.8.0.orig/full/test/threatmate/0000755000000000000000000000000012316770314016523 5ustar rootrootlibosl-0.8.0.orig/full/test/threatmate/richPredictor.t.cc0000644000000000000000000000516412316770314022103 0ustar rootroot#include "osl/threatmate/richPredictor.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::threatmate; BOOST_AUTO_TEST_CASE(RichPredictorTestBeginning) { const NumEffectState state((SimpleState(HIRATE))); const Move move = Move(Square(3,3), PAWN, WHITE); RichPredictor Rich; BOOST_CHECK( Rich.predict(state, move) < 100.0); } BOOST_AUTO_TEST_CASE(RichPredictorTestAddEffect) { const NumEffectState state(CsaString( "P1-KY * * +TO * +KA-OU-KE-KY\n" "P2-KY * * * +HI-KI * * * \n" "P3 * * -KE * * -FU-FU-FU * \n" "P4 * -FU-FU * * * * -KI-FU\n" "P5-FU * * * +FU * * * * \n" "P6 * * +FU-HI * * * +KI * \n" "P7+FU+FU+KE * -TO-NK+FU * * \n" "P8+OU * +GI * * * * * * \n" "P9+KY * -TO * * * * * * \n" "P+00KI00FU\n" "P-00KA00GI00GI00GI00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(5,2), ROOK, BLACK); RichPredictor Rich; BOOST_CHECK( Rich.predict(state, move) > 0.0); } BOOST_AUTO_TEST_CASE(RichPredictorTestNotAddEffect) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * * +GI\n" "P4+FU * * * -KY+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * +KA-UM * \n" "P7 * +FU * * * * -KY+KY-GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(3,6), BISHOP, BLACK); RichPredictor Rich; BOOST_CHECK( Rich.predict(state, move) > 0.0); } BOOST_AUTO_TEST_CASE(RichPredictorTestCheck) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * +KY+GI\n" "P4+FU * * * -UM+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * * * * \n" "P7 * +FU * * * * -KY * -GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00KA00KY00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(2,3), LANCE, BLACK); RichPredictor Rich; BOOST_CHECK( Rich.predict(state, move) > 0.0); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/threatmate/kfendPredictor.t.cc0000644000000000000000000000652212316770314022244 0ustar rootroot#include "osl/threatmate/kfendPredictor.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::threatmate; BOOST_AUTO_TEST_CASE(KfendPredictorTestBeginning) { const NumEffectState state((SimpleState(HIRATE))); const Move move = Move(Square(3,3), PAWN, WHITE); KfendPredictor Kfend; BOOST_CHECK( !Kfend.predict(state, move) ); } BOOST_AUTO_TEST_CASE(KfendPredictorTestAddEffect) { const NumEffectState state(CsaString( "P1-KY * * +TO * +KA-OU-KE-KY\n" "P2-KY * * * +HI-KI * * * \n" "P3 * * -KE * * -FU-FU-FU * \n" "P4 * -FU-FU * * * * -KI-FU\n" "P5-FU * * * +FU * * * * \n" "P6 * * +FU-HI * * * +KI * \n" "P7+FU+FU+KE * -TO-NK+FU * * \n" "P8+OU * +GI * * * * * * \n" "P9+KY * -TO * * * * * * \n" "P+00KI00FU\n" "P-00KA00GI00GI00GI00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(5,2), ROOK, BLACK); KfendPredictor Kfend; BOOST_CHECK( Kfend.predict(state, move) ); } BOOST_AUTO_TEST_CASE(KfendPredictorTestNotAddEffect) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * * +GI\n" "P4+FU * * * -KY+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * +KA-UM * \n" "P7 * +FU * * * * -KY+KY-GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(3,6), BISHOP, BLACK); KfendPredictor Kfend; BOOST_CHECK( !Kfend.predict(state, move) ); } BOOST_AUTO_TEST_CASE(KfendPredictorTestCheck) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * +KY+GI\n" "P4+FU * * * -UM+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * * * * \n" "P7 * +FU * * * * -KY * -GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00KA00KY00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(2,3), LANCE, BLACK); KfendPredictor Kfend; BOOST_CHECK( Kfend.predict(state, move) ); } BOOST_AUTO_TEST_CASE(KfendPredictorTestChecked) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * -FU * \n" "P3 * * * * * * * +KY+GI\n" "P4+FU * * * -UM+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * * * * \n" "P7 * +FU * * * * -KY * -GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00KA00KY00FU00FU00FU00FU00FU\n" "+\n").initialState()); const Move move = Move(Square(2,2), PAWN, BLACK); KfendPredictor Kfend; BOOST_CHECK( !Kfend.predict(state, move) ); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/threatmate/treePredictor.t.cc0000644000000000000000000000546112316770314022115 0ustar rootroot#include "osl/threatmate/treePredictor.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::threatmate; BOOST_AUTO_TEST_CASE(TreePredictorTestBeginning) { const NumEffectState state((SimpleState(HIRATE))); const Move move = Move(Square(3,3), PAWN, WHITE); TreePredictor Tree; BOOST_CHECK(! Tree.predict(state, move) ); BOOST_CHECK(Tree.probability(state, move) < 0.5); } BOOST_AUTO_TEST_CASE(TreePredictorTestAddEffect) { const NumEffectState state(CsaString( "P1-KY * * +TO * +KA-OU-KE-KY\n" "P2-KY * * * +HI-KI * * * \n" "P3 * * -KE * * -FU-FU-FU * \n" "P4 * -FU-FU * * * * -KI-FU\n" "P5-FU * * * +FU * * * * \n" "P6 * * +FU-HI * * * +KI * \n" "P7+FU+FU+KE * -TO-NK+FU * * \n" "P8+OU * +GI * * * * * * \n" "P9+KY * -TO * * * * * * \n" "P+00KI00FU\n" "P-00KA00GI00GI00GI00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(5,2), ROOK, BLACK); TreePredictor Tree; BOOST_CHECK( Tree.predict(state, move) ); BOOST_CHECK(Tree.probability(state, move) > 0.5); } BOOST_AUTO_TEST_CASE(TreePredictorTestNotAddEffect) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * * +GI\n" "P4+FU * * * -KY+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * +KA-UM * \n" "P7 * +FU * * * * -KY+KY-GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(3,6), BISHOP, BLACK); TreePredictor Tree; BOOST_CHECK(! Tree.predict(state, move) ); BOOST_CHECK(Tree.probability(state, move) < 0.5); } BOOST_AUTO_TEST_CASE(TreePredictorTestCheck) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * +KY+GI\n" "P4+FU * * * -UM+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * * * * \n" "P7 * +FU * * * * -KY * -GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00KA00KY00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(2,3), LANCE, BLACK); TreePredictor Tree; BOOST_CHECK( Tree.predict(state, move) ); BOOST_CHECK(Tree.probability(state, move) > 0.5); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/threatmate/mlPredictor.t.cc0000644000000000000000000000545312316770314021567 0ustar rootroot#include "osl/threatmate/mlPredictor.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::threatmate; BOOST_AUTO_TEST_CASE(MlPredictorTestBeginning) { const NumEffectState state((SimpleState(HIRATE))); const Move move = Move(Square(3,3), PAWN, WHITE); MlPredictor Ml; BOOST_CHECK( Ml.predict(state, move) < 0.0 ); BOOST_CHECK( Ml.probability(state, move) < 0.5 ); } BOOST_AUTO_TEST_CASE(MlPredictorTestAddEffect) { const NumEffectState state(CsaString( "P1-KY * * +TO * +KA-OU-KE-KY\n" "P2-KY * * * +HI-KI * * * \n" "P3 * * -KE * * -FU-FU-FU * \n" "P4 * -FU-FU * * * * -KI-FU\n" "P5-FU * * * +FU * * * * \n" "P6 * * +FU-HI * * * +KI * \n" "P7+FU+FU+KE * -TO-NK+FU * * \n" "P8+OU * +GI * * * * * * \n" "P9+KY * -TO * * * * * * \n" "P+00KI00FU\n" "P-00KA00GI00GI00GI00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(5,2), ROOK, BLACK); MlPredictor Ml; BOOST_CHECK( Ml.predict(state, move) > 0.0 ); BOOST_CHECK( Ml.probability(state, move) > 0.5 ); } BOOST_AUTO_TEST_CASE(MlPredictorTestNotAddEffect) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * * +GI\n" "P4+FU * * * -KY+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * +KA-UM * \n" "P7 * +FU * * * * -KY+KY-GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(3,6), BISHOP, BLACK); MlPredictor Ml; BOOST_CHECK( Ml.predict(state, move) < 0.0 ); BOOST_CHECK( Ml.probability(state, move) < 0.5 ); } BOOST_AUTO_TEST_CASE(MlPredictorTestCheck) { const NumEffectState state(CsaString( "P1+RY-KE-FU * +NK * * -OU-FU\n" "P2 * * -GI * * +KI * * * \n" "P3 * * * * * * * +KY+GI\n" "P4+FU * * * -UM+GI-KY * +FU\n" "P5 * -FU * * * * * * -KE\n" "P6 * * +FU * * * * * * \n" "P7 * +FU * * * * -KY * -GI\n" "P8 * * * * * -KI * * * \n" "P9-RY+KE+KI * * * * +KI+OU\n" "P+00FU00FU00FU00FU00FU\n" "P-00KA00KY00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); const Move move = Move(Square(2,3), LANCE, BLACK); MlPredictor Ml; BOOST_CHECK( Ml.predict(state, move) > 0.0 ); BOOST_CHECK( Ml.probability(state, move) > 0.5 ); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/enter_king/0000755000000000000000000000000012316770314016512 5ustar rootrootlibosl-0.8.0.orig/full/test/enter_king/simplePredictor.t.cc0000644000000000000000000001773612316770314022446 0ustar rootroot#include "osl/csa.h" #include "osl/oslConfig.h" #include "osl/enter_king/simplePredictor.h" #include #include #include using namespace osl; using namespace enter_king; BOOST_AUTO_TEST_CASE(SimplePredictorTestBeginning) { const NumEffectState state((SimpleState(HIRATE))); SimplePredictor Predictor; const double pb = Predictor.getProbability(state); const double pw = Predictor.getProbability(state); BOOST_CHECK( !Predictor.predict(state,BLACK) ); BOOST_CHECK( !Predictor.predict(state, WHITE) ); BOOST_CHECK( pb == pw ); const double pb27 = Predictor.getProbability27(state); const double pw27 = Predictor.getProbability27(state); BOOST_CHECK( pb27 < 0.1); BOOST_CHECK( pw27 < 0.1); // BOOST_CHECK( pb27 != pw27 ); } BOOST_AUTO_TEST_CASE(SimplePredictorTestBlackWin) { const NumEffectState state(CsaString( "P1 * * +RY * * +KI * -KE * \n" "P2+OU+TO+UM+UM+TO * -KI-OU * \n" "P3-FU+FU+FU+FU+FU-GI-GI * * \n" "P4 * * * * -FU-FU-FU-FU * \n" "P5 * * -RY-NY-GI * * * * \n" "P6 * * * * * +FU+FU+FU * \n" "P7 * * * * * +KI+KE * -NY\n" "P8 * * * * * +KI+GI * * \n" "P9 * * * * -NY * * * * \n" "P+00FU00FU00FU00FU00KY00KE00KE\n" "+\n").initialState()); SimplePredictor Predictor; BOOST_CHECK( Predictor.predict(state,BLACK) ); BOOST_CHECK( Predictor.predict27(state,BLACK) ); } BOOST_AUTO_TEST_CASE(SimplePredictorTestWhiteWin) { const NumEffectState state(CsaString( "P1 * * * * +NY * * * * \n" "P2 * * * * * -KI-GI * * \n" "P3 * * * * * -KI-KE * +NY\n" "P4 * * * * * -FU-FU-FU * \n" "P5 * * +RY+NY+GI * * * * \n" "P6 * * * * +FU+FU+FU+FU * \n" "P7+FU-FU-FU-FU-FU+GI+GI * * \n" "P8-OU-TO-UM-UM-TO * +KI+OU * \n" "P9 * * -RY * * -KI * +KE * \n" "P-00FU00FU00FU00FU00KY00KE00KE\n" "-\n").initialState()); SimplePredictor Predictor; BOOST_CHECK( Predictor.predict(state, WHITE) ); BOOST_CHECK( Predictor.predict27(state, WHITE) ); } BOOST_AUTO_TEST_CASE(SimplePredictorTestBothEnterBlackWin) { const NumEffectState state(CsaString( "P1+NK+OU * * * +RY * * * \n" "P2 * +TO+NY * * * +KI * * \n" "P3 * * * * * * * +GI * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * -KY\n" "P7 * * * * * * -TO * * \n" "P8 * * * * * * * * -OU\n" "P9+KY-HI * * * * * -NG * \n" "P+00KA00KA00KI00KI00GI00GI00KE00KE00FU00FU00FU00FU00FU\n" "P-00KI00KE00KY00FU00FU00FU00FU00FU00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); SimplePredictor Predictor; BOOST_CHECK(Predictor.predict(state,BLACK)); BOOST_CHECK(! Predictor.predict(state, WHITE)); BOOST_CHECK(Predictor.predict27(state,BLACK)); BOOST_CHECK(! Predictor.predict27(state, WHITE)); } BOOST_AUTO_TEST_CASE(SimplePredictorTestBothEnterWhiteWin) { const NumEffectState state(CsaString( "P1-KY+HI * * * * * +NG * \n" "P2 * * * * * * * * +OU\n" "P3 * * * * * * +TO * * \n" "P4 * * * * * * * * +KY\n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * -GI * \n" "P8 * -TO-NY * * * -KI * * \n" "P9-NK-OU * * * -RY * * * \n" "P-00KA00KA00KI00KI00GI00GI00KE00KE00FU00FU00FU00FU00FU\n" "P+00KI00KE00KY00FU00FU00FU00FU00FU00FU00FU00FU00FU00FU00FU\n" "+\n").initialState()); SimplePredictor Predictor; BOOST_CHECK(! Predictor.predict(state,BLACK)); BOOST_CHECK(Predictor.predict(state, WHITE)); BOOST_CHECK(! Predictor.predict27(state,BLACK)); BOOST_CHECK(Predictor.predict27(state, WHITE)); } BOOST_AUTO_TEST_CASE(SimplePredictorTestBothEnter) { const NumEffectState state(CsaString( "P1 * * * * * * +RY * -KY\n" "P2+TO+OU * +FU+UM * * * * \n" "P3 * * +FU+KI * * * -FU-FU\n" "P4+KI * +GI * * * * * * \n" "P5+KY+KI * * * * * * +FU\n" "P6 * * * * * -UM * * * \n" "P7 * +FU * * * -NG-NK * * \n" "P8 * * * * -TO * * * * \n" "P9 * * * -TO * * -TO-OU-NG\n" "P+00KI00KE00KY00FU00FU00FU00FU\n" "P-00HI00GI00KE00KE00KY00FU00FU00FU00FU\n" "+\n").initialState()); SimplePredictor Predictor; BOOST_CHECK(Predictor.predict(state,BLACK)); BOOST_CHECK(Predictor.predict(state,WHITE)); } BOOST_AUTO_TEST_CASE(SimplePredictorTestOppositionBlackCannotEnter) { const NumEffectState state(CsaString( "P1-KY * * * * * * -KE-OU\n" "P2 * * * * * * -KI-KI-KY\n" "P3-FU * * -FU * * -FU-FU-FU\n" "P4 * * -FU * -FU * * * * \n" "P5 * * * +FU-KA * +FU * +OU\n" "P6 * * +FU * +KA * +KI * * \n" "P7+FU * * * +FU+GI+KE-KI+FU\n" "P8 * * * * * * * -GI+KY\n" "P9 * * * * * * +RY * * \n" "P+00HI00KE00KE00KY00FU00FU00FU00FU00FU\n" "P-00GI00GI\n" "+\n").initialState()); SimplePredictor Predictor; BOOST_CHECK(! Predictor.predict(state,BLACK)); BOOST_CHECK(! Predictor.predict27(state,BLACK)); } BOOST_AUTO_TEST_CASE(SimplePredictorTestOppositionWhiteCannotEnter) { const NumEffectState state(CsaString( "P1 * * * * * * -RY * * \n" "P2 * * * * * * * +GI-KY\n" "P3-FU * * * -FU-GI-KE+KI-FU\n" "P4 * * -FU * -KA * -KI * * \n" "P5 * * * -FU+KA * -FU * -OU\n" "P6 * * +FU * +FU * * * * \n" "P7+FU * * +FU * * +FU+FU+FU\n" "P8 * * * * * * +KI+KI+KY\n" "P9+KY * * * * * * +KE+OU\n" "P+00GI00GI\n" "P-00HI00KE00KE00KY00FU00FU00FU00FU00FU\n" "-\n").initialState()); SimplePredictor Predictor; BOOST_CHECK(! Predictor.predict(state, WHITE)); BOOST_CHECK(! Predictor.predict27(state, WHITE)); } BOOST_AUTO_TEST_CASE(SimplePredictorTestDistantMajorPieceBlackWin){ // 大駒ã¯1æ‰‹ã§æ•µé™£ã«å…¥ã‚Œã‚‹ãŒã€ãれを考慮ã—ã¦ã„ãªã„ãŸã‚ã«å¤±æ•—ã™ã‚‹ã‹ã‚‚ã—れãªã„ const NumEffectState state(CsaString( "P1-FU * * * * * -RY-KE-KY\n" "P2 * * +NG+TO * * -KI-OU * \n" "P3+FU+OU * +KI * -KI * -FU * \n" "P4 * * -FU+FU-FU * * -KE * \n" "P5 * -NY * * -KA-GI+FU * * \n" "P6 * * -GI * * * * +FU+FU\n" "P7 * * * * -NK * -FU+KY+KY\n" "P8+RY * * * * * * * * \n" "P9 * * * * * * * * * \n" "P+00KA00KI00KE00FU00FU00FU00FU00FU00FU00FU\n" "P-00GI\n" "-\n").initialState()); SimplePredictor Predictor; // std::cerr << Predictor.getProbability(state) << std::endl; BOOST_CHECK(Predictor.predict(state,BLACK)); } BOOST_AUTO_TEST_CASE(SimplePredictorTestDistantMajorPieceWhiteWin){ // 大駒ã¯1æ‰‹ã§æ•µé™£ã«å…¥ã‚Œã‚‹ãŒã€ãれを考慮ã—ã¦ã„ãªã„ãŸã‚ã«å¤±æ•—ã™ã‚‹ã‹ã‚‚ã—れãªã„ const NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2-RY * * * * * * * * \n" "P3 * * * * +NK * +FU-KY-KY\n" "P4 * * +GI * * * * -FU-FU\n" "P5 * +NY * * +KA+GI-FU * * \n" "P6 * * +FU-FU+FU * * +KE * \n" "P7-FU-OU * -KI * +KI * +FU * \n" "P8 * * -NG-TO * * +KI+OU * \n" "P9+FU * * * * * +RY+KE+KY\n" "P+00GI\n" "P-00KA00KI00KE00FU00FU00FU00FU00FU00FU00FU\n" "+\n").initialState()); SimplePredictor Predictor; // std::cerr << Predictor.getProbability(state) << std::endl; BOOST_CHECK(Predictor.predict(state, WHITE)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/testOne.cc0000644000000000000000000000073612316770314016323 0ustar rootroot#include "osl/oslConfig.h" #define BOOST_TEST_DYN_LINK #include #include bool init_unit_test() { osl::OslConfig::setInUnitTest(2); osl::OslConfig::showOslHome(); osl::OslConfig::setVerbose(true); osl::OslConfig::setUp(); return true; } int main( int argc, char* argv[] ) { return boost::unit_test::unit_test_main( init_unit_test, argc, argv ); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/stat/0000755000000000000000000000000012316770314015340 5ustar rootrootlibosl-0.8.0.orig/full/test/stat/twoDimensionalStatistics.t.cc0000644000000000000000000000266112316770314023165 0ustar rootroot#include "osl/stat/twoDimensionalStatistics.h" #include using namespace osl; using namespace osl::stat; BOOST_AUTO_TEST_CASE(TwoDimensionalStatisticsTestCorrelation) { TwoDimensionalStatistics t; t.add(0,0); t.add(1,1); BOOST_CHECK_EQUAL(1.0, t.correlation()); t.add(1,2); BOOST_CHECK(t.correlation() < 1.0); BOOST_CHECK(0.0 < t.correlation()); } BOOST_AUTO_TEST_CASE(TwoDimensionalStatisticsTestFitting) { { TwoDimensionalStatistics t; t.add(0,0); t.add(1,1); double a, b, res; t.fitting(a, b, res); BOOST_CHECK_EQUAL(1.0, a); BOOST_CHECK_EQUAL(0.0, b); BOOST_CHECK_EQUAL(0.0, res); } { TwoDimensionalStatistics t; t.add(0,0); t.add(1,-1); double a, b, res; t.fitting(a, b, res); BOOST_CHECK_EQUAL(-1.0, a); BOOST_CHECK_EQUAL(0.0, b); BOOST_CHECK_EQUAL(0.0, res); } { TwoDimensionalStatistics t; t.add(0,1); t.add(1,2); double a, b, res; t.fitting(a, b, res); BOOST_CHECK_EQUAL(1.0, a); BOOST_CHECK_EQUAL(1.0, b); BOOST_CHECK_EQUAL(0.0, res); } { TwoDimensionalStatistics t; t.add(0,1); t.add(1,0); double a, b, res; t.fitting(a, b, res); BOOST_CHECK_EQUAL(-1.0, a); BOOST_CHECK_EQUAL(1.0, b); BOOST_CHECK_EQUAL(0.0, res); } { TwoDimensionalStatistics t; t.add(0,0); t.add(1,1); t.add(1,-1); double a, b, res; t.fitting(a, b, res); BOOST_CHECK_EQUAL(0.0, a); BOOST_CHECK_EQUAL(0.0, b); BOOST_CHECK(res > 0.0); } } libosl-0.8.0.orig/full/test/hash/0000755000000000000000000000000012316770314015310 5ustar rootrootlibosl-0.8.0.orig/full/test/hash/hashRandom.t.cc0000644000000000000000000000112112316770314020140 0ustar rootroot#include "osl/hash/hashRandom.h" #include "osl/stat/variance.h" #include #include #include #include using namespace osl; using namespace osl::hash; BOOST_AUTO_TEST_CASE(HashRandomTestSetUp) { double sigma = 10.0; HashRandom::setUp(sigma); stat::Variance var; for (size_t i=0; i #include using namespace osl; BOOST_AUTO_TEST_CASE(MathTestNthPower) { BOOST_CHECK_EQUAL(1, (osl::misc::nthPower<0>(3))); BOOST_CHECK_EQUAL(3, (osl::misc::nthPower<1>(3))); BOOST_CHECK_EQUAL(3*3, (osl::misc::nthPower<2>(3))); BOOST_CHECK_EQUAL(3*3*3*3*3, (osl::misc::nthPower<5>(3))); } BOOST_AUTO_TEST_CASE(MathTestComputeStdDev) { typedef std::vector data_t; data_t data; data.push_back(154.0); data.push_back(150.0); data.push_back(140.0); data_t::const_iterator first = data.begin(); data_t::const_iterator last = data.end(); const size_t cnt = distance(first, last); const double sum = accumulate(first, last, double()); const double mean = sum / cnt; const double result = misc::computeStdDev(data.begin(), data.end(), mean); BOOST_CHECK_CLOSE(5.89, result, 1); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/Makefile0000644000000000000000000000533512316770314016033 0ustar rootrootOSL_HOME = ../.. -include makefile.local -include $(OSL_HOME)/makefile.local -include $(OSL_HOME)/makefile.conf LDFLAGS += -L../osl -L../../std/osl -L../../core/osl LOADLIBES += -losl_full -losl_std -losl_core $(BOOST_LIBS) -lboost_unit_test_framework $(LDLIBS) INCLUDES += -I.. -I../../std -I../../core PROGRAMS = testAll EVAL_SRC = \ endgame/attackDefense.t.cc endgame/attackKing.t.cc endgame/defenseKing.t.cc \ endgame/kingPieceTable.t.cc minorPieceBonus.t.cc pieceEval.t.cc \ ppair/piecePairIndex.t.cc ppair/piecePairPieceEval.t.cc \ ppair/piecePairRawEval.t.cc progressEval.t.cc SEARCH_SRC = \ alphaBeta2.t.cc lRUMoves.t.cc quiescenceSearch.t.cc \ bigramKillerMove.t.cc moveGenerator.t.cc sacrificeCheck.t.cc \ breakThreatmate.t.cc moveStackRejections.t.cc searchRecorder.t.cc \ dominanceCheck.t.cc problems.cc shouldPromoteCut.t.cc \ dualThreatmateState.t.cc simpleHashRecord.t.cc \ fixedEval.t.cc quiescenceGenerator.t.cc simpleHashTable.t.cc \ hashRejections.t.cc quiescenceRecord.t.cc threatmateState.t.cc EU_SRC = additionalEffect.t.cc neighboring8Direct.t.cc sendOffSquare.t.cc \ virtualPin.t.cc effectUtil.t.cc pin.t.cc shadowEffect.t.cc GP_SRC = alphaBetaOpenMidEndingEvalPlayer.t.cc gameState.t.cc searchPlayer.t.cc \ alphaBetaPlayer.t.cc gnuShogiClient.t.cc weightTracer.t.cc \ bookPlayer.t.cc historyToTable.t.cc csaClient.t.cc recordTracer.t.cc HASH_SRC = hashRandom.t.cc MP_SRC = addEffect8.t.cc attackToPinned.t.cc safeDropMajorPiece.t.cc MO_SRC = captureEstimation.t.cc captureSort.t.cc cheapPtype.t.cc promotion.t.cc TP_SRC = kfendPredictor.t.cc mlPredictor.t.cc richPredictor.t.cc treePredictor.t.cc SRCS = $(patsubst %.cc,eval/%.cc,$(EVAL_SRC)) \ $(patsubst %.cc,effect_util/%.cc,$(EU_SRC)) \ $(patsubst %.cc,game_playing/%.cc,$(GP_SRC)) \ $(patsubst %.cc,hash/%.cc,$(HASH_SRC)) \ $(patsubst %.cc,move_generator/%.cc,$(MP_SRC)) \ $(patsubst %.cc,move_order/%.cc,$(MO_SRC)) \ $(patsubst %.cc,search/%.cc,$(SEARCH_SRC)) \ $(patsubst %.cc,threatmate/%.cc,$(TP_SRC)) \ enter_king/simplePredictor.t.cc stat/twoDimensionalStatistics.t.cc \ repetitionCounter.t.cc misc/math.t.cc TEST_OBJS = $(patsubst %.cc,%.o,$(SRCS)) OBJS = testAll.o $(TEST_OBJS) all : $(MAKE) update-lib $(MAKE) test-target test-target: $(MAKE) $(PROGRAMS) update-lib: cd ../../core/osl; $(MAKE) cd ../../std/osl; $(MAKE) cd ../osl; $(MAKE) -include $(patsubst %.cc,.deps/%.cc.d,$(SRCS)) testAll: $(OBJS) $(FILE_OSL_STD) $(FILE_OSL_CORE) mkdir -p `dirname $@` > /dev/null 2>&1 $(CXX) $(LDFLAGS) -o $@ $^ $(LOADLIBES) %.t: %.t.o testOne.o $(FILE_OSL_STD) $(FILE_OSL_CORE) $(CXX) $(LDFLAGS) -o $@ $^ $(LOADLIBES) light-clean: -rm -rf .deps clean: light-clean -rm -f core *.o $(OBJS) $(PROGRAMS) libosl-0.8.0.orig/full/test/eval/0000755000000000000000000000000012316770314015314 5ustar rootrootlibosl-0.8.0.orig/full/test/eval/endgame/0000755000000000000000000000000012316770314016714 5ustar rootrootlibosl-0.8.0.orig/full/test/eval/endgame/kingPieceTable.t.cc0000644000000000000000000000116712316770314022340 0ustar rootroot#include "osl/eval/endgame/kingPieceTable.h" #include using namespace osl; using namespace osl::eval; using namespace osl::eval::endgame; class KingPieceTableA : public KingPieceTable { public: KingPieceTableA() { } }; BOOST_AUTO_TEST_CASE(KingPieceTableTestLoad) { std::unique_ptr t1(new KingPieceTableA), t2(new KingPieceTableA); t1->randomize(); BOOST_CHECK(! (*t1 == *t2)); t1->saveText("KingPieceTableTest.txt"); t2->loadText("KingPieceTableTest.txt"); BOOST_CHECK(*t1 == *t2); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/endgame/attackDefense.t.cc0000644000000000000000000001603112316770314022227 0ustar rootroot#include "osl/eval/endgame/attackDefense.h" #include "osl/eval/evalTraits.h" #include "osl/eval/pieceEval.h" #include "osl/csa.h" #include "../consistencyTest.h" #include using namespace osl; using namespace osl::eval; using namespace osl::eval::endgame; BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestInitial) { const NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); AttackDefense eval(state); BOOST_CHECK_EQUAL(0, eval.value()); } BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestMax) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); std::string file_name; for (int i=0; i<(OslConfig::inUnitTestShort() ? 10 : 100) && (ifs >> file_name) ; i++) { if ((i % 20) == 0) std::cerr << '.'; if (file_name == "") break; file_name = OslConfig::testCsaFile(file_name); const auto record=CsaFileMinimal(file_name).load(); const auto& moves=record.moves; NumEffectState state(record.initialState()); for (unsigned int i=0; i(); const Piece white_king = state.kingPiece(); const int attack_black = AttackKing::valueOf(black_king, target); const int attack_white = AttackKing::valueOf(white_king, target); BOOST_CHECK((attack_black == 0) || (attack_white == 0)); const int defense_black = DefenseKing::valueOf(black_king, target); const int defense_white = DefenseKing::valueOf(white_king, target); BOOST_CHECK((defense_black == 0) || (defense_white == 0)); const int attack_defense = AttackDefense::valueOf(black_king, white_king, target); BOOST_CHECK_EQUAL(max(target.owner(), attack_black + attack_white, defense_black + defense_white), attack_defense); } } } } BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestStand) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const int black_value = AttackDefense::valueOf(black_king, white_king, newPtypeO(BLACK,GOLD), Square::STAND()); BOOST_CHECK_EQUAL(static_cast(Ptype_Eval_Table.value(GOLD) * 1.1), black_value); const int white_value = AttackDefense::valueOf(black_king, white_king, newPtypeO(WHITE,GOLD), Square::STAND()); BOOST_CHECK_EQUAL(static_cast(-Ptype_Eval_Table.value(GOLD) * 1.1), white_value); const int black_rook = AttackDefense::valueOf(black_king, white_king, newPtypeO(BLACK,ROOK), Square::STAND()); BOOST_CHECK_EQUAL(Ptype_Eval_Table.value(ROOK) + Ptype_Eval_Table.value(PAWN), black_rook); const int white_rook = AttackDefense::valueOf(black_king, white_king, newPtypeO(WHITE,ROOK), Square::STAND()); BOOST_CHECK_EQUAL(-Ptype_Eval_Table.value(ROOK) - Ptype_Eval_Table.value(PAWN), white_rook); } BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestConsistentUpdate) { consistencyTestUpdate(); } BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestConsistentExpect) { consistencyTestExpect(); } BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestYagura) { { NumEffectState in_castle(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3 * * -GI-FU-KA-KI-GI-FU * \n" "P4-FU * -FU * -FU-FU-FU * -FU\n" "P5 * -FU * * * * * +FU * \n" "P6+FU * +FU+FU+FU * +FU * +FU\n" "P7 * +FU+GI+KI+KA+FU+GI * * \n" "P8 * +OU+KI * * * * +HI * \n" "P9+KY+KE * * * * * +KE+KY\n" "+\n").initialState()); NumEffectState out_castle1(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3 * * -GI-FU-KA-KI-GI-FU * \n" "P4-FU * -FU * -FU-FU-FU * -FU\n" "P5 * -FU * * * * * +FU * \n" "P6+FU * +FU+FU+FU * +FU * +FU\n" "P7 * +FU+GI+KI+KA+FU+GI * * \n" "P8 * * +KI * * * * +HI * \n" "P9+KY+KE+OU * * * * +KE+KY\n" "+\n").initialState()); NumEffectState out_castle2(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3 * * -GI-FU-KA-KI-GI-FU * \n" "P4-FU * -FU * -FU-FU-FU * -FU\n" "P5 * -FU * * * * * +FU * \n" "P6+FU * +FU+FU+FU * +FU * +FU\n" "P7 * +FU+GI+KI+KA+FU+GI * * \n" "P8 * * +KI * * * * +HI * \n" "P9+KY+KE * +OU * * * +KE+KY\n" "+\n").initialState()); NumEffectState out_castle3(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3 * * -GI-FU-KA-KI-GI-FU * \n" "P4-FU * -FU * -FU-FU-FU * -FU\n" "P5 * -FU * * * * * +FU * \n" "P6+FU * +FU+FU+FU * +FU * +FU\n" "P7 * +FU+GI+KI+KA+FU+GI * * \n" "P8 * * +KI * * * * +HI * \n" "P9+KY+KE * +OU * * * +KE+KY\n" "+\n").initialState()); AttackDefense in(in_castle), out1(out_castle1), out2(out_castle2), out3(out_castle3); BOOST_CHECK(in.value(BLACK) > out1.value(BLACK)); BOOST_CHECK(out1.value(BLACK) > out2.value(BLACK)); BOOST_CHECK(out1.value(BLACK) > out3.value(BLACK)); BOOST_CHECK(in.value() - out1.value() > -100); // 本当ã¯å·¦è¾ºå¤§ã«ã—ãŸã„ã‘ã©é›£ã—ã„ BOOST_CHECK(out1.value() > out2.value()); BOOST_CHECK(out1.value() > out3.value()); } } BOOST_AUTO_TEST_CASE(EndgameAttackDeffenseTestBlockingSilver) { { NumEffectState castle1(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3 * * -GI-FU-KA-KI-GI-FU * \n" "P4-FU * -FU * -FU-FU-FU * -FU\n" "P5 * -FU * * * * * +FU * \n" "P6+FU * +FU+FU+FU * +FU * +FU\n" "P7 * +FU+GI+KI+KA+FU+GI * * \n" "P8 * * +KI * * * * +HI * \n" "P9+KY+KE+OU * * * * +KE+KY\n" "+\n").initialState()); NumEffectState bad_castle(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3 * * -GI-FU-KA-KI-GI-FU * \n" "P4-FU * -FU * -FU-FU-FU * -FU\n" "P5 * -FU * * * * * +FU * \n" "P6+FU * +FU+FU+FU * +FU * +FU\n" "P7 * +FU * +KI+KA+FU+GI * * \n" "P8 * +GI+KI * * * * +HI * \n" "P9+KY+KE+OU * * * * +KE+KY\n" "+\n").initialState()); AttackDefense normal(castle1), bad(bad_castle); BOOST_CHECK(normal.value(BLACK) > bad.value(BLACK)); BOOST_CHECK(normal.value() > bad.value()); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/full/test/eval/endgame/defenseKing.t.cc0000644000000000000000000001300512316770314021706 0ustar rootroot#include "osl/eval/endgame/defenseKing.h" #include "osl/eval/evalTraits.h" #include "osl/eval/pieceEval.h" #include #include using namespace osl; using namespace osl::eval; using namespace osl::eval::endgame; BOOST_AUTO_TEST_CASE(EndgameDefenseKingTestSymmetry) { for (int king_x=1; king_x <= 9; ++king_x) { for (int king_y=1; king_y <= 9; ++king_y) { const Square bkp(king_x, king_y); const Piece king_b = Piece::makeKing(BLACK, bkp); const Piece king_w = Piece::makeKing(WHITE, bkp.rotate180()); for (int ptype=PTYPE_PIECE_MIN; ptype<=PTYPE_MAX; ++ptype) { const PtypeO ptypeo_b = newPtypeO(BLACK, static_cast(ptype)); const PtypeO ptypeo_w = newPtypeO(WHITE, static_cast(ptype)); for (int x=1; x <= 9; ++x) { for (int y=1; y <= 9; ++y) { const Square position_b(x,y); const Square position_w = position_b.rotate180(); if (king_b.square() == position_b) continue; const int value_b=DefenseKing::valueOf(king_b, ptypeo_b, position_b); const int value_w=DefenseKing::valueOf(king_w, ptypeo_w, position_w); if (value_b != -value_w) { std::cerr << king_b << " " << ptypeo_b << " " << position_b << std::endl; std::cerr << king_w << " " << ptypeo_w << " " << position_w << std::endl; } BOOST_CHECK_EQUAL(value_b, -value_w); } } } } } } BOOST_AUTO_TEST_CASE(EndgameDefenseKingTestPawnLance) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const Square p58(5,8); const Square p52(5,2); // 1ã¤ã—ã‹å‹•ã‘ãªã„é¦™ã¯æ­©ã¨åŒã˜ç‚¹æ•° BOOST_CHECK_EQUAL(DefenseKing::valueOf(black_king, newPtypeO(WHITE,PAWN), p58), DefenseKing::valueOf(black_king, newPtypeO(WHITE,LANCE), p58)); BOOST_CHECK(DefenseKing::valueOf(black_king, newPtypeO(WHITE,PAWN), p52) >= DefenseKing::valueOf(black_king, newPtypeO(WHITE,LANCE), p52)); BOOST_CHECK_EQUAL(DefenseKing::valueOf(black_king, newPtypeO(BLACK,PAWN), p52), DefenseKing::valueOf(black_king, newPtypeO(BLACK,LANCE), p52)); BOOST_CHECK(DefenseKing::valueOf(black_king, newPtypeO(BLACK,PAWN), p58) < DefenseKing::valueOf(black_king, newPtypeO(BLACK,LANCE), p58)); // 後手玉ã§ã‚‚åŒã˜ BOOST_CHECK_EQUAL(DefenseKing::valueOf(white_king, newPtypeO(WHITE,PAWN), p58), DefenseKing::valueOf(white_king, newPtypeO(WHITE,LANCE), p58)); BOOST_CHECK(DefenseKing::valueOf(white_king, newPtypeO(WHITE,PAWN), p52) > DefenseKing::valueOf(white_king, newPtypeO(WHITE,LANCE), p52)); BOOST_CHECK_EQUAL(DefenseKing::valueOf(white_king, newPtypeO(BLACK,PAWN), p52), DefenseKing::valueOf(white_king, newPtypeO(BLACK,LANCE), p52)); BOOST_CHECK(DefenseKing::valueOf(white_king, newPtypeO(BLACK,PAWN), p58) <= DefenseKing::valueOf(white_king, newPtypeO(BLACK,LANCE), p58)); } BOOST_AUTO_TEST_CASE(EndgameDefenseKingTestKing) { const Square p11(1,1); const Square p19(1,9); const Piece black_king11 = Piece::makeKing(BLACK, p11); const Piece black_king19 = Piece::makeKing(BLACK, p19); BOOST_CHECK(EvalTraits::betterThan (DefenseKing::valueOf(black_king11, black_king11), DefenseKing::valueOf(black_king19, black_king19))); const Piece white_king11 = Piece::makeKing(WHITE, p11); const Piece white_king19 = Piece::makeKing(WHITE, p19); BOOST_CHECK(EvalTraits::betterThan (DefenseKing::valueOf(white_king19, white_king19), DefenseKing::valueOf(white_king11, white_king11))); } static void directionTest(Ptype ptype, bool up_is_better) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const Square up(4,4); const Square down(4,6); const int black_defense_front = DefenseKing::valueOf(black_king, newPtypeO(BLACK,ptype), up); const int black_defense_back = DefenseKing::valueOf(black_king, newPtypeO(BLACK,ptype), down); const int white_defense_front = DefenseKing::valueOf(white_king, newPtypeO(WHITE,ptype), down); const int white_defense_back = DefenseKing::valueOf(white_king, newPtypeO(WHITE,ptype), up); if (up_is_better) { BOOST_CHECK(betterThan(WHITE, white_defense_front, white_defense_back)); BOOST_CHECK(betterThan(BLACK, black_defense_front, black_defense_back)); } else { BOOST_CHECK(! betterThan(WHITE, white_defense_front, white_defense_back)); BOOST_CHECK(! betterThan(BLACK, black_defense_front, black_defense_back)); } // 対称性 BOOST_CHECK_EQUAL(black_defense_front, -white_defense_front); BOOST_CHECK_EQUAL(black_defense_back, -white_defense_back); } BOOST_AUTO_TEST_CASE(EndgameDefenseKingTestStand) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const int black_defense = DefenseKing::valueOf(black_king, newPtypeO(BLACK,GOLD), Square::STAND()); BOOST_CHECK_EQUAL(Ptype_Eval_Table.value(GOLD), black_defense); const int white_defense = DefenseKing::valueOf(white_king, newPtypeO(WHITE,GOLD), Square::STAND()); BOOST_CHECK_EQUAL(-Ptype_Eval_Table.value(GOLD), white_defense); } BOOST_AUTO_TEST_CASE(EndgameDefenseKingTestSave) { DefenseKing::saveText("EndgameDefenseKingTest.txt"); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/endgame/attackKing.t.cc0000644000000000000000000001404112316770314021545 0ustar rootroot#include "osl/eval/endgame/attackKing.h" #include "osl/eval/evalTraits.h" #include "osl/eval/pieceEval.h" #include #include #include using namespace osl; using namespace osl::eval; using namespace osl::eval::endgame; BOOST_AUTO_TEST_CASE(EndgameAttackKingTestSymmetry) { for (int king_x=1; king_x <= 9; ++king_x) { for (int king_y=1; king_y <= 9; ++king_y) { const Square bkp(king_x, king_y); const Piece king_b = Piece::makeKing(BLACK, bkp); const Piece king_w = Piece::makeKing(WHITE, bkp.rotate180()); for (int ptype=PTYPE_PIECE_MIN; ptype<=PTYPE_MAX; ++ptype) { const PtypeO ptypeo_b = newPtypeO(BLACK, static_cast(ptype)); const PtypeO ptypeo_w = newPtypeO(WHITE, static_cast(ptype)); for (int x=1; x <= 9; ++x) { for (int y=1; y <= 9; ++y) { const Square position_b(x,y); const Square position_w = position_b.rotate180(); if (king_w.square() == position_b) continue; const int value_b=AttackKing::valueOf(king_w, ptypeo_b, position_b); const int value_w=AttackKing::valueOf(king_b, ptypeo_w, position_w); if (value_b != -value_w) { std::cerr << king_w << " " << ptypeo_b << " " << position_b << std::endl; std::cerr << king_b << " " << ptypeo_w << " " << position_w << std::endl; } BOOST_CHECK_EQUAL(value_b, -value_w); } } } } } } BOOST_AUTO_TEST_CASE(EndgameAttackKingTestPawnLance) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const Square p58(5,8); const Square p52(5,2); // 1ã¤ã—ã‹å‹•ã‘ãªã„é¦™ã¯æ­©ã¨åŒã˜ç‚¹æ•° BOOST_CHECK_EQUAL(AttackKing::valueOf(black_king, newPtypeO(WHITE,PAWN), p58), AttackKing::valueOf(black_king, newPtypeO(WHITE,LANCE), p58)); BOOST_CHECK(AttackKing::valueOf(black_king, newPtypeO(WHITE,PAWN), p52) > AttackKing::valueOf(black_king, newPtypeO(WHITE,LANCE), p52)); BOOST_CHECK_EQUAL(AttackKing::valueOf(black_king, newPtypeO(BLACK,PAWN), p52), AttackKing::valueOf(black_king, newPtypeO(BLACK,LANCE), p52)); BOOST_CHECK(AttackKing::valueOf(black_king, newPtypeO(BLACK,PAWN), p58) <= AttackKing::valueOf(black_king, newPtypeO(BLACK,LANCE), p58)); // 後手玉ã§ã‚‚åŒã˜ BOOST_CHECK_EQUAL(AttackKing::valueOf(white_king, newPtypeO(WHITE,PAWN), p58), AttackKing::valueOf(white_king, newPtypeO(WHITE,LANCE), p58)); BOOST_CHECK(AttackKing::valueOf(white_king, newPtypeO(WHITE,PAWN), p52) >= AttackKing::valueOf(white_king, newPtypeO(WHITE,LANCE), p52)); BOOST_CHECK_EQUAL(AttackKing::valueOf(white_king, newPtypeO(BLACK,PAWN), p52), AttackKing::valueOf(white_king, newPtypeO(BLACK,LANCE), p52)); BOOST_CHECK(AttackKing::valueOf(white_king, newPtypeO(BLACK,PAWN), p58) < AttackKing::valueOf(white_king, newPtypeO(BLACK,LANCE), p58)); } BOOST_AUTO_TEST_CASE(EndgameAttackKingTestGold) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const Square p51(5,1); const Square p52(5,2); const Square p58(5,8); const Square p59(5,9); // 1段目減点 BOOST_CHECK(AttackKing::valueOf(black_king, newPtypeO(WHITE,GOLD), p58) < AttackKing::valueOf(black_king, newPtypeO(WHITE,GOLD), p59)); BOOST_CHECK(AttackKing::valueOf(white_king, newPtypeO(BLACK,GOLD), p52) > AttackKing::valueOf(white_king, newPtypeO(BLACK,GOLD), p51)); } static void testDirection(Ptype ptype) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const Square up(4,4); const Square down(4,6); // 上ã‹ã‚‰æŠ‘ãˆã‚‹æ–¹ãŒç‚¹æ•°ãŒé«˜ã„ const int white_attack_front = AttackKing::valueOf(black_king, newPtypeO(WHITE,ptype), up); const int white_attack_back = AttackKing::valueOf(black_king, newPtypeO(WHITE,ptype), down); const int black_attack_front = AttackKing::valueOf(white_king, newPtypeO(BLACK,ptype), down); const int black_attack_back = AttackKing::valueOf(white_king, newPtypeO(BLACK,ptype), up); BOOST_CHECK(betterThan(WHITE, white_attack_front, white_attack_back)); BOOST_CHECK(betterThan(BLACK, black_attack_front, black_attack_back)); // 対称性 BOOST_CHECK_EQUAL(black_attack_front, -white_attack_front); BOOST_CHECK_EQUAL(black_attack_back, -white_attack_back); } BOOST_AUTO_TEST_CASE(EndgameAttackKingTestStand) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); const int black_attack = AttackKing::valueOf(white_king, newPtypeO(BLACK,GOLD), Square::STAND()); BOOST_CHECK_EQUAL(static_cast(Ptype_Eval_Table.value(GOLD) * 1.1), black_attack); const int white_attack = AttackKing::valueOf(black_king, newPtypeO(WHITE,GOLD), Square::STAND()); BOOST_CHECK_EQUAL(static_cast(-Ptype_Eval_Table.value(GOLD) * 1.1), white_attack); } BOOST_AUTO_TEST_CASE(EndgameAttackKingTestShow) { const Square king_position(5,5); const Piece black_king = Piece::makeKing(BLACK, king_position); const Piece white_king = Piece::makeKing(WHITE, king_position); // debug 用 for (int y=1; y<=9; ++y) { for (int x=1; x<=9; ++x) { std::cerr << std::setw(4) << AttackKing::valueOf(black_king, newPtypeO(WHITE,PAWN), Square(x,y)); } std::cerr << "\n"; } std::cerr << "\n"; for (int y=1; y<=9; ++y) { for (int x=1; x<=9; ++x) { std::cerr << std::setw(4) << AttackKing::valueOf(white_king, newPtypeO(BLACK,PAWN), Square(x,y)); } std::cerr << "\n"; } } BOOST_AUTO_TEST_CASE(EndgameAttackKingTestSave) { AttackKing::saveText("EndgameAttackKingTest.txt"); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/minorPieceBonus.t.cc0000644000000000000000000000312412316770314021166 0ustar rootroot/* minorPieceBonus.t.cc */ #include "osl/eval/minorPieceBonus.h" #include "osl/progress/effect5x3.h" #include "consistencyTest.h" #include using namespace osl; using namespace osl::eval; struct MinorPieceWithProgress { typedef progress::Effect5x3WithBonus progress_t; progress_t current_progress; MinorPieceBonus minor_piece_bonus; MinorPieceWithProgress(const NumEffectState& state) : current_progress(state), minor_piece_bonus(state) { } int value() const { return minor_piece_bonus.value(current_progress.progress16(), current_progress.progress16bonus(BLACK), current_progress.progress16bonus(WHITE)); } void changeTurn() {} int expect(const NumEffectState& state, Move move) const { NumEffectState new_state = state; new_state.makeMove(move); progress_t next = current_progress; next.update(new_state, move); return minor_piece_bonus.expect(state, move, next.progress16(), next.progress16bonus(BLACK), next.progress16bonus(WHITE)); } void update(const NumEffectState& new_state, Move last_move) { current_progress = progress_t(new_state); minor_piece_bonus.update(new_state, last_move); } }; BOOST_AUTO_TEST_CASE(MinorPieceBonusTestConsistentUpdate) { consistencyTestUpdate(); } BOOST_AUTO_TEST_CASE(MinorPieceBonusTestConsistentExpect) { consistencyTestExpect(0); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/progressEval.t.cc0000644000000000000000000001326212316770314020545 0ustar rootroot/* progressEval.t.cc */ #include "osl/eval/endgame/attackDefense.h" #include "osl/eval/progressEval.h" #include "osl/csa.h" #include "consistencyTest.h" #include using namespace osl; using namespace osl::eval; BOOST_AUTO_TEST_CASE(ProgressEvalTestBeginning) { const NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); ProgressEval eval(state); BOOST_CHECK_EQUAL(0, eval.progress16().value()); ProgressEval::opening_eval_t opening(state); #ifdef EXPERIMENTAL_EVAL BOOST_CHECK(opening.value() == 0); #else BOOST_CHECK(opening.value() != 0); #endif BOOST_CHECK(abs(opening.value()*16 - eval.value()) < ProgressEval::ROUND_UP); } BOOST_AUTO_TEST_CASE(ProgressEvalTestInitial) { const NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); ProgressEval eval(state); BOOST_CHECK_EQUAL(0, eval.endgameValue()); } BOOST_AUTO_TEST_CASE(ProgressEvalTestLoad) { BOOST_CHECK(ProgressEval::setUp()); } BOOST_AUTO_TEST_CASE(ProgressEvalTestConsistentUpdate) { consistencyTestUpdate(); } BOOST_AUTO_TEST_CASE(ProgressEvalTestConsistentExpect) { #ifndef EXPERIMENTAL_EVAL consistencyTestExpect(16000); // 48000 #endif } BOOST_AUTO_TEST_CASE(ProgressEvalTestPinBonus) { { const NumEffectState state( CsaString("P1-KY-KE * * * * * -KE-KY\n" "P2 * -HI * * * * -KI-OU * \n" "P3-FU-FU-FU-FU * -KI-GI-FU-FU\n" "P4 * * * * -FU-KA-FU * * \n" "P5 * * * * * -FU * * * \n" "P6 * * +FU+FU+FU * * * * \n" "P7+FU+FU * +KI * +FU+FU+FU+FU\n" "P8 * +OU+GI * * * * -HI * \n" "P9+KY+KE+KA+KI * * * +KE+KY\n" "P+00GI\n" "P-00GI\n" "+\n").initialState()); ProgressEval eval(state); endgame::AttackDefense endgame(state); const Piece black_king = state.kingPiece(); const Piece white_king = state.kingPiece(); const int bonus = eval.calculatePinBonus(state); BOOST_CHECK(bonus < 0); BOOST_CHECK_EQUAL( -(endgame.valueOf(black_king, white_king, state.pieceAt(Square(6, 6))) + endgame.valueOf(black_king, white_king, state.pieceAt(Square(7, 8)))) / 4 * eval.progress16().value() / 16, bonus); } { const NumEffectState state( CsaString("P1-KY-KE * * * * * -KE-KY\n" "P2 * +HI * * * * -KI-OU * \n" "P3-FU-FU-FU-FU * -KI-GI-FU-FU\n" "P4 * * * * -FU-KA-FU * * \n" "P5 * * * * * -FU * * * \n" "P6 * * +FU+FU+FU * * * * \n" "P7+FU+FU+KE+KI * +FU+FU+FU+FU\n" "P8 * +OU+GI * * * * +HI * \n" "P9+KY * +KA+KI * * * +KE+KY\n" "P+00GI\n" "P-00GI\n" "+\n").initialState()); ProgressEval eval(state); endgame::AttackDefense endgame(state); const Piece black_king = state.kingPiece(); const Piece white_king = state.kingPiece(); const int bonus = eval.calculatePinBonus(state); BOOST_CHECK(bonus > 0); BOOST_CHECK_EQUAL( -(endgame.valueOf(black_king, white_king, state.pieceAt(Square(3, 2))) / 4) * eval.progress16().value() / 16, bonus); } } BOOST_AUTO_TEST_CASE(ProgressEvalTestSeeScale) { BOOST_CHECK_EQUAL(16, ProgressEval::seeScale()); } BOOST_AUTO_TEST_CASE(ProgressEvalTestSymmetry) { using namespace osl; std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); std::string file_name; for (int i=0;i<(OslConfig::inUnitTestShort() ? 10 : 200) && (ifs >> file_name) ; i++) { if (file_name == "") break; file_name = OslConfig::testCsaFile(file_name); const RecordMinimal record=CsaFileMinimal(file_name).load(); const auto moves=record.moves; NumEffectState state(record.initialState()); ProgressEval eval(state); for (unsigned int i=0; i #include #include #include namespace osl { inline bool quiet_position(int progress_b, int progress_w, const NumEffectState& state, Move m) { if (state.inCheck() ) return false; #if 0 if (progress_b + progress_w < 13 && m.capturePtype() == PTYPE_EMPTY && std::max(progress_b, progress_w) < 8) return true; #endif if (m.capturePtype() != PTYPE_EMPTY && isMajor(m.capturePtype())) return false; if (std::max(progress_b, progress_w) > 10 && m.capturePtype() != PTYPE_EMPTY) return false; const Square black_king = Centering3x3::adjustCenter(state.kingSquare()); const Square white_king = Centering3x3::adjustCenter(state.kingSquare()); const Square black_king_c = Centering5x3::adjustCenter(black_king); const Square white_king_c = Centering5x3::adjustCenter(white_king); const Square to = m.to(); if (abs(black_king_c.x() - to.x()) < 4 && abs(black_king_c.y() - to.y()) < 3) return false; if (abs(white_king_c.x() - to.x()) < 4 && abs(white_king_c.y() - to.y()) < 3) return false; if (Neighboring8Direct::hasEffect(state, m.ptypeO(), to, black_king) || Neighboring8Direct::hasEffect(state, m.ptypeO(), to, white_king)) return false; if (Neighboring8Direct::hasEffect(state, m.capturePtypeOSafe(), to, black_king) || Neighboring8Direct::hasEffect(state, m.capturePtypeOSafe(), to, white_king)) return false; if (Neighboring8Direct::hasEffect(state, m.ptypeO(), to, black_king_c) || Neighboring8Direct::hasEffect(state, m.ptypeO(), to, white_king_c)) return false; // todo: sokofu return true; } } template void consistencyTestExpect(int threshold=0) { using namespace osl; std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); std::string file_name; for (int i=0;i<10 && (ifs >> file_name) ; i++) { if ((i % 100) == 0) std::cerr << '.'; if (file_name == "") break; file_name = OslConfig::testCsaFile(file_name); const RecordMinimal record=CsaFileMinimal(file_name).load(); const std::vector moves=record.moves; NumEffectState state(record.initialState()); Eval eval(state); for (unsigned int i=0; i value + threshold) || (m.player() == WHITE && eval.value() < value - threshold)) std::cerr << "\n" << state << std::endl << progress_b << " " << progress_w << " " << m << " " << eval.value() << " " << value << std::endl; BOOST_CHECK((m.player() == BLACK && eval.value() <= value + threshold) || (m.player() == WHITE && eval.value() >= value - threshold)); } } } } template void consistencyTestUpdate() { using namespace osl; std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); std::string file_name; for (int i=0;i<(OslConfig::inUnitTestShort() ? 100 : 900) && (ifs >> file_name) ; i++) { if ((i % 100) == 0) std::cerr << '.'; if (file_name == "") break; file_name = OslConfig::testCsaFile(file_name); const RecordMinimal record=CsaFileMinimal(file_name).load(); const std::vector moves=record.moves; NumEffectState state(record.initialState()); Eval eval(state); for (unsigned int i=0; i #include #include using namespace osl; using namespace osl::eval; const int Gold = PtypeEvalTraits::val; const int Rook = PtypeEvalTraits::val; const int Knight = PtypeEvalTraits::val; const int Pawn = PtypeEvalTraits::val; const int Pknight = PtypeEvalTraits::val; const int Bishop = PtypeEvalTraits::val; const int Pbishop = PtypeEvalTraits::val; BOOST_AUTO_TEST_CASE(PieceEvalTestSoma) { const NumEffectState state(CsaString( "P1-KY-KE-GI-KI * * -HI-KE * \n" "P2 * -HI * * -KA-OU * * * \n" "P3-FU * -FU-FU-FU * -GI-FU-KY\n" "P4 * +KE * * * -FU * * -FU\n" "P5 * -FU+KE+KA * * * * +FU\n" "P6 * * +FU * * * +FU * * \n" "P7+FU+FU * +FU+FU+FU * * * \n" "P8 * +GI+KI * * * +GI * * \n" "P9+KY * * * +OU+KI * * +KY\n" "P+00FU\n" "P+00FU\n" "P+00KI\n" "+\n").initialState()); const PieceEval ev(state); { int ret=ev.computeDiffAfterMove (state, Move(Square(1,5),Square(1,4),PAWN,PAWN,false,BLACK)); /** 相手ãŒå–り替ãˆã•ãªã„ã®ãŒæœ€å–„ */ BOOST_CHECK_EQUAL(+Pawn*2, ret); } { int ret=ev.computeDiffAfterMove (state, Move(Square(6,5),Square(9,2),PBISHOP,PTYPE_EMPTY,true,BLACK)); /** 香車å–り返㗠only */ BOOST_CHECK_EQUAL(-Bishop*2, ret); } { int ret=ev.computeDiffAfterMove (state, Move(Square(6,5),Square(8,3),PBISHOP,PTYPE_EMPTY,true,BLACK)); /** æˆã‚Šå¾— */ BOOST_CHECK_EQUAL(+Pbishop-Bishop, ret); } { int ret=ev.computeDiffAfterMove (state, Move(Square(6,5),Square(2,1),PBISHOP,KNIGHT,true,BLACK)); BOOST_CHECK_EQUAL(+Knight*2-Bishop*2, ret); } { int ret=ev.computeDiffAfterMove (state, Move(Square(8,4),Square(7,2),PKNIGHT,PTYPE_EMPTY,true,BLACK)); BOOST_CHECK_EQUAL(-Knight*2, ret); } { int ret1=ev.computeDiffAfterMove (state, Move(Square(6,5),Square(5,4),BISHOP,PTYPE_EMPTY,false,BLACK)); BOOST_CHECK_EQUAL(-Bishop*2, ret1); } } BOOST_AUTO_TEST_CASE(PieceEvalTestBug) { const NumEffectState state=CsaString( "P1-KY-KE * -KI * * * -KE-KY\n" "P2 * -OU-GI * -KI * -HI * * \n" "P3 * -FU * * -FU-GI-KA * -FU\n" "P4 * * -FU-FU * -FU-FU-FU * \n" "P5-FU * * * * * * * * \n" "P6 * * +FU * +FU+GI+FU * +FU\n" "P7 * +FU * +FU * +FU * * * \n" "P8 * +KA+OU * +KI+GI * +HI * \n" "P9+KY+KE * +KI * * * +KE+KY\n" "P-00FU00FU\n" "+\n").initialState(); const PieceEval ev(state); int ret=ev.computeDiffAfterMove (state, Move(Square(5,6),Square(5,5),PAWN,PTYPE_EMPTY,false,BLACK)); BOOST_CHECK_EQUAL(0, ret); } BOOST_AUTO_TEST_CASE(PieceEvalTestCannotTake) { BOOST_CHECK_EQUAL(0, Ptype_Eval_Table.value(PTYPE_EMPTY)); NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2 * * +RY-KI-OU * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState()); { Move m = Move(Square(6,3),GOLD,BLACK); const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); // 相手ã¯å–れãªã„ BOOST_CHECK_EQUAL(0, ret); } } BOOST_AUTO_TEST_CASE(PieceEvalTestComputeDiffAfterMoveForRP) { NumEffectState state(CsaString( "P1-KY-KE-GI-KI * * -HI-KE * \n" "P2 * -HI * * -KA-OU * * * \n" "P3-FU * -FU-FU-FU * -GI-FU-KY\n" "P4 * +KE * * * -FU * * -FU\n" "P5 * -FU+KE+KA * * * * +FU\n" "P6 * * +FU * * * +FU * * \n" "P7+FU+FU * +FU+FU+FU * * * \n" "P8 * +GI+KI * * * +GI * * \n" "P9+KY * * * +OU+KI * * +KY\n" "P+00FU\n" "P+00FU\n" "P+00KI\n" "+\n").initialState()); { Move m = Move(Square(1,5),Square(1,4),PAWN,PAWN,false,BLACK); const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); // 相手ãŒå–り替ãˆã•ãªã„ã®ãŒæœ€å–„ BOOST_CHECK_EQUAL(Pawn*2, ret); } { Move m = Move(Square(8,4),Square(7,2),PKNIGHT,PTYPE_EMPTY,true,BLACK); const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); // ãŸã æ¨ã¦ BOOST_CHECK_EQUAL(-Knight*2, ret); } state.changeTurn(); { Move m = Move(Square(8,5),Square(8,6),PAWN,PTYPE_EMPTY,false,WHITE); const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); // ãŸã æ¨ã¦ BOOST_CHECK_EQUAL(-Pawn*2, ret); } { Move m = Move(Square(8,2),Square(8,4),ROOK,KNIGHT,false,WHITE); const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); // ãŸã å–り BOOST_CHECK_EQUAL(Knight*2, ret); } } BOOST_AUTO_TEST_CASE(PieceEvalTestComputeDiffAfterMoveForRPBug030910) { NumEffectState state(CsaString( "P1 * * * * * * -HI-KE-KY\n" "P2 * * * +RY+UM-GI-KI-OU * \n" "P3+TO * * * -FU * -GI * * \n" "P4-FU * * -FU * -GI+KY-FU * \n" "P5 * -FU+FU-KI * -FU-FU * * \n" "P6+FU+FU * * +KY * +FU * -FU\n" "P7 * * * * +FU+FU * +FU * \n" "P8 * * * * +KI * +GI+OU+FU\n" "P9 * * * * * +KI * +KE+KY\n" "P-00FU\n" "P-00KE\n" "P-00KE\n" "P+00KA\n" "-\n").initialState()); { const Square p86 = Square(8,6); Move m = Move(Square(8,5),p86,PAWN,PAWN,false,WHITE); // ã“ã¡ã‚‰ã¯é€šã‚‹ const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); BOOST_CHECK_EQUAL(Pawn*2, ret); const int rets = PieceEval::computeDiffAfterMoveForRP(state, m); BOOST_CHECK_EQUAL(Pawn*2, rets); } { const Square p36 = Square(3,6); Move m = Move(Square(3,5),p36,PAWN,PAWN,false,WHITE); // EffectUtil::showEffect(state, p36, std::cerr); BOOST_CHECK_EQUAL(-Pawn*2, Ptype_Eval_Table.diffWithMove(state, m)); const int ret = PieceEval::computeDiffAfterMoveForRP(state, m); // ãŸã å–りãªã®ã§å¾—ã™ã‚‹ã¯ãš BOOST_CHECK_EQUAL(Pawn*2, ret); const int rets = PieceEval::computeDiffAfterMoveForRP(state, m); BOOST_CHECK_EQUAL(Pawn*2, rets); } } BOOST_AUTO_TEST_CASE(PieceEvalTestConsistentUpdate) { consistencyTestUpdate(); } BOOST_AUTO_TEST_CASE(PieceEvalTestConsistentExpect) { consistencyTestExpect(); } BOOST_AUTO_TEST_CASE(PieceEvalTestArray) { PieceEval evals[3]; (void)evals[0]; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/ppair/0000755000000000000000000000000012316770314016427 5ustar rootrootlibosl-0.8.0.orig/full/test/eval/ppair/piecePairRawEval.t.cc0000644000000000000000000000666212316770314022375 0ustar rootroot// piecePairRawEval.t.cc #include "osl/eval/ppair/piecePairRawEval.h" #include "osl/state/historyState.h" #include "../consistencyTest.h" #include #include using namespace osl; using namespace osl::eval; using namespace osl::eval::ppair; BOOST_AUTO_TEST_CASE(PiecePairRawEvalTestLoad) { BOOST_CHECK(PiecePairRawEval::setUp()); } BOOST_AUTO_TEST_CASE(PiecePairRawEvalTestEval) { HistoryState state; const int start_value = PiecePairRawEval(state).value(); int value1, value12, value2; const Move m1 = Move(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); { DoUndoMoveLock lock1(state, m1); BOOST_CHECK(state.isConsistent()); value1 = PiecePairRawEval(state).value(); const Move m12 = Move(Square(3,3),Square(3,4),PAWN,PTYPE_EMPTY,false,WHITE); { DoUndoMoveLock lock12(state, m12); BOOST_CHECK(state.isConsistent()); value12 = PiecePairRawEval(state).value(); if (OslConfig::verbose()) std::cerr << "76FU34FU " << start_value << " ==> " << value1 << " ==> " << value12 << "\n"; } // state.undoMove(m12); BOOST_CHECK(state.isConsistent()); } // state.undoMove(m1); BOOST_CHECK(state.isConsistent()); const Move m2 = Move(Square(2,7),Square(2,6),PAWN,PTYPE_EMPTY,false,BLACK); { DoUndoMoveLock lock2(state, m2); BOOST_CHECK(state.isConsistent()); value2 = PiecePairRawEval(state).value(); if (OslConfig::verbose()) std::cerr << "26FU " << start_value << " ==> " << value2 << "\n"; } // state.undoMove(m2); BOOST_CHECK(state.isConsistent()); const Move m3 = Move(Square(8,7),Square(8,6),PAWN,PTYPE_EMPTY,false,BLACK); { DoUndoMoveLock lock2(state, m3); BOOST_CHECK(state.isConsistent()); const int value3 = PiecePairRawEval(state).value(); if (OslConfig::verbose()) std::cerr << "86FU " << start_value << " ==> " << value3 << "\n"; BOOST_CHECK(start_value < value1); BOOST_CHECK(value1 > value12); BOOST_CHECK(start_value <= value2); BOOST_CHECK(value3 < value1); BOOST_CHECK(value3 < value2); } #if 0 NumEffectState state=CsaString( "P1+NY+TO * * * * -OU-KE-KY\n" "P2 * * * * * -GI-KI * *\n" "P3 * +RY * * +UM * -KI-FU-FU\n" "P4 * * +FU-FU * * * * *\n" "P5 * * -KE * +FU * * +FU *\n" "P6-KE * * +FU+GI-FU * * +FU\n" "P7 * * -UM * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00HI00KI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU00FU\n" "P-00AL\n" "+\n").initialState(); PiecePairEval eval(state); std::cerr << "value is " << eval.value() << "\n"; state=CsaString( "P1-KY-KE-GI-KI * * -HI-KE-KY\n" "P2 * -HI * * -KA-OU * * * \n" "P3-FU * -FU-FU-FU * -GI-FU-FU\n" "P4 * * * * * -FU * * * \n" "P5 * -FU * +KA * * * * * \n" "P6 * * +FU * * * +FU * +FU\n" "P7+FU+FU * +FU+FU+FU+KE * * \n" "P8 * +GI+KI * * * +GI * * \n" "P9+KY+KE * * +OU+KI * * +KY\n" "P+00FU\n" "P+00FU\n" "P+00KI\n" "+\n").initialState(); PiecePairEval eval2(state); std::cerr << "value is " << eval2.value() << "\n"; #endif } BOOST_AUTO_TEST_CASE(PiecePairRawEvalTestConsistentUpdate) { consistencyTestUpdate(); } BOOST_AUTO_TEST_CASE(PiecePairRawEvalTestConsistentExpect) { consistencyTestExpect(); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/ppair/piecePairPieceEval.t.cc0000644000000000000000000001004412316770314022656 0ustar rootroot// piecePairPieceEval.t.cc #include "osl/eval/ppair/piecePairPieceEval.h" #include "osl/eval/ppair/piecePairRawEval.h" #include "osl/eval/pieceEval.h" #include "osl/container/pieceValues.h" #include "../consistencyTest.h" #include #include using namespace osl; using namespace osl; using namespace osl::eval; using namespace osl::eval::ppair; BOOST_AUTO_TEST_CASE(PiecePairPieceEvalTestLoad) { BOOST_CHECK(PiecePairPieceEval::setUp()); } BOOST_AUTO_TEST_CASE(PiecePairPieceEvalTestConsistentUpdate) { consistencyTestUpdate(); } BOOST_AUTO_TEST_CASE(PiecePairPieceEvalTestConsistentExpect) { consistencyTestExpect(); } BOOST_AUTO_TEST_CASE(PiecePairPieceEvalTestPieces) { for (int y=1; y<=9; ++y) { for (int x=1; x<=9; ++x) { const Square position(x,y); for (int p=PTYPEO_MIN; p(p); const unsigned int index = PiecePairIndex::indexOf(position, ptypeo); const int value = PiecePairPieceTable::Table.valueOf(index, index); BOOST_CHECK((abs(value) <= 150+PtypeEvalTraits::val*4/5)); } } } } BOOST_AUTO_TEST_CASE(PiecePairPieceEvalTestValues) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); std::string file_name; for (int i=0;i<(OslConfig::inUnitTestShort() ? 10 : 100) && (ifs >> file_name) ; i++) { if (file_name == "") break; file_name = OslConfig::testCsaFile(file_name); const RecordMinimal record=CsaFileMinimal(file_name).load(); const auto moves=record.moves; NumEffectState state(record.initialState()); PieceValues values; PiecePairPieceEval sum_eval(state); PiecePairPieceEval::setValues(state, values); // 1/2 ã®åˆ‡ã‚Šæ¨ã¦ãŒã‚ã‚‹ã®ã§åˆè¨ˆãŒä¸€è‡´ã™ã‚‹ã¨ã¯é™ã‚‰ãªã„ BOOST_CHECK((sum_eval.rawValue() - values.sum()) < 40); for (unsigned int i=0; i::val*4/5*4; // cumulative errors int large_errors = 0; for (int i=0;i<(OslConfig::inUnitTestShort() ? 20 : 400) && (ifs >> file_name) ; i++) { if (file_name == "") break; file_name = OslConfig::testCsaFile(file_name); const RecordMinimal record=CsaFileMinimal(file_name).load(); const auto& moves=record.moves; NumEffectState state(record.initialState()); PieceEval piece_eval(state); PiecePairRawEval raw_eval(state); PiecePairPieceEval sum_eval(state); BOOST_CHECK(abs(piece_eval.value() + raw_eval.value() - sum_eval.value()) < 5); for (unsigned int i=0; i= tolerance) { ++large_errors; std::cerr << expected - actual << "\n"; if (OslConfig::verbose()) { std::cerr << state << "\n"; std::cerr << piece_eval.value() << " + " << raw_eval.rawValue()*128/100 << " (" << raw_eval.rawValue() << ")" << " != " << sum_eval.rawValue(); PieceValues values; PiecePairPieceEval::setValues(state, values); values.showValues(std::cerr, state); PiecePairRawEval::setValues(state, values); values.showValues(std::cerr, state); } } BOOST_CHECK(abs(expected - actual) < tolerance); } } BOOST_CHECK(large_errors < 10); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/eval/ppair/piecePairIndex.t.cc0000644000000000000000000001701612316770314022076 0ustar rootroot/* piecePairIndexTest.cc */ #include "osl/eval/ppair/piecePairIndex.h" #include #include #include #include using namespace osl; using namespace osl::eval; using namespace osl::eval::ppair; typedef std::bitset set_t; set_t visited; static void visitRelation(size_t index) { size_t i1, i2; PiecePairIndex::meltIndex(index, i1, i2); const size_t i = PiecePairIndex::canonicalIndexOf(i1, i2); if (visited[i]) { std::cerr << "oops " << i << "\n"; size_t i1, i2; PiecePairIndex::meltIndex(i, i1, i2); std::cerr << i1 << " " << i2 << "\n"; Square pos; PtypeO ptypeo; PiecePairIndex::meltIndex(i1, pos, ptypeo); std::cerr << pos << " " << ptypeo << "\n"; PiecePairIndex::meltIndex(i2, pos, ptypeo); std::cerr << pos << " " << ptypeo << "\n"; } BOOST_CHECK(! visited[i]); visited.flip(i); } BOOST_AUTO_TEST_CASE(PiecePairIndexTestForEachRelation) { PiecePairIndex::forEachRelation(visitRelation); size_t numCanons = 0; for (size_t i=0; i(p); const unsigned int indexBlack = PiecePairIndex::ptypeOIndexOf(newPtypeO(BLACK,ptype)); const unsigned int indexWhite = PiecePairIndex::ptypeOIndexOf(newPtypeO(WHITE,ptype)); BOOST_CHECK(indexBlack < PiecePairIndex::maxPtypeOIndex); BOOST_CHECK(! s.test(indexBlack)); s.flip(indexBlack); BOOST_CHECK(indexWhite < PiecePairIndex::maxPtypeOIndex); BOOST_CHECK(! s.test(indexWhite)); s.flip(indexWhite); } } /** 本当ã¯member 変数ã«ã™ã‚‹ã¹ãã ãŒæ‰‹æŠœã*/ static set_t dejavu; static void testPieces(Piece p1, Piece p2) { const unsigned int index12 = PiecePairIndex::indexOf(p1, p2); // std::cerr << index12 << " " << p1 << " " << p2 << "\n"; BOOST_CHECK(index12 < PiecePairIndex::maxPairIndex); BOOST_CHECK(! dejavu.test(index12) || (std::cerr << p1 << p2, 0)); dejavu.flip(index12); if ((p1.square() == p2.square()) && (p1.ptype() == p2.ptype()) && (p1.owner() == p2.owner())) return; const unsigned int index21 = PiecePairIndex::indexOf(p2, p1); // std::cerr << index21 << " " << p2 << "\n"; BOOST_CHECK(index21 < PiecePairIndex::maxPairIndex); BOOST_CHECK(! dejavu.test(index21) || (std::cerr << p1 << p2, 0)); dejavu.flip(index21); } BOOST_AUTO_TEST_CASE(PiecePairIndexTestIndex) { for (int x=1; x<=9; ++x) { std::cerr << x << " "; for (int y=1; y<=9; ++y) { const Square pos1 = Square(x,y); for (int ptype=PPAWN; ptype<=PTYPE_MAX; ++ptype) { const Piece p1 = Piece(BLACK, static_cast(ptype), 0/*?*/, pos1); const unsigned int index = PiecePairIndex::indexOf(p1); BOOST_CHECK(index < PiecePairIndex::maxPieceIndex || (std::cerr << p1 << "\n" << index << "\n" << PiecePairIndex::maxPieceIndex << "\n", 0)); { PtypeO ptypeo; Square pos; PiecePairIndex::meltIndex(index, pos, ptypeo); BOOST_CHECK_EQUAL(newPtypeO(BLACK, static_cast(ptype)), ptypeo); BOOST_CHECK_EQUAL(pos1, pos); } const Piece p1w = Piece(WHITE, static_cast(ptype), 0/*?*/, pos1); BOOST_CHECK(PiecePairIndex::indexOf(p1w) < PiecePairIndex::maxPieceIndex); { PtypeO ptypeo; Square pos; PiecePairIndex::meltIndex(PiecePairIndex::indexOf(p1w), pos, ptypeo); BOOST_CHECK_EQUAL(newPtypeO(WHITE, static_cast(ptype)), ptypeo); BOOST_CHECK_EQUAL(pos1, pos); } testPieces(p1, p1); testPieces(p1, p1w); testPieces(p1w, p1w); for (int x2=x; x2<=9; ++x2) { for (int y2=y; y2<=9; ++y2) { Square pos2 = Square(x2,y2); if (pos1 == pos2) continue; for (int ptype2=PPAWN; ptype2<=PTYPE_MAX; ++ptype2) { const Piece p2 = Piece(BLACK, static_cast(ptype2), 0/*?*/, pos2); const unsigned int index2 = PiecePairIndex::indexOf(p2); BOOST_CHECK(index2 < PiecePairIndex::maxPieceIndex || (std::cerr << p1 << "\n" << index << "\n" << PiecePairIndex::maxPieceIndex << "\n", 0)); const Piece p2w = Piece(WHITE, static_cast(ptype2), 0/*?*/, pos2); BOOST_CHECK(PiecePairIndex::indexOf(p2w) < PiecePairIndex::maxPieceIndex); testPieces(p1, p2); testPieces(p1, p2w); testPieces(p1w, p2); testPieces(p1w, p2w); } } } for (int ptype2=KING; ptype2<=PTYPE_MAX; ++ptype2) { const Piece p2 = Piece(BLACK, static_cast(ptype2), 0/*?*/, Square::STAND()); const unsigned int index2 = PiecePairIndex::indexOf(p2); BOOST_CHECK(index2 < PiecePairIndex::maxPieceIndex || (std::cerr << p1 << "\n" << index << "\n" << PiecePairIndex::maxPieceIndex << "\n", 0)); const Piece p2w = Piece(WHITE, static_cast(ptype2), 0/*?*/, Square::STAND()); BOOST_CHECK(PiecePairIndex::indexOf(p2w) < PiecePairIndex::maxPieceIndex); testPieces(p1, p2); testPieces(p1, p2w); testPieces(p1w, p2); testPieces(p1w, p2w); } } // ptype } // x } // y // æŒé§’åŒå£«ã¯æœ€å¾Œã« for (int ptype2=KING; ptype2<=PTYPE_MAX; ++ptype2) { const Piece p2 = Piece(BLACK, static_cast(ptype2), 0/*?*/, Square::STAND()); const unsigned int index2 = PiecePairIndex::indexOf(p2); BOOST_CHECK(index2 < PiecePairIndex::maxPieceIndex); const Piece p2w = Piece(WHITE, static_cast(ptype2), 0/*?*/, Square::STAND()); BOOST_CHECK(PiecePairIndex::indexOf(p2w) < PiecePairIndex::maxPieceIndex); testPieces(p2, p2); testPieces(p2, p2w); testPieces(p2w, p2w); } #if 0 std::cerr << PiecePairIndex::maxPieceIndex << "\n"; std::cerr << PiecePairIndex::maxPairIndex << "\n"; #endif } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/repetitionCounter.t.cc0000644000000000000000000002226612316770314020670 0ustar rootroot#include "osl/repetitionCounter.h" #include "osl/csa.h" #include "osl/move_classifier/check_.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/effect_util/effectUtil.h" #include "osl/oslConfig.h" #include #include #include #include #include using namespace osl; BOOST_AUTO_TEST_CASE(RepetitionCounterTestClone) { using namespace osl::move_classifier; const char *stateString = "P1-KY * * * * * * +NY * \n" "P2 * -OU-KI-KI * * * * +RY\n" "P3 * -GI-KE+KI * * * * +HI\n" "P4 * * -FU-KY-FU * * -FU * \n" "P5-FU-FU * -KE * -FU * * * \n" "P6 * * +FU-FU+FU * -FU * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+GI+GI-UM * * * * * \n" "P9+OU+KE * * * * * +KE * \n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00GI\n" "P+00KI\n" "P-00KA\n" "+\n"; NumEffectState state((CsaString(stateString).initialState())); const Move m = Move(Square(7,1),GOLD,BLACK); RepetitionCounter counter; counter.push(state, m); state.makeMove(m); const Move m2 = Move(Square(7,9),SILVER,WHITE); RepetitionCounter copy(counter); BOOST_CHECK(copy.isConsistent()); copy.push(state,m2); BOOST_CHECK(copy.isConsistent()); copy.pop(); BOOST_CHECK(copy.isConsistent()); } BOOST_AUTO_TEST_CASE(RepetitionCounterTestEmpty) { using namespace osl::move_classifier; const char *stateString = "P1-KY * * * * * * +NY * \n" "P2 * -OU-KI-KI * * * * +RY\n" "P3 * -GI-KE+KI * * * * +HI\n" "P4 * * -FU-KY-FU * * -FU * \n" "P5-FU-FU * -KE * -FU * * * \n" "P6 * * +FU-FU+FU * -FU * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+GI+GI-UM * * * * * \n" "P9+OU+KE * * * * * +KE * \n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00FU\n" "P-00GI\n" "P+00KI\n" "P-00KA\n" "+\n"; NumEffectState state((CsaString(stateString).initialState())); const Move m = Move(Square(7,1),GOLD,BLACK); const HashKey new_key = HashKey(state).newHashWithMove(m); RepetitionCounter counter; BOOST_CHECK_EQUAL(-1, counter.getFirstMove(new_key)); BOOST_CHECK_EQUAL(-1, counter.getLastMove(new_key)); BOOST_CHECK_EQUAL(0u, counter.countRepetition(new_key)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), counter.isSennichite(state, m)); BOOST_CHECK_EQUAL(0, counter.checkCount(BLACK)); BOOST_CHECK_EQUAL(0, counter.checkCount(WHITE)); counter.push(state, m); BOOST_CHECK_EQUAL(0, counter.getFirstMove(new_key)); BOOST_CHECK_EQUAL(0, counter.getLastMove(new_key)); BOOST_CHECK_EQUAL(1u, counter.countRepetition(new_key)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), counter.isSennichite(state, m)); BOOST_CHECK_EQUAL(0, counter.checkCount(BLACK)); BOOST_CHECK_EQUAL(0, counter.checkCount(WHITE)); } BOOST_AUTO_TEST_CASE(RepetitionCounterTestDraw) { const char *test_record_str = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n" "+3948GI\n" "-7162GI\n" "+4839GI\n" "-6271GI\n" "+3948GI\n" "-7162GI\n" "+4839GI\n" "-6271GI\n" "+3948GI\n" "-7162GI\n" "+4839GI\n" "-6271GI\n"; CsaString test_record(test_record_str); NumEffectState state(test_record.initialState()); const auto& moves = test_record.load().moves; HashKey key(state); RepetitionCounter counter(state); for (int i=0; i<(int)moves.size(); ++i) { key = HashKey(state); BOOST_CHECK_EQUAL(i % 4, counter.getFirstMove(key)); BOOST_CHECK_EQUAL(i, counter.getLastMove(key)); BOOST_CHECK_EQUAL((i / 4u)+1, counter.countRepetition(key)); BOOST_CHECK_EQUAL(0, counter.checkCount(BLACK)); BOOST_CHECK_EQUAL(0, counter.checkCount(WHITE)); const Move m = moves[i]; if (i <(int)moves.size() -1) BOOST_CHECK_EQUAL(Sennichite::NORMAL(), counter.isSennichite(state, m)); else BOOST_CHECK_EQUAL(Sennichite::DRAW(), counter.isSennichite(state, m)); counter.push(state, m); state.makeMove(m); } } BOOST_AUTO_TEST_CASE(RepetitionCounterTestLose) { const char *test_record_str = "P1 * * * * * +UM * * -KY\n" "P2 * * * * * * * -KE-OU\n" "P3 * * * * * * +FU * -FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P-00AL\n" "+\n" "+4123UM\n" "-1221OU\n" "+2332UM\n" "-2112OU\n" "+3223UM\n" "-1221OU\n" "+2332UM\n" "-2112OU\n" "+3223UM\n" "-1221OU\n" "+2332UM\n" "-2112OU\n" "+3223UM\n"; CsaString test_record(test_record_str); NumEffectState state(test_record.initialState()); const std::vector& moves = test_record.load().moves; HashKey key = HashKey(state); RepetitionCounter counter(state); for (int i=0; i<(int)moves.size(); ++i) { key = HashKey(state); BOOST_CHECK_EQUAL(i, counter.getLastMove(key)); BOOST_CHECK_EQUAL((i+1)/2, counter.checkCount(BLACK)); BOOST_CHECK_EQUAL(0, counter.checkCount(WHITE)); const Move m = moves[i]; if (i <(int)moves.size() -1) BOOST_CHECK_EQUAL(Sennichite::NORMAL(), counter.isSennichite(state, m)); else BOOST_CHECK_EQUAL(Sennichite::BLACK_LOSE(), counter.isSennichite(state, m)); counter.push(state, m); state.makeMove(m); } } BOOST_AUTO_TEST_CASE(RepetitionCounterTestLose2) { const char *test_record_str = "P1 * * * * * * * * -KY\n" "P2 * * * * * * +UM-KE-OU\n" "P3 * * * * * * +FU * -FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P-00AL\n" "+\n" "+3223UM\n" "-1221OU\n" "+2332UM\n" "-2112OU\n" "+3223UM\n" "-1221OU\n" "+2332UM\n" "-2112OU\n" "+3223UM\n" "-1221OU\n" "+2332UM\n" "-2112OU\n"; CsaString test_record(test_record_str); NumEffectState state(test_record.initialState()); const std::vector& moves = test_record.load().moves; HashKey key = HashKey(state); RepetitionCounter counter(state); for (int i=0; i<(int)moves.size(); ++i) { key = HashKey(state); BOOST_CHECK_EQUAL(i, counter.getLastMove(key)); BOOST_CHECK_EQUAL((i+1)/2, counter.checkCount(BLACK)); BOOST_CHECK_EQUAL(0, counter.checkCount(WHITE)); const Move m = moves[i]; if (i <(int)moves.size() -1) BOOST_CHECK_EQUAL(Sennichite::NORMAL(), counter.isSennichite(state, m)); else BOOST_CHECK_EQUAL(Sennichite::BLACK_LOSE(), counter.isSennichite(state, m)); counter.push(state, m); state.makeMove(m); } } static void testFile(const std::string& filename) { typedef RepetitionCounter::list_t list_t; auto record=CsaFileMinimal(filename).load(); NumEffectState state(record.initialState()); const auto& moves=record.moves; std::vector states; states.push_back(state); RepetitionCounter counter(state); for (size_t i=0;i 1) { const list_t& l = counter.getRepetitions(key); assert(l.size() > 1); list_t::const_iterator p=l.begin(); const SimpleState& s0 = states.at(*p); ++p; for (; p!= l.end(); ++p) { BOOST_CHECK(s0 == states.at(*p)); } if (repeated >= 4) { if (sennichite.isDraw()) { if (OslConfig::verbose()) std::cerr << "DRAW\n"; } else { std::cerr << "王手ãŒã‚‰ã¿ã®4回目\n"; counter.printMatches(key); } BOOST_CHECK(! sennichite.isNormal()); } } } } BOOST_AUTO_TEST_CASE(RepetitionCounterTestCsaFiles) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); int i=0; int count=1000; if (OslConfig::inUnitTest() < 2) count=10; std::string filename; std::unique_ptr progress; if (OslConfig::inUnitTest() >= 2) progress.reset(new boost::progress_display(count, std::cerr)); while((ifs >> filename) && filename != "" && (++i #include #include #include class dfpnNtesukiNopassTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(dfpnNtesukiNopassTest); CPPUNIT_TEST(test0tesuki0); CPPUNIT_TEST(test1tesuki0); CPPUNIT_TEST(test2tesuki0); CPPUNIT_TEST(test3tesuki0); CPPUNIT_TEST(test0tesuki1); CPPUNIT_TEST(test1tesuki1); CPPUNIT_TEST(test2tesuki1); CPPUNIT_TEST(test3tesuki1); //CPPUNIT_TEST(test2tesukiWithEscape); CPPUNIT_TEST_SUITE_END(); public: void test0tesuki0(); void test0tesuki1(); void test1tesuki0(); void test1tesuki1(); void test2tesuki0(); void test2tesuki1(); void test3tesuki0(); void test3tesuki1(); //void test2tesukiWithEscape(); }; CPPUNIT_TEST_SUITE_REGISTRATION(dfpnNtesukiNopassTest); using namespace osl; using namespace osl::ntesuki; const size_t limit = 40000; typedef GetMultipleAttackMoves gam; //typedef GetAttackMoves gam; //typedef GetAllAttackMoves gam; typedef GetNoMoves gdm; static void results() { #if 0 if (OslConfig::verbose()) { std::cerr << "Move reduction(all/used):\t" << gam::allMovesCount << "\t" << gam::reducedMovesCount << "\n"; } gam::allMovesCount = 0; gam::reducedMovesCount = 0; #endif } void dfpnNtesukiNopassTest::test0tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(0, ntesuki_num); } void dfpnNtesukiNopassTest::test0tesuki1() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI+UM-KE-KY\n" "P2 * -HI * * +KA * * * * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00GI\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(0, ntesuki_num); } void dfpnNtesukiNopassTest::test1tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(1, ntesuki_num); } void dfpnNtesukiNopassTest::test1tesuki1() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI+UM-KE-KY\n" "P2 * -HI * * * * * * * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00GI00KA\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(1, ntesuki_num); } void dfpnNtesukiNopassTest::test2tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * +FU * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(2, ntesuki_num); } void dfpnNtesukiNopassTest::test2tesuki1() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * +UM * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00KA\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(2, ntesuki_num); } void dfpnNtesukiNopassTest::test3tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose(), 4); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(3, ntesuki_num); } void dfpnNtesukiNopassTest::test3tesuki1() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState(); HashEffectState hState(state); DfpnNtesukiNopassSearcher searcher (hState, limit, OslConfig::verbose(), 4); const int ntesuki_num = searcher.searchSlow(hState.turn()); results(); BOOST_CHECK_EQUAL(3, ntesuki_num); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/ntesukiSimulationSearcher.t.cc0000644000000000000000000004503012316770314024026 0ustar rootroot#include "osl/ntesuki/ntesukiSimulationSearcher.h" #include "osl/ntesuki/ntesukiSimulationSearcherProof.tcc" #include "osl/ntesuki/ntesukiSimulationSearcherDisproof.tcc" #include "osl/ntesuki/ntesukiSearcher.h" #include "osl/ntesuki/ntesukiTable.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/record/csaString.h" #include #include #include using namespace osl; class NtesukiSimulationSearcherTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(NtesukiSimulationSearcherTest); CPPUNIT_TEST(test0Tesuki0); CPPUNIT_TEST(test0Tesuki1); CPPUNIT_TEST(test0Tesuki2); CPPUNIT_TEST(test1Tesuki0); //CPPUNIT_TEST(test0Tesuki0Fail); //CPPUNIT_TEST(test1Tesuki0Fail); CPPUNIT_TEST_SUITE_END(); public: void test0Tesuki0(); void test0Tesuki1(); void test0Tesuki2(); void test1Tesuki0(); void test1Tesuki1(); void test0Tesuki0Fail(); void test1Tesuki0Fail(); }; using namespace osl; using namespace osl::ntesuki; typedef NtesukiMoveGenerator movegen_t; static volatile int stop_flag = false; static void compare_simulation(SimpleState& sstate_orig, SimpleState& sstate, const int ntesuki_correct, const bool correct) { PathEncoding path; HashEffectState state_orig(sstate_orig); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(state_orig, gam.get(), 100000, &stop_flag, OslConfig::verbose(), ntesuki_correct + 1); NtesukiTable& table = searcher.getTable(); int ntesuki_num = 0; TRY_DFPN; ntesuki_num = searcher.searchSlow(state_orig.turn()); CATCH_DFPN; BOOST_CHECK_EQUAL(ntesuki_correct,ntesuki_num); const NtesukiRecord* record_orig = table.allocateRoot(HashKey(state_orig), PieceStand(WHITE, state_orig), 0); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); NtesukiRecord::state = &state; TRY_DFPN; bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK(correct == result); CATCH_DFPN; } void NtesukiSimulationSearcherTest:: test0Tesuki0() { SimpleState sstate_orig = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); SimpleState sstate = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3+FU+FU * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); compare_simulation(sstate_orig, sstate, 0, true); } void NtesukiSimulationSearcherTest:: test0Tesuki1() { SimpleState sstate_orig = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); SimpleState sstate = CsaString( "P1 * * * * * * -KI-OU * \n" "P2 * * * * * * * * * \n" "P3+FU+FU * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); compare_simulation(sstate_orig, sstate, 0, false); } void NtesukiSimulationSearcherTest:: test0Tesuki2() { SimpleState sstate_orig = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); SimpleState sstate = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3+FU+FU * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P-00AL\n" "+\n").initialState(); compare_simulation(sstate_orig, sstate, 0, false); } void NtesukiSimulationSearcherTest:: test1Tesuki0() { if (isShortTest) return; boost::scoped_ptr gam(new movegen_t()); PathEncoding path; SimpleState sstate_orig = CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * * * * -KE-KI * * * \n" "P3 * * -KA * +UM * +FU * * \n" "P4-FU * -FU-FU-GI * -FU-FU-FU\n" "P5 * * * * -KI * * * * \n" "P6+FU+GI+FU+FU * * * * +FU\n" "P7+OU+FU * * * * * * * \n" "P8 * * -NG * * * * * * \n" "P9+KY+KE * * * -HI * * +KY\n" "P+00FU00FU00FU00GI00HI\n" "P-00FU00FU00FU00KI00KI\n" "+\n").initialState(); /* * +0031HI * -4131OU * +0032GI * -3122OU * +5342UM * %TORYO */ NumEffectState state_orig(sstate_orig); NtesukiSearcher searcher(state_orig, gam.get(), 10000000, &stop_flag, OslConfig::verbose()); NtesukiTable& table = searcher.getTable(); const int ntesuki_num = searcher.searchSlow(state_orig.turn(), 20000000); BOOST_CHECK_EQUAL(1, ntesuki_num); const NtesukiRecord* record_orig = table.allocateRoot(HashKey(state_orig), PieceStand(WHITE, state_orig), 0); { //handed +00HI to -00HI SimpleState sstate = CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * * * * -KE-KI * * * \n" "P3 * * -KA * +UM * +FU * * \n" "P4-FU * -FU-FU-GI * -FU-FU-FU\n" "P5 * * * * -KI * * * * \n" "P6+FU+GI+FU+FU * * * * +FU\n" "P7+OU+FU * * * * * * * \n" "P8 * * -NG * * * * * * \n" "P9+KY+KE * * * -HI * * +KY\n" "P+00FU00FU00FU00GI\n" "P-00FU00FU00FU00KI00KI00HI\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK_EQUAL(false, result); } { //moved -42KI to -31KI SimpleState sstate = CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * * * * -KE * -KI * * \n" "P3 * * -KA * +UM * +FU * * \n" "P4-FU * -FU-FU-GI * -FU-FU-FU\n" "P5 * * * * -KI * * * * \n" "P6+FU+GI+FU+FU * * * * +FU\n" "P7+OU+FU * * * * * * * \n" "P8 * * -NG * * * * * * \n" "P9+KY+KE * * * -HI * * +KY\n" "P+00FU00FU00FU00GI00HI\n" "P-00FU00FU00FU00KI00KI\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK_EQUAL(false, result); } //moved -91KY to -92KY //move +99KY to +98KY } void NtesukiSimulationSearcherTest:: test1Tesuki1() { if (isShortTest) return; boost::scoped_ptr gam(new movegen_t()); PathEncoding path; SimpleState sstate_orig = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state_orig(sstate_orig); NtesukiSearcher searcher(state_orig, gam.get(), 10000000, &stop_flag, OslConfig::verbose()); NtesukiTable& table = searcher.getTable(); const int ntesuki_num = searcher.searchSlow(state_orig.turn(), 20000000); BOOST_CHECK_EQUAL(1, ntesuki_num); const NtesukiRecord* record_orig = table.allocateRoot(HashKey(state_orig), PieceStand(WHITE, state_orig), 0); { //handed +00KA to -00KA SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P-00FU00FU00FU00FU00FU00KA\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK_EQUAL(false, result); } { //moved -61KI to -71KI SimpleState sstate = CsaString( "P1-KY * -KI * * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK_EQUAL(false, result); } { //moved -11KY to -12KY SimpleState sstate = CsaString( "P1-KY * * -KI * * * * * \n" "P2-OU * -GI * * * * * -KY\n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY+KY\n" "P9+KY+KE+OU * +FU * * * * \n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK_EQUAL(true, result); } { //move +19KY to +18KY SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY+KY\n" "P9+KY+KE+OU * +FU * * * * \n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackProof(record, record_orig, ntesuki_num, Move::INVALID()); BOOST_CHECK_EQUAL(true, result); } } void NtesukiSimulationSearcherTest:: test0Tesuki0Fail() { boost::scoped_ptr gam(new movegen_t()); SimpleState sstate_orig = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P-00FU00FU00FU00FU00FU00KA\n" "+\n").initialState(); NumEffectState state_orig(sstate_orig); NtesukiSearcher searcher(state_orig, gam.get(), 100000, &stop_flag, OslConfig::verbose(), 1); NtesukiTable& table = searcher.getTable(); const int ntesuki_num = searcher.searchSlow(state_orig.turn()); BOOST_CHECK_EQUAL(-1, ntesuki_num); const NtesukiRecord* record_orig = table.allocateRoot(HashKey(state_orig), PieceStand(WHITE, state_orig), 0); PathEncoding path(state_orig.turn()); { SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * * \n" "P7 * -NG * +FU * -TO-UM * +FU\n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P-00FU00FU00FU00FU00FU00KA\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackDisproof(record, record_orig, 0, Move::INVALID()); BOOST_CHECK(result); } { SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackDisproof(record, record_orig, 0, Move::INVALID()); BOOST_CHECK(!result); } } void NtesukiSimulationSearcherTest:: test1Tesuki0Fail() { if (isShortTest) return; boost::scoped_ptr gam(new movegen_t()); SimpleState sstate_orig = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P-00FU00FU00FU00FU00FU00KA\n" "+\n").initialState(); NumEffectState state_orig(sstate_orig); NtesukiSearcher searcher(state_orig, gam.get(), 100000, &stop_flag, OslConfig::verbose()); NtesukiTable& table = searcher.getTable(); const int ntesuki_num = searcher.searchSlow(state_orig.turn()); BOOST_CHECK_EQUAL(-1, ntesuki_num); const NtesukiRecord* record_orig = table.allocateRoot(HashKey(state_orig), PieceStand(WHITE, state_orig), 0); PathEncoding path(state_orig.turn()); { SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * * \n" "P7 * -NG * +FU * -TO-UM * +FU\n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P-00FU00FU00FU00FU00FU00KA\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackDisproof(record, record_orig, 1, Move::INVALID()); BOOST_CHECK(result); } { SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); NtesukiSimulationSearcher simulator(state, gam.get(), path, table, osl::ntesuki::NtesukiRecord::no_is, OslConfig::verbose()); NtesukiRecord* record = table.allocateRoot(HashKey(state), PieceStand(WHITE, state), 0); bool result = simulator.startFromAttackDisproof(record, record_orig, 1, Move::INVALID()); BOOST_CHECK(!result); } } CPPUNIT_TEST_SUITE_REGISTRATION(NtesukiSimulationSearcherTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/oracleProverLight.t.cc0000644000000000000000000003101212316770314022250 0ustar rootroot#include "osl/ntesuki/oracleProverLight.h" #include "osl/ntesuki/ntesukiSearcher.h" #include "osl/ntesuki/ntesukiTable.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/record/csaString.h" #include #include #include using namespace osl; class OracleProverLightTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(OracleProverLightTest); CPPUNIT_TEST(test0Tesuki0); CPPUNIT_TEST(test0Tesuki1); CPPUNIT_TEST(test0Tesuki2); CPPUNIT_TEST(test1Tesuki0); //CPPUNIT_TEST(test1Tesuki1); CPPUNIT_TEST_SUITE_END(); public: void test0Tesuki0(); void test0Tesuki1(); void test0Tesuki2(); void test1Tesuki0(); void test1Tesuki1(); }; using namespace osl; using namespace osl::ntesuki; typedef NtesukiMoveGenerator movegen_t; static volatile int stop_flag = false; static void compare_simulation(SimpleState& sstate_orig, SimpleState& sstate, const int ntesuki_correct, const bool correct) { PathEncoding path; HashEffectState state_orig(sstate_orig); boost::scoped_ptr mg(new movegen_t()); NtesukiSearcher searcher(state_orig, mg.get(), 100000, &stop_flag, OslConfig::verbose(), ntesuki_correct + 1); const int ntesuki_num = searcher.searchSlow(state_orig.turn()); BOOST_CHECK_EQUAL(ntesuki_correct, ntesuki_num); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); NtesukiRecord *record = searcher.getTable().allocateRoot(HashKey(state), PieceStand(), 0); NtesukiRecord *record_orig = searcher.getTable().allocateRoot(HashKey(state_orig), PieceStand(), 0); const NtesukiMove& m = record_orig->getBestMove(ntesuki_num); if (m.isImmediateCheckmate()) return; bool result = simulator.startFromAttack(record, record_orig, ntesuki_num); BOOST_CHECK(correct == result); } void OracleProverLightTest:: test0Tesuki0() { SimpleState sstate_orig = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); SimpleState sstate = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3+FU+FU * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); compare_simulation(sstate_orig, sstate, 0, true); } void OracleProverLightTest:: test0Tesuki1() { SimpleState sstate_orig = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); SimpleState sstate = CsaString( "P1 * * * * * * -KI-OU * \n" "P2 * * * * * * * * * \n" "P3+FU+FU * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); compare_simulation(sstate_orig, sstate, 0, false); } void OracleProverLightTest:: test0Tesuki2() { SimpleState sstate_orig = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); SimpleState sstate = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3+FU+FU * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P-00AL\n" "+\n").initialState(); compare_simulation(sstate_orig, sstate, 0, false); } void OracleProverLightTest:: test1Tesuki0() { if (isShortTest) return; boost::scoped_ptr mg(new movegen_t()); PathEncoding path; SimpleState sstate_orig = CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * * * * -KE-KI * * * \n" "P3 * * -KA * +UM * +FU * * \n" "P4-FU * -FU-FU-GI * -FU-FU-FU\n" "P5 * * * * -KI * * * * \n" "P6+FU+GI+FU+FU * * * * +FU\n" "P7+OU+FU * * * * * * * \n" "P8 * * -NG * * * * * * \n" "P9+KY+KE * * * -HI * * +KY\n" "P+00FU00FU00FU00GI00HI\n" "P-00FU00FU00FU00KI00KI\n" "+\n").initialState(); /* * +0031HI * -4131OU * +0032GI * -3122OU * +5342UM * %TORYO */ NumEffectState state_orig(sstate_orig); NtesukiSearcher searcher(state_orig, mg.get(), 10000000, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(state_orig.turn(), 20000000); BOOST_CHECK_EQUAL(1, ntesuki_num); { //handed +00HI to -00HI SimpleState sstate = CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * * * * -KE-KI * * * \n" "P3 * * -KA * +UM * +FU * * \n" "P4-FU * -FU-FU-GI * -FU-FU-FU\n" "P5 * * * * -KI * * * * \n" "P6+FU+GI+FU+FU * * * * +FU\n" "P7+OU+FU * * * * * * * \n" "P8 * * -NG * * * * * * \n" "P9+KY+KE * * * -HI * * +KY\n" "P+00FU00FU00FU00GI\n" "P-00FU00FU00FU00KI00KI00HI\n" "+\n").initialState(); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); bool result = simulator.startFromAttack(searcher.getTable(). allocateRoot(HashKey(state), PieceStand(), 0), searcher.getTable(). allocateRoot(HashKey(state_orig), PieceStand(), 0), ntesuki_num); BOOST_CHECK_EQUAL(false, result); } { //moved -42KI to -31KI SimpleState sstate = CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * * * * -KE * -KI * * \n" "P3 * * -KA * +UM * +FU * * \n" "P4-FU * -FU-FU-GI * -FU-FU-FU\n" "P5 * * * * -KI * * * * \n" "P6+FU+GI+FU+FU * * * * +FU\n" "P7+OU+FU * * * * * * * \n" "P8 * * -NG * * * * * * \n" "P9+KY+KE * * * -HI * * +KY\n" "P+00FU00FU00FU00GI00HI\n" "P-00FU00FU00FU00KI00KI\n" "+\n").initialState(); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); bool result = simulator.startFromAttack(searcher.getTable(). allocateRoot(HashKey(state), PieceStand(), 0), searcher.getTable(). allocateRoot(HashKey(state_orig), PieceStand(), 0), ntesuki_num); BOOST_CHECK_EQUAL(false, result); } //moved -91KY to -92KY //move +99KY to +98KY } void OracleProverLightTest:: test1Tesuki1() { if (isShortTest) return; boost::scoped_ptr mg(new movegen_t()); PathEncoding path; SimpleState sstate_orig = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state_orig(sstate_orig); NtesukiSearcher searcher(state_orig, mg.get(), 10000000, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(state_orig.turn(), 20000000); BOOST_CHECK_EQUAL(1, ntesuki_num); { //handed +00KA to -00KA SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P-00FU00FU00FU00FU00FU00KA\n" "+\n").initialState(); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); bool result = simulator.startFromAttack(searcher.getTable(). allocateRoot(HashKey(state), PieceStand(), 0), searcher.getTable(). allocateRoot(HashKey(state_orig), PieceStand(), 0), ntesuki_num); BOOST_CHECK_EQUAL(false, result); } { //moved -61KI to -71KI SimpleState sstate = CsaString( "P1-KY * -KI * * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY * \n" "P9+KY+KE+OU * +FU * * * +KY\n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); bool result = simulator.startFromAttack(searcher.getTable(). allocateRoot(HashKey(state), PieceStand(), 0), searcher.getTable(). allocateRoot(HashKey(state_orig), PieceStand(), 0), ntesuki_num); BOOST_CHECK_EQUAL(false, result); } { //moved -11KY to -12KY SimpleState sstate = CsaString( "P1-KY * * -KI * * * * * \n" "P2-OU * -GI * * * * * -KY\n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY+KY\n" "P9+KY+KE+OU * +FU * * * * \n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); bool result = simulator.startFromAttack(searcher.getTable(). allocateRoot(HashKey(state), PieceStand(), 0), searcher.getTable(). allocateRoot(HashKey(state_orig), PieceStand(), 0), ntesuki_num); BOOST_CHECK_EQUAL(true, result); } { //move +19KY to +18KY SimpleState sstate = CsaString( "P1-KY * * -KI * * * * -KY\n" "P2-OU * -GI * * * * * * \n" "P3-FU-FU-KE-FU+RY * * * * \n" "P4 * * +KE * -FU+FU+GI-FU-FU\n" "P5+FU * -FU * -KI * +GI-KE * \n" "P6 * * * * * * * * +FU\n" "P7 * -NG * +FU * -TO-UM * * \n" "P8 * * * +KI+KI * * -RY+KY\n" "P9+KY+KE+OU * +FU * * * * \n" "P+00KA\n" "P-00FU00FU00FU00FU00FU\n" "+\n").initialState(); NumEffectState state(sstate); OracleProverLight simulator(state, mg.get(), path, searcher.getTable()); bool result = simulator.startFromAttack(searcher.getTable(). allocateRoot(HashKey(state), PieceStand(), 0), searcher.getTable(). allocateRoot(HashKey(state_orig), PieceStand(), 0), ntesuki_num); BOOST_CHECK_EQUAL(true, result); } } CPPUNIT_TEST_SUITE_REGISTRATION(OracleProverLightTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/ntesukiRecord.t.cc0000644000000000000000000002535712316770314021455 0ustar rootroot#include "osl/ntesuki/ntesukiRecord.h" #include "osl/move.h" #include "osl/record/csaString.h" #include "osl/record/csaRecord.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" //#include "osl/ntesuki/ntesukiRecordPtr.h" #include #include #include using namespace osl; using namespace osl::ntesuki; class NtesukiRecordTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(NtesukiRecordTest); CPPUNIT_TEST(testGenerate); CPPUNIT_TEST(testModify); CPPUNIT_TEST(testDominanceSet_P); //CPPUNIT_TEST(testDominanceSet_Q); //CPPUNIT_TEST(testDominanceSetWhite_P); //CPPUNIT_TEST(testDominanceSetWhite_Q); //CPPUNIT_TEST(testSmartPtr); CPPUNIT_TEST_SUITE_END(); public: void testGenerate() { NtesukiRecord::RecordList list; NtesukiRecord nr(0u, HashKey(), PieceStand(), &list); for (size_t i = 0; i < NtesukiRecord::SIZE; ++i) { BOOST_CHECK_EQUAL(ProofDisproof(1, 1), nr.getValue(i)); BOOST_CHECK_EQUAL(ProofDisproof(1, 1), nr.getValue(i)); } BOOST_CHECK(!nr.isVisited()); SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); osl::Square lastTo = Square::STAND(); NtesukiMoveGenerator mg(OslConfig::verbose()); NtesukiRecord::mg = &mg; NtesukiRecord::state = &nState; NtesukiMoveList movelist; mg.generate(nState, movelist); } void testModify() { NtesukiRecord::RecordList list; NtesukiRecord nr(0, HashKey(), PieceStand(), &list); const NtesukiRecord& nrc = nr; nr.setResult(0, ProofDisproof(), NtesukiMove::INVALID(), false); BOOST_CHECK_EQUAL(ProofDisproof(), nrc.getValue(0)); nr.setResult(1, ProofDisproof(), NtesukiMove::INVALID(), false); BOOST_CHECK_EQUAL(ProofDisproof(), nrc.getValue(1)); } /* Initial settings * P-b P-w Q-b Q-w * 1 0 0 1 * 0 1 1 0 */ /* BLACK_P P has an extra pawn for BLACK compared to Q * * Before: both P and Q is unknown * - L_B^0(P) is success -> nothing * - L_B^0(P) is fail -> L_B^0(Q) is fail * - L_W^0(P) is success -> L_W^0(Q) is success * - L_W^0(P) is fail -> nothing * - L_B^1(P) is success -> nothing * - L_B^1(P) is fail -> L_B^1(Q) is fail * - L_W^1(P) is success -> L_W^1(Q) is success * - L_W^1(P) is fail -> nothing */ /* BLACK_Q Q has an extra pawn for BLACK compared to P * * - L_B^0(P) is success -> L_B^0(Q) is success * - L_B^0(P) is fail -> nothing * - L_W^0(P) is success -> L_W^0(Q) is success * - L_W^0(P) is fail -> L_W^0(Q) is fail * - L_B^1(P) is success -> L_B^1(Q) is success * - L_B^1(P) is fail -> nothing * - L_W^1(P) is success -> nothing * - L_W^1(P) is fail -> L_W^1(Q) is fail */ #define SUCC ProofDisproof::Checkmate() #define FAIL ProofDisproof::NoCheckmate() #define AB ProofDisproof::AttackBack() #define NONE ProofDisproof() //for experiments with positions where black is to play #define TEST_DOMINANCE_BEFORE(I,PL,PV,BV, WV) \ {\ if (OslConfig::verbose()) std::cerr << "\nBEFORE " << I << "\t" << PL << "\t" << PV << "\t" << BV << "\t" << WV;\ NumEffectState state(sstate);\ NtesukiRecord::RecordList list;\ NtesukiRecord best_record(0, HashKey(), PieceStand(), &list);\ NtesukiMove best_move = Move(Square(7,7), Square(7,6), PAWN, PTYPE_EMPTY, false, PL);\ \ list.push_front(NtesukiRecord(0, key_P, ps_P_W, &list));\ NtesukiRecord& record_P = list.front();\ NtesukiRecord::state = &state;\ \ if (PL == BLACK && PV == SUCC)\ record_P.setResult(I, PV, best_move, false, &pp_B);\ else if (PL == WHITE && PV == SUCC)\ record_P.setResult(I, PV, NtesukiMove::INVALID(), false, &pp_W);\ else if (PL == BLACK && PV == FAIL)\ record_P.setResult(I, PV, NtesukiMove::INVALID(), false, &pp_W);\ else if (PL == WHITE && PV == FAIL)\ record_P.setResult(I, PV, best_move, false, &pp_B);\ else\ record_P.setResult(I, PV, NtesukiMove::INVALID(), false, NULL);\ \ list.push_front(NtesukiRecord(0, key_Q, ps_Q_W, &list));\ NtesukiRecord& record_Q = list.front();\ \ BOOST_CHECK_EQUAL(BV, record_Q.getValue(I));\ BOOST_CHECK_EQUAL(WV, record_Q.getValue(I));\ }\ #define TEST_DOMINANCE_AFTER(I,PL,PV,BV,WV) \ {\ if (OslConfig::verbose()) std::cerr << "\nAFTER " << I << "\t" << PL << "\t" << PV << "\t" << BV << "\t" << WV;\ NumEffectState state(sstate);\ NtesukiRecord::RecordList list;\ NtesukiRecord best_record(0, HashKey(), PieceStand(), &list);\ NtesukiMove best_move = Move(Square(7,7), Square(7,6), PAWN, PTYPE_EMPTY, false, PL);\ NtesukiRecord::state = &state;\ \ list.push_front(NtesukiRecord(0, key_P, ps_P_W, &list));\ NtesukiRecord& record_P = list.front();\ list.push_front(NtesukiRecord(0, key_Q, ps_Q_W, &list));\ NtesukiRecord& record_Q = list.front();\ \ if (PL == BLACK && PV == SUCC)\ record_P.setResult(I, PV, best_move, false, &pp_B);\ else if (PL == WHITE && PV == SUCC)\ record_P.setResult(I, PV, NtesukiMove::INVALID(), false, &pp_W);\ else if (PL == BLACK && PV == FAIL)\ record_P.setResult(I, PV, NtesukiMove::INVALID(), false, &pp_W);\ else if (PL == WHITE && PV == FAIL)\ record_P.setResult(I, PV, best_move, false, &pp_B);\ else\ record_P.setResult(I, PV, NtesukiMove::INVALID(), false, NULL);\ \ BOOST_CHECK_EQUAL(BV, record_Q.getValue(I));\ BOOST_CHECK_EQUAL(WV, record_Q.getValue(I));\ }\ void testDominanceSet_P() { NtesukiRecord::use_dominance = true; HashKey key_P, key_Q; SimpleState sstate = CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU * \n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00FU\n" "+\n").initialState();; key_P = HashKey(sstate); PieceStand ps_P_W(0, 0, 0, 0, 0, 0, 0, 0); PieceStand ps_Q_W(1, 0, 0, 0, 0, 0, 0, 0); PieceStand pp_B(1, 0, 0, 0, 0, 0, 0, 0); PieceStand pp_W(0, 0, 0, 0, 0, 0, 0, 0); // - nothing -> nothing TEST_DOMINANCE_BEFORE(0, BLACK, NONE, NONE, NONE); TEST_DOMINANCE_AFTER(0, BLACK, NONE, NONE, NONE); // - L_B^0(P) is success -> nothing TEST_DOMINANCE_BEFORE(0, BLACK, SUCC, NONE, NONE); TEST_DOMINANCE_AFTER(0, BLACK, SUCC, NONE, NONE); // - L_B^0(P) is fail -> L_B^0(Q) is fail TEST_DOMINANCE_BEFORE(0, BLACK, FAIL, FAIL, NONE); TEST_DOMINANCE_AFTER(0, BLACK, FAIL, FAIL, NONE); // - L_B^1(P) is success -> nothing TEST_DOMINANCE_BEFORE(1, BLACK, SUCC, NONE, NONE); TEST_DOMINANCE_AFTER(1, BLACK, SUCC, NONE, NONE); // - L_B^1(P) is fail -> L_B^1(Q) is fail TEST_DOMINANCE_BEFORE(1, BLACK, FAIL, FAIL, NONE); TEST_DOMINANCE_AFTER(1, BLACK, FAIL, FAIL, NONE); // - L_W^0(P) is success -> L_W^0(Q) is success TEST_DOMINANCE_BEFORE(0, WHITE, SUCC, AB, SUCC); TEST_DOMINANCE_AFTER(0, WHITE, SUCC, AB, SUCC); // - L_W^0(P) is fail -> nothing TEST_DOMINANCE_BEFORE(0, WHITE, FAIL, NONE, NONE); TEST_DOMINANCE_AFTER(0, WHITE, FAIL, NONE, NONE); // - L_W^1(P) is success -> L_W^1(Q) is success TEST_DOMINANCE_BEFORE(1, WHITE, SUCC, AB, SUCC); TEST_DOMINANCE_AFTER(1, WHITE, SUCC, AB, SUCC); // - L_W^1(P) is fail -> nothing TEST_DOMINANCE_BEFORE(1, WHITE, FAIL, NONE, NONE); TEST_DOMINANCE_AFTER(1, WHITE, FAIL, NONE, NONE); } void testDominanceSet_Q() { HashKey key_P, key_Q; SimpleState sstate = CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU * \n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P-00FU\n" "+\n").initialState();; key_P = HashKey(sstate); PieceStand ps_P_W(1, 0, 0, 0, 0, 0, 0, 0); PieceStand ps_Q_W(0, 0, 0, 0, 0, 0, 0, 0); PieceStand pp_B(0, 0, 0, 0, 0, 0, 0, 0); PieceStand pp_W(1, 0, 0, 0, 0, 0, 0, 0); // - nothing -> nothing TEST_DOMINANCE_BEFORE(0, BLACK, NONE, NONE, NONE); TEST_DOMINANCE_AFTER(0, BLACK, NONE, NONE, NONE); // - L_B^0(P) is success -> L_B^0(Q) is success TEST_DOMINANCE_BEFORE(0, BLACK, SUCC, SUCC, AB); TEST_DOMINANCE_AFTER(0, BLACK, SUCC, SUCC, AB); // - L_B^0(P) is fail -> nothing TEST_DOMINANCE_BEFORE(0, BLACK, FAIL, NONE, NONE); TEST_DOMINANCE_AFTER(0, BLACK, FAIL, NONE, NONE); // - L_B^1(P) is success -> L_B^1(Q) is success TEST_DOMINANCE_BEFORE(1, BLACK, SUCC, SUCC, AB); TEST_DOMINANCE_AFTER(1, BLACK, SUCC, SUCC, AB); // - L_B^1(P) is fail -> nothing TEST_DOMINANCE_BEFORE(1, BLACK, FAIL, NONE, NONE); TEST_DOMINANCE_AFTER(1, BLACK, FAIL, NONE, NONE); // - L_W^0(P) is success -> nothing TEST_DOMINANCE_BEFORE(0, WHITE, SUCC, NONE, NONE); TEST_DOMINANCE_AFTER(0, WHITE, SUCC, NONE, NONE); // - L_W^0(P) is fail -> L_W^0(Q) is fail TEST_DOMINANCE_BEFORE(0, WHITE, FAIL, NONE, FAIL); TEST_DOMINANCE_AFTER(0, WHITE, FAIL, NONE, FAIL); // - L_W^1(P) is success -> nothing TEST_DOMINANCE_BEFORE(1, WHITE, SUCC, NONE, NONE); TEST_DOMINANCE_AFTER(1, WHITE, SUCC, NONE, NONE); // - L_W^1(P) is fail -> L_W^1(Q) is fail TEST_DOMINANCE_BEFORE(1, WHITE, FAIL, NONE, FAIL); TEST_DOMINANCE_AFTER(1, WHITE, FAIL, NONE, FAIL); } #undef SUCC #undef FAIL #undef AB #undef NONE #undef TEST_DOMINANCE #if 0 void testSmartPtr() { NtesukiRecord::RecordList list; NtesukiRecord nr(0u, HashKey(), &list); { NtesukiRecordPtr ptr(&nr); BOOST_CHECK_EQUAL(nr.key, ptr->key); BOOST_CHECK_EQUAL(nr.key, (*ptr).key); NtesukiRecordPtr ptr2 = ptr; BOOST_CHECK_EQUAL(2, nr.ref_count); NtesukiRecordPtr ptr3(ptr); BOOST_CHECK_EQUAL(3, nr.ref_count); } BOOST_CHECK_EQUAL(0, nr.ref_count); } #endif }; CPPUNIT_TEST_SUITE_REGISTRATION(NtesukiRecordTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/proofDisproofPieces.t.cc0000644000000000000000000007066312316770314022620 0ustar rootroot/* profDisproofPices.t.cc */ #include "osl/ntesuki/ntesukiSearcher.h" #include "osl/state/hashEffectState.h" #include "osl/record/csaString.h" #include "osl/record/csaRecord.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/ntesuki/ntesukiTable.h" #include "osl/checkmate/proofDisproof.h" #include #include #include #include class ProofDisproofPieces : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(ProofDisproofPieces); CPPUNIT_TEST(test_proof0tesuki0); CPPUNIT_TEST(test_proof0tesuki1); CPPUNIT_TEST(test_proof0tesuki2); CPPUNIT_TEST(test_proof1tesuki0); CPPUNIT_TEST(test_proof1tesuki1); CPPUNIT_TEST(test_proof1tesuki2); CPPUNIT_TEST(test_proof1tesuki3); CPPUNIT_TEST(test_proofKatagyoku0); CPPUNIT_TEST(test_disproof0tesuki0); CPPUNIT_TEST(test_disproof0tesuki1); CPPUNIT_TEST(test_disproof1tesuki0); CPPUNIT_TEST(test_disproof1tesuki1); CPPUNIT_TEST(test_disproof1tesuki1_1); CPPUNIT_TEST(test_disproof1tesuki1_2); CPPUNIT_TEST(test_pdp_pieces0); CPPUNIT_TEST_SUITE_END(); public: void test_proof0tesuki0(); void test_proof0tesuki1(); void test_proof0tesuki2(); void test_proof1tesuki0(); void test_proof1tesuki1(); void test_proof1tesuki2(); void test_proof1tesuki3(); void test_proofKatagyoku0(); void test_disproof0tesuki0(); void test_disproof0tesuki1(); void test_disproof1tesuki0(); void test_disproof1tesuki1(); void test_disproof1tesuki1_1(); void test_disproof1tesuki1_2(); void test_pdp_pieces0(); }; CPPUNIT_TEST_SUITE_REGISTRATION(ProofDisproofPieces); using namespace osl; using namespace osl::ntesuki; const size_t TABLE_LIMIT = 1000000; const size_t READ_LIMIT = 2000000; typedef NtesukiMoveGenerator movegen_t; static volatile int stop_flag = false; void ProofDisproofPieces::test_proof0tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(GOLD); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_proof1tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+KY * * * * \n" "P8+HI+GI+KI+GI+GI * * * * \n" "P9+HI+KI+OU+KI+GI * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(GOLD); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_proof1tesuki1() { SimpleState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * -KI * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+KY * * * * \n" "P8+HI+GI+KI+GI+GI * * * * \n" "P9+HI+KI+OU+KI+GI * * * * \n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_proof1tesuki2() { SimpleState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * -KI * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU * * * * * \n" "P8+HI+KY+KI * * * * * * \n" "P9+OU+KI+HI+KI * * * * * \n" "P+00GI00GI00GI00GI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 2, osl::ntesuki::NtesukiRecord::pn_iw, osl::ntesuki::NtesukiRecord::no_ps, osl::ntesuki::NtesukiRecord::no_is, 2); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(SILVER, 4); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_proof0tesuki1() { /* 当åˆä½¿ã£ã¦ã„ãŸä¾‹ã¯ï¼Œå¾Œæ‰‹ã«æ­©ãŒä¸€æžšå¤šã„ã¨ï¼Œåˆ¥ã®(より早ã„)手順を 見ã¤ã‘ã‚‹å¯èƒ½æ€§ãŒã‚ã‚‹ãŸã‚,変更ã™ã‚‹å¿…è¦ãŒã‚る. CsaString csa_str( "P1-KY * * +TO-KI-OU * * * \n" "P2 * * +RY-GI * * -KI * * \n" "P3-FU * -FU-FU * * * -GI-FU\n" "P4 * * * * -KE-FU * * * \n" "P5 * * * * * -KE-FU * * \n" "P6 * +FU+FU * * * * * +FU\n" "P7+FU+OU * +FU * +FU+GI * * \n" "P8 * * * * -RY * * * * \n" "P9+KY+KE+KE * * * -UM * +KY\n" "P+00FU00FU00FU00FU00GI00KY00KA\n" "P-00FU00KI00KI\n" "-\n" ); */ { CsaString csa_str( "P1-KY * * +TO-KI-OU * * * \n" "P2 * * +RY-GI * * -KI * * \n" "P3-FU * -FU-FU * * * -GI-FU\n" "P4 * * * * -KE-FU * * * \n" "P5 * * * * * -KE-FU * * \n" "P6 * +FU+FU * * * * * +FU\n" "P7+FU+OU * +FU * +FU+GI * * \n" "P8 * * * * -RY * * * * \n" "P9+KY+KE+KE * * * -UM * +KY\n" "P+00FU00FU00FU00FU00GI00KY00KA\n" "P-00FU00KI00KI\n" "-\n" ); SimpleState state = csa_str.initialState(); const osl::vector moves = csa_str.load().moves(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(osl::WHITE, READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(PAWN, 1); correct.add(GOLD, 2); BOOST_CHECK_EQUAL(correct, ans); } } void ProofDisproofPieces::test_proof0tesuki2() { /* from search tree of * probles/100/4/1.csa * by ntesuki_searcher 2153 */ { SimpleState state=CsaString( "P1-KY-OU * * * * * * -KY\n" "P2 * +KI * * * * * * * \n" "P3 * * +GI * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * +KE * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * * +KI+GI * * * * * \n" "P9+KY * +OU * +KI * -RY+KE+KY\n" "P+00KE\n" "P-00KA00KI00GI00FU00FU00FU00HI\n" "-\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(BLACK, READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY-OU * * * * * * -KY\n" "P2 * * * * * * * * * \n" "P3 * * +GI * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * +KE * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * * +KI+GI * * * * * \n" "P9+KY * +OU * +KI * -RY+KE+KY\n" "P+00KI\n" "P-00KA00KI00GI00FU00FU00FU00HI00KE\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(BLACK, READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(GOLD, 1); BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY-OU * * * * * * -KY\n" "P2 * * * * * * * * * \n" "P3 * * +GI * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * +KE * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * * +KI+GI * * * * * \n" "P9+KY * +OU * +KI * -RY+KE+KY\n" "P+00KI00KE\n" "P-00KA00KI00GI00FU00FU00FU00HI\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(BLACK, READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(GOLD, 1); BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY * * * * * * * -KY\n" "P2 * -OU * * * * * * * \n" "P3 * * +GI * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * +KE * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * * +KI+GI * * * * * \n" "P9+KY * +OU * +KI * -RY+KE+KY\n" "P+00KI00KE\n" "P-00KA00KI00GI00FU00FU00FU00HI\n" "-\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(BLACK, READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(GOLD, 1); BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY * * * * * * * -KY\n" "P2 * -OU * * * * * * * \n" "P3 * * * * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * +KE * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * * +KI+GI * * * * * \n" "P9+KY * +OU * +KI * -RY+KE+KY\n" "P+00GI00KE00KI\n" "P-00KA00KI00GI00FU00FU00FU00HI\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(SILVER, 1); correct.add(GOLD, 1); //correct.add(KNIGHT, 1); BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY+HI * * * * * * -KY\n" "P2 * -KI * * * * * * * \n" "P3 * -OU * * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * +KE * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * * +KI+GI * * * * * \n" "P9+KY * +OU * +KI * -RY+KE+KY\n" "P+00GI00KE\n" "P-00KA00KI00GI00FU00FU00FU\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(SILVER, 1); //correct.add(KNIGHT, 1); //althogh opponent does not have any KNIGHTs, //we checkmate with unescapable moves //a gold will be captured BOOST_CHECK_EQUAL(correct, ans); } } void ProofDisproofPieces::test_proof1tesuki3() { /* from search tree of * probles/100/4/1.csa * by ntesuki_searcher 2168 * assertion failed in ../include/osl/ntesuki/ntesukiRecord.tcc line 367 * PP is (stand 2 1 2 1 1 0 0) * = 00HI00HI00KA00KI00KI00GI00KE * where 00KA is exessive */ { SimpleState state=CsaString( "P1-KY-OU * * * * * * -KY\n" "P2 * * * * * * * * * \n" "P3 * +TO * * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * -GI * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * +KI * +GI * * * * * \n" "P9+KY+KE * +OU-KI * * +KE+KY\n" "P+00HI00HI00KA00KI00KI00GI00KE\n" "P-00FU00FU\n" "+\n" ).initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 2, osl::ntesuki::NtesukiRecord::pn_iw, osl::ntesuki::NtesukiRecord::no_ps, osl::ntesuki::NtesukiRecord::no_is, 2); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(ROOK, 2); correct.add(BISHOP, 1); correct.add(GOLD, 2); correct.add(SILVER, 1); correct.add(KNIGHT, 1); BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY-OU * * * * * * -KY\n" "P2 * * * * * * * * * \n" "P3 * +TO * * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * -GI * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * +KI * +GI * -KI * * * \n" "P9+KY+KE+OU-UM * * * +KE+KY\n" "P+00HI00HI00KI00KI00GI00KE\n" "P-00FU00FU\n" "+\n" ).initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(),2, osl::ntesuki::NtesukiRecord::pn_iw, osl::ntesuki::NtesukiRecord::no_ps, osl::ntesuki::NtesukiRecord::no_is, 2); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(ROOK, 2); correct.add(GOLD, 2); correct.add(SILVER, 1); correct.add(KNIGHT, 1); BOOST_CHECK_EQUAL(correct, ans); } { SimpleState state=CsaString( "P1-KY-OU * * * * * * -KY\n" "P2 * * * * * * * * * \n" "P3 * +TO * * -GI * -KE * -FU\n" "P4-FU * -FU-FU-FU-KA-FU * * \n" "P5 * -GI * * * -FU * * * \n" "P6+FU-FU * * +FU * * * * \n" "P7 * * +FU+FU * +FU+FU * +FU\n" "P8 * +KI * +GI-KA-KI * * * \n" "P9+KY+KE-HI+OU * * * +KE+KY\n" "P+00HI00KI00KI00GI00KE\n" "P-00FU00FU\n" "+\n" ).initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(),2, osl::ntesuki::NtesukiRecord::pn_iw, osl::ntesuki::NtesukiRecord::no_ps, osl::ntesuki::NtesukiRecord::no_is, 2); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(ROOK, 1); correct.add(GOLD, 2); correct.add(SILVER, 1); correct.add(KNIGHT, 1); BOOST_CHECK_EQUAL(correct, ans); } } /* 勿µ¦ä¿®ã€Œå¿…至ã®ã‹ã‘æ–¹ã€å‰µå…ƒç¤¾ã‚ˆã‚Š */ void ProofDisproofPieces::test_proofKatagyoku0() { SimpleState state=CsaString( "P1 * * * * * -OU * -KE-KY\n" "P2 * * * +TO * -GI * * * \n" "P3 * * * * * -FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+KI * * * * * * * \n" "P9+OU+KI * * * * * * * \n" "P+00KI00KI\n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn()); BOOST_CHECK_EQUAL(1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(ntesuki_num); PieceStand correct; correct.add(GOLD); correct.add(GOLD); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_disproof0tesuki0() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(0); PieceStand correct; //correct.add(PAWN,0); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_disproof0tesuki1() { SimpleState state=CsaString( "P1 * * * +HI-FU * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * +KI\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6-FU-FU-FU-FU * -FU-FU-FU-FU\n" "P7 * * * * * * * * * \n" "P8+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P9+OU * * * * * * * * \n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(0); PieceStand correct; correct.add(ROOK, 1); correct.add(BISHOP, 2); correct.add(GOLD,3); correct.add(SILVER,4); correct.add(KNIGHT,4); correct.add(LANCE,4); //correct.add(PAWN,0); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_disproof1tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * -KE * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU * * * * * * * \n" "P8+KI+GI * * * * * * * \n" "P9+OU+KI * * * * * * * \n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(1); PieceStand correct; correct.add(ROOK, 2); correct.add(BISHOP, 2); correct.add(GOLD,2); correct.add(SILVER,3); correct.add(KNIGHT,3); correct.add(LANCE,4); correct.add(PAWN,15); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_disproof1tesuki1() { SimpleState state=CsaString( "P1 * * * * * * -OU-KI * \n" "P2 * * * * * * * +KI * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU * * * * * * * \n" "P8+KI+GI * * * * * * * \n" "P9+OU+KI * * * * * * * \n" "P-00AL\n" "-\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(BLACK, READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(1); PieceStand correct; correct.add(ROOK, 2); correct.add(BISHOP, 2); correct.add(GOLD,0); correct.add(SILVER,3); correct.add(KNIGHT,4); correct.add(LANCE,4); correct.add(PAWN,16); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_disproof1tesuki1_1() { SimpleState state=CsaString( "P1 * * * * * * -OU * * \n" "P2 * * * * * * * -KI * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU * * * * * * * \n" "P8+KI+GI * * * * * * * \n" "P9+OU+KI * * * * * * * \n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(1); PieceStand correct; correct.add(ROOK, 2); correct.add(BISHOP, 2); correct.add(GOLD,1); correct.add(SILVER,3); correct.add(KNIGHT,4); correct.add(LANCE,4); correct.add(PAWN,16); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_disproof1tesuki1_2() { SimpleState state=CsaString( "P1 * * * * * * * -KI * \n" "P2 * * * * * * * -OU * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU * * * * * * * \n" "P8+KI+GI * * * * * * * \n" "P9+OU+KI * * * * * * * \n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(1); PieceStand correct; correct.add(ROOK, 2); correct.add(BISHOP, 2); correct.add(GOLD,1); correct.add(SILVER,3); correct.add(KNIGHT,4); correct.add(LANCE,4); correct.add(PAWN,16); BOOST_CHECK_EQUAL(correct, ans); } void ProofDisproofPieces::test_pdp_pieces0() { /* from the search tree of * problems/100/4/012.csa */ {//proof SimpleState state=CsaString( "P1-KY-KE-OU * * * * -KE-KY\n" "P2 * * * -KI+NG * * * * \n" "P3 * -FU * -FU-FU * * -FU-FU\n" "P4-FU * -FU-KA * * * * * \n" "P5 * -KE * -GI * -FU * +FU * \n" "P6+FU+OU+FU * * * * * * \n" "P7 * +FU * +FU+FU+FU * * +FU\n" "P8 * * * +GI * +GI * * * \n" "P9+KY * * * +KI-RY * +KE+KY\n" "P+00HI00KA00KI\n" "P-00KI00FU00FU\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(WHITE, READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(0); PieceStand correct; correct.add(GOLD,1); correct.add(PAWN,2); BOOST_CHECK_EQUAL(correct, ans); } {//disproof SimpleState state=CsaString( "P1-KY-KE-OU * * * * -KE-KY\n" "P2 * * * -KI+NG * * * * \n" "P3 * -FU * -FU-FU * * -FU-FU\n" "P4-FU * -FU-KA * * * * * \n" "P5 * -KE * -GI * -FU * +FU * \n" "P6+FU+OU+FU * * * * * * \n" "P7 * +FU * +FU+FU+FU * * +FU\n" "P8 * * * +GI * +GI * * * \n" "P9+KY * * * +KI-RY * +KE+KY\n" "P+00HI00KA00KI00KI\n" "P-00FU00FU\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(WHITE, READ_LIMIT); BOOST_CHECK_EQUAL(-1, ntesuki_num); HashKey key (state); NtesukiRecord *record = searcher.getTable().allocateRoot(key, PieceStand(), 0); PieceStand ans = record->getPDPieces(0); PieceStand correct; correct.add(ROOK, 1); correct.add(BISHOP, 1); correct.add(GOLD,2); correct.add(SILVER,0); correct.add(KNIGHT,0); correct.add(LANCE,0); correct.add(PAWN,0); BOOST_CHECK_EQUAL(correct, ans); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/ntesukiResult.t.cc0000644000000000000000000000127312316770314021504 0ustar rootroot#include "osl/ntesuki/ntesukiResult.h" #include #include #include #include #include using namespace osl; using namespace osl::ntesuki; class NtesukiResultTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(NtesukiResultTest); CPPUNIT_TEST(testGenerate); CPPUNIT_TEST_SUITE_END(); public: void testGenerate() { NtesukiResult nr; nr = ProofDisproof::NoCheckmate(); nr = ProofDisproof::Checkmate(); nr = ProofDisproof(1, 1); } }; CPPUNIT_TEST_SUITE_REGISTRATION(NtesukiResultTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/ntesukiSearcher.t.cc0000644000000000000000000004212212316770314021760 0ustar rootroot/* ntesukiSeacher.cc */ #include "osl/ntesuki/ntesukiSearcher.h" #include "osl/state/hashEffectState.h" #include "osl/record/csaString.h" #include "osl/record/csaRecord.h" #include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/ntesuki/ntesukiTable.h" #include "osl/checkmate/proofDisproof.h" #include "osl/apply_move/applyMove.h" #include "osl/oslConfig.h" #include #include #include #include class NtesukiSearcherTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(NtesukiSearcherTest); CPPUNIT_TEST(test0tesuki0); CPPUNIT_TEST(test0tesuki0op); CPPUNIT_TEST(test0tesuki2); CPPUNIT_TEST(test0tesuki1); CPPUNIT_TEST(test1tesuki0); CPPUNIT_TEST(testKatagyoku0); CPPUNIT_TEST(testRecognizeAttackBack0); CPPUNIT_TEST(testRecognizeAttackBack1); CPPUNIT_TEST(test1tesukiTest01); CPPUNIT_TEST(test1tesukiTest13); CPPUNIT_TEST(test1tesukiTest22); CPPUNIT_TEST(test1tesukiTest25); CPPUNIT_TEST(test1tesukiTest29); CPPUNIT_TEST(test1tesukiTest56); CPPUNIT_TEST(test1tesukiTest76); CPPUNIT_TEST(test1tesukiTest94); #if 0 CPPUNIT_TEST(test2tesuki0); CPPUNIT_TEST(test2tesuki1); #endif CPPUNIT_TEST_SUITE_END(); public: void test0tesuki0(); void test0tesuki0op(); void test0tesuki1(); void test0tesuki2(); void test1tesuki0(); void test2tesuki0(); void test2tesuki1(); void testRecognizeAttackBack0(); void testRecognizeAttackBack1(); void test1tesukiTest01(); void test1tesukiTest13(); void test1tesukiTest22(); void test1tesukiTest25(); void test1tesukiTest29(); void test1tesukiTest56(); void test1tesukiTest76(); void test1tesukiTest94(); void test3tesuki0(); void test3tesuki1(); void testKatagyoku0(); }; CPPUNIT_TEST_SUITE_REGISTRATION(NtesukiSearcherTest); using namespace osl; using namespace osl::ntesuki; const size_t TABLE_LIMIT = 5000000; const size_t READ_LIMIT = 10000000; typedef NtesukiMoveGenerator movegen_t; volatile int stop_flag = false; void NtesukiSearcherTest::test0tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, !isShortTest, 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); } void NtesukiSearcherTest::test0tesuki0op() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * -FU * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00FU00FU00FU00FU00FU00FU00FU00FU\n" "P+00FU00FU00FU00FU00FU00FU00FU00FU\n" "P+00FU\n" "P+00KY00KY00KY00KY00KE00KE00KE00KE\n" "P+00GI00GI00GI00GI00KI00KI00KI\n" "P+00KA00KA00HI00HI\n" "P-00KI\n" "-\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(0, ntesuki_num); } void NtesukiSearcherTest::test0tesuki1() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI+UM-KE-KY\n" "P2 * -HI * * +KA * * * * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00GI\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag,OslConfig::verbose(), 1); const int ntesuki_num = searcher.searchSlow(nState.turn()); BOOST_CHECK_EQUAL(0, ntesuki_num); } void NtesukiSearcherTest::test0tesuki2() { for (int i = 17; i >= 0; i--) { CsaString csa_str( "P1-KY * * +TO-KI-OU * * * \n" "P2 * * +RY-GI * * -KI * * \n" "P3-FU * -FU-FU * * * -GI-FU\n" "P4 * * * * -KE-FU * * * \n" "P5 * * * * * -KE-FU * * \n" "P6 * +FU+FU * * * * * +FU\n" "P7+FU+OU * +FU * +FU+GI * * \n" "P8 * * * * -RY * * * * \n" "P9+KY+KE+KE * * * -UM * +KY\n" "P+00FU00FU00FU00GI00KY00KA\n" "P-00FU00FU00KI00KI\n" "-\n" "-0088KI\n" "+8796OU\n" "-0095KI\n" "+9695OU\n" "-9394FU\n" "+9596OU\n" "-9495FU\n" "+9685OU\n" "-5855RY\n" "+0075KY\n" "-0084FU\n" "+8584OU\n" "-5564RY\n" "+8483OU\n" "-6494RY\n" "+8382OU\n" "-9492RY\n" ); SimpleState state = csa_str.initialState(); const osl::vector moves = csa_str.load().moves(); for (int j = 0; j < i; j++) { ApplyMoveOfTurn::doMove(state, moves[j]); } NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 1); if (OslConfig::verbose()) { std::cerr << "trying" << i << "\n" << state; } const int ntesuki_num = searcher.searchSlow(osl::WHITE, READ_LIMIT); if (OslConfig::verbose()) { std::cerr << "\tresult\t" << ntesuki_num << std::endl; } BOOST_CHECK_EQUAL(0, ntesuki_num); } } void NtesukiSearcherTest::test1tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+KY * * * * \n" "P8+HI+GI+KI+GI+GI * * * * \n" "P9+HI+KI+OU+KI+GI * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest::test2tesuki0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * +FU * \n" "P6 * * * * * * * * * \n" "P7 * +FU+FU+FU * * * * * \n" "P8 * +GI+KI+GI * * * * * \n" "P9 * +KI+OU+KI * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn()); BOOST_CHECK_EQUAL(2, ntesuki_num); } void NtesukiSearcherTest::test2tesuki1() { SimpleState state=CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * +UM * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00KA\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn()); BOOST_CHECK_EQUAL(2, ntesuki_num); } void NtesukiSearcherTest::testRecognizeAttackBack0() { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * -FU * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 2, osl::ntesuki::NtesukiRecord::pn_iw, osl::ntesuki::NtesukiRecord::pn_ps, osl::ntesuki::NtesukiRecord::tonshi_is, 0); const int ntesuki_num = searcher.searchSlow(nState.turn()); BOOST_CHECK_EQUAL(-1, ntesuki_num); } void NtesukiSearcherTest::testRecognizeAttackBack1() { CsaFile file(OslConfig::testFile("grimbergen_testset/test12.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); NumEffectState nState(state); boost::scoped_ptr gam(new movegen_t()); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 2, osl::ntesuki::NtesukiRecord::pn_iw, osl::ntesuki::NtesukiRecord::pn_ps, osl::ntesuki::NtesukiRecord::tonshi_is, 0); NtesukiSearcher::delay_non_pass = true; NtesukiSearcher::ptt_invalid_defense = true; //NtesukiSearcher::ptt_siblings_fail = true; NtesukiSearcher::ptt_siblings_success = true; NtesukiSearcher::delay_interpose = true; NtesukiSearcher::delay_nopromote = true; NtesukiRecord::use_dominance = true; NtesukiRecord::fixed_search_depth = 4; const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); if (!searcher.exceedReadNodeLimit()) { BOOST_CHECK_EQUAL(1, ntesuki_num); } const NtesukiTable& table = searcher.getTable(); const HashKey key = HashKey(state). newHashWithMove(Move(Square(6,2), BISHOP, BLACK)); const NtesukiRecord *record = table.find(key); if (record) { BOOST_CHECK(!record->getValue(1).isCheckmateSuccess()); } else { std::cerr << "node not searched\n"; } } /* see if can solve some problems */ static void test_state(const char *csa_filename) { CsaFile file(csa_filename); SimpleState init_state = file.initialState (); Player winner = init_state.turn(); const osl::vector moves=file.load().moves(); std::cerr << "for " << csa_filename << "\n"; for (int i = moves.size(); i >= 0; i--) { std::cerr << "trying " << i << "..."; SimpleState state(init_state); for (int j = 0; j < i; j++) { ApplyMoveOfTurn::doMove(state, moves[j]); } boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose(), 2, NtesukiRecord::pn_iw, NtesukiRecord::no_ps, NtesukiRecord::no_is, 2 /* tsumero cost */, 1 /* tsumero estimates */); NtesukiSearcher::delay_non_pass = true; NtesukiSearcher::ptt_invalid_defense = true; //NtesukiSearcher::ptt_siblings_fail = true; //NtesukiSearcher::ptt_siblings_success = true; NtesukiSearcher::delay_interpose = true; NtesukiSearcher::delay_nopromote = true; NtesukiRecord::use_dominance = true; NtesukiRecord::fixed_search_depth = 4; const int ntesuki_num = searcher.searchSlow(winner, READ_LIMIT); std::cerr << ntesuki_num << "\n"; BOOST_CHECK(ntesuki_num >= 0); } } void NtesukiSearcherTest:: test1tesukiTest01() { if (isShortTest) return; test_state(OslConfig::testFile("grimbergen_testset/test1.csa")); } void NtesukiSearcherTest:: test1tesukiTest22() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test22.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest:: test1tesukiTest13() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test13.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest:: test1tesukiTest25() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test25.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest:: test1tesukiTest29() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test29.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest:: test1tesukiTest56() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test56.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest:: test1tesukiTest76() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test76.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } void NtesukiSearcherTest:: test1tesukiTest94() { if (isShortTest) return; CsaFile file(OslConfig::testFile("grimbergen_testset/test94.csa")); SimpleState state = file.initialState (); const osl::vector moves=file.load().moves(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn(), READ_LIMIT); BOOST_CHECK_EQUAL(1, ntesuki_num); } /* 勿µ¦ä¿®ã€Œå¿…至ã®ã‹ã‘æ–¹ã€å‰µå…ƒç¤¾ã‚ˆã‚Š */ void NtesukiSearcherTest::testKatagyoku0() { SimpleState state=CsaString( "P1 * * * * * -OU * -KE-KY\n" "P2 * * * +TO * -GI * * * \n" "P3 * * * * * -FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+KI * * * * * * * \n" "P9+OU+KI * * * * * * * \n" "P+00KI00KI\n" "P-00AL\n" "+\n").initialState(); boost::scoped_ptr gam(new movegen_t()); NumEffectState nState(state); NtesukiSearcher searcher(nState, gam.get(), TABLE_LIMIT, &stop_flag, OslConfig::verbose()); const int ntesuki_num = searcher.searchSlow(nState.turn()); BOOST_CHECK_EQUAL(1, ntesuki_num); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/ntesukiMoveGenerator.t.cc0000644000000000000000000000712112316770314023001 0ustar rootroot#include "osl/ntesuki/ntesukiMoveGenerator.h" #include "osl/state/numEffectState.tcc" #include "osl/record/csaString.h" #include "osl/record/csaRecord.h" #include #include #include #include using namespace osl; using namespace osl::ntesuki; class NtesukiMoveGeneratorTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(NtesukiMoveGeneratorTest); CPPUNIT_TEST(testGetAttackMoves); CPPUNIT_TEST_SUITE_END(); public: void testGetAttackMoves(); }; //----------------------------------------------------------------------------- // Attack //----------------------------------------------------------------------------- void NtesukiMoveGeneratorTest:: testGetAttackMoves() { NtesukiMoveGenerator gam(OslConfig::verbose()); { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); NtesukiMoveList moves; osl::Square lastTo = Square::STAND(); gam.generate(nState, moves); BOOST_CHECK_EQUAL(size_t(85), moves.size()); } { SimpleState state=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * +HI * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); NtesukiMoveGenerator gam(OslConfig::verbose()); NtesukiMoveList moves; osl::Square lastTo = Square::STAND(); gam.generate(nState, moves); BOOST_CHECK_EQUAL((size_t)91, moves.size()); } { SimpleState state = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * -HI * +HI * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); NtesukiMoveGenerator gam(OslConfig::verbose()); NtesukiMoveList moves; osl::Square lastTo = Square::STAND(); gam.generate(nState, moves); BOOST_CHECK_EQUAL((size_t)6, moves.size()); } { SimpleState state = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * +OU * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState(); NumEffectState nState(state); NtesukiMoveGenerator gam(OslConfig::verbose()); NtesukiMoveList moves; gam.generate(nState, moves); BOOST_CHECK_EQUAL((size_t)86, moves.size()); } } CPPUNIT_TEST_SUITE_REGISTRATION(NtesukiMoveGeneratorTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/move_generator/0000755000000000000000000000000012316770314021063 5ustar rootrootlibosl-0.8.0.orig/full/test/ntesuki/move_generator/addEffect8Defense.t.cc0000644000000000000000000000526712316770314025075 0ustar rootroot#include "osl/move_generator/addEffect8Defense.h" #include "osl/move_action/store.h" #include "osl/record/csaString.h" #include "osl/record/csaRecord.h" #include "osl/move.h" #include "osl/container/moveVector.h" #include "osl/oslConfig.h" #include #include #include #include using namespace osl; using namespace osl::move_action; using namespace osl::move_generator; #include class AddEffect8DefenseTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(AddEffect8DefenseTest); CPPUNIT_TEST(testSimple0); CPPUNIT_TEST(testSuicide0); CPPUNIT_TEST(testTest11); CPPUNIT_TEST_SUITE_END(); public: void testSimple0(); void testSuicide0(); void testTest11(); }; void AddEffect8DefenseTest:: testSimple0() { SimpleState sstate=CsaString( "P1 * * * * * * -KE-OU * \n" "P2 * * * * * * * * -KI\n" "P3 * * * -HI * * * +FU * \n" "P4 * * +KI * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * +OU * * * * * * \n" "P9 * * * +KY * * * * * \n" "P-00KI\n" "P+00AL\n" "-\n").initialState(); NumEffectState state(sstate); { MoveVector moves; AddEffect8Defense::generate(state, moves); BOOST_CHECK_EQUAL((size_t) (7 + 4 /*Drop GOLD*/ + 1 /*KING*/ + 3 /*GOLD*/ + 4 /*ROOK*/), moves.size()); } } void AddEffect8DefenseTest:: testSuicide0() { SimpleState sstate=CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * -KI * * * \n" "P4 * * * * * * * * * \n" "P5 * * * +KA * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * +OU * * * * * * \n" "P9 * * * +KY * * * * * \n" "P+00AL\n" "-\n").initialState(); NumEffectState state(sstate); { MoveVector moves; AddEffect8Defense::generate(state, moves); BOOST_CHECK_EQUAL((size_t)3u, moves.size()); } } void AddEffect8DefenseTest:: testTest11() { CsaFile file(OslConfig::testFile("grimbergen_testset/test11.csa")); SimpleState sstate = file.initialState (); const osl::vector moves=file.load().moves(); NumEffectState state(sstate); { MoveVector moves; AddEffect8Defense::generate(state, moves); } } CPPUNIT_TEST_SUITE_REGISTRATION(AddEffect8DefenseTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/move_generator/captureEffectToAroundKing8.t.cc0000644000000000000000000000555412316770314027002 0ustar rootroot#include "osl/move_generator/captureEffectToAroundKing8.h" #include "osl/move_action/store.h" #include "osl/record/csaString.h" #include "osl/record/csaRecord.h" #include "osl/move.h" #include "osl/container/moveVector.h" #include "osl/oslConfig.h" #include #include #include #include using namespace osl; using namespace osl::move_action; using namespace osl::move_generator; #include class CaptureEffectToAroundKing8Test : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(CaptureEffectToAroundKing8Test); CPPUNIT_TEST(testSimple0); CPPUNIT_TEST(testCentering0); CPPUNIT_TEST(testTest11); CPPUNIT_TEST_SUITE_END(); public: void testSimple0(); void testCentering0(); void testTest11(); }; void CaptureEffectToAroundKing8Test:: testSimple0() { SimpleState sstate=CsaString( "P1 * * * * * * -KE-OU * \n" "P2 * * * * * * * * -KI\n" "P3 * * * -HI * * * +FU * \n" "P4 * * +KI * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * +OU * * * * * * \n" "P9 * * * +KY * * * * * \n" "P+00KI\n" "P-00AL\n" "-\n").initialState(); NumEffectState state(sstate); { MoveVector moves; CaptureEffectToAroundKing8::generate(state, moves); BOOST_CHECK_EQUAL((size_t)3u, moves.size()); } { MoveVector moves; CaptureEffectToAroundKing8::generate(state, moves); BOOST_CHECK_EQUAL((size_t)3u, moves.size()); } } void CaptureEffectToAroundKing8Test:: testCentering0() { SimpleState sstate=CsaString( "P1-OU-KE-GI * * * * +HI * \n" "P2 * * * * * * * -KI * \n" "P3 * * * * * * * +FU * \n" "P4 * * +KI * * * * -HI * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * +OU * * * * * * \n" "P9 * * * +KY * * * * * \n" "P+00KI\n" "P-00AL\n" "-\n").initialState(); NumEffectState state(sstate); { MoveVector moves; CaptureEffectToAroundKing8::generate(state, moves); BOOST_CHECK_EQUAL((size_t)2u, moves.size()); } } void CaptureEffectToAroundKing8Test:: testTest11() { CsaFile file(OslConfig::testFile("grimbergen_testset/test11.csa")); SimpleState sstate = file.initialState (); const osl::vector moves=file.load().moves(); NumEffectState state(sstate); { MoveVector moves; CaptureEffectToAroundKing8::generate(state, moves); } } CPPUNIT_TEST_SUITE_REGISTRATION(CaptureEffectToAroundKing8Test); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/ntesukiTable.t.cc0000644000000000000000000001245212316770314021256 0ustar rootroot#include "osl/ntesuki/ntesukiTable.h" #include "osl/hash/hashKey.h" #include "osl/move_generator/allMoves.h" #include "osl/move_action/store.h" #include "osl/apply_move/applyMove.h" #include "osl/effect_util/effectUtil.h" #include "osl/move_generator/escape_.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/safeMove.h" #include #include #include using namespace osl; using namespace osl::ntesuki; extern int isShortTest; class NtesukiTableTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(NtesukiTableTest); CPPUNIT_TEST(testCreation); CPPUNIT_TEST(testSize); CPPUNIT_TEST(testAllocate); CPPUNIT_TEST(testFind); CPPUNIT_TEST(testAllocateWithMove); CPPUNIT_TEST(testErase); CPPUNIT_TEST(testGC); #if 0 CPPUNIT_TEST(testPass); #endif CPPUNIT_TEST_SUITE_END(); public: void testCreation(); void testSize(); void testAllocate(); void testFind(); void testAllocateWithMove(); void testErase(); void testGC(); #if 0 void testPass(); #endif }; void NtesukiTableTest::testCreation() { NtesukiTable table(1, 0, false); } void NtesukiTableTest::testSize() { NtesukiTable table(1,0, false); BOOST_CHECK_EQUAL(0u, table.size()); } void NtesukiTableTest::testAllocate() { NtesukiTable table(100,0, false); HashKey k; BOOST_CHECK_EQUAL(0u, table.size()); NtesukiRecord *record = table.allocateRoot(k, PieceStand(), 0); BOOST_CHECK(record); BOOST_CHECK_EQUAL(1u, table.size()); } void NtesukiTableTest::testFind() { NtesukiTable table(100,0, false); const HashKey k; BOOST_CHECK_EQUAL(0u, table.size()); NtesukiRecord *record = table.allocateRoot(k, PieceStand(), 0); BOOST_CHECK(record); NtesukiRecord *newrecord = table.find(k); BOOST_CHECK(newrecord); BOOST_CHECK_EQUAL(record, newrecord); const HashKey kb = k.newHashWithMove(Move::PASS(BLACK)); NtesukiRecord *brecord = table.allocateRoot(kb, PieceStand(), 0); BOOST_CHECK(brecord); BOOST_CHECK(record != brecord); BOOST_CHECK(newrecord != brecord); NtesukiRecord *newrecord2 = table.find(k); BOOST_CHECK_EQUAL(newrecord, newrecord2); #if 0 newrecord = table.find(k); BOOST_CHECK(!newrecord); #endif } void NtesukiTableTest::testAllocateWithMove() { NtesukiTable table(100,0, false); const HashKey k; BOOST_CHECK_EQUAL(0u, table.size()); NtesukiRecord *record = table.allocateRoot(k, PieceStand(), 0); BOOST_CHECK(record); BOOST_CHECK_EQUAL(1u, table.size()); NtesukiMove move(Move(Square(7, 7), Square(7, 6), PAWN, PTYPE_EMPTY, false, BLACK)); NtesukiRecord *record_move = table.allocateWithMove(record, move); BOOST_CHECK(record_move); BOOST_CHECK_EQUAL(record_move, table.findWithMove(record, move)); BOOST_CHECK_EQUAL(2u, table.size()); } void NtesukiTableTest::testErase() { NtesukiTable table(10,0, false); const HashKey k; for (int i = 0; i < 100; ++i) { BOOST_CHECK_EQUAL(0u, table.size()); NtesukiRecord *record = table.allocateRoot(k, PieceStand(), 0); BOOST_CHECK(record); BOOST_CHECK_EQUAL(1u, table.size()); table.erase(k); BOOST_CHECK_EQUAL(0u, table.size()); record = table.find(k); BOOST_CHECK_EQUAL((NtesukiRecord *)NULL, record); } } void generate_valid_moves(const NumEffectState& state, MoveVector& moves) { if (state.inCheck(state.turn())) { GenerateEscapeKing::generate(state, moves); return; } GenerateAllMoves::generate(state.turn(), state, moves); } void NtesukiTableTest::testGC() { NtesukiTable table(100, 10, !isShortTest); NtesukiTable::Table::largeGCCount = 1000; SimpleState sstate(HIRATE); NumEffectState state(sstate); HashKey key; unsigned int correct_size = 0; for (int i = 0; i < 1000; ++i) { BOOST_CHECK_EQUAL(correct_size, table.size()); MoveVector moves; generate_valid_moves(state, moves); unsigned int j; HashKey new_key; for (j = 0; j < moves.size(); j++) { using namespace osl::move_classifier; if (!PlayerMoveAdaptor::isMember(state, moves[j])) continue; new_key = key.newHashWithMove(moves[j]); if(!table.find(new_key)) break; } if (j == moves.size()) { return; } key = new_key; ApplyMoveOfTurn::doMove(state, moves[j]); NtesukiRecord *record = table.allocateRoot(key, PieceStand(), 0); BOOST_CHECK(record); record->addChildCount(i * 4);//Must be multiple of 4 ++correct_size; if (correct_size > 100) correct_size = 11; BOOST_CHECK_EQUAL(correct_size, table.size()); } } #if 0 void NtesukiTableTest::testPass() { NtesukiTable table(100, 0, false); const HashKey k; BOOST_CHECK_EQUAL(0u, table.size()); NtesukiRecord *record = table.allocateRoot(k, PieceStand(), 0); BOOST_CHECK(record); BOOST_CHECK_EQUAL(1u, table.size()); NtesukiRecord *record_pass = table.allocatePass(record, 0); BOOST_CHECK(record_pass); BOOST_CHECK_EQUAL(2u, table.size()); BOOST_CHECK_EQUAL(record_pass, record->getPass()); NtesukiRecord *record_pass_pass = table.allocatePass(record_pass, 0); BOOST_CHECK(record_pass_pass); BOOST_CHECK_EQUAL(2u, table.size()); BOOST_CHECK_EQUAL(record, record_pass_pass); } #endif CPPUNIT_TEST_SUITE_REGISTRATION(NtesukiTableTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/ntesuki/rzone.t.cc0000644000000000000000000000600312316770314017754 0ustar rootroot#include "osl/ntesuki/rzone.h" #include "osl/record/csaString.h" #include #include #include using namespace osl::ntesuki; namespace osl { class RzoneTest : public CppUnit::TestFixture { CPPUNIT_TEST_SUITE(RzoneTest); CPPUNIT_TEST(testConstruct); CPPUNIT_TEST(testTest); CPPUNIT_TEST(testAdd); CPPUNIT_TEST(testSub); CPPUNIT_TEST(testUpdate); CPPUNIT_TEST_SUITE_END(); public: void testConstruct() { { SimpleState sstate(HIRATE); NumEffectState state(sstate); Rzone rzone(state, BLACK); } { SimpleState sstate = CsaString( "P1 * * * * * * * -OU * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * +FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * * * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState();; NumEffectState state(sstate); Rzone rzone(state, BLACK); BOOST_CHECK(!rzone.any()); } } void testTest() { SimpleState sstate(HIRATE); NumEffectState state(sstate); Rzone rzone(state, BLACK); for (int x = 1; x <= 9; ++x) { for (int y = 1; y <= 9; ++y) { Square pos(x, y); if (x ==5 && y == 9) { BOOST_CHECK(rzone.test(pos)); } else { BOOST_CHECK(!rzone.test(pos)); } } } } void testAdd() { Rzone rzone1(Square(5,9)); Rzone rzone2(Square(5,8)); Rzone rzone = rzone1 + rzone2; BOOST_CHECK(rzone.test(Square(5,8))); BOOST_CHECK(rzone.test(Square(5,9))); BOOST_CHECK(!rzone.test(Square(4,8))); BOOST_CHECK(!rzone.test(Square(4,9))); BOOST_CHECK(!rzone.test(Square(6,8))); BOOST_CHECK(!rzone.test(Square(6,9))); BOOST_CHECK(!rzone.test(Square(5,7))); } void testSub() { Rzone rzone1(Square(5,9)); Rzone rzone2(Square(5,8)); Rzone rzone = rzone1 + rzone2; bool exception_handled = false; try { Rzone rzone0 = rzone2 - rzone1; } catch (DfpnError& e) { exception_handled = true; } BOOST_CHECK(exception_handled); Rzone rzone0 = rzone - rzone1; BOOST_CHECK(rzone0 == rzone2); } void testUpdate() { Rzone rzone1(Square(5,9)); Rzone rzone2(Square(5,8)); Rzone rzone3(Square(5,7)); rzone1 = rzone1 + rzone3; rzone2 = rzone2 + rzone3; Rzone rzone = rzone1.update(rzone2); BOOST_CHECK(!rzone.test(Square(5,7))); BOOST_CHECK(rzone.test(Square(5,8))); BOOST_CHECK(!rzone.test(Square(5,9))); BOOST_CHECK(rzone1.test(Square(5,7))); BOOST_CHECK(rzone1.test(Square(5,8))); BOOST_CHECK(rzone1.test(Square(5,9))); } }; } // namespace osl CPPUNIT_TEST_SUITE_REGISTRATION(osl::RzoneTest); // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/move_generator/0000755000000000000000000000000012316770314017401 5ustar rootrootlibosl-0.8.0.orig/full/test/move_generator/safeDropMajorPiece.t.cc0000644000000000000000000000776312316770314023671 0ustar rootroot#include "osl/move_generator/safeDropMajorPiece.h" #include "osl/move_generator/move_action.h" #include "osl/csa.h" #include #include using namespace osl; using namespace osl::move_action; using namespace osl::move_generator; BOOST_AUTO_TEST_CASE(TestSafeMajorPieceRookBlack) { NumEffectState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * +OU * * * * * * * \n" "P9 * * * * * * * * * \n" "P+00HI\n" "P-00AL\n" "-\n").initialState(); { MoveVector moves; { Store store(moves); SafeDropMajorPiece::generate<>(state, store); } BOOST_CHECK(23u == moves.size()); for (size_t i = 0; i < moves.size(); i++) { BOOST_CHECK(moves[i].ptype() == ROOK); BOOST_CHECK(moves[i].from().isPieceStand()); BOOST_CHECK(moves[i].to().y() <= 3); BOOST_CHECK(!state.hasEffectAt(alt(state.turn()), moves[i].to())); } } } BOOST_AUTO_TEST_CASE(TestSafeMajorPieceRookWhite) { NumEffectState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * +OU * * * * * * * \n" "P9 * * * * * * * * * \n" "P-00HI\n" "P+00AL\n" "-\n").initialState(); { MoveVector moves; { Store store(moves); SafeDropMajorPiece::generate<>(state, store); } BOOST_CHECK(18u == moves.size()); for (size_t i = 0; i < moves.size(); i++) { BOOST_CHECK(moves[i].ptype() == ROOK); BOOST_CHECK(moves[i].from().isPieceStand()); BOOST_CHECK(moves[i].to().y() >= 7); BOOST_CHECK(!state.hasEffectAt(alt(state.turn()), moves[i].to())); } } } BOOST_AUTO_TEST_CASE(TestSafeMajorPieceBishopBlack) { NumEffectState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * +OU * * * * * * * \n" "P9 * * * * * * * * * \n" "P+00KA\n" "P-00AL\n" "-\n").initialState(); { MoveVector moves; { Store store(moves); SafeDropMajorPiece::generate<>(state, store); } BOOST_CHECK(23u == moves.size()); for (size_t i = 0; i < moves.size(); i++) { BOOST_CHECK(moves[i].ptype() == BISHOP); BOOST_CHECK(moves[i].from().isPieceStand()); BOOST_CHECK(moves[i].to().y() <= 3); BOOST_CHECK(!state.hasEffectAt(alt(state.turn()), moves[i].to())); } } } BOOST_AUTO_TEST_CASE(TestSafeMajorPieceBishopWhite) { NumEffectState state=CsaString( "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * +OU * * * * * * * \n" "P9 * * * * * * * * * \n" "P-00KA\n" "P+00AL\n" "-\n").initialState(); { MoveVector moves; { Store store(moves); SafeDropMajorPiece::generate<>(state, store); } BOOST_CHECK(18u == moves.size()); for (size_t i = 0; i < moves.size(); i++) { BOOST_CHECK(moves[i].ptype() == BISHOP); BOOST_CHECK(moves[i].from().isPieceStand()); BOOST_CHECK(moves[i].to().y() >= 7); BOOST_CHECK(!state.hasEffectAt(alt(state.turn()), moves[i].to())); } } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/move_generator/attackToPinned.t.cc0000644000000000000000000000346412316770314023071 0ustar rootroot#include "osl/move_generator/attackToPinned.h" #include "osl/move_generator/allMoves.h" // #include "osl/move_generator/move_action.h" #include "osl/csa.h" #include #include #include using namespace osl; using namespace osl::move_generator; using namespace osl::move_action; BOOST_AUTO_TEST_CASE(AttackToPinnedTestSimple) { { SimpleState state= CsaString( "P1+NY+RY * * -KI * -OU-KE *\n" "P2 * * * * * -GI-KI-FU *\n" "P3 * +TO * * * * * * +KA\n" "P4 * * +FU+UM * * * * *\n" "P5 * * -KE-FU-FU * * * -FU\n" "P6+KE * * +FU+GI-FU * * +FU\n" "P7 * * * * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * +KY * -NG\n" "P+00HI00KI00KE00KY00FU00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAttackToPinned::generate(BLACK,eState,store); } // æ­©ã‚’æ”»ã‚る手も生æˆã™ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(1,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,3),PAWN,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(1,2),GOLD,BLACK))); // 金を攻ã‚ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(2,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,3),GOLD,BLACK))); // 利ãã‚’ãµã•ã„ã§ã„ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(3,3),PAWN,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,3),GOLD,BLACK))); // 銀を攻ã‚ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(4,3),PAWN,BLACK))); // 金を攻ã‚ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(5,2),PAWN,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(6,4),Square(7,3),PBISHOP,PTYPE_EMPTY,false,BLACK))); } } libosl-0.8.0.orig/full/test/move_generator/addEffect8.t.cc0000644000000000000000000011306712316770314022117 0ustar rootroot#include "osl/move_generator/addEffect8.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/move_action.h" #include "osl/csa.h" #include "osl/effect_util/effectUtil.h" #include "osl/additionalEffect.h" #include "osl/oslConfig.h" #include #include #include #include using namespace osl; using namespace osl::move_generator; using namespace osl::move_action; static bool isAddEffect8Move(const NumEffectState& state_org,Move move); static bool mayNotGeneratedMove(const NumEffectState& savedState,Move move); BOOST_AUTO_TEST_CASE(AddEffect8TestOne) { { NumEffectState state(CsaString( "P1-KY-KE-OU-KI * * * * +RY\n" "P2 * * * -KI * * * * * \n" "P3 * +GI-FU-FU * -FU * -FU * \n" "P4-FU * * * -FU+FU * * +FU\n" "P5 * +KE+KE-KA * * -FU+FU * \n" "P6+FU * -KY * +FU * * * * \n" "P7 * * * +FU+KA * +FU * * \n" "P8 * * * +GI * * * * * \n" "P9+KY+OU * * +KI * * * -RY\n" "P+00KI00GI00KY\n" "P-00GI00KE00FU00FU00FU00FU\n" "-\n" ).initialState()); BOOST_CHECK(mayNotGeneratedMove(state,Move(Square(7,6),Square(7,8),LANCE,PTYPE_EMPTY,false,WHITE))); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(state.turn(),state,store); } BOOST_CHECK(!moves.isMember(Move(Square(7,6),Square(7,8),LANCE,PTYPE_EMPTY,false,WHITE)) || (std::cerr << moves << std::endl,0)); } { NumEffectState state(CsaString( "P1-KY * * * * * * -KE-KY\n" "P2-HI * * * * * -KI-OU * \n" "P3 * * +UM-FU * * -KI-FU * \n" "P4-FU * -FU * * -GI-FU * -FU\n" "P5 * * * * -FU-FU * +FU * \n" "P6+FU * +FU+FU * * +FU * +FU\n" "P7 * +FU+KE+GI+GI+FU * -UM * \n" "P8 * * +KI * +OU * -KI * * \n" "P9+KY+HI * * * * * * +KY\n" "P+00GI00KE00KE00FU00FU\n" "-\n" ).initialState()); BOOST_CHECK(mayNotGeneratedMove(state,Move(Square(3,8),Square(3,9),GOLD,PTYPE_EMPTY,false,WHITE))); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(state.turn(),state,store); } BOOST_CHECK(!moves.isMember(Move(Square(3,8),Square(3,9),GOLD,PTYPE_EMPTY,false,WHITE)) || (std::cerr << moves << std::endl,0)); } { NumEffectState state(CsaString( "P1-KY-KE * -KI * -KA-FU * +RY\n" "P2 * +GI-GI * -FU * * * * \n" "P3 * -OU * -FU * -FU * * -FU\n" "P4-FU-RY+KE-KY * * * * * \n" "P5 * * +KI * +UM * * * * \n" "P6+FU * +FU * * * * * * \n" "P7 * * * * +OU+FU+FU * +FU\n" "P8 * * * * * * * * * \n" "P9+KY * * * * +KI+GI+KE+KY\n" "P+00KI00GI00FU00FU00FU00FU\n" "P-00KE00FU00FU00FU\n" "-\n").initialState()); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(state.turn(),state,store); } BOOST_CHECK(!moves.isMember(Move(Square(6,4),Square(6,7),LANCE,PTYPE_EMPTY,false,WHITE)) || (std::cerr << moves << std::endl,0)); } } BOOST_AUTO_TEST_CASE(AddEffect8TestDropShort) { { SimpleState state= CsaString( "P1+NY+TO * * * * -OU-KE-KY\n" "P2 * * * * * -GI-KI * *\n" "P3 * +RY * * +UM * -KI-FU-FU\n" "P4 * * +FU-FU * * * * *\n" "P5 * * -KE * +FU * * +FU *\n" "P6+KE * * +FU+GI-FU * * +FU\n" "P7 * * * * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00HI00KA00KI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(4,3),PAWN,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(1,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,4),KNIGHT,BLACK))); // 王手ã¯produceã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(2,2),GOLD,BLACK))); // 二歩 BOOST_CHECK(!moves.isMember(Move(Square(2,2),PAWN,BLACK))); // 玉以外ã‹ã‚‰å–られる飛車ã¯ç”Ÿæˆã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(2,2),ROOK,BLACK))); // 玉以外ã‹ã‚‰å–られãªã„角生æˆã™ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(4,1),BISHOP,BLACK))); } { SimpleState state= CsaString( "P1+NY+TO * * * * -OU * -KY\n" "P2 * * * * * -KE-KI * * \n" "P3 * * * * +UM * * -FU-FU\n" "P4 * * +FU-FU * * * * -KI\n" "P5 * * -KE * +FU * * +FU-GI\n" "P6+KE * * +FU+GI-FU+HI * +FU\n" "P7 * * * * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00HI00KA00KI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } // pinnedãªã‚‰é£›è»Šè§’ã‚‚dropã™ã‚‹ BOOST_CHECK(moves.isMember(Move(Square(2,2),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,1),BISHOP,BLACK))); } } BOOST_AUTO_TEST_CASE(AddEffect8TestDropLong) { { SimpleState state= CsaString( "P1-KY * * * * -OU * -KE-KY\n" "P2 * -HI * * * * -KI * * \n" "P3-FU * * * +KI-GI * -FU-FU\n" "P4 * * -FU-FU * * -FU * * \n" "P5 * * * -KE * * * +FU * \n" "P6+GI-FU+FU * * * +FU * * \n" "P7+FU * * +FU-KI * * * +FU\n" "P8 * +OU+KI * -FU * * * * \n" "P9+KY+KE * * -RY * * * +KY\n" "P+00KA00GI00GI00KE00FU00FU00FU00FU\n" "P-00KA\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } BOOST_CHECK(!moves.isMember(Move(Square(4,6),BISHOP,WHITE)) || (std::cerr << moves << std::endl,0) ); } { SimpleState state= CsaString( "P1+NY+TO * * * * -OU-KE *\n" "P2 * * * * * -GI-KI * -KY\n" "P3 * +RY * * * * * -FU-FU\n" "P4 * * +FU-FU * * * * *\n" "P5 * * -KE * +FU * * +FU *\n" "P6+KE * * +FU+GI-FU * * +FU\n" "P7 * * -UM * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00HI00KA00KI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00KI00KI00KY00FU00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(!moves.isMember(Move(Square(2,2),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,2),LANCE,BLACK))); // 飛車ã®ãŸã æ¨ã¦ BOOST_CHECK(!moves.isMember(Move(Square(4,3),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,3),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,4),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,4),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,5),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,5),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(5,2),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(6,2),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(7,2),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(8,2),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(9,2),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(1,1),BISHOP,BLACK))); // BOOST_CHECK(!moves.isMember(Move(Square(3,3),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,4),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(4,3),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(5,4),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(6,5),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(7,6),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(8,7),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(9,8),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,1),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(2,4),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(1,5),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(5,1),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(5,2),BISHOP,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(6,3),BISHOP,BLACK))); // directç³» BOOST_CHECK(moves.isMember(Move(Square(1,1),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(3,3),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,3),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,4),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,4),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,5),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,5),LANCE,BLACK))); // 2ã¤ä»¥ä¸Šã¯ç”Ÿæˆã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(3,6),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(3,7),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(3,8),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(3,9),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,6),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,7),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,8),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,9),LANCE,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(5,3),BISHOP,BLACK))); // 王手ã¯produceã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(2,2),BISHOP,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(4,1),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(5,1),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(6,1),ROOK,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(7,1),ROOK,BLACK))); // 盤外ã¸ã®åˆ©ã BOOST_CHECK(!moves.isMember(Move(Square(4,1),LANCE,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(6,2),BISHOP,BLACK))); } } BOOST_AUTO_TEST_CASE(AddEffect8TestShort) { { SimpleState state= CsaString( "P1+NY+TO * * * * -OU-KE-KY\n" "P2 * * * * * -GI-KI * *\n" "P3 * +RY * * +UM * -KI-FU-FU\n" "P4 * * +FU-FU * * * * *\n" "P5 * * -KE * +FU * * +FU *\n" "P6+KE * * +FU+GI-FU * * +FU\n" "P7 * * -UM * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00HI00KI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(4,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(3,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(1,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,4),KNIGHT,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,3),PAWN,BLACK))); // 王手ã¯produceã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(4,3),KNIGHT,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(2,2),GOLD,BLACK))); } { SimpleState state= CsaString( "P1+NY * * * * * -OU-KE-KY\n" "P2 * +HI * * -FU-GI-KI-FU *\n" "P3 * +RY * * +UM-FU-KI * -FU\n" "P4 * * +FU-FU * * * +FU *\n" "P5 * * -KE * +FU+KY * * *\n" "P6+KE * +KA+FU+GI * * * +FU\n" "P7 * * * * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00KI00KE00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(!moves.isMember(Move(Square(2,4),Square(2,3),PAWN,PTYPE_EMPTY,false,BLACK))); } } BOOST_AUTO_TEST_CASE(AddEffect8TestLong) { { SimpleState state= CsaString( "P1 * * * * +RY * * * -KY\n" "P2 * * * -HI * * * * * \n" "P3-KY * * -OU-KA * +KI * * \n" "P4 * -FU-FU-GI-KI * * * * \n" "P5 * * * -KE-FU-FU-FU * * \n" "P6-KY * +FU+GI * * * * * \n" "P7+KE+FU * +KI * * * * +FU\n" "P8+FU+OU+KI+KA-GI * * * * \n" "P9 * +KE * * * * * * +KY\n" "P+00GI00KE00FU00FU00FU00FU00FU00FU00FU\n" "P-00FU00FU\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } // 2é‡ã®è¿½åŠ åˆ©ã BOOST_CHECK(moves.isMember(Move(Square(6,2),Square(9,2),ROOK,PTYPE_EMPTY,false,WHITE))); } { SimpleState state= CsaString( "P1 * * * * * * * +TO+RY\n" "P2 * * * * * * * * * \n" "P3+OU+NK * +TO * * * * * \n" "P4+GI+KI * * * * * * * \n" "P5-KI * * * * +GI * * * \n" "P6 * * -UM * +FU * +TO-KI * \n" "P7 * * * * * * -NK-NY * \n" "P8 * * * * * * -NY-OU-KI\n" "P9-RY * * * * * * * * \n" "P+00KA00KY00KY00FU00FU00FU00FU\n" "P-00GI00GI00KE00KE00FU00FU00FU00FU00FU00FU00FU00FU00FU00FU\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } // open,直接利ãを減らã—ã¦ã„ã‚‹ãŒï¼Œç”Ÿæˆã™ã‚‹ï¼Ž BOOST_CHECK(moves.isMember(Move(Square(9,5),Square(8,6),GOLD,PTYPE_EMPTY,false,WHITE))); } { SimpleState state= CsaString( "P1 * * * * * * * +TO+RY\n" "P2 * * * * * * * * * \n" "P3+OU+NK * +TO * * * * * \n" "P4+GI+KI * * * * * * * \n" "P5-GI * * * * +GI * * * \n" "P6 * * -UM * +FU * +TO-KI * \n" "P7 * * * * * * -NK-NY * \n" "P8 * * * * * * -NY-OU-KI\n" "P9-RY * * * * * * * * \n" "P+00KA00KY00KY00FU00FU00FU00FU\n" "P-00KI00GI00KE00KE00FU00FU00FU00FU00FU00FU00FU00FU00FU00FU\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } // open BOOST_CHECK(moves.isMember(Move(Square(9,5),Square(8,6),SILVER,PTYPE_EMPTY,false,WHITE))); } { SimpleState state= CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * * * * -KI-OU * \n" "P3 * * -FU * * -KI * * * \n" "P4-FU-HI * * -FU * -FU+GI-FU\n" "P5 * -FU+FU * +GI-FU * -FU+KY\n" "P6+FU * * * * * +KE * * \n" "P7 * +FU * -TO * +FU+FU+FU * \n" "P8+KY * * * * +KI+KI+GI * \n" "P9 * +KE-UM * +KA * * +KE+OU\n" "P+00FU\n" "P-00HI00GI00FU00FU\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } // 飛車角ã®è¿½åŠ åˆ©ãã¯å–られるã¨ã“ã‚ã«ã¯ç§»å‹•ã—ã¦ã‚‚良ㄠBOOST_CHECK(moves.isMember(Move(Square(5,9),Square(6,8),BISHOP,PTYPE_EMPTY,false,BLACK))); } { SimpleState state= CsaString( "P1 * +RY * * -FU-OU * -KE-KY\n" "P2 * * * * +FU-GI-KI * * \n" "P3-FU * -FU-FU * -KI * * * \n" "P4 * * * * * -FU+FU * -FU\n" "P5 * * * * * * * * * \n" "P6 * * +FU+FU * * +KY * * \n" "P7+FU+FU * * * +FU-UM * +FU\n" "P8 * +KI * +GI+OU * * * * \n" "P9+KY+KE * * +KE * * -RY+KY\n" "P+00KA00GI00FU\n" "P-00KI00GI00KE00FU00FU00FU\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(2,9),Square(2,7),PROOK,PTYPE_EMPTY,false,WHITE))); } { SimpleState state= CsaString( "P1-KY-KE * -KI * * -GI+RY-KY\n" "P2 * * * -OU * * -KI * * \n" "P3-FU * -GI-FU-FU-FU * * -FU\n" "P4 * * -FU * * * * * * \n" "P5 * * * * +KA * * * * \n" "P6 * * * * * * * * * \n" "P7+FU * +FU+FU+FU+FU+FU * +FU\n" "P8 * +GI+KI * * * * * * \n" "P9+KY+KE * * +OU+KI+GI * +KY\n" "P+00KE00FU00FU\n" "P-00HI00KA00KE00FU00FU00FU\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(5,5),Square(6,4),BISHOP,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(5,5),Square(4,4),BISHOP,PTYPE_EMPTY,false,BLACK))); // 飛車角ã¯åˆ©ãã®ã‚ã‚‹ã¨ã“ã‚ã«ã¯ç§»å‹•ã—ã¦ã‚‚良ㄠ} { SimpleState state= CsaString( "P1+NY+TO * * * * -OU-KE-KY\n" "P2 * * * * * -GI-KI * *\n" "P3 * +RY * * +UM * -KI-FU-FU\n" "P4 * * +FU-FU * * * * *\n" "P5 * * -KE * +FU * * +FU *\n" "P6+KE * * +FU+GI-FU * * +FU\n" "P7 * * -UM * * * * * *\n" "P8 * * * * * * * * * \n" "P9 * +OU * -GI * * * * -NG\n" "P+00HI00KI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00KI00KY00FU00FU\n" "P-00AL\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(5,3),Square(5,2),PBISHOP,PTYPE_EMPTY,false,BLACK))|| (std::cerr << moves << std::endl,0) ); BOOST_CHECK(moves.isMember(Move(Square(5,3),Square(4,3),PBISHOP,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(8,3),Square(8,2),PROOK,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(8,3),Square(7,2),PROOK,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(8,3),Square(9,2),PROOK,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(2,2),ROOK,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(2,2),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,5),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,4),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(4,3),LANCE,BLACK))); // 王手ã¯produceã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(5,3),Square(4,2),PBISHOP,PTYPE_EMPTY,false,BLACK))); // 盤外ã«åˆ©ãを付ã‘る手ã¯ç”Ÿæˆã—ãªã„ BOOST_CHECK(!moves.isMember(Move(Square(5,3),Square(6,2),PBISHOP,PTYPE_EMPTY,false,BLACK))); // 利ããŒblockã•れã¦ã„ã‚‹ã“ã¨ã¯ãƒã‚§ãƒƒã‚¯ã™ã‚‹ BOOST_CHECK(!moves.isMember(Move(Square(5,3),Square(4,4),PBISHOP,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(!moves.isMember(Move(Square(3,4),LANCE,BLACK))); } } BOOST_AUTO_TEST_CASE(AddEffect8TestAdditional) { { SimpleState state= CsaString( "P1-KY-KE * -KI * * * * +RY\n" "P2 * -OU-GI-KI * * * * * \n" "P3 * * -FU-FU * -FU * -FU * \n" "P4-FU+FU * * -FU-GI * * +FU\n" "P5 * * * * * * -FU+FU * \n" "P6+FU * * * +FU+FU * * * \n" "P7 * +GI+KE+FU+KA * +FU * * \n" "P8 * * +OU+GI * * * * * \n" "P9+KY * * * +KI * * * -RY\n" "P+00KE00KY\n" "P-00KA00KI00KE00KY00FU00FU00FU\n" "+\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(BLACK,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(8,5),LANCE,BLACK))); BOOST_CHECK(moves.isMember(Move(Square(8,6),LANCE,BLACK))); } { SimpleState state= CsaString( "P1-KY-KE * -KI * * * * +RY\n" "P2 * -OU-GI * -KI * * * * \n" "P3 * -FU-FU-FU-FU-FU * -FU * \n" "P4-FU * * * +KE-GI * * +FU\n" "P5 * +FU * * * * -FU+FU * \n" "P6+FU * -KY * +FU+FU * * * \n" "P7 * +GI+KA+FU * * +FU * * \n" "P8 * +OU+KI+GI * * * * * \n" "P9+KY+KE * * +KI * * * -RY\n" "P+00KA\n" "P-00KE00KY00FU00FU\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } BOOST_CHECK(moves.isMember(Move(Square(7,4),LANCE,WHITE))); } { SimpleState state= CsaString( "P1-KY-KE * -KI * * * * +RY\n" "P2 * -OU-GI * -KI * * * * \n" "P3 * -FU * -FU-FU-FU * -FU * \n" "P4 * * * * +KE-GI * * +FU\n" "P5 * +FU-FU * * * -FU+FU * \n" "P6-FU * * * +FU+FU * * * \n" "P7+FU+GI+KA+FU * * +FU * * \n" "P8 * +OU+KI+GI * * * * * \n" "P9+KY+KE * * +KI * * * -RY\n" "P+00KA\n" "P-00KE00KY00KY00FU00FU\n" "-\n" ).initialState(); NumEffectState eState(state); MoveVector moves; { move_action::Store store(moves); GenerateAddEffect8::generate(WHITE,eState,store); } BOOST_CHECK(!moves.isMember(Move(Square(7,4),LANCE,WHITE))); BOOST_CHECK(moves.isMember(Move(Square(7,6),LANCE,WHITE))); BOOST_CHECK(moves.isMember(Move(Square(9,4),LANCE,WHITE))); } } static bool isCheckMove(NumEffectState& state,Move move){ // 自分ã§å‹•ã„ã¦å…ƒã®positionã«åˆ©ãã‚’ã¤ã‘る手ã¯å«ã¾ãªã„ Player pl=state.turn(); Square kingSquare=state.kingSquare(alt(pl)); NumEffectState next_state(state); next_state.makeMove(move); // ãªã‚‹ã¹ã王手ã¯ç”Ÿæˆã—ãŸããªã„ãŒï¼Œç”Ÿæˆã—ã¦ã—ã¾ã†ã“ã¨ã‚‚ã‚る. return next_state.hasEffectAt(pl,kingSquare); } /** * 作られãªã„å¯èƒ½æ€§ã®ã‚ã‚‹move * 作られるå¯èƒ½æ€§ã‚‚ã‚る. */ static bool mayNotGeneratedMove(const NumEffectState& savedState,Move move){ NumEffectState state = savedState; Player pl=state.turn(); Square kingSquare=state.kingSquare(alt(pl)); Ptype ptype=move.ptype(); // if(move.isPromotion()) return true; if(move.capturePtype()!=PTYPE_EMPTY) return true; // 王ãŒå‹•ã„ãŸæ™‚ã¯ç”Ÿæˆã—ãªã„ã“ã¨ãŒã‚る. if(ptype==KING) return true; // 飛車角ã®dropã¯2ã¤ã—ã‹ç”Ÿæˆã—ãªã„ã®ã§ if((ptype==ROOK || ptype==BISHOP) && !move.from().isOnBoard()) return true; // 飛車角歩ãŒpromoteå¯èƒ½ãªã®ã«promoteã—ãªã„手ã¯ç”Ÿæˆã—ãªã„ if(move.from().isOnBoard() && (ptype==ROOK || ptype==BISHOP || ptype==PAWN) && (move.from().canPromote(pl) || move.to().canPromote(pl))) return true; // 二段目ã®é¦™è»Šã¯å¿…ãšæˆã‚‹ if(move.from().isOnBoard() && ptype==LANCE && ((pl==BLACK && move.to().y()==2) || (pl==WHITE && move.to().y()==8))) return true; state.makeMove(move); // ãªã‚‹ã¹ã王手ã¯ç”Ÿæˆã—ãŸããªã„ãŒï¼Œç”Ÿæˆã—ã¦ã—ã¾ã†ã“ã¨ã‚‚ã‚る. if(state.hasEffectAt(pl,kingSquare)) return true; for(int i=0;i<8;i++){ Direction d=static_cast(i); Square pos=kingSquare+Board_Table.getOffsetForBlack(d); if(!pos.isOnBoard()) continue; if(savedState.countEffect(pl,pos)>state.countEffect(pl,pos)) continue; if(effect_util::AdditionalEffect::count2(savedState,pos,pl)> effect_util::AdditionalEffect::count2(state,pos,pl)){ // 元々ã®é§’ãŒåˆ©ãã®ã‚ã£ãŸã¨ã“ã‚ã«å‹•ã„ã¦ã‚‚利ãã‚’æŒã¤ãŒï¼Œè¿½åŠ ãŒå¤‰ã‚る例 // 元々ã®é§’ãŒç›´æŽ¥åˆ©ãã‚’æŒã£ã¦ã„ãŸã®ã‚’間接利ãã«å¤‰ã‚る例も // ã“ã‚Œã¯æœªå¯¾å¿œ if(move.from().isOnBoard() && savedState.hasEffectByPiece(savedState.pieceAt(move.from()),pos)){ return true; } continue; } else if(effect_util::AdditionalEffect::count2(savedState,pos,pl)== effect_util::AdditionalEffect::count2(state,pos,pl)) continue; else return false; } return true; } /** * 相手ã®8è¿‘å‚ã«åˆ©ãã‚’ã¤ã‘る手ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯. * 欲ã—ã„仕様ã¯8è¿‘å‚ã®ã©ã“ã‹ã«ã“れã¾ã§åˆ©ãã®ãªã‹ã£ãŸé§’ã®åˆ©ããŒè¿½åŠ ã•れるã“ã¨ï¼Ž * 全体ã¨ã—ã¦ãã®ãƒžã‚¹ã¸ã®åˆ©ããŒæ¸›ã£ã¦ã‚‚å¯ï¼Ž * 王手ã¯é™¤å¤–ã™ã‚‹ï¼Ž * 王ã«ã‚ˆã£ã¦8è¿‘å‚ã«åˆ©ãã‚’ã¤ã‘る手も除外ã™ã‚‹ï¼Ž * 自殺手ã¯ç”Ÿæˆã—ã¦ã—ã¾ã†ã“ã¨ã¯ã‚ã£ã¦ã‚‚よã„. * @param state - moveå‰ã®å±€é¢ * @param move - ãƒã‚§ãƒƒã‚¯ã®å¯¾è±¡ã®æ‰‹ */ static bool isAddEffect8Move(const NumEffectState& state_org,Move move){ // 自分ã§å‹•ã„ã¦å…ƒã®positionã«åˆ©ãã‚’ã¤ã‘る手ã¯å«ã¾ãªã„ NumEffectState state = state_org; Player pl=state.turn(); Square kingSquare=state.kingSquare(alt(pl)); NumEffectState savedState(state); Ptype ptype=move.ptype(); if(move.isPromotion()) return false; if(move.capturePtype()!=PTYPE_EMPTY) return false; if(isCheckMove(state,move)) return false; // 飛車角ã¯ç›¸æ‰‹ã®åˆ©ãã®ã‚ã‚‹ã¨ã“ã‚ã«ã¯dropã—ãªã„ if(!move.from().isOnBoard() && (ptype==ROOK || ptype==BISHOP) && state.hasEffectByNotPinnedAndKing(alt(pl),move.to())) return false; state.makeMove(move); for(int i=0;i<8;i++){ Direction d=static_cast(i); Square pos=kingSquare+Board_Table.getOffsetForBlack(d); if(!pos.isOnBoard()){ PtypeO ptypeO=newPtypeO(pl,ptype); // 盤外ã§ã‚ã£ã¦ã‚‚短ã„利ããŒå¢—ãˆãŸã‚‰OK Square from=move.from(); Square to=move.to(); if(move.from().isOnBoard() && (abs(from.x()-pos.x())>1 || abs(from.y()-pos.y())>1 || !Ptype_Table.getEffect(ptypeO,Offset32(pos,move.from())).hasUnblockableEffect()) && abs(to.x()-pos.x())<=1 && abs(to.y()-pos.y())<=1 && Ptype_Table.getEffect(ptypeO,Offset32(pos,move.to())).hasUnblockableEffect() && (!(ptype==ROOK || ptype==BISHOP || ptype==PAWN) || !(move.from().canPromote(pl) || move.to().canPromote(pl)))){ return true; } continue; } if(state.hasEffectAt(pl,pos) && (effect_util::AdditionalEffect::count2(savedState,pos,pl)< effect_util::AdditionalEffect::count2(state,pos,pl))){ return true; } if(state.hasEffectAt(pl,pos) && (effect_util::AdditionalEffect::count(savedState,pl,pos)< effect_util::AdditionalEffect::count(state,pl,pos))){ return true; } for(int num=0;num<40;num++){ Piece p=state.pieceOf(num); if(p.ptype()==KING) continue; if(p.isOnBoardByOwner(pl) && state.hasEffectByPiece(p,pos)){ if(!savedState.hasEffectByPiece(savedState.pieceOf(num),pos) && ((p.square()!=move.to() && move.to() != pos)|| !move.from().isOnBoard() || !(ptype==ROOK || ptype==BISHOP || ptype==PAWN) || !(move.from().canPromote(pl) || move.to().canPromote(pl)))){ // ãŸã æ¨ã¦ã®é£›è»Šï¼Œè§’ã®dropã¯ç”Ÿæˆã—ãªã„ return true; } // PROOKãŒæ–œã‚ã«å‹•ã„ã¦æ–œã‚ã«åˆ©ãã‚’ã¤ã‘ã‚‹å ´åˆã¯ // 元々長ã„利ããŒã‚ã‚‹å ´åˆã‚‚ã‚ã‚‹ãŒï¼Œå¸¸ã«trueã«ã™ã‚‹ï¼Ž if(p.square()==move.to() && ptype==PROOK && abs(move.from().x()-move.to().x())==1 && abs(move.from().y()-move.to().y())==1 && abs(move.to().x()-pos.x())==1 && abs(move.to().y()-pos.y())==1){ return true; } } } } return false; } BOOST_AUTO_TEST_CASE(AddEffect8TestIsAddEffect8) { { SimpleState state= CsaString( "P1-KY-KE-OU-KY+RY * * * * \n" "P2 * * -KI-KI * * * * * \n" "P3 * +GI-FU * * +TO * -FU * \n" "P4-FU * * * -FU * * * +FU\n" "P5 * +KE * -KA * * -FU+FU * \n" "P6+FU * +KY * +FU * * * * \n" "P7 * +OU * +FU+KA * +FU * * \n" "P8 * * * +GI * * * * * \n" "P9+KY * * * +KI * * * -RY\n" "P+00GI00KE00FU00FU\n" "P-00KI00GI00KE00FU00FU00FU00FU\n" "+\n" ).initialState(); NumEffectState eState(state); BOOST_CHECK(isAddEffect8Move(eState,Move(Square(5,1),Square(4,2),PROOK,PTYPE_EMPTY,false,BLACK))); } { SimpleState state= CsaString( "P1 * * +RY-KE * * * -KE-KY\n" "P2 * * * +GI * -OU-KI * * \n" "P3-FU * -FU-FU * -KI * * * \n" "P4 * * * -UM * -FU+FU * -FU\n" "P5+OU * * * * * * * * \n" "P6 * * +FU-KI * * +KY * * \n" "P7+FU+FU * * +FU+FU * * +FU\n" "P8 * +KI * * * * * * * \n" "P9+KY+KE * * -RY * * * +KY\n" "P+00GI00KE00FU\n" "P-00KA00GI00GI00FU00FU00FU00FU00FU\n" "+\n" ).initialState(); NumEffectState eState(state); // BOOST_CHECK(!isAddEffect8Move(eState,Move(Square(3,4),Square(3,3),PAWN,PTYPE_EMPTY,false,BLACK))); } } static bool isAddEffect8Drop(const NumEffectState& state_org,Move move){ // 自分ã§å‹•ã„ã¦å…ƒã®positionã«åˆ©ãã‚’ã¤ã‘る手ã¯å«ã¾ãªã„ if(!move.isDrop()) return false; NumEffectState state = state_org; Player pl=state.turn(); Square kingSquare=state.kingSquare(alt(pl)); NumEffectState savedState(state); state.makeMove(move); if(state.hasEffectAt(pl,kingSquare)) return false; // ãŸã æ¨ã¦ã®é£›è»Šè§’ if(!move.from().isOnBoard() && (move.ptype()==ROOK || move.ptype()==BISHOP) && state.hasEffectByNotPinnedAndKing(alt(pl),move.to())) return false; for(int i=0;i<8;i++){ Direction d=static_cast(i); Square pos=kingSquare+Board_Table.getOffsetForBlack(d); if(!pos.isOnBoard()) continue; if(effect_util::AdditionalEffect::count2(savedState,pos,pl)< effect_util::AdditionalEffect::count2(state,pos,pl)) return true; for(int num=0;num<40;num++){ Piece p=state.pieceOf(num); if(p.ptype()==KING) continue; if(p.isOnBoardByOwner(pl) && state.hasEffectByPiece(p,pos) && !savedState.hasEffectByPiece(p,pos)) return true; } } return false; } static void testDropFile(const std::string& fileName){ auto record=CsaFileMinimal(fileName).load(); NumEffectState state(record.initialState()); const auto& moves=record.moves; for(unsigned int i=0;i:: generate(state.turn(),state,store); } // 次ã®1行ã¯addEffect.hã®ãƒã‚°ã®ç¯„囲をçªãæ­¢ã‚ã‚‹ãŸã‚ã®ãƒ†ã‚¹ãƒˆ // if(state.hasEffectAt(state.turn(),pos)) continue; MoveVector effectMoves; { Store storeEffect(effectMoves); GenerateAddEffect8:: generate(state.turn(),state,storeEffect); } size_t count1=0; for(size_t j=0;j progress; if (OslConfig::inUnitTestLong()) progress.reset(new boost::progress_display(count, std::cerr)); while((ifs >> filename) && filename != "" && ++i:: generate(state.turn(),state,store); } // 次ã®1行ã¯addEffect.hã®ãƒã‚°ã®ç¯„囲をçªãæ­¢ã‚ã‚‹ãŸã‚ã®ãƒ†ã‚¹ãƒˆ // if(state.hasEffectAt(state.turn(),pos)) continue; MoveVector effectMoves; { Store storeEffect(effectMoves); GenerateAddEffect8:: generate(state.turn(),state,storeEffect); } for(size_t j=0;j progress; if (OslConfig::inUnitTestLong()) progress.reset(new boost::progress_display(count, std::cerr)); std::string filename; while((ifs >> filename) && filename != "" && ++i::generate(state, store); // assersion failure here with r3527 } BOOST_CHECK(! moves.empty()); } BOOST_AUTO_TEST_CASE(AddEffect8Test20100117) { { NumEffectState state(CsaString( "P1-KY * * * * -KI * * -KY\n" "P2 * * * * -KI * * * * \n" "P3-FU * * * * -FU * -FU * \n" "P4 * * * * * * -FU * -FU\n" "P5 * * * +FU * +KE * * * \n" "P6 * -OU * * +GI+FU * * +FU\n" "P7+FU * * * +KA * +FU+FU * \n" "P8+GI-UM * * +KI * +GI * +OU\n" "P9+KY * +FU * * * * +KE+KY\n" "P+00GI00FU00FU\n" "P-00HI00HI00KI00KE00KE00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; { Store store(moves); move_generator::AddEffect8::generate(state, store); } Move m89gi(Square(9,8), Square(8,9), SILVER, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m89gi) || mayNotGeneratedMove(state,m89gi) || ! isAddEffect8Move(state,m89gi)); } { NumEffectState state(CsaString( "P1-KY * * * * -KI * * -KY\n" "P2 * * * * -KI * * * * \n" "P3-FU * * * * -FU * -FU * \n" "P4 * * * * * * -FU * -FU\n" "P5+FU * * +FU * +KE * * * \n" "P6+KE-OU * * +GI+FU * * +FU\n" "P7 * * * * +GI * +FU+FU * \n" "P8 * -UM * * +KI * +GI * +OU\n" "P9+KY * +FU * * * * +KA+KY\n" "P+00GI00FU00FU\n" "P-00HI00HI00KI00KE00KE00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; { Store store(moves); move_generator::AddEffect8::generate(state, store); } Move m84ke(Square(9,6), Square(8,4), KNIGHT, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m84ke) || mayNotGeneratedMove(state, m84ke) ||! isAddEffect8Move(state, m84ke)); } { NumEffectState state(CsaString( "P1-KY * * * * -KI * * -KY\n" "P2 * * * * -KI * * * * \n" "P3-FU * * * * -FU * -FU * \n" "P4 * * * * * * -FU * -FU\n" "P5+FU * * +FU * +KE * * * \n" "P6+KA-OU * * +GI+FU * * +FU\n" "P7 * * * * +GI * +FU+FU * \n" "P8 * -UM * * +KI * +GI * +OU\n" "P9+KY * +FU * * * * +KE+KY\n" "P+00GI00FU00FU\n" "P-00HI00HI00KI00KE00KE00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; { Store store(moves); move_generator::AddEffect8::generate(state, store); } Move m69ka(Square(9,6), Square(6,9), BISHOP, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m69ka) || mayNotGeneratedMove(state, m69ka) ||! isAddEffect8Move(state, m69ka)); } { NumEffectState state(CsaString( "P1-KY * * * * -KI * * -KY\n" "P2 * * * * -KI * * * * \n" "P3-FU * * * * -FU * -FU * \n" "P4 * * * * * * -FU * -FU\n" "P5 * * * +FU * +KE * * * \n" "P6 * -OU * * +GI+FU * * +FU\n" "P7+FU * * * +GI * +FU+FU * \n" "P8+KA-UM * * +KI * +GI * +OU\n" "P9+KY * +FU * * * * +KE+KY\n" "P+00GI00FU00FU\n" "P-00HI00HI00KI00KE00KE00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; { Store store(moves); move_generator::AddEffect8::generate(state, store); } Move m89ka(Square(9,8), Square(8,9), BISHOP, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m89ka) || mayNotGeneratedMove(state,m89ka) || ! isAddEffect8Move(state,m89ka)); } { NumEffectState state(CsaString( "P1-KY * -OU * +GI * * * -KY\n" "P2 * * * -HI * * * +TO * \n" "P3-KE * * -KI-FU+KA * * -FU\n" "P4-FU+OU * -FU * * * +HI * \n" "P5 * * * -KE * * * * * \n" "P6+FU * +FU * +FU+FU * * * \n" "P7 * * +KA+FU * * * * +FU\n" "P8-GI * * * +KI * * * * \n" "P9 * -TO * +KI * * * +KE+KY\n" "P+00KI00GI00KE00KY00FU00FU00FU00FU00FU00FU\n" "P-00GI\n" "-\n").initialState()); MoveVector moves; { Store store(moves); move_generator::AddEffect8::generate(state, store); } Move m85ke(Square(9,3), Square(8,5), KNIGHT, PTYPE_EMPTY, false, WHITE); BOOST_CHECK(moves.isMember(m85ke) || mayNotGeneratedMove(state, m85ke) ||! isAddEffect8Move(state, m85ke)); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/move_order/0000755000000000000000000000000012316770314016526 5ustar rootrootlibosl-0.8.0.orig/full/test/move_order/captureSort.t.cc0000644000000000000000000000361512316770314021617 0ustar rootroot#include "osl/move_order/captureSort.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/move_action.h" #include "osl/csa.h" #include "osl/oslConfig.h" #include #include #include #include #include using namespace osl; using namespace osl::move_generator; using namespace osl::move_action; static bool isSorted(const MoveVector& moves) { MoveVector::const_iterator p=moves.begin(); for (;(p!=moves.end()) && (p->capturePtype() != PTYPE_EMPTY); ++p) ; // 一度 å–らãªã„手ãŒè¡¨ã‚ŒãŸã‚‰ï¼Œã‚‚ã†å–る手ã¯ãªã„ for (; p!=moves.end(); ++p) { if (p->capturePtype() != PTYPE_EMPTY) { std::cerr << moves; return false; } } return true; } static bool hasSameMember(const MoveVector& l, const MoveVector& r) { typedef std::set set_t; set_t ls(l.begin(), l.end()), rs(r.begin(), r.end()); return ls == rs; } static void testOrder(const std::string& filename) { auto record=CsaFileMinimal(filename).load(); NumEffectState state(record.initialState()); const auto& moves=record.moves; for (unsigned int i=0;i::generate(state.turn(),state,action); } curMoves.unique(); MoveVector sorted = curMoves; CaptureSort::sort(sorted.begin(), sorted.end()); BOOST_CHECK(isSorted(sorted)); BOOST_CHECK(hasSameMember(sorted, curMoves)); const Move move=moves[i]; state.makeMove(move); } } BOOST_AUTO_TEST_CASE(CaptureSortTestOrder){ std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); int i=0; std::string filename; while((ifs >> filename) && ++i<10){ if(filename == "") break; testOrder(std::string(OslConfig::testCsaFile(filename))); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/move_order/captureEstimation.t.cc0000644000000000000000000000204212316770314022775 0ustar rootroot#include "osl/move_order/captureEstimation.h" #include "osl/move_order/moveSorter.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::move_order; BOOST_AUTO_TEST_CASE(CaptureEstimationTestSort) { NumEffectState state(CsaString( "P1-KY-KE-GI * -OU * -GI-KE-KY\n" "P2 * * * * * * -KI-KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5-KI * * * * * * * * \n" "P6+FU * * * +HI * * +HI * \n" "P7 * +FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * * * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); const Move m1 = Move(Square(2,6), Square(2,3), PROOK, PAWN, true, BLACK); const Move m2 = Move(Square(5,6), Square(5,3), PROOK, PAWN, true, BLACK); MoveVector moves; moves.push_back(m1); moves.push_back(m2); MoveSorter::sort(moves, CaptureEstimation(state)); BOOST_CHECK(moves[0] == m2); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/move_order/promotion.t.cc0000644000000000000000000000121112316770314021320 0ustar rootroot#include "osl/move_order/promotion.h" #include "osl/move_order/moveSorter.h" #include using namespace osl; using namespace osl::move_order; BOOST_AUTO_TEST_CASE(MoveOrderPromotionTestSort) { const Square from = Square(2,8); const Square to = Square(2,2); const Move m1 = Move(from, to, ROOK, PTYPE_EMPTY, false, BLACK); const Move m2 = Move(from, to, PROOK, PTYPE_EMPTY, true, BLACK); MoveVector moves; moves.push_back(m1); moves.push_back(m2); MoveSorter::sort(moves, Promotion()); BOOST_CHECK(moves[0] == m2); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/move_order/cheapPtype.t.cc0000644000000000000000000000120512316770314021377 0ustar rootroot#include "osl/move_order/cheapPtype.h" #include "osl/move_order/moveSorter.h" #include using namespace osl; using namespace osl::move_order; BOOST_AUTO_TEST_CASE(CheapPtypeTestSort) { const Square from = Square(2,3); const Square to = Square(2,2); const Move m1 = Move(from, to, ROOK, PTYPE_EMPTY, false, BLACK); const Move m2 = Move(from, to, SILVER, PTYPE_EMPTY, false, BLACK); MoveVector moves; moves.push_back(m1); moves.push_back(m2); MoveSorter::sort(moves, CheapPtype()); BOOST_CHECK(moves[0] == m2); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/0000755000000000000000000000000012316770314015632 5ustar rootrootlibosl-0.8.0.orig/full/test/search/threatmateState.t.cc0000644000000000000000000000172512316770314021547 0ustar rootroot#include "osl/search/threatmateState.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(ThreatmateStateTestConstruction) { ThreatmateState s; BOOST_CHECK_EQUAL(ThreatmateState::UNKNOWN, s.status()); } BOOST_AUTO_TEST_CASE(ThreatmateStateTestTransition) { ThreatmateState t; t.setThreatmate(ThreatmateState::THREATMATE); BOOST_CHECK_EQUAL(ThreatmateState::THREATMATE, t.status()); ThreatmateState mc(t.newStatus(false)); BOOST_CHECK_EQUAL(ThreatmateState::MAY_HAVE_CHECKMATE, mc.status()); ThreatmateState ct(t.newStatus(true)); BOOST_CHECK_EQUAL(ThreatmateState::CHECK_AFTER_THREATMATE, ct.status()); ThreatmateState u(ct.newStatus(true)); BOOST_CHECK_EQUAL(ThreatmateState::UNKNOWN, u.status()); ThreatmateState mc2(ct.newStatus(false)); BOOST_CHECK_EQUAL(ThreatmateState::MAYBE_THREATMATE, mc2.status()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/moveGenerator.t.cc0000644000000000000000000001167712316770314021234 0ustar rootroot/* moveGenerator.t.cc */ #include "osl/search/moveGenerator.h" #include "osl/search/searchState2.h" #include "osl/move_classifier/shouldPromoteCut.h" #include "osl/search/analyzer/categoryMoveVector.h" #include "osl/move_classifier/pawnDropCheckmate.h" #include "osl/move_classifier/moveAdaptor.h" #include "osl/effect_util/effectUtil.h" #include "osl/effect_util/pin.h" #include "osl/eval/progressEval.h" #include "osl/csa.h" #include "osl/oslConfig.h" #include #include #include #include #include #include using namespace osl; using namespace osl::search; typedef SearchState2::checkmate_t checkmate_t; BOOST_AUTO_TEST_CASE(MoveGeneratorTestCopy) { eval::ProgressEval::setUp(); MoveGenerator::initOnce(); std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); int i=0; int count=100; if (OslConfig::inUnitTestShort()) count=10; checkmate_t checkmate; std::string file_name; while((ifs >> file_name) && ++i moves=record.moves; MoveGenerator gen; for (unsigned int i=0; i> file_name) && ++i moves=record.moves; MoveGenerator gen; for(unsigned int i=0;i all_moves.size()) { typedef std::set set_t; set_t s, t; for (size_t j=0; j diff; std::set_difference(s.begin(), s.end(), t.begin(), t.end(), std::back_inserter(diff)); for (size_t j=0; j ::isMember(state, diff[j])) continue; std::cerr << "\n" << state; std::cerr << "not legal " << *search_moves.find(diff[j]) << "\n"; analyzer::CategoryMoveVector a; MoveGenerator g2; eval::ProgressEval eval(state); gen.init(400, &record, eval, state, true, Move()); gen.generateAll(state.turn(), sstate, a); for (analyzer::CategoryMoveVector::const_iterator p=a.begin(); p!=a.end(); ++p) { std::cerr << p->category << "\n"; std::cerr << p->moves << "\n"; } BOOST_CHECK(search_moves.size() <= all_moves.size()); } } if (all_moves.size() != search_moves.size()) { for (size_t j=0; j using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(SacrificeCheckTestCount2) { MoveStack history; RecordStack2 record_stack; BOOST_CHECK_EQUAL(0, SacrificeCheck::count2(record_stack, history, 100)); SimpleHashRecord *record0 = new SimpleHashRecord(); record0->setInCheck(true); record_stack.push(record0); history.push(Move(Square(5,5),SILVER,BLACK)); BOOST_CHECK_EQUAL(0, SacrificeCheck::count2(record_stack, history, 100)); SimpleHashRecord *record1 = new SimpleHashRecord(); record_stack.push(record1); history.push(Move(Square(5,4),Square(5,5),KING,SILVER,false,WHITE)); BOOST_CHECK_EQUAL(1, SacrificeCheck::count2(record_stack, history, 100)); SimpleHashRecord *record2 = new SimpleHashRecord(); record2->setInCheck(true); record_stack.push(record2); history.push(Move(Square(5,6),GOLD,BLACK)); BOOST_CHECK_EQUAL(0, SacrificeCheck::count2(record_stack, history, 100)); SimpleHashRecord *record3 = new SimpleHashRecord(); record_stack.push(record3); history.push(Move(Square(5,5),Square(5,6),KING,GOLD,false,WHITE)); BOOST_CHECK_EQUAL(2, SacrificeCheck::count2(record_stack, history, 100)); BOOST_CHECK_EQUAL(1, SacrificeCheck::count2(record_stack, history, 2)); history.pop(); history.push(Move(Square(5,5),Square(4,4),KING,PTYPE_EMPTY,false,WHITE)); BOOST_CHECK_EQUAL(0, SacrificeCheck::count2(record_stack, history, 100)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/fixedEval.t.cc0000644000000000000000000000674612316770314020327 0ustar rootroot// fixedEval.t.cc #include "osl/search/fixedEval.h" #include "osl/oslConfig.h" #include #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(FixedEvalTestShow) { if (! OslConfig::verbose()) return; std::cerr << "max\t" << eval::EvalTraits::MAX_VALUE << "\n"; std::cerr << "foul\t" << FixedEval::winByFoul(BLACK) << "\n"; std::cerr << "checkmate\t" << FixedEval::winByCheckmate(BLACK) << "\n"; std::cerr << "window max\t" << FixedEval::windowMax(BLACK) << "\n"; std::cerr << "win th\t" << FixedEval::winThreshold(BLACK) << "\n"; std::cerr << "-inf\t" << FixedEval::minusInfty(BLACK) << "\n"; std::cerr << "threat\t" << FixedEval::threatmatePenalty(BLACK) << "\n"; } static bool isEven(int val) { return (val % 2) == 0; } BOOST_AUTO_TEST_CASE(FixedEvalTestConstant) { BOOST_CHECK(FixedEval::winByFoul(BLACK) > 0); BOOST_CHECK(FixedEval::winByFoul(WHITE) < 0); BOOST_CHECK(isEven(FixedEval::winByFoul(BLACK))); BOOST_CHECK(isEven(FixedEval::winByFoul(WHITE))); BOOST_CHECK_EQUAL(FixedEval::winByFoul(BLACK), FixedEval::winByLoop(BLACK)); BOOST_CHECK_EQUAL(FixedEval::winByFoul(WHITE), FixedEval::winByLoop(WHITE)); BOOST_CHECK(FixedEval::winByCheckmate(BLACK) > 0); BOOST_CHECK(FixedEval::winByCheckmate(WHITE) < 0); BOOST_CHECK(isEven(FixedEval::winByCheckmate(BLACK))); BOOST_CHECK(isEven(FixedEval::winByCheckmate(WHITE))); BOOST_CHECK(FixedEval::isWinValue(BLACK, FixedEval::winByCheckmate(BLACK))); BOOST_CHECK(FixedEval::isWinValue(WHITE, FixedEval::winByCheckmate(WHITE))); BOOST_CHECK(FixedEval::brinkmatePenalty(BLACK, 0) < 0); BOOST_CHECK(FixedEval::brinkmatePenalty(WHITE, 0) > 0); BOOST_CHECK(isEven(FixedEval::brinkmatePenalty(BLACK, 2))); BOOST_CHECK(isEven(FixedEval::brinkmatePenalty(WHITE, 3))); BOOST_CHECK(FixedEval::brinkmatePenalty(BLACK, 0) > FixedEval::brinkmatePenalty(BLACK, 1000)); BOOST_CHECK(FixedEval::brinkmatePenalty(WHITE, 0) < FixedEval::brinkmatePenalty(WHITE, 1000)); BOOST_CHECK(! FixedEval::isWinValue (WHITE, FixedEval::brinkmatePenalty(BLACK, 4000))); BOOST_CHECK(FixedEval::threatmatePenalty(BLACK) < 0); BOOST_CHECK(FixedEval::threatmatePenalty(WHITE) > 0); BOOST_CHECK(isEven(FixedEval::threatmatePenalty(BLACK))); BOOST_CHECK(isEven(FixedEval::threatmatePenalty(WHITE))); BOOST_CHECK(FixedEval::minusInfty(BLACK) < 0); BOOST_CHECK(FixedEval::minusInfty(WHITE) > 0); BOOST_CHECK(isEven(FixedEval::minusInfty(BLACK))); BOOST_CHECK(isEven(FixedEval::minusInfty(WHITE))); BOOST_CHECK(eval::isConsistentValue(FixedEval::minusInfty(BLACK))); BOOST_CHECK(eval::isConsistentValue(FixedEval::minusInfty(WHITE))); BOOST_CHECK(FixedEval::winThreshold(BLACK) > 0); BOOST_CHECK(FixedEval::winThreshold(WHITE) < 0); BOOST_CHECK(! isEven(FixedEval::winThreshold(BLACK))); BOOST_CHECK(! isEven(FixedEval::winThreshold(WHITE))); BOOST_CHECK(FixedEval::windowMax(BLACK) > 0); BOOST_CHECK(FixedEval::windowMax(WHITE) < 0); BOOST_CHECK(isEven(FixedEval::windowMax(BLACK))); BOOST_CHECK(isEven(FixedEval::windowMax(WHITE))); BOOST_CHECK(FixedEval::winByCheckmate(BLACK) < FixedEval::winByFoul(BLACK)); BOOST_CHECK(FixedEval::winByCheckmate(WHITE) > FixedEval::winByFoul(WHITE)); BOOST_CHECK(FixedEval::threatmatePenalty(BLACK) < FixedEval::winByCheckmate(BLACK)); BOOST_CHECK(FixedEval::threatmatePenalty(WHITE) > FixedEval::winByCheckmate(WHITE)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/shouldPromoteCut.t.cc0000644000000000000000000000167112316770314021730 0ustar rootroot#include "osl/move_classifier/shouldPromoteCut.h" #include using namespace osl; BOOST_AUTO_TEST_CASE(ShouldPromoteCutTestPlayer) { const Square p39(3,9); const Square p66(6,6); // WHITE const Move w3966ump(p39,p66,PBISHOP,PTYPE_EMPTY,true,WHITE); BOOST_CHECK(! ShouldPromoteCut::canIgnoreAndNotDrop(w3966ump)); const Move w3966um(p39,p66,PBISHOP,PTYPE_EMPTY,false,WHITE); BOOST_CHECK(! ShouldPromoteCut::canIgnoreAndNotDrop(w3966um)); const Move w3966ka(p39,p66,BISHOP,PTYPE_EMPTY,false,WHITE); BOOST_CHECK(ShouldPromoteCut::canIgnoreAndNotDrop(w3966ka)); // BLACK const Move b3966um(p39,p66,PBISHOP,PTYPE_EMPTY,false,BLACK); BOOST_CHECK(! ShouldPromoteCut::canIgnoreAndNotDrop(b3966um)); const Move b3966ka(p39,p66,BISHOP,PTYPE_EMPTY,false,BLACK); BOOST_CHECK(! ShouldPromoteCut::canIgnoreAndNotDrop(b3966ka)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/bigramKillerMove.t.cc0000644000000000000000000000460312316770314021641 0ustar rootroot#include "osl/search/bigramKillerMove.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(BigramKillerMoveTestAdust) { BigramKillerMove bigrams; const Move m68b(Square(2,8),Square(6,8),ROOK,PTYPE_EMPTY,false,BLACK); const Move m26w(Square(2,3),Square(2,6),ROOK,GOLD,false,WHITE); // 先手ã®é£›è»ŠãŒå‹•ã„ãŸã‚‰ï¼Œå¾Œæ‰‹ãŒ26ã®é‡‘ã‚’å–ã‚‹ bigrams.setMove(m68b, m26w); BOOST_CHECK_EQUAL(m26w, bigrams[m68b][0]); MoveVector moves; NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-HI-FU\n" "P4 * * * * * * * * -TO\n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +KI * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * +HI * * * * * \n" "P9+KY+KE+GI+KI+OU * +GI+KE+KY\n" "P+00FU\n" "-\n").initialState()); bigrams.getMove(state, m68b, moves); BOOST_CHECK_EQUAL((size_t)1, moves.size()); BOOST_CHECK_EQUAL(m26w, *moves.begin()); moves.clear(); // 後手ã®é£›è»Šã«æ­©ã‚’å©ã„ã¦ã‚‚killer move ãŒå¯¾å¿œ NumEffectState state2(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU * -FU\n" "P4 * * * * * * * -HI-TO\n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +KI * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * +HI * * * * * \n" "P9+KY+KE+GI+KI+OU * +GI+KE+KY\n" "P-00FU\n" "-\n").initialState()); bigrams.getMove(state2, m68b, moves); BOOST_CHECK_EQUAL((size_t)1, moves.size()); const Move m26w_from24(Square(2,4),Square(2,6),ROOK,GOLD,false,WHITE); BOOST_CHECK_EQUAL(m26w_from24, *moves.begin()); moves.clear(); // 後手ã®é£›è»ŠãŒè¾ºãªã¨ã“ã‚ã«ã„れã°ç„¡è¦– NumEffectState state3(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU * -FU\n" "P4 * * * -HI * * * * -TO\n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +KI * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * +HI * * * * * \n" "P9+KY+KE+GI+KI+OU * +GI+KE+KY\n" "P-00FU\n" "-\n").initialState()); bigrams.getMove(state3, m68b, moves); BOOST_CHECK(moves.empty()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/simpleHashTable.t.cc0000644000000000000000000001141312316770314021450 0ustar rootroot#include "osl/search/simpleHashTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/moveLogProb.h" #include "osl/hashKey.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(SimpleHashTableTestCreation) { SimpleHashTable table(1,1,false); BOOST_CHECK_EQUAL(1, table.minimumRecordLimit()); SimpleHashTable table2(3,-4,false); BOOST_CHECK_EQUAL(-4, table2.minimumRecordLimit()); } BOOST_AUTO_TEST_CASE(SimpleHashTableTestSize) { SimpleHashTable table(1,1,false); BOOST_CHECK_EQUAL((size_t)0, table.size()); } BOOST_AUTO_TEST_CASE(SimpleHashTableTestAllocate) { SimpleHashTable table(100,1,false); HashKey k; BOOST_CHECK_EQUAL((size_t)0, table.size()); SimpleHashRecord *record = table.allocate(k, 100); BOOST_CHECK_EQUAL((size_t)1, table.size()); BOOST_CHECK(! record->hasLowerBound(0)); BOOST_CHECK(! record->hasUpperBound(0)); } BOOST_AUTO_TEST_CASE(SimpleHashTableTestIsRecordedUpper) { SimpleHashTable table(100,1,false); MoveLogProb m1; const HashKey k; const int limit = 100; const int value = 8; { SimpleHashRecord *record = table.allocate(k, limit); record->setUpperBound(BLACK, limit, m1, value); } const SimpleHashRecord *record = table.find(k); BOOST_CHECK(record); BOOST_CHECK_EQUAL(value, record->upperBound()); } BOOST_AUTO_TEST_CASE(SimpleHashTableTestIsRecordedLower) { SimpleHashTable table(100,1,false); MoveLogProb m1; const HashKey k; const int limit = 100; const int value = 8; { SimpleHashRecord *record = table.allocate(k, limit); record->setLowerBound(BLACK, limit, m1, value); } const SimpleHashRecord *record = table.find(k); BOOST_CHECK(record); BOOST_CHECK_EQUAL(value, record->lowerBound()); } /** * 2回登録ã—ãŸã‚‰æ·±ã„ã»ã†ã®çµæžœãŒæ®‹ã‚‹ */ BOOST_AUTO_TEST_CASE(SimpleHashTableTestOverWrite) { const HashKey k; MoveLogProb m1; const int shallow_limit = 100; const int shallow_value = 8; const int deep_limit = 200; const int deep_value = 888; { // shallow -> deep SimpleHashTable table(100,1,false); SimpleHashRecord *record = table.allocate(k, shallow_limit); record->setLowerBound(BLACK, shallow_limit, m1, shallow_value); record->setLowerBound(BLACK, deep_limit, m1, deep_value); BOOST_CHECK(record->hasLowerBound(deep_limit)); BOOST_CHECK_EQUAL(deep_value, record->lowerBound()); } { // deep -> shallow SimpleHashTable table(100,1,false); SimpleHashRecord *record = table.allocate(k, shallow_limit); record->setLowerBound(BLACK, deep_limit, m1, deep_value); record->setLowerBound(BLACK, shallow_limit, m1, shallow_value); BOOST_CHECK(record->hasLowerBound(deep_limit)); BOOST_CHECK_EQUAL(deep_value, record->lowerBound()); } } /** capacity ã‚’è¶Šãˆã¦ insert ã—ãªã„ */ BOOST_AUTO_TEST_CASE(SimpleHashTableTestCapacity) { const size_t capacity = 128; SimpleHashTable table(capacity,1,false); BOOST_CHECK_EQUAL(capacity, table.capacity()); int table_full = 0; for (unsigned int i=1; i<=capacity*5; ++i) { HashKey k; k.setRandom(); const int limit = i; // const int value = i*2; if (table.size() < capacity) { try { SimpleHashRecord *r = table.allocate(k, limit); BOOST_CHECK_EQUAL((size_t)i, table.size()+table_full); const SimpleHashRecord *record = table.find(k); // std::cerr << r << " " << record << "\n"; BOOST_CHECK_EQUAL(const_cast(r), record); } catch (TableFull&) { BOOST_CHECK(table.size() >= (capacity / table.divSize())); ++table_full; } } else { if (table.find(k) || (limit < table.minimumRecordLimit())) { // already recorded BOOST_CHECK_EQUAL(capacity, table.size()); table.allocate(k, limit); BOOST_CHECK_EQUAL(capacity, table.size()); } else { try { BOOST_CHECK_EQUAL(capacity, table.size()); table.allocate(k, limit); BOOST_CHECK(! table.find(k)); BOOST_CHECK_EQUAL(capacity, table.size()); } catch (TableFull&) { BOOST_CHECK(! table.find(k)); BOOST_CHECK_EQUAL(capacity, table.size()); } } } } } BOOST_AUTO_TEST_CASE(SimpleHashTableTestClear) { SimpleHashTable table(100,1,false); const HashKey k; BOOST_CHECK_EQUAL((size_t)0, table.size()); table.allocate(k, 100); BOOST_CHECK_EQUAL((size_t)1, table.size()); table.clear(); BOOST_CHECK_EQUAL((size_t)0, table.size()); } BOOST_AUTO_TEST_CASE(SimpleHashTableTestSetMinimumRecordLimit) { SimpleHashTable table(100,10000,false); const HashKey k; table.setMinimumRecordLimit(1000); table.allocate(k, 100); BOOST_CHECK_EQUAL((size_t)0, table.size()); table.allocate(k, 10000); BOOST_CHECK_EQUAL((size_t)1, table.size()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/breakThreatmate.t.cc0000644000000000000000000001623212316770314021512 0ustar rootroot/* breakThreatmate.t.cc */ #include "osl/search/breakThreatmate.h" #include "osl/numEffectState.h" #include "osl/csa.h" #include "osl/container/moveLogProbVector.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(BreakThreatmateTestBlock) { { NumEffectState state(CsaString( "P1-OU-KE * * * * * * +TO\n" "P2-KY * -KI+TO+KI * -FU * * \n" "P3 * -FU * * * -FU-KE * * \n" "P4-FU * +FU-UM * -RY * * * \n" "P5 * * * -FU * -GI * * * \n" "P6+FU * +KI * -KA-KY * * * \n" "P7 * +FU * * * * * -FU+FU\n" "P8+KY+GI-GI * * * * * * \n" "P9+OU+KE * +KY * +FU * * * \n" "P+00HI00GI00KE00FU00FU00FU00FU00FU\n" "P-00KI\n" "+\n").initialState()); MoveLogProbVector moves; BreakThreatmate::generate(500, state, Move(Square(7,8), Square(8,9), PSILVER, KNIGHT, true, WHITE), moves); BOOST_CHECK(! moves.empty()); BOOST_CHECK(moves.find(Move(Square(6,7), PAWN, BLACK))); } { NumEffectState state(CsaString( "P1-KY-HI * * * * * * +TO\n" "P2 * -OU-FU * * +RY * * * \n" "P3 * * * * * -KE * * * \n" "P4 * * +KI * -GI * +KA-FU-FU\n" "P5-FU * +GI * -FU * * * * \n" "P6 * * * * * -FU+FU-KY+FU\n" "P7+FU * * * * * * * * \n" "P8+KY-FU * * * +KI+GI * * \n" "P9 * -NG-KA * -TO * +OU+KE+KY\n" "P+00KE\n" "P-00KI00KI00KE00FU00FU00FU00FU00FU00FU\n" "+\n").initialState()); MoveLogProbVector moves; BreakThreatmate::generate(500, state, Move(Square(2,8), GOLD, WHITE), moves); BOOST_CHECK(! moves.empty()); BOOST_CHECK(moves.find(Move(Square(2,7), KNIGHT, BLACK))); } { NumEffectState state(CsaString( "P1-OU-KE * * * +HI * * -KY\n" "P2-KY-GI+KI-FU * * +FU * * \n" "P3 * * * * * -FU * * -FU\n" "P4-FU-FU * -KI-FU * -FU-FU * \n" "P5 * * * -GI * * * * +FU\n" "P6+FU * -FU-KE+FU * * * * \n" "P7 * +FU+KI * * +FU * * * \n" "P8+KY+GI * * * * * * * \n" "P9+OU+KE+KI * * -HI * * +KY\n" "P+00FU00FU\n" "P-00KA00KA00GI00KE00FU\n" "-\n").initialState()); MoveLogProbVector moves; const Move m81ki(Square(7,2), Square(8,1), GOLD, KNIGHT, false, BLACK); BreakThreatmate::generate(500, state, m81ki, moves); const Move m71gi(Square(7,1), SILVER, WHITE); // ·ËÇÏ¤ÏµÍ¤ß BOOST_CHECK(moves.isMember(MoveLogProb(m71gi, 300))); } } BOOST_AUTO_TEST_CASE(BreakThreatmateTestDropValidity) { { NumEffectState state(CsaString( "P1+OU * * * * * -KI-KE-OU\n" "P2+FU-FU-GI * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * * * * * * \n" "P+00KE00KY00FU\n" "P-00AL\n" "+\n").initialState()); MoveLogProbVector moves; BreakThreatmate::generate(500, state, Move(Square(8,1), ROOK, WHITE), moves); BOOST_CHECK(! moves.empty()); BOOST_CHECK(moves.size() == 3); // 73KE, 93KE, 82OU } } BOOST_AUTO_TEST_CASE(BreakThreatmateTestGenerate) { { NumEffectState state(CsaString( "P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7-FU * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P-00KI\n" "P+00AL\n" "+\n").initialState()); MoveLogProbVector moves; BreakThreatmate::generate(500, state, Move(Square(9,8), GOLD, WHITE), moves); BOOST_CHECK(! moves.empty()); } { NumEffectState state(CsaString( "P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU * * * * * \n" "P8+OU * +KI * * -HI * * * \n" "P9+KY+KE-GI * * * * * * \n" "P+00AL\n" "+\n").initialState()); MoveLogProbVector moves; const Move threatmate_move(Square(4,8), Square(7,8), PROOK, GOLD, false, WHITE); BreakThreatmate::generate(500, state, threatmate_move, moves); BOOST_CHECK(! moves.empty()); BOOST_CHECK(moves.isMember(MoveLogProb(Move(Square(5,8), GOLD, BLACK), 400))); } { NumEffectState state(CsaString( "P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * -FU-KE-FU * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU * * * * * * \n" "P8+KY+KA * * * * * * * \n" "P9+OU+KE * * * * * * * \n" "P+00AL\n" "+\n").initialState()); MoveLogProbVector moves; const Move threatmate_move(Square(7,5), Square(8,7), KNIGHT, PAWN, false, WHITE); BreakThreatmate::generate(500, state, threatmate_move, moves); BOOST_CHECK(! moves.empty()); BOOST_CHECK(moves.isMember(MoveLogProb(Move(Square(8,8),Square(7,9), BISHOP, PTYPE_EMPTY, false, BLACK), 100))); } { NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * -FU+FU * * * * \n" "P3-FU+RY * * * * +TO+HI-FU\n" "P4 * * * +FU * -GI+KA * * \n" "P5 * * +FU * -GI-FU-FU * * \n" "P6 * +KI * * -OU * -KE * * \n" "P7+FU+FU-KI * * -TO * * +FU\n" "P8+OU * -KI * * * * * * \n" "P9+KY * * * * * +GI * +KY\n" "P+00KA00KI00GI00KE00FU00FU00FU\n" "P-00KE00FU00FU\n" "+\n").initialState()); MoveLogProbVector moves; const Move m88ki(Square(7,8), Square(8,8), GOLD, PTYPE_EMPTY, false, WHITE); BreakThreatmate::generate(500, state, m88ki, moves); const Move m96fu(Square(9,7), Square(9,6), PAWN, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(MoveLogProb(m96fu, 100))); } } BOOST_AUTO_TEST_CASE(BreakThreatmateTestDropCandidate) { { NumEffectState state(CsaString( "P1-OU-KE * * * * * * -KY\n" "P2-KY * +KI-FU * * +FU * * \n" "P3 * * * -KI * -FU * * -FU\n" "P4-FU-FU * -GI-FU * -FU-FU * \n" "P5 * * * -GI * * * * +FU\n" "P6+FU * -FU-KE+FU+KA * * * \n" "P7 * +FU+KI * * +FU * * * \n" "P8+KY+GI * * * * * * * \n" "P9+OU+KE+KI * * -HI * * +KY\n" "P+00HI00FU00FU\n" "P-00KA00GI00KE00FU\n" "-\n").initialState()); MoveLogProbVector moves; const Move m64ka(Square(4,6), Square(6,4), BISHOP, SILVER, false, BLACK); BreakThreatmate::generate(500, state, m64ka, moves); const Move m71gi(Square(7,1), SILVER, WHITE); BOOST_CHECK(moves.isMember(MoveLogProb(m71gi, 100))); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/quiescenceRecord.t.cc0000644000000000000000000000260712316770314021673 0ustar rootroot/* quiescenceRecord.t.cc */ #include "osl/search/quiescenceRecord.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(QuiescenceRecordTestBestMoves) { QuiescenceRecord r; BOOST_CHECK_EQUAL(Move(), r.bestMove()); BestMoves best_moves; BOOST_CHECK(best_moves.sizeFilled() == 0); MoveVector moves; for (int x=1; x<=9; ++x) moves.push_back(Move(Square(x,5), GOLD, BLACK)); best_moves.add(moves[0]); BOOST_CHECK_EQUAL(moves[0], best_moves[0]); best_moves.add(moves[1]); BOOST_CHECK_EQUAL(moves[1], best_moves[0]); BOOST_CHECK_EQUAL(moves[0], best_moves[1]); MoveVector test; test.push_back(moves[2]); best_moves.addSecondary(test); BOOST_CHECK_EQUAL(moves[1], best_moves[0]); // best move remains BOOST_CHECK_EQUAL(moves[2], best_moves[1]); // inserted here BOOST_CHECK_EQUAL(moves[0], best_moves[2]); test.push_back(moves[3]); test.push_back(moves[4]); best_moves.addSecondary(test); BOOST_CHECK_EQUAL((size_t)4, best_moves.size()); // best move remains BOOST_CHECK_EQUAL(moves[1], best_moves[0]); // best move remains BOOST_CHECK_EQUAL(moves[2], best_moves[1]); // same contents stored BOOST_CHECK_EQUAL(moves[3], best_moves[2]); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/hashRejections.t.cc0000644000000000000000000000443112316770314021356 0ustar rootroot#include "osl/search/hashRejections.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(HashRejectionsTestProbe) { HashRejections table; NumEffectState state; HashKey key(state); Move good_move(Square(7,7), Square(7,6), PAWN, PTYPE_EMPTY, false, BLACK); Move another_move(Square(1,9), Square(1,8), LANCE, PTYPE_EMPTY, false, BLACK); table.addRejectionRoot(state, key, good_move); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(good_move), key)); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(another_move), key)); BOOST_CHECK(table.rejectionProbe(key.newHashWithMove(another_move), HashKey())); table.clearRejectionRoot(state, key, good_move); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(good_move), key)); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(another_move), key)); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(another_move), HashKey())); table.addRejection(state, key, good_move); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(good_move), key)); BOOST_CHECK(table.rejectionProbe(key.newHashWithMove(another_move), key)); BOOST_CHECK(table.rejectionProbe(key.newHashWithMove(another_move), HashKey())); table.clearRejection(state, key, good_move); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(good_move), key)); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(another_move), key)); BOOST_CHECK(! table.rejectionProbe(key.newHashWithMove(another_move), HashKey())); } BOOST_AUTO_TEST_CASE(HashRejectionsTestCopy) { HashRejections table; NumEffectState state; HashKey key(state); Move good_move(Square(7,7), Square(7,6), PAWN, PTYPE_EMPTY, false, BLACK); Move another_move(Square(1,9), Square(1,8), LANCE, PTYPE_EMPTY, false, BLACK); table.addRejectionRoot(state, key, good_move); HashRejections table2 = table; BOOST_CHECK(table2.rejectionProbe(key.newHashWithMove(another_move), HashKey())); table.addRejection(state, key, good_move); HashRejections table3; table3 = table; BOOST_CHECK(table3.rejectionProbe(key.newHashWithMove(another_move), key)); BOOST_CHECK(table3.rejectionProbe(key.newHashWithMove(another_move), HashKey())); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/moveStackRejections.t.cc0000644000000000000000000015441712316770314022401 0ustar rootroot#include "osl/search/moveStackRejections.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/escape_.h" #include "osl/csa.h" #include "osl/repetitionCounter.h" #include "osl/hashKey.h" #include "osl/oslConfig.h" #include #include #include #include using namespace osl; using namespace osl::search; using namespace osl::move_generator; using namespace osl::move_action; static bool testString(const char *str,int alpha=0){ CsaString csaString(str); NumEffectState state(csaString.initialState()); std::vector moves=csaString.load().moves; MoveStack history; RepetitionCounter repCounter(state); for(int i=0;i<(int)moves.size()-1;i++){ Move move=moves[i]; history.push(move); state.makeMove(move); repCounter.push(state); } Move lastMove=moves[moves.size()-1]; int size=moves.size()-1; int cc=repCounter.checkCount(alt(state.turn())); if(state.turn()==BLACK) return MoveStackRejections::probe(state,history,size,lastMove,alpha,cc); else return MoveStackRejections::probe(state,history,size,lastMove,alpha,cc); } BOOST_AUTO_TEST_CASE(MoveStackRejectionsTestProbe) { { // myPlus = 0, opPlus = 1, opMinus=1, myMinus=0, valid, gt BOOST_CHECK(testString( "P1-KY-HI * * * * * * -KY\n" "P2 * * -OU-KI * * -KI * * \n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU+FU+FU\n" "P6+FU * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * +HI * \n" "P9+KY * * * * * * * +KY\n" "P+00KA\n" "P-00KA\n" "-\n" "-0039KA\n" "+2838HI\n" "-3928UM\n" )); } { // myPlus = 0, opPlus = 1, opMinus=1, myMinus=0, valid, eq, rejectSennichite BOOST_CHECK(testString( "P1-KY-HI * * * * * * -KY\n" "P2 * * -OU-KI * * -KI * * \n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU+FU+FU\n" "P6+FU * +FU+FU+FU+FU+FU * -UM\n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA\n" "-\n" "-1627UM\n" "+1828HI\n" "-2716UM\n" )); } { // myPlus = 0, opPlus = 1, opMinus=1, myMinus=0, valid, eq, notrejectSennichite // alpha is greater than zero, so white prefers the draw game. BOOST_CHECK(!testString( "P1-KY-HI * * * * * * -KY\n" "P2 * * -OU-KI * * -KI * * \n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU+FU+FU\n" "P6+FU * +FU+FU+FU+FU+FU * -UM\n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA\n" "-\n" "-1627UM\n" "+1828HI\n" "-2716UM\n" ,100)); } { // myPlus = 0, opPlus = 1, opMinus=1, myMinus=0, invalid, gt // the ROOK at square 81 can't capture the PAWN at square 86, // because there is a ROOK at square 85 BOOST_CHECK(!testString( "P1-KY * * * * * * -KE-KY\n" "P2 * * * * * * -KI-OU * \n" "P3-FU * * -GI * -FU-GI-FU-FU\n" "P4 * * * -KI * -KA-FU * * \n" "P5 * -HI+FU-FU-FU * * * +FU\n" "P6+FU+HI * * * +FU * * * \n" "P7 * +FU * +FU+FU+GI+FU * * \n" "P8 * +KA+KI * * * +GI * * \n" "P9+KY * * * * +KI+OU+KE+KY\n" "P+00KE00FU\n" "P-00KE00FU00FU\n" "-\n" "-8575HI\n" "+0076FU\n" "-0085FU\n" "+7675FU\n" "-8586FU\n" "+0081HI\n" "-0085HI\n" )); } { // myPlus = 0, opPlus = 1, opMinus=2, myMinus=0, valid, eq, rejectSennichite BOOST_CHECK(!testString( "P1-KY-HI * * * * * * -KY\n" "P2 * * -OU-KI * * -KI * * \n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6+FU * +FU+FU+FU+FU+FU * -UM\n" "P7 * +FU+KE+KI * +GI+KE+FU * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA\n" "-\n" "-1627UM\n" "+1828HI\n" "-2716UM\n" )); } { // myPlus = 0, opPlus = 1, opMinus=1, myMinus=1, valid, eq, rejectSennichite BOOST_CHECK(!testString( "P1-KY-HI * * * * * * -KY\n" "P2 * * -OU-KI * * -KI * * \n" "P3 * * -KE-GI * -FU-KE * -FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU+FU+FU\n" "P6+FU * +FU+FU+FU+FU+FU * -UM\n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * -FU+HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA\n" "-\n" "-1627UM\n" "+1828HI\n" "-2716UM\n" )); } { // myPlus=0, opPlus=0, opMinus=1, myMinus=0, !isPromoted, gt BOOST_CHECK(testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+0024FU\n" "-2122RY\n" "+2423FU\n" "-2223RY\n" "+0024FU\n" "-2324RY\n" "+1816HI\n" "-2421RY\n" "+1618HI\n" )); } { // myPlus=0, opPlus=0, opMinus=1, myMinus=0, !isPromoted, eq, rejectSennichite BOOST_CHECK(testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+0024FU\n" "-2122RY\n" "+2423FU\n" "-2223RY\n" "+1816HI\n" "-2321RY\n" "+1618HI\n" )); } { // myPlus=0, opPlus=0, opMinus=1, myMinus=0, !isPromoted, eq, rejectSennichite BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE-FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+0024FU\n" "-2122RY\n" "+2423FU\n" "-2223RY\n" "+1816HI\n" "-2321RY\n" "+1618HI\n", -100)); } { // myPlus=0, opPlus=0, opMinus=1, myMinus=0, isPromoted, eq, rejectSennichite BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * -UM * \n" "P3 * * -KE-GI * -FU-KE-TO-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+0024FU\n" "-2132RY\n" "+2423FU\n" "-3223RY\n" "+1816HI\n" "-2332RY\n" "+1617HI\n" "-3221RY\n" "+1718HI\n" )); } { // myPlus=0, opPlus=0, opMinus=0, myMinus=0 eq, rejectSennichite BOOST_CHECK(testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * -UM * \n" "P3 * * -KE-GI * -FU-KE-TO-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+1816HI\n" "-2112RY\n" "+1618HI\n" "-1221RY\n" )); } { // myPlus=0, opPlus=0, opMinus=0, myMinus=0 eq, notRejectSennichite BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * -UM * \n" "P3 * * -KE-GI * -FU-KE-TO-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+1816HI\n" "-2112RY\n" "+1618HI\n" "-1221RY\n" ,100)); } { // myPlus=0, opPlus=0, opMinus=2 BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE * -FU\n" "P4-FU * -FU-FU-FU-GI * +FU * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "+\n" "+2423TO\n" "-2123RY\n" "+3725KE\n" "-2325RY\n" "+1816HI\n" "-2522RY\n" "+1618HI\n" "-2221RY\n" )); } { // myPlus=1, myMinus=1, opMinus=1, opPlus=0, valid, ge BOOST_CHECK(testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE+FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "-\n" "-1223UM\n" "+1816HI\n" "-2312UM\n" "+1618HI\n" "-2123RY\n" )); } { // myPlus=1, myMinus=1, opMinus=1, opPlus=0, invalid, ge BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * -UM * \n" "P3 * * -KE-GI * -FU * +FU * \n" "P4-FU * -FU-FU-FU-GI-KE * -FU\n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "-\n" "-2223UM\n" "+1816HI\n" "-2322UM\n" "+1617HI\n" "-2132RY\n" "+1718HI\n" "-3223RY\n" )); } { // myPlus=1, myMinus=1, opMinus=1, opPlus=1 BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE+FU-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "-\n" "-1223UM\n" "+0025FU\n" "-2312UM\n" "+2524FU\n" "-2123RY\n" )); } { // myPlus=1, myMinus=1, opMinus=0, opPlus=0, valid, ge BOOST_CHECK(testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE * -FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU+FU+FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "-\n" "-1223UM\n" "+1816HI\n" "-2312UM\n" "+1618HI\n" "-2123RY\n" )); } { // myPlus=1, myMinus=1, opMinus=1, opPlus=0, invalid, ge BOOST_CHECK(!testString( "P1-KY-KI * * * * * -RY-KY\n" "P2 * * -OU-KI * * * -UM * \n" "P3 * * -KE-GI * -FU * * * \n" "P4-FU * -FU-FU-FU-GI-KE * -FU\n" "P5 * -FU * * * * -FU+FU+FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "-\n" "-2223UM\n" "+1816HI\n" "-2322UM\n" "+1617HI\n" "-2132RY\n" "+1718HI\n" "-3223RY\n" )); } { // myPlus=1, myMinus=0, opPlus=1, opMinus=1, valid, eq, rejectSennichite BOOST_CHECK(testString( "P1-KY-KI * * * * * * -KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE-RY-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "P-00FU\n" "+\n" "+0025FU\n" "-2321RY\n" "+2524FU\n" "-0023FU\n" "+2423TO\n" )); } { // myPlus=1, myMinus=0, opPlus=1, opMinus=1, valid, eq, notRejectSennichite BOOST_CHECK(!testString( "P1-KY-KI * * * * * * -KY\n" "P2 * * -OU-KI * * * * -UM\n" "P3 * * -KE-GI * -FU-KE-RY-FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "P-00FU\n" "+\n" "+0025FU\n" "-2321RY\n" "+2524FU\n" "-0023FU\n" "+2423TO\n" ,-100)); } { // myPlus=1, myMinus=0, opPlus=1, opMinus=0 BOOST_CHECK(!testString( "P1-KY-KI * * * * * * -KY\n" "P2 * * -OU-KI * * * -RY-UM\n" "P3 * * -KE-GI * -FU-KE * -FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "P-00FU\n" "+\n" "+0026FU\n" "-2221RY\n" "+2625FU\n" "-0024FU\n" "+2524FU\n" "-2122RY\n" )); } { // myPlus=1, myMinus=0, opPlus=0, opMinus=0, not promoted BOOST_CHECK(testString( "P1-KY-KI * * * * * * -KY\n" "P2 * * -OU-KI * * * -RY-UM\n" "P3 * * -KE-GI * -FU-KE * -FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "P-00FU\n" "+\n" "+0026FU\n" "-2221RY\n" "+2625FU\n" "-2122RY\n" "+2524FU\n" )); } { // myPlus=1, myMinus=0, opPlus=0, opMinus=0, promoted BOOST_CHECK(!testString( "P1-KY-KI * * * * * * -KY\n" "P2 * * -OU-KI * * * -RY-UM\n" "P3 * * -KE-GI * -FU-KE * -FU\n" "P4-FU * -FU-FU-FU-GI * * * \n" "P5 * -FU * * * * -FU * +FU\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7 * +FU+KE+KI * +GI+KE * * \n" "P8 * +OU+KI+GI * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00FU00FU\n" "P-00FU\n" "+\n" "+0025FU\n" "-2221RY\n" "+2524FU\n" "-2122RY\n" "+2423TO\n" )); } { // é§’æãƒ«ãƒ¼ãƒ—ã®æ¨©åˆ©ã‚’相手ã«ä¸Žãˆã‚‹ã‚ˆã†ã«è¦‹ãˆã‚‹ãŒï¼Œå®Ÿã¯ãã®æ‰‹ãŒå­˜åœ¨ã—ãªã„ NumEffectState state(CsaString( "P1-GI-KE * * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU * * * * * -KY\n" "P4 * -KY * * +FU * * -UM-FU\n" "P5 * * * -KI * -HI-FU * * \n" "P6 * * +KE+RY * +KY * * +KE\n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA+KI * +OU * * * * \n" "P9+KY * +GI * * +KI+GI * * \n" "P-00FU\n" "-\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(6,5),Square(7,5),GOLD,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,6),Square(5,5),PROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,4),PAWN,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,5),Square(6,4),PROOK,PAWN,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,-1,0))); state.makeMove(m); history.push(m); } { // PROOKã¯6,6ã«æˆ»ã‚Œãªã„ Move m(Square(7,5),Square(6,5),GOLD,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,4,m,1,0))); state.makeMove(m); history.push(m); } } { // é§’æãƒ«ãƒ¼ãƒ—ã®æ¨©åˆ©ã‚’相手ã«ä¸Žãˆã‚‹ã‚ˆã†ã«è¦‹ãˆï¼Œãã®æ™‚点ã§ã¯ã§ããã†ã«ãªã„ãŒï¼Œå®Ÿã¯ãã®æ‰‹ãŒå­˜åœ¨ã™ã‚‹ã€€ NumEffectState state(CsaString( "P1-GI-KE * * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU * * * * * -KY\n" "P4 * -KY * * +FU * * -UM-FU\n" "P5 * * -KI * * -HI-FU * * \n" "P6 * * +KE+RY * +KY * * +KE\n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA+KI * +OU * * * * \n" "P9+KY * +GI * * +KI+GI * * \n" "P-00FU\n" "-\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(7,5),Square(6,5),GOLD,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,6),Square(5,5),PROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,4),PAWN,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,5),Square(6,4),PROOK,PAWN,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,-1,0))); state.makeMove(m); history.push(m); } { // PROOKã¯6,6ã«æˆ»ã‚Œã‚‹ Move m(Square(6,5),Square(7,5),GOLD,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,1,0))); state.makeMove(m); history.push(m); } } { // é§’æã‚’ã—ã¦ï¼Œãƒ«ãƒ¼ãƒ—ã™ã‚‹æ¨©åˆ©ã‚’相手ã«ä¸Žãˆã‚‹ NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU-FU * * * * -KY\n" "P4 * -KY * * +FU * * -UM-FU\n" "P5 * * * * * -HI-FU * * \n" "P6 * * +KE * * +KY * * +KE\n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA+KI * +OU * * +HI * \n" "P9+KY * +GI * * +KI+GI * * \n" "+\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(5,4),Square(5,3),PPAWN,PTYPE_EMPTY,true,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,2),Square(5,3),SILVER,PPAWN,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,4),PAWN,BLACK); BOOST_CHECK((MoveStackRejections::probe(state,history,2,m,-1,0))); } } { // 相手ã®ãƒ‘ス後ã«å…ƒã‹ã‚‰ã„ã‘る所ã«è¡Œã NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU-FU * * * * -KY\n" "P4 * -KY * * +FU+GI * -UM-FU\n" "P5 * * * * * -HI-FU * * \n" "P6 * * +KE * * +KY * * +KE\n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA+KI * +OU * * +HI * \n" "P9+KY * * * * +KI+GI * * \n" "+\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(4,4),Square(4,3),PSILVER,PTYPE_EMPTY,true,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,-1,0))); state.makeMove(m); history.push(m); } { Move m=Move::PASS(WHITE); state.makeMove(m); history.push(m); } { Move m(Square(4,3),Square(5,3),PSILVER,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); } } { // 敵味方往復中ã«ï¼Œå…ƒã‹ã‚‰ã„ã‘ã‚‹ã¨ã“ã‚ã«ä¸€æ‰‹ã¯ã•ã‚€ NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * * -FU * * * * -KY\n" "P4 * -KY-FU * +FU+GI * -UM-FU\n" "P5 * * * * * -HI-FU * * \n" "P6 * * +KE * * +KY * * +KE\n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA+KI * +OU * * +HI * \n" "P9+KY * * * * +KI+GI * * \n" "+\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(4,4),Square(3,3),SILVER,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,2),Square(7,3),SILVER,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,4),Square(5,3),PPAWN,PTYPE_EMPTY,true,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(7,3),Square(6,2),SILVER,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(3,3),Square(4,4),SILVER,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); } } { // 歩を交æ›ã—ã¦å…ƒã‹ã‚‰ã„ã‘ã‚‹ã¨ã“ã‚ã«ã„ã NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU-FU * * * * -KY\n" "P4 * -KY * * +FU * * -UM-FU\n" "P5 * * * * * -HI-FU * * \n" "P6 * * +KE * * +KY * * +KE\n" "P7+FU+FU+FU * * +FU+FU+FU+FU\n" "P8 * +KA+KI+HI+OU * * * * \n" "P9+KY * +GI * * +KI+GI * * \n" "P+00FU\n" "+\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(6,4),PAWN,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,3),Square(6,4),PAWN,PAWN,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,8),Square(6,4),ROOK,PAWN,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,3),PAWN,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,4),Square(6,5),ROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); } } { // 元々一手ã§ã„ã‘ãªã„ã¨ã“ã‚ã«è¡Œãã®ã¯å¯ NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU-FU * * * * -KY\n" "P4 * -KY * * * * * -UM-FU\n" "P5 * * * +FU * -HI-FU * * \n" "P6 * * +KE+HI * +KY * * +KE\n" "P7+FU+FU+FU * +FU+FU+FU+FU+FU\n" "P8 * +KA+KI * +OU * * * * \n" "P9+KY * +GI * * +KI+GI * * \n" "+\n").initialState()); MoveStack history; history.push(Move()); history.push(Move()); { Move m(Square(6,6),Square(5,6),ROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(2,4),Square(2,3),PBISHOP,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,6),Square(5,4),ROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(2,3),Square(2,4),PBISHOP,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((MoveStackRejections::probe(state,history,3,m,-1,0))); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,4),Square(6,4),ROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,4,m,-1,0))); } } { // 角交æ›ã§æ´¾æ‰‹ã ãŒå…ƒã€…ã„ã‘ã‚‹ã¨ã“ã‚ NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU-FU * * * * -KY\n" "P4 * -KY * * * * * * -FU\n" "P5 * * * +FU * -HI-FU * * \n" "P6 * * +FU * * +KY * * +KE\n" "P7+FU+FU * * +FU+FU+FU+FU+FU\n" "P8 * * +KI+HI+OU * * * * \n" "P9+KY+KE+GI * * +KI+GI * * \n" "P+00KA\n" "P-00KA\n" "+\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(8,8),BISHOP,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(3,3),BISHOP,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(8,8),Square(7,7),BISHOP,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(3,3),Square(7,7),PBISHOP,BISHOP,true,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(8,9),Square(7,7),KNIGHT,PBISHOP,false,BLACK); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); BOOST_CHECK((MoveStackRejections::probe(state,history,4,m,-1,0))); } } { // progress2/01.csa NumEffectState state(CsaString( "P1-KY+HI * +KA * * * -KE-KY\n" "P2 * * -KI-FU * * * * * \n" "P3-KE-KI-OU * +UM-GI-FU+FU-FU\n" "P4 * -GI * * -FU * * -FU * \n" "P5-FU * * * * +GI * * * \n" "P6 * +FU-FU * * * * * * \n" "P7+FU * * * * * +FU * +FU\n" "P8+KY+KI+KI * * * * * * \n" "P9+OU+KE * * * * * +KE+KY\n" "P+00FU\n" "P-00HI00GI00FU00FU00FU00FU00FU\n" "+\n").initialState()); MoveStack history; history.push(Move()); { Move m(Square(7,4),PAWN,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(7,3),Square(7,4),KING,PAWN,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,1),Square(7,2),PBISHOP,GOLD,true,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,3),ROOK,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(5,3),Square(6,3),PBISHOP,ROOK,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,4,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(7,4),Square(7,5),KING,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,5,m,1,1))); state.makeMove(m); history.push(m); } { Move m(Square(6,3),Square(5,3),PBISHOP,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,6,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(7,5),Square(7,4),KING,PTYPE_EMPTY,false,WHITE); BOOST_CHECK((MoveStackRejections::probe(state,history,7,m,1,2))); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,1,2))); state.makeMove(m); history.push(m); } } { // 一手パスもrejectã™ã‚‹? -> ã—ãªã„ NumEffectState state(CsaString( "P1-GI-KE-KI * -KE-TO-TO-TO-OU\n" "P2 * * * -GI * * * -TO-KI\n" "P3-FU * -FU-FU * * * * -KY\n" "P4 * -KY * * +FU * * -UM-FU\n" "P5 * * * * * -HI-FU * * \n" "P6 * * +KE * * +KY * * +KE\n" "P7+FU+FU+FU * * +FU+FU+FU+FU\n" "P8 * +KA+KI+HI+OU * * * * \n" "P9+KY * +GI * * +KI+GI * * \n" "P+00FU\n" "+\n").initialState()); MoveStack history; history.push(Move()); history.push(Move()); { Move m(Square(6,4),PAWN,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,0,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,3),Square(6,4),PAWN,PAWN,false,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,1,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,8),Square(6,4),ROOK,PAWN,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,2,m,-1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,3),PAWN,WHITE); BOOST_CHECK((!MoveStackRejections::probe(state,history,3,m,1,0))); state.makeMove(m); history.push(m); } { Move m(Square(6,4),Square(6,8),ROOK,PTYPE_EMPTY,false,BLACK); BOOST_CHECK((!MoveStackRejections::probe(state,history,4,m,1,0))); BOOST_CHECK((MoveStackRejections::probe(state,history,5,m,-1,0))); } } } BOOST_AUTO_TEST_CASE(MoveStackRejectionsTestBug20110212) { NumEffectState state(CsaString( "P1-KY-KE-GI * -OU-KI-GI-KE-KY\n" "P2 * * * * -HI * * -KA * \n" "P3-FU+FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * +HI * * * * * * * \n" "P7+FU * +FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * * * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00KI00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(8,3),Square(8,2),PPAWN,PTYPE_EMPTY,true,BLACK), // +8382TO Move(Square(7,1),Square(8,2),SILVER,PPAWN,false,WHITE), // -7182GI Move(Square(8,4),PAWN,BLACK), // +0084FU Move::PASS(WHITE), // pass }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m83to(Square(8,4),Square(8,3),PPAWN,PTYPE_EMPTY,true,BLACK); for (int i=-1024; i<=1024; ++i) BOOST_CHECK(! MoveStackRejections::probe(state,history,4,m83to,0,i)); } static bool isRejectMove(NumEffectState const& state,MoveStack const& history,Move move, std::vector const& record,std::vector > const& branches, RepetitionCounter const& repCounter, int alpha,bool showDebug=false) { Player player=state.turn(); assert(player == move.player()); assert(!record.empty()); HashKey h=record[record.size()-1].newMakeMove(move); HashKey h_r(h); h_r.changeTurn(); assert(record[record.size()-1]==HashKey(state)); PieceStand new_stand=h.blackStand(); /** * 一手パス,ãŠã‚ˆã³ä¸€æ‰‹ãƒ‘ス+é§’æ * recã§è‡ªåˆ†ã®æ‰‹ç•ªã®å±€é¢ã«æˆ»ã‚‹ã‚‚ã®ã§ï¼Œé§’æã‹é§’ã®æå¾—ãªã— * alphaã®å€¤ã¯é–¢ä¿‚ãªã— */ for(int i=(int)record.size()-3; i>=0; i-=2){ if(showDebug) std::cerr << "i=" << i << std::endl; const HashKey& old_h=record[i]; PieceStand old_stand=old_h.blackStand(); assert(old_h.turn()==player); if(old_h.isSameBoard(h_r) && (old_stand==new_stand|| old_stand.hasMoreThan(player,new_stand))){ if(showDebug) std::cerr << "type 1" << std::endl; return true; } } /** * ループ(åƒæ—¥æ‰‹),ãŠã‚ˆã³ãƒ«ãƒ¼ãƒ—+é§’æ * recã§ç›¸æ‰‹ã®æ‰‹ç•ªã®å±€é¢ã«æˆ»ã‚‹ã‚‚ã® * é§’æã‹é§’ã®æå¾—ãªã— * ãŸã ã—,alphaãŒè² ã§æ‰‹ç•ªã§é»’, alphaãŒæ­£ã§æ‰‹ç•ªãŒç™½ã®æ™‚ã¯ï¼Œåƒæ—¥æ‰‹æ­“迎 */ for(int i=(int)record.size()-2; i>=0; i-=2){ if(showDebug) std::cerr << "i=" << i << std::endl; const HashKey& old_h=record[i]; PieceStand old_stand=old_h.blackStand(); bool rejectSennichite=(player==BLACK ? alpha>=0 : alpha<=0); int j=(int)record.size()-1-i; // ? op(nocheck) my ? op(check) my ? op(check) in record // myMove // ã®æ™‚ã¯ï¼ŒrepCounterã¯2 // j=1,checkCount=1 - not reject // j=3,checkCount=2 - not reject // j=5,checkCount=2 - reject if(j=0; i-=2){ if(showDebug) std::cerr << "i=" << i << std::endl; for(int j=0;j<(int)branches[i].size();j++){ const HashKey& old_h=branches[i][j]; PieceStand old_stand=old_h.blackStand(); #if 0 std::cerr << "i=" << i << ",j=" << j << ",old_h.turn()=" << old_h.turn() << ",player=" << player << std::endl; if(old_h.turn()!=alt(player)){ for(int k=0;k<(int)record.size();k++){ std::cerr << "record[" << k << "].turn()=" << record[k].turn() << std::endl; if(branches[k].size()>0) std::cerr << "branches[" << k << "][0].turn()=" << branches[k][0].turn() << std::endl; } } #endif assert(old_h.turn()==alt(player)); if(old_h.isSameBoard(h)){ if(old_stand==new_stand){ // int d=(int)record.size()-1-i; // Move branchMove=history.lastMove(d); // if(showDebug) std::cerr << "branchMove=" << branchMove << ",move=" << move << std::endl; // assert(branchMove.player()==player); if(old_h!=record[i+1]){ if(showDebug) std::cerr << "type 3.1" << std::endl; return true; } else{ bool rejectSennichite=(player==BLACK ? alpha>=0 : alpha<=0); int k=(int)record.size()-1-(i+1); // ? op(nocheck) ? my op(check) ? my op(check) in record // myMove // ã®æ™‚ã¯ï¼ŒrepCounterã¯2 // j=1,checkCount=1 - not reject // j=3,checkCount=2 - not reject // j=5,checkCount=2 - reject if(k:: generate(state1.turn(),state1,store); } for (int i=(int)allMoves.size()-1; i>=0; --i) if (allMoves[i].hasIgnoredUnpromote()) allMoves.push_back(allMoves[i].unpromote()); } for (Move move: allMoves){ const HashKey& new_h=h.newMakeMove(move); PieceStand new_stand=new_h.blackStand(); for(int i=(int)record.size()-3; i>=0; i-=2){ const HashKey& old_h=record[i]; PieceStand old_stand=old_h.blackStand(); assert(old_h.turn()==player); assert(new_h.turn()==player); if(old_h.isSameBoard(new_h)){ if(old_stand==new_stand){ bool rejectSennichite=(player==BLACK ? alpha>=0 : alpha<=0); int j=(int)record.size()-1-(i+1); // ? op(nocheck) ? my op(check) ? my op(check) in record // myMove // ã®æ™‚ã¯ï¼ŒrepCounterã¯2 // j=1,checkCount=1 - not reject // j=3,checkCount=2 - not reject // j=5,checkCount=2 - reject if(j record; std::vector > branches; HashKey hash(state); RepetitionCounter repCounter(state); history.push(Move()); history.push(Move()); for(unsigned int i=0;i(state,history,record,branches,repCounter,alpha,alpha==-1); else testState(state,history,record,branches,repCounter,alpha,alpha==-1); } Move move=moves[i]; state.makeMove(move); hash=hash.newMakeMove(move); history.push(move); } } BOOST_AUTO_TEST_CASE(MoveStackRejectionsTestCsaFiles) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); int i=0; int count=3000; if (OslConfig::inUnitTestShort()) count=10; std::string fileName; while ((ifs >> fileName) && (++i moves = {{ Move(Square(6,3),Square(6,2),PBISHOP,ROOK,false,BLACK), //+6362UM Move(Square(6,1),Square(6,2),KING,PBISHOP,false,WHITE), //-6162OU Move(Square(8,2),ROOK,BLACK), //+0082HI Move(Square(7,2),SILVER,WHITE),//-0072GI Move(Square(8,3),SILVER,BLACK),//+0083GI Move(Square(6,3),BISHOP,WHITE),//-0063KA Move(Square(8,3),Square(7,2),PSILVER,SILVER,true,BLACK),//+8372NG Move(Square(6,3),Square(7,2),BISHOP,PSILVER,false,WHITE),//-6372KA Move(Square(8,3),SILVER,BLACK),//+0083GI Move(Square(7,1),SILVER,WHITE),//-0071GI Move(Square(8,3),Square(7,2),PSILVER,BISHOP,true,BLACK), // +8372NG }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m72gi(Square(7,1),Square(7,2),SILVER,PSILVER,false,WHITE);//-7172GI BOOST_CHECK(!MoveStackRejections::probe(state,history,11,m72gi,0,0)); } { NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2 * +UM+GI * -OU-KI * * * \n" "P3 * +NK * -KY * * * -FU * \n" "P4 * * -FU-GI-FU-FU-FU * * \n" "P5-GI-KY * * * * * +FU * \n" "P6-KE-FU+FU+FU+FU+FU+FU+HI * \n" "P7+GI * * +KI+KA * * * * \n" "P8+OU * +KI * * +KY * * -RY\n" "P9 * * * -KI * * * +KE * \n" "P+00KE00KY00FU00FU00FU\n" "P-00FU00FU00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(9,9),KNIGHT,BLACK), // +0099KE Move(Square(1,8),Square(1,5),PROOK,PTYPE_EMPTY,false,WHITE), // -1815RY Move(Square(2,6),Square(2,8),ROOK,PTYPE_EMPTY,false,BLACK), // +2628HI Move(Square(1,5),Square(1,9),PROOK,PTYPE_EMPTY,false,WHITE), // -1519RY Move(Square(2,8),Square(2,6),ROOK,PTYPE_EMPTY,false,BLACK), // +2826HI }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m18ry(Square(1,9),Square(1,8),PROOK,PTYPE_EMPTY,false,WHITE); BOOST_CHECK(MoveStackRejections::probe(state,history,5,m18ry,0,0)); } { NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2 * +UM+GI * -OU-KI * * * \n" "P3 * +NK * -KY * * * -FU * \n" "P4 * * -FU-GI-FU-FU-FU * * \n" "P5-GI-KY * * * * * +FU * \n" "P6-KE-FU+FU+FU+FU+FU+FU+HI * \n" "P7+GI * * +KI+KA * * * * \n" "P8+OU * +KI * * +KY * * -RY\n" "P9+KE * * -KI * * * +KE * \n" "P+00KY00FU00FU00FU\n" "P-00FU00FU00FU\n" "-\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(1,8),Square(1,5),PROOK,PTYPE_EMPTY,false,WHITE), // -1815RY Move(Square(2,6),Square(2,8),ROOK,PTYPE_EMPTY,false,BLACK), // +2628HI Move(Square(1,5),Square(1,9),PROOK,PTYPE_EMPTY,false,WHITE), // -1519RY Move(Square(2,8),Square(2,6),ROOK,PTYPE_EMPTY,false,BLACK), // +2826HI }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m18ry(Square(1,9),Square(1,8),PROOK,PTYPE_EMPTY,false,WHITE); // root loop BOOST_CHECK(!MoveStackRejections::probe(state,history,4,m18ry,0,0)); } { NumEffectState state(CsaString( "P1 * +GI * * * * * * * \n" "P2 * +UM * * -OU-KI * * * \n" "P3 * +NK * -KY * * * -FU * \n" "P4 * * -FU-GI-FU-FU-FU * * \n" "P5-GI * * * * * * +FU * \n" "P6-KE-FU+FU+FU+FU+FU+FU+HI * \n" "P7+GI * * +KI+KA * * * * \n" "P8+OU * +KI * * +KY * * -RY\n" "P9 * * * -KI * * * +KE * \n" "P+00KE00KY00FU00FU00FU\n" "P-00KY00FU00FU00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(8,1),Square(7,2),SILVER,PTYPE_EMPTY,false,BLACK), // +8172GI Move(Square(8,5),LANCE,WHITE), // -0085KY Move(Square(9,9),KNIGHT,BLACK), // +0099KE Move(Square(1,8),Square(1,5),PROOK,PTYPE_EMPTY,false,WHITE), // -1815RY Move(Square(2,6),Square(2,8),ROOK,PTYPE_EMPTY,false,BLACK), // +2628HI Move(Square(1,5),Square(1,9),PROOK,PTYPE_EMPTY,false,WHITE), // -1519RY Move(Square(2,8),Square(2,6),ROOK,PTYPE_EMPTY,false,BLACK), // +2826HI }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m18ry(Square(1,9),Square(1,8),PROOK,PTYPE_EMPTY,false,WHITE); BOOST_CHECK(MoveStackRejections::probe(state,history,7,m18ry,0,0)); } { NumEffectState state(CsaString( "P1 * -KE * * * * -OU-KE * \n" "P2 * -HI * * * -KA-KI * * \n" "P3 * * * +NY * -KI-GI-FU * \n" "P4 * * -FU * -FU-FU-FU * * \n" "P5-GI+KE * * * * * +FU+KY\n" "P6 * * +FU+FU+FU+FU+FU * * \n" "P7+KY+FU+GI+KI * * * * * \n" "P8 * +OU+KI+KA * * * +HI * \n" "P9 * * * * * * * +KE * \n" "P+00KY00FU00FU00FU00FU00FU\n" "P-00GI00FU\n" "-\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(9,6),PAWN,WHITE), // -0096FU Move(Square(9,8),PAWN,BLACK), // +0098FU Move(Square(9,6),Square(9,7),PPAWN,LANCE,true,WHITE), // -9697TO Move(Square(9,8),Square(9,7),PAWN,PPAWN,false,BLACK), // -9897FU }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m97um(Square(4,2),Square(9,7),PBISHOP,PAWN,true,WHITE); BOOST_CHECK(MoveStackRejections::probe(state,history,4,m97um,0,0)); } { NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * +HI-KA-OU * * -KI-GI * \n" "P3-FU * * * -FU-FU-KE * -FU\n" "P4 * +FU * -FU * * * -FU * \n" "P5 * * * * * * -FU * * \n" "P6 * * * * * +FU * * +FU\n" "P7+FU * -TO * +FU * +FU+FU * \n" "P8 * -HI * * * * +GI+OU * \n" "P9+KY+KE * +KI * +KI * +KE+KY\n" "P+00GI00FU\n" "P-00KA00KI00GI00FU00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(8,3),SILVER,BLACK), // +0083GI Move(Square(7,1),SILVER,WHITE), // -0071GI Move(Square(8,3),Square(7,2),PSILVER,BISHOP,true,BLACK), // +8472NG Move(Square(7,1),Square(7,2),SILVER,PSILVER,false,WHITE), // +7172GI }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m72ry(Square(8,2),Square(7,2),PROOK,SILVER,true,BLACK); BOOST_CHECK(MoveStackRejections::probe(state,history,4,m72ry,0,0)); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-HI * * -KE-KY\n" "P2 * * -OU * * * -KI * * \n" "P3 * -FU-FU-FU * -FU-FU-FU-FU\n" "P4-FU-UM * * * * * * * \n" "P5 * * * +KA * * +HI * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU * +FU * +FU+FU\n" "P8+KY+GI * * +KI * * * * \n" "P9+OU+KE * +KI * * * +KE+KY\n" "P+00FU00FU00GI\n" "P-00GI00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(7,5),SILVER,BLACK), // +0075GI Move(Square(8,4),Square(9,3),PBISHOP,PTYPE_EMPTY,false,WHITE), // +8493UM }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m84gi(Square(7,5),Square(8,4),SILVER,PTYPE_EMPTY,false,BLACK); BOOST_CHECK(MoveStackRejections::probe(state,history,4,m84gi,0,0)); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU * -FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * -FU * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * +KA * +OU+KI+GI * +HI * \n" "P9+KY+KE+GI+KI * * * +KE+KY\n" "-\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(8,2),Square(5,2),ROOK,PTYPE_EMPTY,false,WHITE), // -8252HI Move(Square(6,8),Square(7,8),KING,PTYPE_EMPTY,false,BLACK), // +6878OU }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m82hi(Square(5,2),Square(8,2),ROOK,PTYPE_EMPTY,false,WHITE); BOOST_CHECK(MoveStackRejections::probe(state,history,4,m82hi,0,0)); } { NumEffectState state(CsaString( "P1 * * * * * * +KI+NY+NK\n" "P2 * +TO * +UM * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * +GI * * * * * -FU\n" "P5+FU+KI * * * * * * * \n" "P6 * * * * * +FU * * * \n" "P7 * * * +FU+FU+OU+FU * +FU\n" "P8 * -UM+FU-FU+HI * +GI * * \n" "P9 * -OU-RY * +KE+GI * * +KY\n" "P+00KE00KY00KY00FU00FU00FU00FU00FU00FU00FU\n" "P-00KI00KI00GI00KE00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(5,8),Square(4,8),ROOK,PTYPE_EMPTY,false,BLACK), // +5848HI Move(Square(7,9),Square(5,9),PROOK,KNIGHT,false,WHITE), // -7959RY Move(Square(4,8),Square(5,8),ROOK,PTYPE_EMPTY,false,BLACK), // +4858HI Move(Square(5,9),Square(7,9),PROOK,PTYPE_EMPTY,false,WHITE), // -5979RY }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m59ke(Square(5,9),KNIGHT,BLACK); BOOST_CHECK(MoveStackRejections::probe(state,history,4,m59ke,0,0)); } { NumEffectState state(CsaString( "P1-KY-HI * * * * * -KE-KY\n" "P2 * * * -GI * * -KI-OU * \n" "P3 * * * -FU-KA-KI * -FU * \n" "P4 * -FU-FU * -FU-FU * * -FU\n" "P5-FU-KE * +FU * * +KA * * \n" "P6 * +GI+FU * +FU * -GI * * \n" "P7+FU+FU * +KI * +FU * +FU+KY\n" "P8 * +OU+KI * * * * * +HI\n" "P9+KY+KE * * * * * +KE * \n" "P+00GI00FU\n" "P-00FU00FU\n" "+\n" ).initialState()); MoveStack history; CArray moves = {{ Move(Square(1,7),Square(1,4),LANCE,PAWN,false,BLACK), // +1714KY Move(Square(1,1),Square(1,4),LANCE,LANCE,false,WHITE), // -1114KY Move(Square(1,8),Square(1,4),ROOK,LANCE,false,BLACK), // +1814HI Move(Square(1,1),LANCE,WHITE), // +0011KY }}; for (Move move: moves) { history.push(move); state.makeMove(move); } Move m17ky(Square(1,7),LANCE,BLACK); BOOST_CHECK(! MoveStackRejections::probe(state,history,4,m17ky,0,0)); } } BOOST_AUTO_TEST_CASE(MoveStackRejectionsTestBug20110217) { // testFile("/home/ktanaka/work/osl/public-domain/floodgate2010/wdoor+floodgate-10800-60+Bonanza_W3680_180_59+YssL980X_6c+20100811050008.csa"); return; { // wdoor+floodgate-10800-60+Bonanza_W3680_180_59+YssL980X_6c+20100811050008.csa // alpha値ãŒ-100ãªã®ã§åƒæ—¥æ‰‹æ­“迎 const char *str= "P1 * * +TO * * * * * +UM\n" "P2 * * * * * * * * * \n" "P3-FU * +TO+TO * * +NY * * \n" "P4 * * * * +KE * * * +UM\n" "P5 * * * +RY * * * * * \n" "P6 * +FU-FU+GI * -GI * * * \n" "P7+FU * * +GI-KI-NG * * * \n" "P8 * +KY+OU+KI * -TO * -KI * \n" "P9+KY+KE * +FU * * -RY-OU * \n" "P+00KI00KE00KE00FU00FU00FU00FU00FU00FU00FU00FU00FU\n" "P-00KY\n" "+\n" "+0079KI\n" "-5768KI\n" "+7968KI\n" "-0057KI\n" "+0079KI\n" ; BOOST_CHECK(!testString(str,-100)); } { // wdoor+floodgate-900-0+d01+gps_l+20110217190000 const char *str= "P1-KY-KE * * -FU * * * * \n" "P2 * +GI * * * -OU * -KA+HI\n" "P3-FU * * -FU+FU-KI * +FU * \n" "P4 * -FU+GI-KE * * -FU * -FU\n" "P5 * * +OU * * -GI * * * \n" "P6 * * * * * -KE+FU * * \n" "P7+FU+FU-UM * * * -GI-FU+FU\n" "P8 * * * * * * * * * \n" "P9+KY * * * * +HI * * +KY\n" "P+00KI00KI00KI00KE00FU00FU00FU00FU00FU\n" "P-00KY\n" "-\n" "-7776UM\n" "+7584OU\n" "-7694UM\n" "+8475OU\n" "-9476UM\n" "+7584OU\n" ; BOOST_CHECK(!testString(str,-100)); } } BOOST_AUTO_TEST_CASE(MoveStackRejectionsTestCheckLoop) { { // wdoor+floodgate-900-0+d01+gps_l+20110217190000 const char *str= "P1-KY-KE * * -FU * * * * \n" "P2 * +GI * * * -OU * -KA+HI\n" "P3-FU * * -FU+FU-KI * +FU * \n" "P4 * -FU+GI-KE * * -FU * -FU\n" "P5 * * +OU * * -GI * * * \n" "P6 * * * * * -KE+FU * * \n" "P7+FU+FU-UM * * * -GI-FU+FU\n" "P8 * * * * * * * * * \n" "P9+KY * * * * +HI * * +KY\n" "P+00KI00KI00KI00KE00FU00FU00FU00FU00FU\n" "P-00KY\n" "-\n" "-7776UM\n" "+7584OU\n" "-7694UM\n" "+8475OU\n" "-9476UM\n" "+7584OU\n" ; BOOST_CHECK(!testString(str,+100)); } { // wdoor+floodgate-900-0+d01+gps_l+20110217190000 // check side const char *str= "P1-KY-KE * * -FU * * * * \n" "P2 * +GI * * * -OU * -KA+HI\n" "P3-FU * * -FU+FU-KI * +FU * \n" "P4 * -FU+GI-KE * * -FU * -FU\n" "P5 * * +OU * * -GI * * * \n" "P6 * * * * * -KE+FU * * \n" "P7+FU+FU-UM * * * -GI-FU+FU\n" "P8 * * * * * * * * * \n" "P9+KY * * * * +HI * * +KY\n" "P+00KI00KI00KI00KE00FU00FU00FU00FU00FU\n" "P-00KY\n" "-\n" "-7776UM\n" "+7584OU\n" "-7694UM\n" "+8475OU\n" "-9476UM\n" ; BOOST_CHECK(testString(str,-100)); } { // wdoor+floodgate-900-0+d01+gps_l+20110217190000 const char *str= "P1-KY-KE * * -FU * * * * \n" "P2 * +GI * * * -OU * -KA+HI\n" "P3-FU * * -FU+FU-KI * +FU * \n" "P4 * -FU+GI-KE * * -FU * -FU\n" "P5 * * +OU * * -GI * * * \n" "P6 * * * * * -KE+FU * * \n" "P7+FU+FU-UM * * * -GI-FU+FU\n" "P8 * * * * * * * * * \n" "P9+KY * * * * +HI * * +KY\n" "P+00KI00KI00KI00KE00FU00FU00FU00FU00FU\n" "P-00KY\n" "-\n" "-7776UM\n" "+7584OU\n" "-7694UM\n" "+8475OU\n" "-9476UM\n" ; // 本æ¥ã¯alpha値ã«ã‹ã‹ã‚らãštrueã«ãªã£ã¦ã»ã—ã„ãŒï¼Œã§ãã¦ã„ãªã„. // BOOST_CHECK(testString(str,100)); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/quiescenceSearch.t.cc0000644000000000000000000011513512316770314021663 0ustar rootroot/* quiescenceSearch.t.cc */ // #define QSEARCH_DEBUG #include "osl/search/quiescenceSearch2.h" #include "osl/search/quiescenceSearch2.tcc" #include "osl/search/simpleHashTable.h" #include "osl/game_playing/historyToTable.h" #include "osl/game_playing/gameState.h" #include "osl/numEffectState.h" #include "osl/csa.h" #include "osl/misc/milliSeconds.h" #include "osl/oslConfig.h" #include #include #include #include using namespace osl; using namespace osl::search; using namespace osl::game_playing; using namespace osl::eval; const int Gold = PtypeEvalTraits::val; const int Silver = PtypeEvalTraits::val; const int Psilver = PtypeEvalTraits::val; const int Rook = PtypeEvalTraits::val; const int Knight = PtypeEvalTraits::val; const int Pawn = PtypeEvalTraits::val; const int Pknight = PtypeEvalTraits::val; const int Bishop = PtypeEvalTraits::val; const int Pbishop = PtypeEvalTraits::val; typedef NumEffectState state_t; typedef QuiescenceSearch2 qsearch_t; BOOST_AUTO_TEST_CASE(QuiescenceSearchTest050313) { osl::search::SearchState2::checkmate_t checkmate_searcher; // 81RY 82FU PASS ã¯68RY ã§è©°ã§ã™ã‚ˆã‚“ //P1-KY-KE * * * * +RY * -KY //P2 * * * * +UM * +NK * * //P3-FU-OU-GI-FU-FU-FU * * -FU //P4 * * -FU * * * * * * //P5 * * * * +KA * * * * //P6 * * * * * * * * * //P7+FU * +FU+FU+FU+FU+FU * +FU //P8 * * -NK * +OU * * * * //P9+KY+KE * -HI * +KI+GI * +KY //P+00KI00FU00FU //P-00KI00KI00GI00GI00FU00FU00FU //+ // 王手を入れるã¨ãƒ«ãƒ¼ãƒ—ãŒã‚ã‚‹å•題 { state_t state(CsaString( "P1-KY+HI * * * -OU * -KE-KY\n" "P2 * * * * * * -KI * * \n" "P3 * * -KE * -KI-FU * -FU * \n" "P4-FU * +KI * * * -FU * -FU\n" "P5 * * * -KE-GI+GI * * * \n" "P6 * * * * * * +FU * +FU\n" "P7+FU+FU+KI * +KA+FU * * * \n" "P8+KA * * * * * * +HI * \n" "P9+KY * +OU * * * * +KE+KY\n" "P+00FU00FU00FU00FU00FU00FU\n" "P-00GI00GI00FU00FU\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(10000,-6); qsearch_t searcher(sstate, table); PieceEval ev(state); const int result = searcher.search(WHITE, ev, Move(Square(8,1),ROOK,BLACK)); BOOST_CHECK(result < 1000000); } { state_t state(CsaString( "P1 * * * * * * * -KE-KY\n" "P2 * +RY * * * * -KI-OU * \n" "P3 * * * * * +FU-GI-KI * \n" "P4-FU * * -FU-FU * * * -FU\n" "P5 * -UM * * * -FU-FU * * \n" "P6+FU+KI+FU+FU+FU * * * +FU\n" "P7+OU * * * +GI * * * * \n" "P8 * * * * * * * -RY * \n" "P9+KY+KE-GI * * * * * * \n" "P+00GI00FU00FU00FU00FU00FU\n" "P-00KA00KI00KE00KE00KY00KY00FU\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(10000,-6); qsearch_t searcher(sstate, table); PieceEval ev(state); const int result = searcher.search(WHITE, ev, Move(Square(8,6),GOLD,BLACK)); BOOST_CHECK(result < -5000000); BOOST_CHECK(searcher.nodeCount() < 5000); // 1手詰ãªã‚“ã ã‘ã©... } { state_t state(CsaString( "P1 * * * * * * * -KE-KY\n" "P2 * +RY * * * * -KI-OU * \n" "P3 * * * * * +FU-GI-KI * \n" "P4-FU * * -FU-FU * * * -FU\n" "P5 * -UM * * * -FU-FU * * \n" "P6+FU+KI+FU+FU+FU * * * +FU\n" "P7+OU * * * +GI * * * * \n" "P8 * -GI * * * * * -RY * \n" "P9+KY+KE+KE * * * * * * \n" "P+00GI00FU00FU00FU00FU00FU\n" "P-00KA00KI00KE00KY00KY00FU\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(10000,-6); qsearch_t searcher(sstate, table); PieceEval ev(state); const int result = searcher.search(BLACK, ev, Move(Square(8,8),SILVER,WHITE)); BOOST_CHECK(result < 0); } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestLose2) { osl::search::SearchState2::checkmate_t checkmate_searcher; // -8889TO ãŒå…ˆã«ç”Ÿæˆã•れるã¨ï¼Œè² ã‘ã‚’èªè­˜ã§ããªã„ãƒã‚°ãŒä»¥å‰ã‚ã£ãŸ // -0097FU ã‹ã‚‰ä½œã£ãŸå±€é¢ã¨ã¯é§’番å·ãŒé•ã†? state_t state(CsaString( "P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7-FU-GI * * * * * * * \n" "P8 * -FU * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(1000,-6); qsearch_t searcher(sstate, table); PieceEval ev(state); const int result = searcher.search(ev, Move(Square(9,7),PAWN,WHITE)); BOOST_CHECK(result < -100000); } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestLose) { osl::search::SearchState2::checkmate_t checkmate_searcher; state_t state(CsaString( // 色々ã¨ã‚Œã‚‹ãŒå–ã‚‹ã¨è©°ï¼Œå®Ÿã¯å¿…æ­» "P1-KY-KE-GI * -OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU+FU-FU-FU+FU-FU-FU+FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * -FU * \n" "P6 * -FU * * * +FU * * * \n" "P7+FU * +FU+FU-FU-KI+FU+HI+FU\n" "P8 * +KA+KE * +KE * * +KI * \n" "P9+KY+KI+GI * +OU * +GI * +KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(BLACK, ev, Move(Square(5,7),PAWN,WHITE)); // TODO: ã¾ã å¿…æ­»ã¯èªè­˜ã§ããªã„ // BOOST_CHECK_EQUAL(FixedEval::winValue(WHITE), val1); // std::cerr << val1 << "\n"; BOOST_CHECK(val1 < -1000); } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestForcedEscape) { osl::search::SearchState2::checkmate_t checkmate_searcher; state_t state(CsaString( // 色々ã¨ã‚Œã‚‹ãŒå–ã‚‹ã¨è©°ï¼Œæ¡‚æç¢ºå®š "P1-KY-KE-GI * -OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU+FU-FU-FU+FU-FU-FU+FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * -FU * \n" "P6 * -FU+KI * * +FU * * * \n" "P7+FU * +FU+FU-FU-KI+FU+HI+FU\n" "P8 * +KA * * +KE * * +KI * \n" "P9+KY+KE+GI * +OU * +GI * +KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(BLACK, ev, Move(Square(5,7),PAWN,WHITE)); BOOST_CHECK(val1 <= -PtypeEvalTraits::val*2); } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestKnightAttack) { osl::search::SearchState2::checkmate_t checkmate_searcher; #if 0 { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI * -KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * -KE * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * +FU * * \n" "P7+FU+FU+FU+FU+FU+FU * +FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(BLACK, ev, Move(Square(3,4),KNIGHT,WHITE)); BOOST_CHECK(val1 > 0); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU * -FU * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * +KE * -FU\n" "P7+FU * +FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI * +KY\n" "P-00FU00FU\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(BLACK, ev, Move(Square(1,6),PAWN,WHITE)); BOOST_CHECK(val1 < 0); } #endif } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestNoCapture) { osl::search::SearchState2::checkmate_t checkmate_searcher; { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(BLACK, ev, Move(Square(8,2),ROOK,WHITE)); BOOST_CHECK_EQUAL(0, val1); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * -HI * * +GI * * * * \n" "P6 * * * * +FU * * * * \n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * * +KI * * +KA * +HI * \n" "P9+KY+KE * * +OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(WHITE, ev, Move(Square(5,6),PAWN,BLACK)); BOOST_CHECK_EQUAL(0, val1); } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestCaptureBlack) { osl::search::SearchState2::checkmate_t checkmate_searcher; SimpleHashTable table(0); { state_t state1(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * -HI * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state1, checkmate_searcher); qsearch_t searcher1(sstate, table); PieceEval ev(state1); const int val1 = searcher1.search(BLACK, ev, Move(Square(8,6),ROOK,WHITE)); BOOST_CHECK_EQUAL(PtypeEvalTraits::val*2, val1); } { // 飛車より角をå–ã‚‹ã®ãŒå¾— state_t state2(CsaString( "P1-KY-KE * -KI-OU-KI-GI-KE-KY\n" "P2 * -GI * * * * * * * \n" "P3-FU * -FU-FU-FU-FU-FU-FU-FU\n" "P4 * +FU * * * * * * * \n" "P5 * -FU * * * * * * * \n" "P6 * -HI * * * * * -KA * \n" "P7+FU+HI+FU+FU+FU+FU+GI+FU+FU\n" "P8 * +KA+GI * * * +FU * * \n" "P9+KY+KE * +KI+OU * +KI+KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state2, checkmate_searcher); qsearch_t searcher2(sstate, table); PieceEval ev2(state2); const int val2 = searcher2.search(BLACK, ev2, Move(Square(8,6),ROOK,WHITE)); BOOST_CHECK_EQUAL(PtypeEvalTraits::val*2, val2); // + è„…å¨ } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestCaptureWhite) { osl::search::SearchState2::checkmate_t checkmate_searcher; SimpleHashTable table(0); { state_t state1(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * -HI * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * +HI+GI+KI\n" "P9+KY+KE * * +OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state1, checkmate_searcher); qsearch_t searcher1(sstate, table); PieceEval ev(state1); const int val1 = searcher1.search(WHITE, ev, Move(Square(8,7),PAWN,BLACK)); BOOST_CHECK_EQUAL(-PtypeEvalTraits::val -PtypeEvalTraits::val*2 +PtypeEvalTraits::val, val1); } { // 飛車を先ã«ã¨ã‚Œã°é§’æãªã— state_t state2(CsaString( "P1-KY-KE * -KI-OU-KI-GI-KE-KY\n" "P2 * -GI * * * * * * * \n" "P3-FU * -FU-FU-FU-FU-FU-FU-FU\n" "P4 * +FU * * * * * * * \n" "P5 * -FU * * * * * * -KA\n" "P6 * -HI+FU * * * * * * \n" "P7+FU+HI+KA+FU+FU+FU+GI+FU+FU\n" "P8 * * +GI * +OU * +FU * * \n" "P9+KY+KE * +KI * +KI * +KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state2, checkmate_searcher); qsearch_t searcher2(sstate, table); PieceEval ev2(state2); const int val2 = searcher2.search(WHITE, ev2, Move(Square(7,8),SILVER,BLACK)); BOOST_CHECK_EQUAL(0, val2); // 0 + è„…å¨ } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestCaptureCheck) { osl::search::SearchState2::checkmate_t checkmate_searcher; SimpleHashTable table(0); { // 銀をå–ã‚‹ã¨é¾ãŒç´ æŠœããªã®ã§æ­©ã‚’å–ã‚‹ state_t state0(CsaString( "P1 * -OU * * -RY-GI * +RY * \n" "P2 * * * * -KA * +GI * * \n" "P3-FU-FU-FU-FU * -FU-FU-FU-FU\n" "P4 * * * * -FU * -GI-KI * \n" "P5 * * * * +FU * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA * * * * +KI * * \n" "P9+KY+KE+GI+KI+OU * * +KE+KY\n" "P-00AL\n" "-\n").initialState()); SearchState2Core sstate(state0, checkmate_searcher); qsearch_t searcher0(sstate, table); PieceEval ev0(state0); const int val0 = searcher0.search(WHITE, ev0, Move(Square(3,2),SILVER,BLACK)); BOOST_CHECK_EQUAL(-Pawn*2+Psilver-Silver, val0); } { // 32金をå–ã‚‹ã¨çŽ‹ãŒç´ æŠœã state_t state1(CsaString( "P1-KY-OU * * * -KI * +RY * \n" "P2-KY * * * -GI * +KI * * \n" "P3-FU-FU-FU-KA * -FU-FU-FU-FU\n" "P4 * * * * -FU * * -RY * \n" "P5 * * * -FU+FU * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * +KA * * * * +GI * * \n" "P9+KY+KE+GI * +OU+KI * +KE+KY\n" "P-00AL\n" "-\n").initialState()); SearchState2Core sstate(state1, checkmate_searcher); BOOST_CHECK_EQUAL(0, PieceEval(state1).value()); qsearch_t searcher1(sstate, table); PieceEval ev(state1); const int val1 = searcher1.search(WHITE, ev, Move(Square(3,2),GOLD,BLACK)); BOOST_CHECK_EQUAL(-PtypeEvalTraits::val*2, val1); } { state_t state2(CsaString( "P1-KY-KE-KE-KI * * * +RY-KY\n" "P2-KA-GI-OU-FU * * * * * \n" "P3-FU-FU * -KI * * * * * \n" "P4 * * * * +FU * * -FU-FU\n" "P5 * * * +FU * * * * * \n" "P6 * * +FU * * * +GI+FU+FU\n" "P7+FU * * * -GI * +KI * * \n" "P8 * * * * * -RY+FU+OU * \n" "P9+KY+KE * * * * -GI+KE+KY\n" "P+00FU00FU00KI00KA\n" "P-00FU00FU00FU00FU\n" "+\n" ).initialState()); // +2818OU -6354KI +2111RY ã§æãªã®ã§å¾Œæ‰‹ã¯2手目ã§ãƒ‘ス SearchState2Core sstate(state2, checkmate_searcher); qsearch_t searcher2(sstate, table); PieceEval ev(state2); if (OslConfig::verbose()) std::cerr << ev.value() << "\n"; const Move last_move = Move(Square(3,9),SILVER,WHITE); const int val2 = searcher2.search(BLACK, ev, last_move); const int val2n = searcher2.search(-899, -895, ev, last_move); BOOST_CHECK_EQUAL(val2, val2n); } { state_t state3(CsaString( "P1-KY-KE * -KI * * * +RY-KY\n" "P2 * -GI-OU-FU * * * * * \n" "P3-FU-FU * -KI * * * * * \n" "P4 * * * * +FU * * * -FU\n" "P5 * * * +FU * * * * * \n" "P6 * * +FU * * * +GI * +FU\n" "P7+FU * * * * * +KI+FU * \n" "P8 * * * * * -RY+FU+OU * \n" "P9+KY+KE * * * -GI-KA+KE+KY\n" "P+00FU00FU00KI00KA\n" "P-00FU00FU00FU00FU00FU00KE00GI\n" "+\n" ).initialState()); SearchState2Core sstate(state3, checkmate_searcher); qsearch_t searcher3(sstate, table); PieceEval ev(state3); if (OslConfig::verbose()) std::cerr << ev.value() << "\n"; // +2818OU -4938NG PASS const Move last_move = Move(Square(3,9),BISHOP,WHITE); const int val3 = searcher3.search(BLACK, ev, last_move); const int val3n = searcher3.search(val3-1, val3+1, ev, last_move); // window ã‚’ç‹­ã‚ã¦ã‚‚çµæžœãŒåŒã˜ BOOST_CHECK_EQUAL(val3, val3n); } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestCaptureCheckMate) { osl::search::SearchState2::checkmate_t checkmate_searcher; SimpleHashTable table(0); { // è©° state_t state(CsaString( "P1-KY-KE-GI-KI-KA-KI-GI-KE-KY\n" "P2 * -HI * * * * * -OU * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(BLACK, ev, Move(Square(2,3),PAWN,WHITE)); BOOST_CHECK_EQUAL(FixedEval::winByCheckmate(BLACK), val1); } { // 王手ã˜ã‚ƒãªã‘れã°é£›è»ŠãŒã¨ã‚Œã‚‹ãŒï¼Œé€ƒã’ã¦ã„ã‚‹é–“ã«æ­©ã‚’ã¨ã‚‰ã‚Œã‚‹ï¼Ž state_t state(CsaString( "P1-KY-KE-GI-KI * -KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU * -FU-FU-FU-OU-FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * -FU * * * +HI * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * * * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(WHITE, ev, Move(Square(7,6),PAWN,BLACK)); BOOST_CHECK_EQUAL(Pawn*2, val1); } { // 王ã§é£›è»Šã‚’å–ã£ã¦çŽ‹æ‰‹å›žé¿ state_t state(CsaString( "P1-KY-KE-GI-KI * -KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-OU-FU-FU\n" "P4 * * * * * * -FU+HI * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * * * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(WHITE, ev, Move(Square(7,6),PAWN,BLACK)); BOOST_CHECK_EQUAL(-PtypeEvalTraits::val*2, val1); } { // é€ã‚Šé‡‘ state_t state(CsaString( "P1 * * * * * * * * * \n" "P2 * +KI-OU-KI+RY * * * * \n" "P3-FU-FU-FU-FU-FU * -FU-FU-FU\n" "P4 * * -RY * * * -KI * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * +GI * * * * * \n" "P9+KY+KE * * +OU+KI+GI+KE+KY\n" "P-00AL\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(WHITE, ev, Move(Square(8,2),GOLD,BLACK)); BOOST_CHECK_EQUAL(Pawn*2, val1); } { // ãƒã‚°ã®å¯èƒ½æ€§ãŒã‚ã£ãŸãŒ QuiescenceSearch ã®ã›ã„ã§ã¯ãªã„よã†ã  state_t state(CsaString( "P1-KY * * * * +NK-OU * -KY\n" "P2 * * * * +TO-GI-KI * * \n" "P3-FU * -HI * * -FU * -FU * \n" "P4 * * * * -GI * -FU-KY-FU\n" "P5 * -FU * * * -KE * +FU * \n" "P6+FU * * -FU+FU * * * * \n" "P7+KA+FU+KE+GI * +FU+FU * +FU\n" "P8-GI+KI+KI * * * * +HI * \n" "P9-UM * +OU * * * * +KE+KY\n" "P+00FU\n" "P+00FU\n" "P-00FU\n" "P-00KI\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); qsearch_t searcher(sstate, table); PieceEval ev(state); const int val1 = searcher.search(WHITE, ev, Move(Square(5,1),Square(4,1), PKNIGHT,PTYPE_EMPTY,false,BLACK)); BOOST_CHECK(eval::isConsistentValueForNormalState(val1)); BOOST_CHECK(! FixedEval::isWinValue(BLACK, val1)); } } static int error_count = 0; static void testIsEvalValueConsistent(std::string const& filename) { osl::search::SearchState2::checkmate_t checkmate_searcher; // QuiescenceLog::init("qsearch.log"); auto record=CsaFileMinimal(filename).load(); const NumEffectState src(record.initialState()); const std::vector moves=record.moves; typedef QuiescenceSearch2 qsearch_t; PieceEval ev(src); GameState state(src); SimpleHashTable table(400000,-8,OslConfig::verbose()); SimpleHashTable null_table(400000,100,false); const int black_win = search::FixedEval::winByLoop(BLACK); const int white_win = search::FixedEval::winByLoop(WHITE); time_point started = clock::now(); size_t node_count = 0; for (unsigned int i=0;i 0) { #if 0 if ((i % 64) == 0) table.clear(); #endif NumEffectState state0(state.state()); NumEffectState state1(state0); HistoryToTable::adjustTable(state, table, black_win, 0, white_win); HistoryToTable::adjustTable(state, null_table, black_win, 0, white_win); SearchState2Core sstate0(state0, checkmate_searcher); SearchState2Core sstate1(state1, checkmate_searcher); qsearch_t qs_null(sstate0, null_table); qsearch_t qs(sstate1, table); const Move last_move = moves[i-1]; const int val_null = qs_null.search(state0.turn(), ev, last_move, 6); const int val = qs.searchIteratively(state1.turn(), ev, last_move, 6); node_count += qs.nodeCount() + qs_null.nodeCount(); if (abs(val_null - val) > 10000) { if (OslConfig::verbose()) std::cerr << filename << " " << i << "\n" << state0 << "\n" << ev.value() << " " << val_null << " " << val << "\n"; ++error_count; } BOOST_CHECK(isConsistentValue(val)); if (OslConfig::inUnitTestShort()) // 最近ã¯ã‹ãªã‚Šç•°ãªã‚‹ BOOST_CHECK(error_count < 50); // BOOST_CHECK_EQUAL(val_null, val); BOOST_CHECK(state0.isConsistent(true)); BOOST_CHECK(state1.isConsistent(true)); } const Move move = moves[i]; state.pushMove(move); ev.update(state.state(), move); } if (OslConfig::verbose()) { std::cerr << node_count << " " << toSeconds(clock::now() - started) << "\n"; } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestEquality) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); const int count = (OslConfig::inUnitTestShort() ? 10: 100); std::unique_ptr progress; if (OslConfig::inUnitTestLong() && !OslConfig::verbose()) progress.reset(new boost::progress_display(count, std::cerr)); std::string file_name; for (int i=0; i> file_name); i++){ if (progress) ++(*progress); if (file_name == "") break; testIsEvalValueConsistent(OslConfig::testCsaFile(file_name)); } BOOST_CHECK(error_count < 50); // BOOST_CHECK_EQUAL(0, error_count); } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestTakeBack) { osl::search::SearchState2::checkmate_t checkmate_searcher; { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.takeBackValue (1001, -1001, ev, Move(Square(2,6),PAWN,BLACK)); BOOST_CHECK_EQUAL(0, value); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.takeBackValue (1001, -1001, ev, Move(Square(2,4),PAWN,BLACK)); BOOST_CHECK_EQUAL(0, value); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * * +HI\n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.takeBackValue (1001, -1001, ev, Move(Square(2,4),PAWN,BLACK)); BOOST_CHECK_EQUAL(-Pawn*2, value); } { state_t state(CsaString( // å–れãªã„ "P1-KY-KE-GI-KI-OU-KI-GI * -KY\n" "P2 * -HI * * * * * * * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * +FU+FU * -KA\n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU-KE * +FU+FU\n" "P8 * +KA * * * +GI * +HI * \n" "P9+KY+KE+GI+KI+OU+KI * +KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.takeBackValue (-1001, 1001, ev, Move(Square(4,7),KNIGHT,WHITE)); BOOST_CHECK_EQUAL(0, value); } { // è©° state_t state(CsaString( "P1-KY-KE * -KI * * * +RY-KY\n" "P2 * -GI-OU-FU * * * * * \n" "P3-FU-FU * -KI * * * * * \n" "P4 * * * * +FU * * * -FU\n" "P5 * * * +FU * * * * * \n" "P6 * * +FU * * * +GI * +FU\n" "P7+FU * * * * * -NG+FU * \n" "P8 * * * * * -RY * * +OU\n" "P9+KY+KE * * * * -KA+KE+KY\n" "P+00FU00FU00KI00KA\n" "P-00FU00FU00FU00FU00FU00KE00GI00FU00KI\n" "+\n" ).initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.takeBackValue (-10001,+10001,ev,Move(Square(3,8),Square(3,7),PSILVER,GOLD,false,WHITE)); BOOST_CHECK_EQUAL(FixedEval::winByCheckmate(WHITE), value); } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestThreat) { osl::search::SearchState2::checkmate_t checkmate_searcher; { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * +FU * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK_EQUAL(ev.value(), value); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK(ev.value() < value); // 後手ãŒãƒ‘スã™ã‚‹ã¨å±é™º } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * * +HI\n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK(ev.value() < value); BOOST_CHECK(state.isConsistent()); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU * -GI-KE-KY\n" "P2 * -HI * * * * -KI-KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * * +HI\n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK_EQUAL(ev.value(), value); BOOST_CHECK(state.isConsistent()); } { state_t state(CsaString( // å–れãªã„ "P1-KY-KE-GI-KI-OU-KE-GI * -KY\n" "P2 * -HI * * * * * * * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * +FU+FU * -KA\n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU-KI * +FU+FU\n" "P8 * +KA * +GI * +KI * +HI * \n" "P9+KY+KE * +KI+OU * +GI+KE+KY\n" "+\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK_EQUAL(ev.value(), value); BOOST_CHECK(state.isConsistent()); } { state_t state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * -HI * * +GI * * * * \n" "P6 * * * * +FU * * * * \n" "P7+FU+FU+FU+FU * +FU+FU+FU+FU\n" "P8 * * +KI * * +KA * +HI * \n" "P9+KY+KE * * +OU+KI+GI+KE+KY\n" "+\n").initialState()); SimpleHashTable table(0); SearchState2Core sstate(state, checkmate_searcher); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK_EQUAL(0, value); } { state_t state(CsaString( "P1-KY-KE * -KI * * * +RY-KY\n" "P2 * -GI-OU-FU * * * * * \n" "P3-FU-FU * -KI * * * * * \n" "P4 * * * * +FU * * * -FU\n" "P5 * * * +FU * * * * * \n" "P6 * * +FU * * * +GI * +FU\n" "P7+FU * * * * * +KI+FU * \n" "P8 * * * * * -RY-NG * +OU\n" "P9+KY+KE * * * * -KA+KE+KY\n" "P+00FU00FU00KI00KA\n" "P-00FU00FU00FU00FU00FU00KE00GI00FU\n" "+\n" ).initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(0); qsearch_t searcher(sstate, table); PieceEval ev(state); const int value = searcher.staticValueWithThreat(ev); BOOST_CHECK(value < -8000); } } static bool betterThan(const char *l, const char *r) { osl::search::SearchState2::checkmate_t checkmate_searcher; state_t state_l(CsaString(l).initialState()); state_t state_r(CsaString(r).initialState()); assert(state_l.turn() == state_r.turn()); SimpleHashTable table(1000); int value_l, value_r; { // root ã§ã¯ãªã„状態ã«ã™ã‚‹ãŸã‚ã€æ‰‹ç•ªã‚’変更ã—ã¦ãŠã„ã¦ã‹ã‚‰ãƒ‘ス SearchState2Core sstate(state_l, checkmate_searcher); sstate.pushPass(); qsearch_t searcher(sstate, table); sstate.pushPass(); PieceEval ev(state_l); value_l = searcher.staticValueWithThreat(ev); } table.clear(); { // root ã§ã¯ãªã„状態ã«ã™ã‚‹ SearchState2Core sstate(state_r, checkmate_searcher); sstate.pushPass(); qsearch_t searcher(sstate, table); sstate.pushPass(); PieceEval ev(state_r); value_r = searcher.staticValueWithThreat(ev); } return eval::betterThan(state_l.turn(), value_l, value_r); } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestCompare) { if (QSearchTraits::FirstThreat >= 20) { const char *l = "P1-KY-KE-GI-KI-OU * -GI-KE-KY\n" "P2 * -HI * * * * -KI-KA * \n" "P3-FU * -FU-FU-FU-FU-FU-FU-FU\n" "P4 * -FU * * * * * +HI * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * * * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00FU\n" "+\n"; const char *r = "P1-KY-KE-GI-KI-OU * -GI-KE-KY\n" "P2 * -HI * * * * -KI-KA * \n" "P3-FU * -FU-FU-FU-FU-FU * -FU\n" "P4 * -FU * * * * * -FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * * +HI\n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P-00FU\n" "+\n"; BOOST_CHECK(betterThan(l, r)); // 交æ›ã—ãŸæ–¹ãŒè‰¯ã„ } { // 二ã¤ã®è„…å¨ // http://www31.ocn.ne.jp/~kfend/inside_kfend/quiescence.html#c5 const char *l = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * -HI * * +GI * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * * +KI * * +KA * +HI * \n" "P9+KY+KE * * +OU+KI+GI+KE+KY\n" "+\n"; const char *r = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * -HI * * +GI * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * * * * * +KA * +HI * \n" "P9+KY+KE * +KI+OU+KI+GI+KE+KY\n" "+\n"; BOOST_CHECK(betterThan(l, r)); } { // 二ã¤ã®è„…å¨ åŒã˜ptype const char *l = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * -FU * * -KA * \n" "P3-FU-FU-FU-FU * -FU-FU-FU-FU\n" "P4 * -HI * * +GI * * * * \n" "P5 * * * * * * * * * \n" "P6 * +GI * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * * +KI * * +KA * +HI * \n" "P9+KY+KE * * +OU+KI * +KE+KY\n" "+\n"; const char *r = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * -FU * * -KA * \n" "P3-FU-FU-FU-FU * -FU-FU-FU-FU\n" "P4 * -HI * * +GI * * * * \n" "P5 * * * * * * * * * \n" "P6 * +GI * * * * * * * \n" "P7+FU * +FU+FU+FU+FU+FU+FU+FU\n" "P8 * +FU+KI * * +KA * +HI * \n" "P9+KY+KE * * +OU+KI * +KE+KY\n" "+\n"; BOOST_CHECK(betterThan(l, r)); } { // æˆã‚‹è„…å¨ const char *l = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * -HI * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * * +GI * * +KA * +HI * \n" "P9+KY+KE * +KI+OU+KI+GI+KE+KY\n" "+\n"; const char *r = "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * -HI * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU * +FU+FU+FU+FU+FU+FU+FU\n" "P8 * * +GI * * +KA * +HI * \n" "P9+KY+KE * +KI+OU+KI+GI+KE+KY\n" "P+00FU\n" "+\n"; BOOST_CHECK(betterThan(l, r)); } { // 逃ã’られãªã„è„…å¨ã¯r4103ã§å»ƒæ­¢ } } BOOST_AUTO_TEST_CASE(QuiescenceSearchTestFocalPawn) { osl::search::SearchState2::checkmate_t checkmate_searcher; #if 0 { // -2324FU+3524GI-4334GI ã§å¾Œæ‰‹æ­©å¾—ã§æœ‰åˆ© ã¨ã‹æ€ã£ã¦ã„る㨠// +0033FUã§ç ´æ»… state_t state(CsaString( "P1-KY-KE * -KI * * * -KE * \n" "P2 * -OU-GI * -KI * -HI-KA-KY\n" "P3 * -FU-FU * * -GI * -FU-FU\n" "P4-FU * * -FU-FU-FU+FU+FU * \n" "P5 * * * * * * +GI * * \n" "P6+FU * +FU * +FU * * * +FU\n" "P7 * +FU * +FU * +FU * * * \n" "P8 * +KA+OU * +KI * +HI * * \n" "P9+KY+KE+GI+KI * * * +KE+KY\n" "P-00FU\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(10000,-6); qsearch_t searcher(sstate, table); PieceEval ev(state); const Move m24fu(Square(2,5),Square(2,4),PAWN,PTYPE_EMPTY,false,BLACK); const int val = searcher.search(WHITE, ev, m24fu); BOOST_CHECK(val > 0); // 先手有利! } { // è§’ãŒå¼•ã£è¾¼ã‚“ã§ã„ã¦ã‚‚åŒã˜ state_t state(CsaString( "P1-KY-KE * -KI * * * -KE-KA\n" "P2 * -OU-GI * -KI * -HI * -KY\n" "P3 * -FU-FU * -FU-GI * -FU-FU\n" "P4-FU * * -FU * -FU+FU+FU * \n" "P5 * * * * * * +GI * * \n" "P6+FU * +FU * +FU * * * +FU\n" "P7 * +FU * +FU * +FU * * * \n" "P8 * +KA+OU * +KI * +HI * * \n" "P9+KY+KE+GI+KI * * * +KE+KY\n" "P-00FU\n" "-\n").initialState()); SearchState2Core sstate(state, checkmate_searcher); SimpleHashTable table(10000,-6); qsearch_t searcher(sstate, table); PieceEval ev(state); const Move m24fu(Square(2,5),Square(2,4),PAWN,PTYPE_EMPTY,false,BLACK); const int val = searcher.search(WHITE, ev, m24fu); BOOST_CHECK(val > 0); // 先手有利! } #endif } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/lRUMoves.t.cc0000644000000000000000000000137212316770314020122 0ustar rootroot#include "osl/search/lRUMoves.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(LRUMovesTestSetMove) { LRUMoves moves; BOOST_CHECK_EQUAL(Move::INVALID(), moves[0]); BOOST_CHECK_EQUAL(Move::INVALID(), moves[1]); const Move m24ki(Square(2,4), GOLD, BLACK); moves.setMove(m24ki); BOOST_CHECK_EQUAL(m24ki, moves[0]); BOOST_CHECK_EQUAL(Move::INVALID(), moves[1]); const Move m24fu(Square(2,4), PAWN, BLACK); moves.setMove(m24fu); BOOST_CHECK_EQUAL(m24fu, moves[0]); BOOST_CHECK_EQUAL(m24ki, moves[1]); moves.setMove(m24fu); BOOST_CHECK_EQUAL(m24fu, moves[0]); BOOST_CHECK_EQUAL(m24ki, moves[1]); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/dominanceCheck.t.cc0000644000000000000000000000725612316770314021310 0ustar rootroot// dominanceCheck.t.cc #include "osl/search/dominanceCheck.h" #include "osl/csa.h" #include "osl/numEffectState.h" #include using namespace osl; using namespace osl::search; static void confirmDetectionInLast(HashKey key, const std::vector& moves, DominanceCheck::Result result) { HashKeyStack history; for (size_t i=0; i& moves = test_record.load().moves; confirmDetectionInLast(HashKey(state), moves, DominanceCheck::LOSE); } BOOST_AUTO_TEST_CASE(SearchDominanceCheckLoseWhite) { const char *test_record_str = "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * -KE * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * +KE * * * * * * * \n" "P8-TO+KY * * * * * * * \n" "P9+OU+KY * * * * * * * \n" "P+00FU\n" "P-00AL\n" "+\n" "+9998OU\n" "-0097FU\n" "+9899OU\n" "-9798TO\n"; CsaString test_record(test_record_str); NumEffectState state(test_record.initialState()); const std::vector& moves = test_record.load().moves; confirmDetectionInLast(HashKey(state), moves, DominanceCheck::LOSE); } BOOST_AUTO_TEST_CASE(SearchDominanceCheckWinWhite) { const char *test_record_str = "P1 * * * * * * * -KY-OU \n" "P2 * * * * * * * -KY * \n" "P3 * * * * * * * -KY+FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * +KE * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00FU\n" "P-00AL\n" "+\n" "+1312TO\n" "-1112OU\n" "+0013FU\n" "-1211OU\n"; CsaString test_record(test_record_str); NumEffectState state(test_record.initialState()); const std::vector& moves = test_record.load().moves; confirmDetectionInLast(HashKey(state), moves, DominanceCheck::WIN); } BOOST_AUTO_TEST_CASE(SearchDominanceCheckWinBlack) { const char *test_record_str = "P1 * * * * * * * * -OU\n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * -KE * * * * * * * \n" "P6 * * * * * * * * * \n" "P7-FU+KE * * * * * * * \n" "P8 * +KY * * * * * * * \n" "P9+OU+KY * * * * * * * \n" "P+00FU\n" "P-00AL\n" "-\n" "-9798TO\n" "+9998OU\n" "-0097FU\n" "+9899OU\n"; CsaString test_record(test_record_str); NumEffectState state(test_record.initialState()); const std::vector& moves = test_record.load().moves; confirmDetectionInLast(HashKey(state), moves, DominanceCheck::WIN); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/problems.h0000644000000000000000000000111512316770314017624 0ustar rootroot/* problems.h */ #ifndef _PROBLEMS_H #define _PROBLEMS_H #include "osl/basic_type.h" namespace osl { struct Problem { enum { MaxExpected = 8 }; const char *state; const char *expected[MaxExpected]; bool acceptable(Move) const; }; // 1手ã§è§£ã‘ã‚‹ã¨æ€ã‚れるå•題 extern const Problem problems1[]; extern const int numProblems1; // 3手ã§è§£ã‘ã‚‹ã¨æ€ã‚れるå•題 ... extern const Problem problems3[]; extern const int numProblems3; } #endif /* _PROBLEMS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/searchRecorder.t.cc0000644000000000000000000000125012316770314021334 0ustar rootroot#include "osl/search/searchRecorder.h" #include "osl/moveLogProb.h" #include using namespace osl; BOOST_AUTO_TEST_CASE(SearchRecorderTestWrite) { const bool verbose = OslConfig::verbose(); SearchRecorder recorder("SearchRecorderTest.log"); MoveLogProb m(Move(Square(6,5),Square(2,1),PBISHOP,KNIGHT,true,BLACK), 7777777); recorder.tryMove(m, 111, 11111); recorder.recordValue(m, 222, true, 22222); recorder.recordTopLevelLowFail(m, 333); recorder.recordTopLevelHighFail(m, 444); recorder.startSearch(555); recorder.finishSearch(m.move(), 1.0, verbose); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/dualThreatmateState.t.cc0000644000000000000000000000250412316770314022351 0ustar rootroot#include "osl/search/dualThreatmateState.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(DualThreatmateStateTestConstruction) { DualThreatmateState s; BOOST_CHECK(s.status(BLACK).isUnknown()); BOOST_CHECK(s.status(WHITE).isUnknown()); } BOOST_AUTO_TEST_CASE(DualThreatmateStateTestTransition) { DualThreatmateState t; const Move bmove(Square(5,2),GOLD,BLACK); const Move wmove(Square(5,8),GOLD,WHITE); t.setThreatmate(BLACK, bmove); // 先手番ã€å…ˆæ‰‹çމã«è©°ã‚ã‚ BOOST_CHECK(t.isThreatmate(BLACK)); BOOST_CHECK(! t.isThreatmate(WHITE)); BOOST_CHECK_EQUAL(bmove, t.threatmateMove(BLACK)); DualThreatmateState mc; mc.updateInLock(BLACK, &t, false); BOOST_CHECK(mc.mayHaveCheckmate(BLACK)); BOOST_CHECK(mc.status(WHITE).isUnknown()); mc.setThreatmate(WHITE, wmove); // ã•ã£ãã®å…ˆæ‰‹ã®æŒ‡ã—ã¦ã¯è©°ã‚ã‚ã ã£ãŸ BOOST_CHECK(mc.mayHaveCheckmate(BLACK)); BOOST_CHECK(mc.isThreatmate(WHITE)); DualThreatmateState ct; ct.updateInLock(WHITE, &mc, true); // 後手ãŒçŽ‹æ‰‹ DualThreatmateState cte; cte.updateInLock(BLACK, &ct, false); // 先手ãŒé€ƒã’ã‚‹ BOOST_CHECK(cte.status(BLACK).isUnknown()); BOOST_CHECK(cte.maybeThreatmate(WHITE)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/simpleHashRecord.t.cc0000644000000000000000000000317212316770314021642 0ustar rootroot#include "osl/search/simpleHashRecord.h" #include using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(SimpleHashRecordTestSize) { BOOST_CHECK(sizeof(SimpleHashRecord) <= 256); } BOOST_AUTO_TEST_CASE(SimpleHashRecordTestAbsoluteBound) { search::SimpleHashRecord record; const int limit = 100; const int value = 300; BOOST_CHECK_EQUAL(false, record.hasLowerBound(limit)); BOOST_CHECK_EQUAL(false, record.hasUpperBound(limit)); record.setLowerBound(BLACK, limit, MoveLogProb(), value); BOOST_CHECK_EQUAL(true, record.hasLowerBound(limit)); BOOST_CHECK_EQUAL(false, record.hasUpperBound(limit)); BOOST_CHECK_EQUAL(true, record.hasAbsoluteLowerBound(BLACK, limit)); BOOST_CHECK_EQUAL(false, record.hasAbsoluteLowerBound(WHITE, limit)); BOOST_CHECK_EQUAL(false, record.hasAbsoluteUpperBound(BLACK, limit)); BOOST_CHECK_EQUAL(true, record.hasAbsoluteUpperBound(WHITE, limit)); BOOST_CHECK_EQUAL(value, record.absoluteLowerBound(BLACK)); BOOST_CHECK_EQUAL(value, record.absoluteUpperBound(WHITE)); record = SimpleHashRecord(); record.setUpperBound(BLACK, 100, MoveLogProb(), -value); BOOST_CHECK_EQUAL(false, record.hasAbsoluteLowerBound(BLACK, limit)); BOOST_CHECK_EQUAL(true, record.hasAbsoluteLowerBound(WHITE, limit)); BOOST_CHECK_EQUAL(true, record.hasAbsoluteUpperBound(BLACK, limit)); BOOST_CHECK_EQUAL(false, record.hasAbsoluteUpperBound(WHITE, limit)); BOOST_CHECK_EQUAL(-value, record.absoluteLowerBound(WHITE)); BOOST_CHECK_EQUAL(-value, record.absoluteUpperBound(BLACK)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/search/problems.cc0000644000000000000000000001070112316770314017763 0ustar rootroot/* problems.cc */ #include "problems.h" #include "osl/csa.h" #include #include #include const osl::Problem osl::problems1[] = { { // åˆæ³•手無㗠"P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KE-KA-KY\n" "P3 * * * * * * -FU+KE-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7-FU-GI * * * * * * * \n" "P8 * -FU * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "-", { "%TORYO", } }, { "P1+KA+TO+TO+HI * +TO-KI-KE-OU\n" "P2+KA+TO+TO+KY+FU+TO-FU-FU-KY\n" "P3+HI * +FU+FU * * -KI-GI-FU\n" "P4+KE+KE+KY+KY * * * * * \n" "P5+FU+KE * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * -GI * +GI * +FU+FU * * \n" "P8 * -FU * * +KI * * * * \n" "P9+OU * * * * * * * * \n" "P-00FU\n" "P+00AL\n" "-\n", { "-0097FU", } // -0098FUã¯æ‰“æ­©è©° }, { "P1-KY-KE-GI-KI-OU * -GI-KE-KY\n" "P2 * -HI * * * * -KI * * \n" "P3-FU * -FU-FU-FU-FU-KA * -FU\n" "P4 * -FU * * * * -FU+FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00FU\n" "+\n", { "+2423TO", } }, { "P1-KY-KE-GI-KI-OU * -GI-KE-KY\n" "P2 * -HI * * * * -KI-KA * \n" "P3-FU * -FU-FU-FU-FU-FU-FU-FU\n" "P4 * -FU * * * * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "-\n", { "-2324FU", } }, { "P1-KY-KE-GI-KI-OU-KI * -KE-KY\n" "P2 * * * * * * * -GI * \n" "P3-FU * * -FU-FU-FU * -FU-FU\n" "P4 * * -FU * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * -HI * * * * * * * \n" "P7+FU * * +FU+FU+FU+FU+FU+FU\n" "P8 * * +HI * * +OU * * * \n" "P9+KY+KE+GI+KI * +KI+GI+KE+KY\n" "P+00KA00FU\n" "P-00KA00FU00FU\n" "+\n", { "+0095KA", } }, { "P1-KY-KE-GI-KI-OU-KI * -KE-KY\n" "P2 * -HI * * * -GI * -KA * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU * +FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n", { "+8822UM", } }, }; const int osl::numProblems1 = sizeof(osl::problems1)/sizeof(osl::Problem); const osl::Problem osl::problems3[] = { { "P1-KY-KE-GI-KI-OU * -GI-KE-KY\n" "P2 * -HI * * * * -KI-KA * \n" "P3-FU * -FU-FU-FU-FU-FU * -FU\n" "P4 * -FU * * * * * -FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU * +FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P-00FU\n" "+\n", { "+2824HI", } }, #if 0 { // ç„¡é§„ãªçŽ‹æ‰‹ã‚’ã‹ã‘ãšã«æ½”è‰¯ãæŠ•了ã™ã‚‹ // 3手読ã¿ãŒå¿…è¦ "P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU * -FU\n" "P4 * * * * * * * -FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7-KI-GI * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00KE\n" "P-00AL\n" "+\n", { "%TORYO", } }, #endif }; const int osl::numProblems3 = sizeof(osl::problems3)/sizeof(osl::Problem); // "P1 * * * * * * * * * \n" // "P2 * * * * * * * * * \n" // "P3 * * * * * * * * * \n" // "P4 * * * * * * * * * \n" // "P5 * * * * * * * * * \n" // "P6 * * * * * * * * * \n" // "P7 * * * * * * * * * \n" // "P8 * * * * * * * * * \n" // "P9 * * * * * * * * * \n" // "P+\n" // "P-\n" // "+\n", bool osl::Problem::acceptable(Move m) const { std::stringstream ss; ss << csa::show(m); for (int i=0; i #include #include #include using namespace osl; using namespace osl::search; typedef SearchState2::checkmate_t checkmate_t; static void testProblems(const Problem *problems, int numProblems, int depth) { static bool loaded = eval::ProgressEval::setUp() && osl::eval::ml::OpenMidEndingEval::setUp() && osl::progress::ml::NewProgress::setUp(); BOOST_CHECK(loaded); CountRecorder recorder; for (int i=0; i using namespace osl; using namespace osl::search; BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestPromote) { { NumEffectState state(CsaString( "P1+HI * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7-FU-GI * +GI * * * * * \n" "P8 * -FU * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::promote(state, PieceMask(), moves); // 98æˆéŠ€ã‚’check ã¯çœãã®ã§promoteã§ç”Ÿæˆã—ã¦ã„ãªã„ã¨èª­ã¾ãªã„ BOOST_CHECK_EQUAL((size_t)3, moves.size()); } { NumEffectState state(CsaString( "P1-KY * * * * * * * -KY\n" "P2 * -HI * * * -GI-KI-OU * \n" "P3 * * -KE * -KA-KI-KE-FU+FU\n" "P4 * -GI-FU-FU-FU-FU * * * \n" "P5-FU-FU * * * * -FU+FU+HI\n" "P6 * * +FU+FU+FU+FU * * * \n" "P7+FU+FU+GI+KI+GI * +KE * * \n" "P8 * +OU+KI * * * * * * \n" "P9+KY+KE * * * * * * +KY\n" "P+00FU\n" "P-00KA00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::promote(state, PieceMask(), moves); BOOST_CHECK_EQUAL((size_t)1, moves.size()); // 12TO } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestEscapeFromLastMove) { { NumEffectState state(CsaString( "P1-KY-KE * * * -OU * -KE-KY\n" "P2 * -HI * * * * -KI * * \n" "P3-FU * * -FU * -KI-GI-FU-FU\n" "P4 * * * * -FU-FU-FU * * \n" "P5 * * * * * * * +FU * \n" "P6 * -KA * +FU+FU+FU+FU * * \n" "P7+FU+FU * +KI+KA+GI+KE * +FU\n" "P8 * * +KI * * * * +HI * \n" "P9+KY+KE * +OU * * * * +KY\n" "P+00GI00FU\n" "P-00GI00FU00FU\n" "-\n").initialState()); MoveVector moves; Move last_move(Square(8,7),PAWN,BLACK); QuiescenceGenerator::escapeFromLastMove(state, last_move, moves); // 角逃ã’ã‚ BOOST_CHECK_EQUAL((size_t)6, moves.size()); } { NumEffectState state(CsaString( "P1+TO * * * * -OU * -KE-KY\n" "P2 * * * * * * -KI-KA * \n" "P3-FU * -KE-FU * -KI-GI-FU-FU\n" "P4 * * -FU-GI * -FU-FU * * \n" "P5 * -HI * * * * * +FU * \n" "P6 * +KY+FU+FU * +FU+FU * * \n" "P7+FU * +GI+KI * +GI * * +FU\n" "P8 * * +OU+KA * * * +HI * \n" "P9+KY+KE * * * * * +KE+KY\n" "P+00FU\n" "P-00KI00FU00FU\n" "-\n").initialState()); MoveVector moves; Move last_move(Square(8,6),LANCE,BLACK); QuiescenceGenerator::escapeFromLastMove(state, last_move, moves); // 飛車逃ã’ã‚ BOOST_CHECK_EQUAL((size_t)2, moves.size()); // 95,55 } { NumEffectState state(CsaString( "P1-KY-KE * -HI * -OU * * -KY\n" "P2 * * * * -KI-GI-KI * * \n" "P3-FU * -FU * * -FU-KE-FU-FU\n" "P4 * -FU * * -HI * * * * \n" "P5 * * * * +KA * * * * \n" "P6 * * +FU+FU * * * * * \n" "P7+FU+FU+GI+KI * +FU * +FU+FU\n" "P8 * * +KI * * +GI * * * \n" "P9+KY+KE * * +OU * * +KE+KY\n" "P+00KA00GI00FU\n" "P-00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; const Move last_move(Square(5,4),ROOK,WHITE); QuiescenceGenerator::escapeFromLastMove(state, last_move, moves); const Move m56fu(Square(5,6),PAWN,BLACK); BOOST_CHECK(moves.isMember(m56fu)); } { NumEffectState state(CsaString( "P1-KY-KE * * * -KI * -KE-KY\n" "P2 * * -HI * -KI * -GI+KA * \n" "P3-FU * * -FU * -FU * * * \n" "P4 * * * * -FU * -FU-OU-FU\n" "P5 * -FU-GI+FU * * * -FU * \n" "P6 * * * * * +FU+FU * +FU\n" "P7+FU+FU+GI * +FU+KI+KE * * \n" "P8 * * * +HI * * +GI * * \n" "P9+KY+KE * * * +KI+OU * +KY\n" "P-00KA00FU00FU00FU\n" "-\n").initialState()); MoveVector moves; const Move last_move(Square(2,2),BISHOP,BLACK); QuiescenceGenerator::escapeFromLastMove(state, last_move, moves); const Move m33ka(Square(3,3),BISHOP,WHITE); BOOST_CHECK(moves.isMember(m33ka)); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestEscapeKingInTakeBack) { { NumEffectState state(CsaString( "P1 * * * * * * -KI-KE-OU\n" "P2 * * * * * * -KI-GI-KY\n" "P3 * * * * * * -FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * -GI * * * * * * * \n" "P8-TO-FU * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); MoveVector moves; const bool has_safe_move = QuiescenceGenerator::escapeKingInTakeBack(state, moves, false); BOOST_CHECK_EQUAL((size_t)0, moves.size()); BOOST_CHECK_EQUAL(false, has_safe_move); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestAdvanceBishop) { { NumEffectState state(CsaString( "P1-KY * * -KI * * * * * \n" "P2 * -OU-GI * * -KA-HI * -KY\n" "P3 * -FU * -KI-KE-GI * -FU * \n" "P4-FU * -FU-KE-FU * -FU * -FU\n" "P5 * * * -FU * +GI * +FU * \n" "P6+FU+FU+FU * +FU+FU+FU * * \n" "P7 * +GI+KI+FU+KA * * * +FU\n" "P8 * * +KI * * +KE * +HI * \n" "P9+KY+OU * * * * * * +KY\n" "P+00KE00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::advanceBishop(state, moves); BOOST_CHECK_EQUAL((size_t)2, moves.size()); // 15è§’ãŒç—›ã„ } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestOpenCheck) { { NumEffectState state(CsaString( "P1-KY-KE-GI-KI * -KI-GI-KE-KY\n" "P2 * * * * -FU * * -KA * \n" "P3-FU-FU-FU-FU-OU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * +KY * * -HI * * \n" "P6 * * * +GI+KI+KE * * * \n" "P7+FU+FU+FU+FU+HI+FU+FU+FU+FU\n" "P8 * +KA * * +FU * * * * \n" "P9+KY+KE+GI+KI+OU * * * * \n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::check(state, PieceMask(), moves); // 一見ãŸã ã§ã‚‚玉ãŒé€ƒã’ã¦ã„ã‚‹é–“ã«é£›è»ŠãŒã¨ã‚Œã‚‹ BOOST_CHECK_EQUAL((size_t)1, moves.size()); // +5645KI } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestCheckPin) { { NumEffectState state(CsaString( "P1-KY * -KI * -KE * * * +RY\n" "P2 * -OU * -GI+GI * * * * \n" "P3 * -GI * -KI * * * * * \n" "P4-FU+KE-FU-FU-FU * +KA * -FU\n" "P5 * -FU * * * +FU * * * \n" "P6+FU * +FU+FU+FU * * * +FU\n" "P7 * +FU * * * +GI * * * \n" "P8 * +OU+KI-RY * * +FU * * \n" "P9+KY * * * * * * * +KY\n" "P+00KA00KE00KY00FU00FU00FU\n" "P-00KI00KE00FU\n" "-\n").initialState()); MoveVector moves; const PieceMask pins = effect_util::Pin::make(state,Square(8,8),BLACK); QuiescenceGenerator::check(state, pins, moves); // â–³7七金ã§è² ã‘ const Move m77ki(Square(7,7),GOLD,WHITE); BOOST_CHECK(moves.isMember(m77ki)); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestCheck) { { NumEffectState state(CsaString( "P1-KY * -KI * -KE * * * +RY\n" "P2 * -OU * -GI+GI * * * * \n" "P3 * -GI * -KI * * * * * \n" "P4-FU+KE-FU-FU-FU * +KA * -FU\n" "P5 * -FU * * * +FU * * * \n" "P6+FU * +FU+FU+FU * * * +FU\n" "P7 * +OU+KA * * +GI * * * \n" "P8 * * * -RY * * +FU * * \n" "P9+KY * * * * * * * +KY\n" "P+00KI00KE00KY00FU00FU00FU\n" "P-00KI00KE00FU00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::check(state, PieceMask(), moves); const Move m86ki(Square(8,6), GOLD, WHITE); BOOST_CHECK(moves.isMember(m86ki)); } { NumEffectState state(CsaString( "P1-KY-KE * -KI * * * * +RY\n" "P2 * -OU * * -GI * * +NG-KY\n" "P3 * -FU * * * * * -FU * \n" "P4-FU * * * -FU * -FU * -FU\n" "P5 * +FU * * * * * +FU * \n" "P6+FU * -FU+KE+FU * +FU * * \n" "P7 * * * +KI * * * +KE+FU\n" "P8 * * * +KI * -UM * * * \n" "P9+KY+OU+KI * * * * * -RY\n" "P+00GI00KY\n" "P-00KA00GI00FU00FU00FU00FU00FU00KE\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::check(state, PieceMask(), moves); // 74æ¡‚ã¯æŒ‡ã—ã¦ã­ BOOST_CHECK_EQUAL((size_t)1, moves.size()); } { NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * -HI * -GI * -OU * * * \n" "P3-FU * -FU-FU * -KI * * -FU\n" "P4 * -FU * * -FU * -FU-FU * \n" "P5 * * * * * +HI * * * \n" "P6+FU * +FU * * * +FU+FU * \n" "P7 * +FU * +FU+FU * * * +FU\n" "P8 * +KA+KI+GI * * * * * \n" "P9+KY+KE * +OU * +KI * * -UM\n" "P+00KI00KE\n" "P-00GI00GI00KE00KY00FU00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::check(state, PieceMask(), moves); // 43金ã«å¯¾ã™ã‚‹sendoffpositionãŒã‚ã‚‹ã®ã§ï¼Œ // 33金ã®ã‚ˆã†ãªå¤šå°‘乱暴ãªçŽ‹æ‰‹ã‚‚èª­ã‚€ BOOST_CHECK_EQUAL((size_t)3, moves.size()); } { NumEffectState state(CsaString( "P1-OU * * * * -HI * -KE-KY\n" "P2-KY-KI-KI * * * * * * \n" "P3 * -GI * * -FU * * * -FU\n" "P4 * -FU-FU * * -KA+FU-FU * \n" "P5-FU+FU * * * -FU * * +FU\n" "P6 * * +FU * * * * * * \n" "P7+FU * * +KI+FU+FU+GI * * \n" "P8+KY+GI * * * * * +HI * \n" "P9+OU+KE+KI * * * * * +KY\n" "P+00KA00GI00KE00FU00FU\n" "P-00KE00FU00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::check(state, PieceMask(), moves); // 87æ¡‚ BOOST_CHECK_EQUAL((size_t)1, moves.size()); } { NumEffectState state(CsaString( "P1-KY-KE * * * * * * * \n" "P2 * -OU-KI+RY * * * * * \n" "P3-FU-FU-FU-GI * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * +FU+FU+FU\n" "P8 * * * * * * +KI+GI+KY\n" "P9 * * * * * * +KI+KE+OU\n" "P+00GI\n" "P-00AL\n" "-\n").initialState()); MoveVector moves; const PieceMask pins = effect_util::Pin::make(state, Square(8,2), WHITE); QuiescenceGenerator::check(state, pins, moves, false); // 71GI BOOST_CHECK_EQUAL((size_t)1, moves.size()); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestEscape) { { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU * -FU-FU-FU-FU\n" "P4 * * * * -FU * * * * \n" "P5 * * * * +KA * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::escapeAll(state, moves); BOOST_CHECK_EQUAL((size_t)2, moves.size()); // 46, 66 } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE * \n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * -KY * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * +FU * +FU * * * \n" "P7+FU+FU+FU * +KA * +FU+FU+FU\n" "P8 * * * * +KY * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE * \n" "P+00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::escapeAll(state, moves); // ç„¡é§„ãªåˆé§’ã‚’ã—ãªã‘れ㰠48, 68 BOOST_CHECK_EQUAL((size_t)2, moves.size()); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE * \n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * -KY * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * +FU * +FU * * * \n" "P7+FU+FU+FU+GI+KA * +FU+FU+FU\n" "P8 * * * * +KY * * +HI * \n" "P9+KY+KE+KI * +OU+KI+GI+KE * \n" "P+00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::escapeAll(state, moves); // ç„¡é§„ãªåˆé§’ã‚’ã—ãªã‘れ㰠48, 68, +56FU BOOST_CHECK_EQUAL((size_t)3, moves.size()); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5-HI * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * +FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KY+KE * * * * +HI * \n" "P9+KA * +KI+GI+OU+KI+GI+KE+KY\n" "P-00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::escapeAll(state, moves); // 逃ã’られãªã„ãŒåˆ©ãã¯ã¤ã‘られる BOOST_CHECK_EQUAL((size_t)1, moves.size()); // +7989KI } { NumEffectState state(CsaString( "P1-KY-KE * -HI * -OU * * -KY\n" "P2 * * * * -KI-GI-KI * * \n" "P3-FU * -FU * * -FU-KE-FU-FU\n" "P4 * -FU * * -HI * * * * \n" "P5 * * * * +KA * * * * \n" "P6 * * +FU+FU * * * * * \n" "P7+FU+FU+GI+KI * +FU * +FU+FU\n" "P8 * * +KI * * +GI * * * \n" "P9+KY+KE * * +OU * * +KE+KY\n" "P+00KA00GI00FU\n" "P-00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::escapeAll(state, moves); const Move m56fu(Square(5,6),PAWN,BLACK); BOOST_CHECK(moves.isMember(m56fu)); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestEscapeKing) { { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * -HI * * * * * +OU * \n" "P6 * * * * * +FU * * * \n" "P7+FU+FU+FU+FU+FU * +FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9 * +KE+GI+KI * +KI+GI+KE+KY\n" "P+00KY\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::escapeKing(state, moves); // 中åˆç¦æ­¢: king 36,26,16, lance 35, 45 BOOST_CHECK_EQUAL((size_t)5, moves.size()); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestAttackKing8) { { NumEffectState state(CsaString( "P1+UM * * * * * -OU * -KY\n" "P2 * * -HI-KI * -GI-KI * * \n" "P3 * * * -FU-GI-FU * * -KE\n" "P4-FU * * * -FU * -FU+HI-FU\n" "P5 * +KE * +FU * +FU * * * \n" "P6+FU * * +KI+FU * +GI * +FU\n" "P7+OU+FU-TO * * * +KE * * \n" "P8 * * * * * * * * * \n" "P9+KY * * * * * * * +KY\n" "P+00KA00GI00KE00KY00FU00FU\n" "P-00KI00FU00FU00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::attackKing8(state, PieceMask(), moves); // 86æ­©ã¨88金,95æ­©ãらã„? // å ´åˆã«ã‚ˆã£ã¦ã¯76TO ã¨ã‹ 76KI ã¨ã‹ã‚‚ã—ょã†ãŒãªã„? BOOST_CHECK_EQUAL((size_t)3, moves.size()); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestAttackMajorPiece) { { NumEffectState state(CsaString( "P1-KY-KE * * * * -OU * -KY\n" "P2-HI * * * * * -KI * * \n" "P3-FU * * -FU * -KI * -FU-FU\n" "P4 * -FU * * * * +FU * * \n" "P5 * * +GI+FU+FU-KE+KA+FU-KA\n" "P6 * * * +KI * * * * * \n" "P7+FU+FU * +KI * * * * +FU\n" "P8 * * * * * +GI+HI * * \n" "P9+KY+KE * +OU * * * +KE+KY\n" "P+00GI00FU00FU00FU00FU00FU\n" "P-00GI00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); BOOST_CHECK_EQUAL((size_t)6, moves.size()); // Drop(-,PAWN,Square(36)) ã“れを作るã‹ã©ã†ã‹ã¯å¾®å¦™ // Drop(-,PAWN,Square(37)) // Drop(-,SILVER,Square(27)) // Drop(-,SILVER,Square(49)) // Drop(-,SILVER,Square(44)) // Drop(-,SILVER,Square(26)) } { NumEffectState state(CsaString( "P1-KY-KE+KA * * * * * * \n" "P2-OU * -GI * * +TO * * * \n" "P3 * -FU-FU-KI * * -KE * -FU\n" "P4-FU * * * * * * * * \n" "P5 * * * -KI * -FU * * * \n" "P6+FU * +FU-FU-FU * * * +FU\n" "P7 * +FU+KI * * +FU+GI-FU * \n" "P8 * * +OU * * * * * +HI\n" "P9+KY+KE * +KI+RY * * * +KY\n" "P+00KY00FU00FU\n" "P-00KA00GI00GI00KE00FU00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); const Move m62gi(Square(6,2), SILVER, WHITE); BOOST_CHECK(moves.isMember(m62gi)); } { NumEffectState state(CsaString( "P1-OU-KE * * * * * * -KY\n" "P2-KY-GI-GI * -KI * * * -HI\n" "P3-FU * -FU * -FU * * -FU * \n" "P4 * +FU * * * +UM * * -FU\n" "P5 * * * -FU * * * * * \n" "P6+FU * +FU * * * * +FU * \n" "P7 * +GI+GI+FU * -TO+FU * +FU\n" "P8 * +OU+KI+KI * * * * * \n" "P9+KY+KE+HI * * * * +KE-UM\n" "P+00KI00FU00FU00FU\n" "P-00KE00KY00FU\n" "+\n").initialState()); // 上ã«é€ƒã’られる MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); BOOST_CHECK(moves.empty()); } { NumEffectState state(CsaString( "P1-OU-KE * * * * +UM * -KY\n" "P2-KY-GI-GI * -KI * * * -HI\n" "P3-FU * -FU * -FU * * -FU-FU\n" "P4 * +FU * * * * * * * \n" "P5 * * * -FU * * * * * \n" "P6+FU * +FU * * * * +FU * \n" "P7 * +GI+GI+FU * -TO+FU * +FU\n" "P8 * +OU+KI+KI * * * * * \n" "P9+KY+KE+HI * * * * +KE-UM\n" "P+00KI00FU00FU00FU\n" "P-00KE00KY00FU\n" "+\n").initialState()); // 仕留ã‚られる MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); const Move m22ki(Square(2,2), GOLD, BLACK); BOOST_CHECK(moves.isMember(m22ki)); } { NumEffectState state(CsaString( "P1-KY-KE * * * * * -KE-KY\n" "P2 * * * * * * -KI-OU * \n" "P3 * * * * -GI-KI-KA * * \n" "P4-FU-HI-FU-FU-FU * -GI * * \n" "P5 * -FU * * * -FU-FU-FU-FU\n" "P6+FU * +HI+GI+FU * * * * \n" "P7 * +FU+KE * +KA+FU+FU+FU+FU\n" "P8 * * * * * * +KI+GI+KY\n" "P9+KY * * * * * +KI+KE+OU\n" "P-00FU00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); const Move m65gi(Square(6,6), Square(6,5), SILVER, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m65gi)); } { NumEffectState state(CsaString( "P1-KY-KE * * -OU-KI-GI-KE-KY\n" "P2 * -HI * -GI-KI * * -KA * \n" "P3-FU * -FU-FU * -FU * -FU-FU\n" "P4 * * * * -FU * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * +KA+FU+FU * * * * * \n" "P7+FU * * +GI+FU+FU+FU+FU+FU\n" "P8 * +HI * * * +OU * * * \n" "P9+KY+KE * +KI * +KI+GI+KE+KY\n" "P+00FU\n" "P-00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); const Move m42um(Square(8,6), Square(4,2), PBISHOP, PTYPE_EMPTY, true, BLACK); BOOST_CHECK(moves.isMember(m42um)); } { NumEffectState state(CsaString( "P1-KY * +UM * * * * -KE-KY\n" "P2 * * * * * * * -OU * \n" "P3 * * * * * -HI * -FU-FU\n" "P4-FU * -FU * -FU-KI-FU-GI * \n" "P5 * * * * * * * * +FU\n" "P6+FU+FU+FU+KI+FU * +FU * * \n" "P7 * +KI * +FU * * -UM * * \n" "P8 * +OU * +GI * * -NG * * \n" "P9+KY+KE * * * * * * -RY\n" "P+00KI00GI00KY00FU\n" "P-00KE00KE00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); const Move m52gi(Square(5,2), SILVER, BLACK); const Move m82um(Square(7,1), Square(8,2), PBISHOP, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(! moves.isMember(m82um)); BOOST_CHECK(moves.isMember(m52gi)); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-HI-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * +FU * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU * +FU+FU+FU+FU+FU+FU+FU\n" "P8 * +HI * * * * * * * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "P+00FU\n" "P-00KA\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackMajorPiece(state, PieceMask(), moves); const Move m84fu(Square(8,5), Square(8,4), PAWN, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m84fu)); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestAttackGoldWithPawn) { { NumEffectState state(CsaString( "P1-KY-KE * * * -OU * * -KY\n" "P2 * -HI * -GI * -KA-KI * * \n" "P3-FU * -FU-FU * -KI * * -FU\n" "P4 * -FU * * -FU * -FU-FU * \n" "P5 * * * * * -KE * * * \n" "P6 * * +FU * * * +FU+FU * \n" "P7+FU+FU * +FU+FU * * * +FU\n" "P8 * +KA+KI+GI * +HI * * * \n" "P9+KY+KE * +OU * +KI * * +KY\n" "P+00GI00FU\n" "P-00GI00KE00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackGoldWithPawn(state, PieceMask(), moves); BOOST_CHECK(moves.size() >= 1); } { NumEffectState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * -KI * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * +FU * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P+00KY00KE00GI\n" "P-00AL\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackGoldWithPawn(state, PieceMask(), moves); const Move m53ky(Square(5,3), LANCE, BLACK); const Move m53gi(Square(5,3), SILVER, BLACK); const Move m44ke(Square(4,4), KNIGHT, BLACK); BOOST_CHECK(moves.isMember(m53ky)); BOOST_CHECK(moves.isMember(m53gi)); BOOST_CHECK(moves.isMember(m44ke)); } { NumEffectState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * -KE\n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * -KA \n" "P8 * * * * * * +KI * * \n" "P9 * * * * +OU * +KI * * \n" "P-00AL\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::attackGoldWithPawn(state, PieceMask(), moves); const Move m47ke(Square(4,7), KNIGHT, WHITE); const Move m27ke(Square(1,5), Square(2,7), KNIGHT, PTYPE_EMPTY, false, WHITE); BOOST_CHECK(moves.isMember(m47ke)); BOOST_CHECK(moves.isMember(m27ke)); } { NumEffectState state(CsaString( "P1-KY * * -KI * * +TO * * \n" "P2 * -OU-GI * -KI * * * * \n" "P3 * -FU-KE * -FU * * * -FU\n" "P4-FU * -FU * * * -FU * * \n" "P5 * * * -FU * * * * * \n" "P6+FU+FU+FU * -KY * +KA * * \n" "P7 * +OU+GI * * * +FU * +FU\n" "P8 * * +GI+KI * * * -RY * \n" "P9+KY+KE * +KI * * * * * \n" "P+00HI00GI00KY00FU\n" "P-00KA00KE00KE00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackGoldWithPawn(state, PieceMask(), moves); const Move m64ky(Square(6,4), LANCE, BLACK); BOOST_CHECK(moves.isMember(m64ky)); } { NumEffectState state(CsaString( "P1-KY-KE * -KI * * * * +RY\n" "P2 * -OU-GI * -KI * +TO * * \n" "P3 * -FU-FU-FU * -FU * -FU-FU\n" "P4-FU * * -KA-FU * * * * \n" "P5 * * * * * * * +GI * \n" "P6+FU+FU * +FU+FU+GI * * * \n" "P7+KY * * +GI * * +KI+FU+FU\n" "P8 * * * +KA * * * +HI * \n" "P9 * -NK * * * +OU * * +KY\n" "P+00KE00KY\n" "P-00KI00KE00FU00FU00FU\n" "-\n").initialState()); MoveVector moves; QuiescenceGenerator::attackGoldWithPawn(state, PieceMask(), moves); const Move m45ke(Square(4,5), KNIGHT, WHITE); BOOST_CHECK(moves.isMember(m45ke)); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestAttackSilverWithPawn) { { NumEffectState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * -GI * * -GI * \n" "P3 * * * * * * * * * \n" "P4 * * * * +FU * * +FU * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P+00KY00KE\n" "P-00AL\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackSilverWithPawn(state, PieceMask(), moves); const Move m53ky(Square(5,3), LANCE, BLACK); const Move m44ke(Square(4,4), KNIGHT, BLACK); BOOST_CHECK(moves.isMember(m53ky)); BOOST_CHECK(moves.isMember(m44ke)); const Move m23ky(Square(2,3), LANCE, BLACK); const Move m34ke(Square(3,4), KNIGHT, BLACK); BOOST_CHECK(! moves.isMember(m23ky)); BOOST_CHECK(! moves.isMember(m34ke)); } { NumEffectState state(CsaString( "P1 * * * * -HI-KI-KA * -KY\n" "P2 * * -GI * * * * -OU * \n" "P3+TO * -KE * * -KI-KE * * \n" "P4 * * -FU-FU-FU-FU-FU-GI-FU\n" "P5+KA * * * * * * -FU * \n" "P6 * * +FU+FU * +GI+FU * +FU\n" "P7 * -TO * * * +FU+KE+FU * \n" "P8 * -FU * +HI * * +KI+KI+KY\n" "P9 * +KE * * * * * +GI+OU\n" "P+00KY00FU00FU\n" "P-00KY\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::attackSilverWithPawn(state, PieceMask(), moves); const Move m82to(Square(9,3), Square(8,2), PPAWN, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m82to)); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestAddLance) { { NumEffectState state(CsaString( "P1 * * * * * * -GI-OU-KY\n" "P2 * * * * * -KA-KI-GI * \n" "P3 * * * * * * -KE-FU-FU\n" "P4+RY * +KI * -FU-FU+FU * * \n" "P5 * * * -FU * * * * +FU\n" "P6 * +FU * * +FU+FU * * * \n" "P7+KE * -UM * +GI+GI * * * \n" "P8 * * * * * +KI+OU * * \n" "P9+KY * * * * * * +HI+KY\n" "P+00KE00KE00KY00FU00FU00FU\n" "P-00KI00FU00FU00FU00FU00FU\n" "+\n").initialState()); MoveVector moves; QuiescenceGenerator::capture(state, moves,Piece::EMPTY()); // 33to // 35,36,37kyo BOOST_CHECK_EQUAL((size_t)4, moves.size()); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestUtilizePromoted) { { NumEffectState state(CsaString( "P1-KY-KE * * * * -KI-KE-OU\n" "P2 * * * * -HI * * -GI-KY\n" "P3-FU * +NK-FU * -FU-KA-FU-FU\n" "P4 * -FU * -KI-FU * -FU * * \n" "P5 * * * * * * * * * \n" "P6+FU * +HI+FU * * * * * \n" "P7 * +FU * +GI+FU+FU+FU+FU+FU\n" "P8 * * * * +KI * +OU * * \n" "P9+KY * * * * +KI+GI+KE+KY\n" "P+00GI00FU00FU\n" "P-00KA\n" "+\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(7,3)); QuiescenceGenerator::utilizePromoted(state, target, moves); BOOST_CHECK_EQUAL((size_t)5, moves.size()); } { NumEffectState state(CsaString( "P1-KY-KE * * * * -KI-KE-OU\n" "P2 * * * * -HI * * -GI-KY\n" "P3-FU * +NK-FU * -FU-KA-FU-FU\n" "P4 * -FU * -KI-FU * -FU * * \n" "P5 * * * * * * * * * \n" "P6+FU+HI * +FU * * * * * \n" "P7 * +FU * +GI+FU+FU+FU+FU+FU\n" "P8 * * * * +KI * +OU * * \n" "P9+KY * * * * +KI+GI+KE+KY\n" "P+00GI00FU00FU\n" "P-00KA\n" "+\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(7,3)); QuiescenceGenerator::utilizePromoted(state, target, moves); BOOST_CHECK_EQUAL((size_t)1, moves.size()); } { NumEffectState state(CsaString( "P1-KY * * * * * -KI-KE-OU\n" "P2 * * * * -HI * * -GI-KY\n" "P3-FU-KE+NK-FU * -FU-KA-FU-FU\n" "P4 * -FU * -KI-FU * -FU * * \n" "P5 * * * * * * * * * \n" "P6+FU * +HI+FU * * * * * \n" "P7 * +FU * +GI+FU+FU+FU+FU+FU\n" "P8 * * * * +KI * +OU * * \n" "P9+KY * * * * +KI+GI+KE+KY\n" "P+00GI00FU00FU\n" "P-00KA\n" "+\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(7,3)); QuiescenceGenerator::utilizePromoted(state, target, moves); BOOST_CHECK_EQUAL((size_t)2, moves.size()); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestEscapeByMoveOnly) { { NumEffectState state(CsaString( "P1-KY-KE * * -OU-KI * -KE-KA\n" "P2 * * * -GI-KI * -GI * * \n" "P3-FU * -FU-FU * -FU * -FU-FU\n" "P4 * * * * -FU * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * -HI+FU+FU * * * * * \n" "P7+FU+KY * +KI+FU+FU+FU+FU+FU\n" "P8 * +GI+KI * * * * +HI * \n" "P9+KY+KE * +OU * * +GI+KE+KY\n" "P+00FU\n" "P-00KA00FU\n" "-\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(8,6)); const bool has_safe_move = QuiescenceGenerator::escapeByMoveOnly(state, target, moves); // 後ã‚ã«ä¸‹ãŒã£ã¦ã‚‚å–られる BOOST_CHECK(! has_safe_move); } { NumEffectState state(CsaString( "P1-KY-KE * * -OU-KI * -KE-KA\n" "P2 * * * -GI-KI * -GI * * \n" "P3-FU * -FU-FU * -FU * -FU-FU\n" "P4 * * * * -FU * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * -HI+FU+FU * * * * * \n" "P7+FU+FU * +KI+FU+FU+FU+FU+FU\n" "P8 * +GI+KI * * * * +HI * \n" "P9+KY+KE * +OU * * +GI+KE+KY\n" "P+00KY\n" "P-00KA00FU\n" "-\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(8,6)); const bool has_safe_move = QuiescenceGenerator::escapeByMoveOnly(state, target, moves); // 後ã‚ã«ä¸‹ãŒã‚Œã‚‹ BOOST_CHECK(has_safe_move); } { NumEffectState state(CsaString( "P1-KY-KE * -KI * * -KI-KE-OU\n" "P2 * * * -GI * * * -GI-KY\n" "P3-FU-HI-FU-FU-FU-FU-UM-FU-FU\n" "P4 * +FU * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * +FU * * * * \n" "P7+FU * +KE+FU * +FU+FU+FU+FU\n" "P8 * +HI * +GI+KI * +GI+OU * \n" "P9+KY * * * * +KI * +KE+KY\n" "P+00FU\n" "P-00KA\n" "-\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(8,3)); const bool has_safe_move = QuiescenceGenerator::escapeByMoveOnly(state, target, moves); // 後ã‚ã«ä¸‹ãŒã£ã¦ã‚‚追撃ã•れる BOOST_CHECK(! has_safe_move); } { NumEffectState state(CsaString( "P1-KY-KE * -KI * * -KI-KE-OU\n" "P2 * * * -GI * * * -GI-KY\n" "P3-FU-HI * * -FU-FU-UM-FU-FU\n" "P4 * +FU-FU-FU * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * +FU * * * * \n" "P7+FU * +KE+FU * +FU+FU+FU+FU\n" "P8 * +HI * +GI+KI * +GI+OU * \n" "P9+KY * * * * +KI * +KE+KY\n" "P+00FU\n" "P-00KA\n" "-\n").initialState()); MoveVector moves; const Piece target = state.pieceOnBoard(Square(8,3)); const bool has_safe_move = QuiescenceGenerator::escapeByMoveOnly(state, target, moves); // 横ã«äºŒæ­©é€ƒã’られる BOOST_CHECK(has_safe_move); } } BOOST_AUTO_TEST_CASE(QuiescenceGeneratorTestBreakThreatmate) { { NumEffectState state(CsaString( "P1-KY-HI * * * * -GI-OU-KY\n" "P2 * * * * +FU * * * * \n" "P3 * * * * -KI * * +KI * \n" "P4 * -FU-FU * -GI * +KE+UM * \n" "P5-FU * * +FU-FU-KE * -FU-FU\n" "P6 * * +FU * * * * * * \n" "P7+FU+FU+KI * -TO * * * * \n" "P8 * +OU+KI * * * +FU * +HI\n" "P9+KY+KE * * -UM * * * * \n" "P+00KE\n" "P-00GI00GI00KY00FU00FU00FU00FU00FU\n" "-\n").initialState()); MoveVector moves; const Move m33ke(Square(3,3), KNIGHT, BLACK); QuiescenceGenerator::breakThreatmate(state, m33ke, PieceMask(), moves); BOOST_CHECK(! moves.empty()); } { NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * -FU+FU * * * * \n" "P3-FU+RY * * * * +TO+HI-FU\n" "P4 * * * +FU * -GI+KA * * \n" "P5 * * +FU * -GI-FU-FU * * \n" "P6 * +KI * * -OU * -KE * * \n" "P7+FU+FU-KI * * -TO * * +FU\n" "P8+OU * -KI * * * * * * \n" "P9+KY * * * * * +GI * +KY\n" "P+00KA00KI00GI00KE00FU00FU00FU\n" "P-00KE00FU00FU\n" "+\n").initialState()); MoveVector moves; const Move m88ki(Square(7,8), Square(8,8), GOLD, PTYPE_EMPTY, false, WHITE); QuiescenceGenerator::breakThreatmate(state, m88ki, PieceMask(), moves); const Move m96fu(Square(9,7), Square(9,6), PAWN, PTYPE_EMPTY, false, BLACK); BOOST_CHECK(moves.isMember(m96fu)); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/testAll.cc0000644000000000000000000000113412316770314016303 0ustar rootroot#include "osl/oslConfig.h" #define BOOST_TEST_DYN_LINK #include #include bool long_test = false; bool init_unit_test() { osl::OslConfig::setInUnitTest(long_test ? 2 : 1); osl::OslConfig::showOslHome(); osl::OslConfig::setVerbose(false); osl::OslConfig::setUp(); return true; } int main( int argc, char* argv[] ) { nice(20); if (argc >= 2 && argv[1] == std::string("--long")) long_test = true; return boost::unit_test::unit_test_main( init_unit_test, argc, argv ); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/effect_util/0000755000000000000000000000000012316770314016656 5ustar rootrootlibosl-0.8.0.orig/full/test/effect_util/virtualPin.t.cc0000644000000000000000000000165712316770314021575 0ustar rootroot#include "osl/effect_util/virtualPin.h" #include "osl/csa.h" #include "osl/oslConfig.h" #include #include #include using namespace osl; using namespace osl::effect_util; BOOST_AUTO_TEST_CASE(VirtualPinTestFind) { { NumEffectState state(CsaString( "P1-KY-KE * * -FU * * * * \n" "P2 * -OU * -KA-KI+NG+RY * * \n" "P3 * -FU-GI-RY * * * * * \n" "P4 * -KY-FU-FU * -FU * +UM * \n" "P5-FU * * -KI * +FU * * -FU\n" "P6 * * -KE+KE * * * -FU * \n" "P7+FU+FU+GI+FU+FU * * * +FU\n" "P8+KY * +KI * * +GI * * * \n" "P9+OU+KE+KI * * * +FU * +KY\n" "P+00FU00FU\n" "P-00FU\n" "+\n").initialState()); BOOST_CHECK(VirtualPin::find(state, WHITE, Square(5,1))); BOOST_CHECK(! VirtualPin::find(state, WHITE, Square(7,4))); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/effect_util/additionalEffect.t.cc0000644000000000000000000001572512316770314022666 0ustar rootroot#include "osl/additionalEffect.h" #include "osl/csa.h" #include "osl/oslConfig.h" #include #include #include using namespace osl; using namespace osl::effect_util; BOOST_AUTO_TEST_CASE(AdditionalEffectTestHasEffect) { NumEffectState state(CsaString( "P1+UM * * * * * -OU * -KY\n" "P2 * * -HI-KI * -GI-KI * * \n" "P3 * * * -FU-GI-FU * * -KE\n" "P4-FU * * * -FU * -FU-FU-FU\n" "P5 * +KE * +FU * +FU * * * \n" "P6+FU * -FU+KI+FU * +GI * +FU\n" "P7 * +FU * * * * +KE * * \n" "P8 * +OU+KI * * * * * +HI\n" "P9+KY * * * * * * * +KY\n" "P+00KA00KE00KY00FU\n" "P-00GI00FU00FU00FU\n" "-\n").initialState()); BOOST_CHECK_EQUAL(true, AdditionalEffect::hasEffect (state, Square(7,7), WHITE)); BOOST_CHECK_EQUAL(false, AdditionalEffect::hasEffect (state, Square(7,7), BLACK)); BOOST_CHECK_EQUAL(false, AdditionalEffect::hasEffect (state, Square(8,8), WHITE)); BOOST_CHECK_EQUAL(true, AdditionalEffect::hasEffect (state, Square(8,8), BLACK)); } static void testFile(const std::string& filename) { const auto record = CsaFileMinimal(filename).load(); NumEffectState state(record.initialState()); const auto& moves = record.moves; for (unsigned int i=0; i> filename) && (++i #include #include using namespace osl; using namespace osl::effect_util; BOOST_AUTO_TEST_CASE(PinTestNoPin) { { NumEffectState state((SimpleState(HIRATE))); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK(pins.none()); } { NumEffectState state(CsaString( "P1-KY-KE-GI * +OU * -GI-KE * \n" "P2 * -HI-KI * * * -KI-KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * -KY * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA+KI * * * +KI+HI * \n" "P9+KY+KE+GI * -OU * +GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK(pins.none()); } } BOOST_AUTO_TEST_CASE(PinTestUp) { { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * -HI * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece p57fu = state.pieceOnBoard(Square(5,7)); BOOST_CHECK(pins.test(p57fu.number())); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE * \n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * -KY * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece p57fu = state.pieceOnBoard(Square(5,7)); BOOST_CHECK(pins.test(p57fu.number())); } } BOOST_AUTO_TEST_CASE(PinTestDown) { { NumEffectState state(CsaString( "P1-KY-KE-GI * +OU * -GI-KE-KY\n" "P2 * * -KI * * * -KI-KA * \n" "P3-FU-FU-FU-FU+FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * -HI * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU-FU+FU+FU+FU+FU\n" "P8 * +KA+KI * * * +KI+HI * \n" "P9+KY+KE+GI * -OU * +GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece p53fu = state.pieceOnBoard(Square(5,3)); BOOST_CHECK(pins.test(p53fu.number())); } } BOOST_AUTO_TEST_CASE(PinTestNeighbor) { // é§’ãŒéš£ã«ã‚ã‚‹å ´åˆã®ãƒ†ã‚¹ãƒˆ { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * -HI+FU+OU * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU * +FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI * +KI+GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece p45fu = state.pieceOnBoard(Square(4,5)); BOOST_CHECK(pins.test(p45fu.number())); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * -HI * +FU+OU * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU * +FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI * +KI+GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece p45fu = state.pieceOnBoard(Square(4,5)); BOOST_CHECK(pins.test(p45fu.number())); } { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * * * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * * * * * * \n" "P5 * * * * -HI+FU * +OU * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU * +FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI * +KI+GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece p45fu = state.pieceOnBoard(Square(4,5)); BOOST_CHECK(pins.test(p45fu.number())); } } BOOST_AUTO_TEST_CASE(PinTestDiagonal) { { NumEffectState state(CsaString( "P1-KY-KE-GI * -OU * -GI-KE-KY\n" "P2 * -HI-KI * * * -KI-KA * \n" "P3-FU-FU-FU-FU-FU-FU * -FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +OU+KI * * * +KI+HI * \n" "P9+KY+KE+GI * +KA * +GI+KE+KY\n" "+\n").initialState()); const PieceMask pins = Pin::make(state, BLACK); BOOST_CHECK_EQUAL(1, pins.countBit2()); const Piece pin = state.pieceOnBoard(Square(7,7)); BOOST_CHECK(pins.test(pin.number())); } } static void testEquality(const std::string& filename) { auto record=CsaFileMinimal(filename).load(); NumEffectState state(record.initialState()); const auto& moves=record.moves; size_t i=0; while (true) { const PieceMask black_pins = Pin::makeNaive(state, BLACK); const PieceMask black_pins2 = Pin::makeByPiece(state, BLACK); if (black_pins != black_pins2) std::cerr << state; BOOST_CHECK_EQUAL(black_pins, black_pins2); const PieceMask black_pins3 = Pin::makeStep(state, state.kingSquare(), BLACK); if (black_pins != black_pins3) std::cerr << state; BOOST_CHECK_EQUAL(black_pins, black_pins3); const PieceMask white_pins = Pin::makeNaive(state, WHITE); const PieceMask white_pins2 = Pin::makeByPiece(state, WHITE); if (white_pins != white_pins2) std::cerr << state; BOOST_CHECK_EQUAL(white_pins, white_pins2); const PieceMask white_pins3 = Pin::makeStep(state, state.kingSquare(), WHITE); if (white_pins != white_pins3) std::cerr << state; BOOST_CHECK_EQUAL(white_pins, white_pins3); if (i >= moves.size()) break; const Move move = moves[i++]; state.makeMove(move); } } BOOST_AUTO_TEST_CASE(PinTestEquality) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); int i=0; int count=100; if (OslConfig::inUnitTestShort()) count=10; std::string file_name; while ((ifs >> file_name) && (++i #include using namespace osl; using namespace osl::effect_util; typedef osl::effect_util::SendOffSquare::SendOff8 SendOff8; BOOST_AUTO_TEST_CASE(SendOffSquareTestSimple) { { NumEffectState state(CsaString( "P1 * * * * * * +HI * * \n" "P2 * * -OU-KI * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); Square8 sendoffs, sendoffs2; Square king(7,2); SendOff8 data = SendOffSquare::find(state, king, sendoffs); BOOST_CHECK(sendoffs.empty()); SendOffSquare::unpack(data, king, sendoffs2); BOOST_CHECK_EQUAL(sendoffs, sendoffs2); } { NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2 * * -OU-KI * * +HI * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); Square8 sendoffs, sendoffs2; Square king(7,2); SendOff8 data = SendOffSquare::find(state, king, sendoffs); BOOST_CHECK_EQUAL((size_t)3, sendoffs.size()); SendOffSquare::unpack(data, king, sendoffs2); BOOST_CHECK_EQUAL(sendoffs, sendoffs2); } { NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2 * * * -KI * * +HI * * \n" "P3 * * -OU * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); Square8 sendoffs, sendoffs2; Square king(7,3); SendOff8 data = SendOffSquare::find(state, king, sendoffs); BOOST_CHECK_EQUAL((size_t)5, sendoffs.size()); SendOffSquare::unpack(data, king, sendoffs2); BOOST_CHECK_EQUAL(sendoffs, sendoffs2); } } BOOST_AUTO_TEST_CASE(SendOffSquareTestDefense) { { NumEffectState state(CsaString( "P1 * * * * * * * * * \n" "P2 * * * -KI * * +HI * * \n" "P3 * * -OU * * * * * * \n" "P4 * * -KI * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); Square8 sendoffs, sendoffs2; Square king(7,3); SendOff8 data = SendOffSquare::find(state, king, sendoffs); #if 0 for (Square8::const_iterator p=sendoffs.begin(); p!=sendoffs.end(); ++p) { std::cerr << *p << "\n"; } #endif BOOST_CHECK_EQUAL((size_t)3, sendoffs.size()); // 82, 83, 72 SendOffSquare::unpack(data, king, sendoffs2); BOOST_CHECK_EQUAL(sendoffs, sendoffs2); } } BOOST_AUTO_TEST_CASE(SendOffSquareTestEdge) { { NumEffectState state(CsaString( "P1 * -KI * +HI * * * * * \n" "P2-OU * * * * * * * * \n" "P3 * * * * * * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9+OU * * * * * * * * \n" "P+00AL\n" "+\n").initialState()); Square8 sendoffs, sendoffs2; Square king(9,2); SendOff8 data = SendOffSquare::find(state, king, sendoffs); BOOST_CHECK_EQUAL((size_t)2, sendoffs.size()); // 93, 83 SendOffSquare::unpack(data, king, sendoffs2); BOOST_CHECK_EQUAL(sendoffs, sendoffs2); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/effect_util/effectUtil.t.cc0000644000000000000000000000517312316770314021527 0ustar rootroot/* effectUtil.t.cc */ #include "osl/effect_util/effectUtil.h" #include "osl/effect_util/effectUtil.tcc" #include "osl/numEffectState.h" #include "osl/csa.h" #include #include using namespace osl; struct SquareVector : public FixedCapacityVector { }; std::ostream& operator<<(std::ostream& os, const SquareVector& vec) { for (size_t i=0; i using namespace osl; using namespace osl::effect_util; BOOST_AUTO_TEST_CASE(ShadowEffectTestHasEffect) { { NumEffectState state(CsaString( "P1-KY-KE-GI-KI-OU-KI-GI-KE-KY\n" "P2 * -HI * * * * * * * \n" "P3-FU-FU-FU-FU-FU-FU-KA-FU-FU\n" "P4 * * * * * * -FU * * \n" "P5 * * * * * * * * * \n" "P6 * * +FU * * * * * * \n" "P7+FU+FU+KA+FU+FU+FU+FU+FU+FU\n" "P8 * * * * * * * +HI * \n" "P9+KY+KE+GI+KI+OU+KI+GI+KE+KY\n" "+\n" ).initialState()); BOOST_CHECK_EQUAL(false, ShadowEffect::hasEffect (state, Square(8,8), BLACK)); BOOST_CHECK_EQUAL(true, ShadowEffect::hasEffect (state, Square(8,8), WHITE)); BOOST_CHECK_EQUAL(true, ShadowEffect::hasEffect (state, Square(2,2), BLACK)); BOOST_CHECK_EQUAL(false, ShadowEffect::hasEffect (state, Square(2,2), WHITE)); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/effect_util/neighboring8Direct.t.cc0000644000000000000000000002303612316770314023151 0ustar rootroot#include "osl/effect_util/neighboring8Direct.h" #include "osl/csa.h" #include "osl/numEffectState.h" #include "osl/oslConfig.h" #include #include #include using namespace osl; BOOST_AUTO_TEST_CASE(Neighboring8DirectTestBishop) { const NumEffectState state(CsaString( "P1-KY+HI * * * * * -KE-KY\n" "P2 * * +UM-FU * * * * * \n" "P3-KE-KI * * +UM-GI-FU+FU-FU\n" "P4 * -GI-OU * -FU * * -FU * \n" "P5-FU * * * * +GI * * * \n" "P6 * +FU-FU * * * * * * \n" "P7+FU * * * * * +FU * +FU\n" "P8+KY+KI+KI * * * * * * \n" "P9+OU+KE * * * * * +KE+KY\n" "P+00KI\n" "P-00HI00GI00FU00FU00FU00FU00FU00FU\n" "-\n").initialState()); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,PBISHOP), Square(7,2), Square(7,4))); } BOOST_AUTO_TEST_CASE(Neighboring8DirectTestRook) { const NumEffectState state(CsaString("P1-KY-KE * * * * * -KE-KY\n" "P2 * * * * * * -KI * -OU\n" "P3 * * -FU * * -KI * * -KA\n" "P4-FU-HI * * -FU * -FU * -GI\n" "P5 * -FU+FU * +GI-FU * -FU * \n" "P6+FU * +HI * * * * * -FU\n" "P7 * +FU * -TO * +FU+FU+FU * \n" "P8+KY * * * * +KI+KI+GI+KY\n" "P9 * +KE * * +KA * * +KE+OU\n" "P-00FU00FU00FU\n" "P+00GI\n" "+").initialState()); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,ROOK), Square(1,6), Square(1,9))); } BOOST_AUTO_TEST_CASE(Neighboring8DirectTestLance) { { const NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * * * * -KI * * \n" "P3 * * -FU * * -KI * * -OU\n" "P4-FU-HI * * -FU * -FU * * \n" "P5 * -FU+FU * +GI-FU * -FU+KY\n" "P6+FU * * * * * +KE * * \n" "P7 * +FU * -TO * +FU+FU+FU * \n" "P8+KY * * * * +KI+KI+GI * \n" "P9 * +KE-UM * +KA * * +KE+OU\n" "P+00GI00FU\n" "P-00HI00GI00FU00FU00FU\n" "-\n").initialState()); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,LANCE), Square(1,5), Square(1,3))); } { const NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * * * * -KI * * \n" "P3 * * -FU * * -KI * * -OU\n" "P4-FU-HI * * -FU * -FU * * \n" "P5 * -FU+FU * +GI-FU * -FU+KY\n" "P6+FU * * * * * +KE * * \n" "P7 * +FU * -TO * +FU+FU+FU * \n" "P8+KY * * * * +KI+KI+GI * \n" "P9 * +KE-UM * +KA * * +KE+OU\n" "P+00GI00FU\n" "P-00HI00GI00FU00FU00FU\n" "-\n").initialState()); BOOST_CHECK(! Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,LANCE), Square(1,5), Square(1,6))); } { const NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * * * * -KI * -OU\n" "P3 * * -FU * * -KI * * * \n" "P4-FU-HI * * -FU * -FU * * \n" "P5 * -FU+FU * +GI-FU * -FU+KY\n" "P6+FU * * * * * +KE * * \n" "P7 * +FU * -TO * +FU+FU+FU * \n" "P8+KY * * * * +KI+KI+GI * \n" "P9 * +KE-UM * +KA * * +KE+OU\n" "P+00GI00FU\n" "P-00HI00GI00FU00FU00FU\n" "-\n").initialState()); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,LANCE), Square(1,5), Square(1,2))); } { const NumEffectState state(CsaString( "P1-KY-KE * * * * * * -KY\n" "P2 * * * * * * -KI-OU * \n" "P3 * * -FU * * -KI * * * \n" "P4-FU-HI * * -FU * -FU * * \n" "P5 * -FU+FU * +GI-FU * -FU+KY\n" "P6+FU * * * * * +KE * * \n" "P7 * +FU * -TO * +FU+FU+FU * \n" "P8+KY * * * * +KI+KI+GI * \n" "P9 * +KE-UM * +KA * * +KE+OU\n" "P+00GI00FU\n" "P-00HI00GI00FU00FU00FU\n" "-\n").initialState()); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,LANCE), Square(1,5), Square(2,2))); } } BOOST_AUTO_TEST_CASE(Neighboring8DirectTestFindNearest) { { const NumEffectState state(CsaString( "P1-KY-KE-KI-GI * +HI-FU * * \n" "P2 * -OU-GI * -FU * * * * \n" "P3 * * -FU-FU-KI * * * -FU\n" "P4 * * * * * * * * * \n" "P5-FU * +FU * * * * * * \n" "P6 * * * * +UM * * * * \n" "P7+FU+FU+KE * * +FU * * +FU\n" "P8 * * +OU * +FU * * * * \n" "P9+KY * +GI+KI * * * * +KY\n" "P+00KA00KI00GI00FU00FU00FU00FU00FU\n" "P-00HI00KE00KE00KY00FU\n" "+\n").initialState()); BOOST_CHECK_EQUAL(Square(8,3), Neighboring8Direct::findNearest (state, newPtypeO(BLACK,BISHOP), Square(6,5), Square(8,2))); BOOST_CHECK_EQUAL(Square::STAND(), Neighboring8Direct::findNearest (state, newPtypeO(BLACK,BISHOP), Square(3,6), Square(8,2))); } } BOOST_AUTO_TEST_CASE(Neighboring8DirectTestTable) { const NumEffectState state; // gold // direct const Square white_king = Square(5,1); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,GOLD), Square(4,2), white_king)); // 3x3 BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,GOLD), Square(3,2), white_king)); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,GOLD), Square(4,2), white_king)); // out BOOST_CHECK(!Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,GOLD), Square(2,2), white_king)); BOOST_CHECK(!Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,GOLD), Square(3,3), white_king)); // black king const Square black_king = Square(5,9); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,GOLD), Square(4,8), black_king)); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,GOLD), Square(3,8), black_king)); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,GOLD), Square(4,8), black_king)); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,GOLD), Square(3,7), black_king)); BOOST_CHECK(!Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,GOLD), Square(3,7), black_king)); // lance BOOST_CHECK(! Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,LANCE), Square(4,7), black_king)); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,LANCE), Square(4,7), black_king)); BOOST_CHECK(! Neighboring8Direct::hasEffect (state, newPtypeO(WHITE,LANCE), Square(4,6), black_king)); // bishop BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,BISHOP), Square(6,3), white_king)); BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,BISHOP), Square(8,3), white_king)); BOOST_CHECK(!Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,BISHOP), Square(9,4), white_king)); // rook BOOST_CHECK(Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,ROOK), Square(1,4), Square(1,7))); // nearestãŒã¯ã¿ã ã™ BOOST_CHECK(!Neighboring8Direct::hasEffect (state, newPtypeO(BLACK,BISHOP), Square(8,8), black_king)); } BOOST_AUTO_TEST_CASE(Neighboring8DirectTestEqual) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); int max=100; if (OslConfig::inUnitTestShort()) max=10; std::string filename; int i=0; while((ifs >> filename) && (++i using namespace osl; using namespace osl::game_playing; BOOST_AUTO_TEST_CASE(RecordTracerTestEmpty) { std::vector moves; RecordTracer tracer(moves); BOOST_CHECK_EQUAL(true, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(Move::INVALID(), tracer.selectMove()); } BOOST_AUTO_TEST_CASE(RecordTracerTestTrace) { std::vector moves; const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m26fu(Square(2,7),Square(2,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m34fu(Square(3,3),Square(3,4),PAWN,PTYPE_EMPTY,false,WHITE); moves.push_back(m76fu); moves.push_back(m34fu); RecordTracer tracer(moves); moves.clear(); // copy ã•れãŸã¯ãš BOOST_CHECK_EQUAL(false, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(m76fu, tracer.selectMove()); tracer.update(m76fu); BOOST_CHECK_EQUAL(false, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(m34fu, tracer.selectMove()); tracer.update(m34fu); BOOST_CHECK_EQUAL(true, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(Move::INVALID(), tracer.selectMove()); tracer.popMove(); BOOST_CHECK_EQUAL(false, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(m34fu, tracer.selectMove()); tracer.popMove(); BOOST_CHECK_EQUAL(false, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(m76fu, tracer.selectMove()); tracer.update(m26fu); BOOST_CHECK_EQUAL(true, tracer.isOutOfBook()); BOOST_CHECK_EQUAL(Move::INVALID(), tracer.selectMove()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/gnuShogiClient.t.cc0000644000000000000000000000204212316770314022512 0ustar rootroot#include "osl/game_playing/gnuShogiClient.h" #include "osl/game_playing/recordTracer.h" #include "osl/game_playing/bookPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/csaLogger.h" #include #include using namespace osl; using namespace osl::game_playing; BOOST_AUTO_TEST_CASE(testUndo) { std::vector moves; const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m34fu(Square(3,3),Square(3,4),PAWN,PTYPE_EMPTY,false,WHITE); moves.push_back(m76fu); moves.push_back(m34fu); BookPlayer white(new RecordTracer(moves), new ResignPlayer()); std::ostringstream log; CsaLogger *logger = new CsaLogger(log); std::istringstream is("7g7f\n"); std::ostringstream os; GnuShogiClient client(0, &white, logger, is, os); client.setComputerPlayer(WHITE, true); client.run(); BOOST_CHECK_EQUAL(std::string("1. 7g7f 149800\n" "1. ... 3c3d 149900\n"), os.str()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/searchPlayer.t.cc0000644000000000000000000000463312316770314022222 0ustar rootroot#include "osl/game_playing/searchPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/search/timeControl.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::game_playing; BOOST_AUTO_TEST_CASE(SearchPlayerTestSecondsForThisMove) { const int moves_penalty = 1-240; { const SimpleState state(CsaString( "P1-KY-KE-GI-KI * -KI-GI-KE-KY\n" "P2 * -HI * * * * * -KA * \n" "P3-FU-FU-FU-FU-FU-FU-FU-FU-FU\n" "P4 * * * * -OU * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * +OU * * * * \n" "P7+FU+FU+FU+FU+FU+FU+FU+FU+FU\n" "P8 * +KA * * * * * +HI * \n" "P9+KY+KE+GI+KI * +KI+GI+KE+KY\n" "+\n").initialState()); const GameState gs(state); const int e1400 = search::TimeControl::secondsForThisMove(1400); BOOST_CHECK_EQUAL(e1400, SearchPlayer::secondsForThisMove(gs, 1500-moves_penalty, 100, 0, 0)); const int e300 = search::TimeControl::secondsForThisMove(300); BOOST_CHECK_EQUAL(e300, SearchPlayer::secondsForThisMove(gs, 1500-moves_penalty, 1200, 0, 0)); BOOST_CHECK_EQUAL(1, SearchPlayer::secondsForThisMove(gs, 0, 0, 0, 0)); BOOST_CHECK_EQUAL(-1, SearchPlayer::secondsForThisMove(gs, 0, -1, -1, 0)); } { // çµ‚ç›¤ã§æ™‚é–“ãŒè±Šå¯Œã«ã‚れã°å€ const SimpleState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * * * * * * \n" "P3 * * * +KI+GI+KI * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * -KI-GI-KI * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P-00AL\n" "-\n").initialState()); const GameState gs(state); const int e1400 = search::TimeControl::secondsForThisMove(1400); BOOST_CHECK_EQUAL(e1400*2, SearchPlayer::secondsForThisMove(gs, 1500-moves_penalty, 100, 0, 0)); const int e300 = search::TimeControl::secondsForThisMove(300); BOOST_CHECK_EQUAL(e300, SearchPlayer::secondsForThisMove(gs, 1500-moves_penalty, 1200, 0, 0)); BOOST_CHECK_EQUAL(1, SearchPlayer::secondsForThisMove(gs, 0, 0, 0, 0)); BOOST_CHECK_EQUAL(-1, SearchPlayer::secondsForThisMove(gs, 0, -1, -1, 0)); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/bookPlayer.t.cc0000644000000000000000000000334212316770314021703 0ustar rootroot#include "osl/game_playing/bookPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/recordTracer.h" #include "osl/sennichite.h" #include #include using namespace osl; using namespace osl::game_playing; BOOST_AUTO_TEST_CASE(BookPlayerTestUndo) { std::vector moves; const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m34fu(Square(3,3),Square(3,4),PAWN,PTYPE_EMPTY,false,WHITE); moves.push_back(m76fu); moves.push_back(m34fu); BookPlayer white(new RecordTracer(moves), new ResignPlayer()); GameState state((SimpleState(HIRATE))); white.pushMove(m76fu); state.pushMove(m76fu); BOOST_CHECK_EQUAL(m34fu, white.selectBestMove(state, 20, 10, 0).move); white.popMove(); white.pushMove(m76fu); BOOST_CHECK_EQUAL(m34fu, white.selectBestMove(state, 20, 10, 0).move); white.pushMove(m34fu); state.pushMove(m34fu); const Move m26fu(Square(2,7),Square(2,6),PAWN,PTYPE_EMPTY,false,BLACK); white.pushMove(m26fu); state.pushMove(m26fu); BOOST_CHECK_EQUAL(Move::INVALID(), white.selectBestMove(state, 20, 10, 0).move); } BOOST_AUTO_TEST_CASE(BookPlayerTestLimit) { std::vector moves; const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m34fu(Square(3,3),Square(3,4),PAWN,PTYPE_EMPTY,false,WHITE); moves.push_back(m76fu); moves.push_back(m34fu); BookPlayer player(new RecordTracer(moves), new ResignPlayer()); BOOST_CHECK(player.bookAvailable()); player.pushMove(m76fu); BOOST_CHECK(player.bookAvailable()); player.setBookLimit(0); BOOST_CHECK(! player.bookAvailable()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/weightTracer.t.cc0000644000000000000000000000203612316770314022223 0ustar rootroot#include "osl/game_playing/weightTracer.h" #include "osl/oslConfig.h" #include using namespace osl; using namespace osl::game_playing; BOOST_AUTO_TEST_CASE(WeightTracerTestTop1) { osl::book::WeightedBook book(osl::OslConfig::openingBook()); osl::game_playing::DeterminateWeightTracer tracer(book, false, 1); const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); for (int i=0; i<100; ++i) { BOOST_CHECK_EQUAL(m76fu, tracer.selectMove()); } } BOOST_AUTO_TEST_CASE(WeightTracerTestTop2) { osl::book::WeightedBook book(osl::OslConfig::openingBook()); osl::game_playing::DeterminateWeightTracer tracer(book, false, 2); const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m26fu(Square(2,7),Square(2,6),PAWN,PTYPE_EMPTY,false,BLACK); for (int i=0; i<100; ++i) { const Move selected = tracer.selectMove(); BOOST_CHECK(selected == m76fu || selected == m26fu); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/csaClient.t.cc0000644000000000000000000000177712316770314021513 0ustar rootroot#include "osl/game_playing/csaClient.h" #include "osl/game_playing/recordTracer.h" #include "osl/game_playing/bookPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/game_playing/csaLogger.h" #include #include using namespace osl; using namespace osl::game_playing; BOOST_AUTO_TEST_CASE(CsaClientTestUndo) { std::vector moves; const Move m76fu(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); const Move m34fu(Square(3,3),Square(3,4),PAWN,PTYPE_EMPTY,false,WHITE); moves.push_back(m76fu); moves.push_back(m34fu); BookPlayer white(new RecordTracer(moves), new ResignPlayer()); std::ostringstream log; CsaLogger *logger = new CsaLogger(log); std::istringstream is("+7776FU\n%TORYO\n"); std::ostringstream os; CsaClient client(0, &white, logger, is, os); client.setSilent(true); client.run(); BOOST_CHECK_EQUAL(std::string("-3334FU\n"), os.str()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/historyToTable.t.cc0000644000000000000000000001641512316770314022555 0ustar rootroot// historyToTable.t.cc #include "osl/game_playing/historyToTable.h" #include "osl/game_playing/gameState.h" #include "osl/search/simpleHashTable.h" #include "osl/search/simpleHashRecord.h" #include "osl/csa.h" #include "osl/hashKey.h" #include "osl/sennichite.h" #include using namespace osl; using namespace osl::game_playing; const int BLACK_WIN = 1000; const int DRAW = 0; const int WHITE_WIN = -1000; const int limit = search::SearchTable::HistorySpecialDepth; BOOST_AUTO_TEST_CASE(HistoryToTableTestBestMoveInWin) { const char *horizon_drop_string = "P1-KY * * -KI * * * -KE-KY\n" "P2 * -OU * -RY-KI * * -KA * \n" "P3 * +TO * -FU * -FU * -FU * \n" "P4+HI * -GI-GI-FU * * * -FU\n" "P5+FU * * * * * * * * \n" "P6 * * * +FU * * * * * \n" "P7 * * -KA+GI+FU+FU+FU+FU+FU\n" "P8 * * * * +KI+GI+KI+OU * \n" "P9+KY * * * * * * +KE+KY\n" "P+00FU00FU\n" "P-00AL\n" "-\n" "-7483GI\n" "+0084FU\n" "-8374GI\n" "+8483TO\n"; CsaString horizon_drop(horizon_drop_string); GameState state(horizon_drop.initialState()); const auto& moves = horizon_drop.load().moves; for (size_t i=0; ihasLowerBound(limit)); BOOST_CHECK(record->hasUpperBound(limit)); BOOST_CHECK_EQUAL(WHITE_WIN, record->lowerBound()); BOOST_CHECK_EQUAL(WHITE_WIN, record->upperBound()); BOOST_CHECK(record->bestMove().move().isValid()); BOOST_CHECK_EQUAL(Move(Square(7,4),Square(8,3), SILVER,PPAWN,false,WHITE), record->bestMove().move()); } BOOST_AUTO_TEST_CASE(HistoryToTableTestBestMoveInLose) { const char *horizon_drop_string = "P1-KY * * -KI * * * -KE-KY\n" "P2 * * * -RY-KI * * -KA * \n" "P3 * -OU * -FU * -FU * -FU * \n" "P4+HI * -GI-GI-FU * * * -FU\n" "P5+FU * * * * * * * * \n" "P6 * * * +FU * * * * * \n" "P7 * * -KA+GI+FU+FU+FU+FU+FU\n" "P8 * * * * +KI+GI+KI+OU * \n" "P9+KY * * * * * * +KE+KY\n" "P+00FU00FU\n" "P-00AL\n" "+\n" "+0084FU\n" "-8382OU\n" "+8483TO\n" "-8283OU\n"; CsaString horizon_drop(horizon_drop_string); GameState state(horizon_drop.initialState()); const auto& moves = horizon_drop.load().moves; for (size_t i=0; ihasLowerBound(limit)); BOOST_CHECK(record->hasUpperBound(limit)); BOOST_CHECK_EQUAL(WHITE_WIN, record->lowerBound()); BOOST_CHECK_EQUAL(WHITE_WIN, record->upperBound()); BOOST_CHECK(record->bestMove().move().isInvalid()); } BOOST_AUTO_TEST_CASE(HistoryToTableTestCurrentState) { GameState state((SimpleState(HIRATE))); SimpleHashTable table; HistoryToTable::adjustTable(state, table, BLACK_WIN, DRAW, WHITE_WIN); const SimpleHashRecord *record = table.find(HashKey(state.state())); BOOST_CHECK_EQUAL((const SimpleHashRecord*)0, record); } BOOST_AUTO_TEST_CASE(HistoryToTableTestDominance) { GameState state(CsaString( "P1-KY * * * * * * +NY * \n" "P2 * -OU-KI-KI * * * * +RY\n" "P3 * -GI-KE+KI * * * * +HI\n" "P4 * * -FU-KY-FU * * -FU * \n" "P5-FU-FU * -KE * -FU * * * \n" "P6 * * +FU-FU+FU * -FU * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+GI+GI-UM * * * * * \n" "P9+OU+KE * * * * * +KE * \n" "P-00FU00FU00FU00FU00FU00FU00GI00KA\n" "P+00KI\n" "+\n").initialState()); SimpleHashTable table; HistoryToTable::adjustTable(state, table, BLACK_WIN, DRAW, WHITE_WIN); { // black have more pawn NumEffectState dominance_state(CsaString( "P1-KY * * * * * * +NY * \n" "P2 * -OU-KI-KI * * * * +RY\n" "P3 * -GI-KE+KI * * * * +HI\n" "P4 * * -FU-KY-FU * * -FU * \n" "P5-FU-FU * -KE * -FU * * * \n" "P6 * * +FU-FU+FU * -FU * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+GI+GI-UM * * * * * \n" "P9+OU+KE * * * * * +KE * \n" "P-00FU00FU00FU00FU00FU00GI00KA\n" "P+00FU00KI\n" "+\n").initialState()); const SimpleHashRecord *record = table.find(HashKey(dominance_state)); BOOST_CHECK(record); BOOST_CHECK(record->hasLowerBound(limit)); BOOST_CHECK(record->hasUpperBound(limit)); BOOST_CHECK_EQUAL(BLACK_WIN, record->lowerBound()); BOOST_CHECK_EQUAL(BLACK_WIN, record->upperBound()); } { // white have more gold NumEffectState dominance_state(CsaString( "P1-KY * * * * * * +NY * \n" "P2 * -OU-KI-KI * * * * +RY\n" "P3 * -GI-KE+KI * * * * +HI\n" "P4 * * -FU-KY-FU * * -FU * \n" "P5-FU-FU * -KE * -FU * * * \n" "P6 * * +FU-FU+FU * -FU * * \n" "P7+FU+FU * * * * * * * \n" "P8+KY+GI+GI-UM * * * * * \n" "P9+OU+KE * * * * * +KE * \n" "P-00FU00FU00FU00FU00FU00FU00KI00GI00KA\n" "+\n").initialState()); const SimpleHashRecord *record = table.find(HashKey(dominance_state)); BOOST_CHECK(record); BOOST_CHECK(record->hasLowerBound(limit)); BOOST_CHECK(record->hasUpperBound(limit)); BOOST_CHECK_EQUAL(WHITE_WIN, record->lowerBound()); BOOST_CHECK_EQUAL(WHITE_WIN, record->upperBound()); } } BOOST_AUTO_TEST_CASE(HistoryToTableTestLose) { const char *oute_string = "P1-KY * * * * * * * * \n" "P2 * -KY+TO * * +NK * +HI * \n" "P3 * * * -FU-KI * -KE * -FU\n" "P4-FU * +NK * * -OU * * * \n" "P5 * * * * * * -GI * * \n" "P6 * * * * * * * -FU * \n" "P7 * +FU * +FU+FU+OU+FU * +FU\n" "P8 * +GI+KI+GI * * * * +GI\n" "P9 * * * * * * * +KE+KY\n" "P+00HI00KA00KA00KI00KI00KY00FU00FU00FU00FU00FU00FU00FU00FU\n" "-\n" "-3546GI\n" "+4736OU\n" "-4635GI\n" "+3647OU\n"; CsaString oute_sennnichite(oute_string); GameState state(oute_sennnichite.initialState()); const auto& moves = oute_sennnichite.load().moves; for (size_t i=0; ihasLowerBound(limit)); BOOST_CHECK(record->hasUpperBound(limit)); BOOST_CHECK_EQUAL(BLACK_WIN, record->lowerBound()); BOOST_CHECK_EQUAL(BLACK_WIN, record->upperBound()); BOOST_CHECK(record->bestMove().move().isInvalid()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/alphaBetaPlayer.t.cc0000644000000000000000000000351712316770314022636 0ustar rootroot#include "osl/game_playing/alphaBetaPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/eval/progressEval.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::game_playing; static void load() { static bool loaded = osl::eval::ProgressEval::setUp(); BOOST_CHECK(loaded); } const int seconds = 5; BOOST_AUTO_TEST_CASE(AlphaBetaPlayerTestResign) { load(); const SimpleState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * +KI * * * * \n" "P3 * * * * +FU * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P-00AL\n" "-\n").initialState()); const GameState gs(state); AlphaBeta2ProgressEvalPlayer player; const MoveWithComment best_move = player.selectBestMove(gs, 1500, seconds, 0); BOOST_CHECK_EQUAL(Move::INVALID(), best_move.move); } BOOST_AUTO_TEST_CASE(AlphaBetaPlayerTestWin) { load(); const SimpleState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * * * * * * \n" "P3 * * * * +FU * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState()); const GameState gs(state); AlphaBeta2ProgressEvalPlayer player; const MoveWithComment best_move = player.selectBestMove(gs, 1500, seconds, 0); const Move expected(Square(5,2), GOLD, BLACK); BOOST_CHECK_EQUAL(expected, best_move.move); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/alphaBetaOpenMidEndingEvalPlayer.t.cc0000644000000000000000000000375112316770314026047 0ustar rootroot#include "osl/game_playing/alphaBetaPlayer.h" #include "osl/game_playing/gameState.h" #include "osl/eval/openMidEndingEval.h" #include "osl/csa.h" #include using namespace osl; using namespace osl::game_playing; static void load() { static bool loaded = osl::eval::OpenMidEndingEval::setUp(); BOOST_CHECK(loaded); static bool loaded_progress = osl::progress::NewProgress::setUp(); BOOST_CHECK(loaded_progress); } const int seconds = 5; BOOST_AUTO_TEST_CASE(AlphaBetaOpenMidEndingEvalPlayerTestResign) { load(); const SimpleState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * +KI * * * * \n" "P3 * * * * +FU * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P-00AL\n" "-\n").initialState()); const GameState gs(state); AlphaBeta2OpenMidEndingEvalPlayer player; const MoveWithComment best_move = player.selectBestMove(gs, 1500, seconds, 0); BOOST_CHECK_EQUAL(Move::INVALID(), best_move.move); } BOOST_AUTO_TEST_CASE(AlphaBetaOpenMidEndingEvalPlayerTestWin) { load(); const SimpleState state(CsaString( "P1 * * * * -OU * * * * \n" "P2 * * * * * * * * * \n" "P3 * * * * +FU * * * * \n" "P4 * * * * * * * * * \n" "P5 * * * * * * * * * \n" "P6 * * * * * * * * * \n" "P7 * * * * * * * * * \n" "P8 * * * * * * * * * \n" "P9 * * * * +OU * * * * \n" "P+00KI\n" "P-00AL\n" "+\n").initialState()); const GameState gs(state); AlphaBeta2OpenMidEndingEvalPlayer player; const MoveWithComment best_move = player.selectBestMove(gs, 1500, seconds, 0); const Move expected(Square(5,2), GOLD, BLACK); BOOST_CHECK_EQUAL(expected, best_move.move); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/full/test/game_playing/gameState.t.cc0000644000000000000000000001646112316770314021514 0ustar rootroot#include "osl/game_playing/gameState.h" #include "osl/game_playing/searchPlayer.tcc" #include "osl/sennichite.h" #include "osl/csa.h" #include "osl/oslConfig.h" #include #include #include using namespace osl; using namespace game_playing; BOOST_AUTO_TEST_CASE(GameStateTestCanPopMove) { SimpleState initialState(HIRATE); GameState state(initialState); BOOST_CHECK(! state.canPopMove()); const Move m76(Square(7,7),Square(7,6),PAWN,PTYPE_EMPTY,false,BLACK); state.pushMove(m76); BOOST_CHECK(state.canPopMove()); BOOST_CHECK_EQUAL(initialState, state.initialState()); std::shared_ptr state_clone = state.clone(); BOOST_CHECK(state_clone->canPopMove()); const Move m84(Square(8,3),Square(8,4),PAWN,PTYPE_EMPTY,false,WHITE); state_clone->pushMove(m84); BOOST_CHECK(state_clone->canPopMove()); BOOST_CHECK_EQUAL(m84, state_clone->popMove()); BOOST_CHECK_EQUAL(m76, state.popMove()); BOOST_CHECK_EQUAL(initialState, state_clone->initialState()); } BOOST_AUTO_TEST_CASE(GameStateTestRepetition) { GameState state((SimpleState(HIRATE))); const Move m48(Square(3,9),Square(4,8),SILVER,PTYPE_EMPTY,false,BLACK); const Move m39(Square(4,8),Square(3,9),SILVER,PTYPE_EMPTY,false,BLACK); const Move m42(Square(3,1),Square(4,2),SILVER,PTYPE_EMPTY,false,WHITE); const Move m31(Square(4,2),Square(3,1),SILVER,PTYPE_EMPTY,false,WHITE); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m48)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m42)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m39)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m31)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m48)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m42)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m39)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m31)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m48)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m42)); BOOST_CHECK_EQUAL(Sennichite::NORMAL(), state.pushMove(m39)); BOOST_CHECK_EQUAL(Sennichite::DRAW(), state.pushMove(m31)); } static void testRootHistoryRecord(const SimpleState& sstate, const std::vector& moves) { GameState state(sstate); for (unsigned int i=0;i moves; moves.push_back(Move(Square(1,5),PAWN,WHITE)); moves.push_back(Move(Square(1,7),SILVER,BLACK)); moves.push_back(Move(Square(1,6),Square(1,7),KING,SILVER,false,WHITE)); moves.push_back(Move(Square(1,3),Square(1,5),PROOK,PAWN,true,BLACK)); moves.push_back(Move(Square(1,6),SILVER,WHITE)); testRootHistoryRecord(state, moves); } BOOST_AUTO_TEST_CASE(GameStateTestRootHistoryFiles) { std::ifstream ifs(OslConfig::testCsaFile("FILES")); BOOST_CHECK(ifs); std::string file_name; for (int i=0; i<(OslConfig::inUnitTestShort() ? 3: 300) && (ifs >> file_name); i++){ if (file_name == "") break; if (OslConfig::verbose()) std::cerr << file_name << "\n"; file_name = OslConfig::testCsaFile(file_name); auto record=CsaFileMinimal(file_name).load(); const auto& moves=record.moves; testRootHistoryRecord(SimpleState(HIRATE), moves); } } BOOST_AUTO_TEST_CASE(GameStateTestGenerateNotLosingMoves) { { GameState state(CsaString( "P1 * * * * * * * -KE-OU\n" "P2 * * * -GI * -KI-KI * * \n" "P3 * * * -FU * * -GI-FU+UM\n" "P4-KY-FU * * -FU+FU-FU * -KY\n" "P5 * * * * * -FU * +KE * \n" "P6-HI * -FU+FU+FU * * +GI * \n" "P7+KE+FU * +KI * * +KE+FU * \n" "P8+FU+OU+KI+KA * -NY * * * \n" "P9 * * * * * * * * * \n" "P+00FU00FU\n" "P-00HI00GI00KY00FU00FU00FU\n" "+\n").initialState()); MoveVector normal_or_win_or_draw, loss; state.generateNotLosingMoves(normal_or_win_or_draw, loss); const Move m12fu(Square(1,2),PAWN,BLACK); BOOST_CHECK(! normal_or_win_or_draw.isMember(m12fu)); } { // loss by kachi GameState state(CsaString( "P1 * * +RY * * +KI * -KE * \n" "P2+OU+TO+UM+UM+TO * -KI-OU * \n" "P3-FU+FU+FU+FU+FU-GI-GI * * \n" "P4 * * * * -FU-FU-FU-FU * \n" "P5 * * -RY-NY-GI * * * * \n" "P6 * * * * * +FU+FU+FU * \n" "P7 * * * * * +KI+KE * -NY\n" "P8 * * * * * +KI+GI * * \n" "P9 * * * * -NY * * * * \n" "P+00FU00FU00FU00FU00KY00KE00KE\n" "-\n").initialState()); MoveVector normal_or_win_or_draw, loss; state.generateNotLosingMoves(normal_or_win_or_draw, loss); BOOST_CHECK(normal_or_win_or_draw.size() == 2); // -7573RY or -4352GI } } BOOST_AUTO_TEST_CASE(GameStateTestGenerateMoves) { { CsaString csa("P1-KY-KE-OU-KI * * * * -KY\n" "P2 * * -GI * * * * -KI * \n" "P3-FU * -FU-FU-FU-FU * * * \n" "P4 * * * * * * -HI-GI-FU\n" "P5 * * +FU * * +KE * * * \n" "P6 * * +KE * * +FU-FU * * \n" "P7+FU+FU * +FU+FU * * +HI+FU\n" "P8 * +GI+KI+OU * * * * * \n" "P9+KY+KE * * * +KI * * +KY\n" "P+00KA00FU00FU00FU\n" "P-00KA00GI00FU\n" "+\n" "+0035FU\n" "-3494HI\n"); GameState state(csa.initialState()); const auto& moves = csa.load().moves; BOOST_FOREACH(Move move, moves) state.pushMove(move); MoveVector normal, win, draw, loss; state.generateMoves(normal, win, draw, loss); BOOST_CHECK(loss.isMember(Move(Square(3,5),Square(3,4),PAWN,PTYPE_EMPTY,false,BLACK))); BOOST_CHECK(loss.size() == 1); } { CsaString csa("P1-KY * * -KI * * * -KE-KY\n" "P2 * -OU-GI * -KI-HI * * * \n" "P3 * -FU-KE * -FU * -KA-FU * \n" "P4-FU * -FU-FU-GI * -FU * -FU\n" "P5 * * * * * -FU * +FU * \n" "P6+FU+FU+FU+FU+FU * +FU * * \n" "P7 * +GI+KA+KI+GI+FU * * +FU\n" "P8 * +OU+KI * * * * +HI * \n" "P9+KY+KE * * * * * +KE+KY\n" "+\n" "+2838HI\n" "-3344KA\n" "+3828HI\n"); GameState state(csa.initialState()); const auto& moves = csa.load().moves; for (Move move: moves) state.pushMove(move); const Move m33ka(Square(4,4),Square(3,3),BISHOP,PTYPE_EMPTY,false,WHITE); MoveVector normal, win, draw, loss; state.generateMoves(normal, win, draw, loss); BOOST_CHECK(! loss.isMember(m33ka)); BOOST_CHECK(draw.isMember(m33ka)); BOOST_CHECK(loss.empty()); BOOST_CHECK_EQUAL((size_t)1u, draw.size()); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/tools/0000755000000000000000000000000011702205404013573 5ustar rootrootlibosl-0.8.0.orig/tools/bi.pl0000755000000000000000000000564411702205404014536 0ustar rootroot#!/usr/bin/perl -w # Æó¹àʬÉۤγÎΨ·×»» use strict; use Getopt::Std; my %options=(); getopts("t:w:p:s:",\%options); my $total = $options{t} ? $options{t} : 20; my $win = defined $options{w} ? $options{w} : $total/2; my $p = defined $options{p} ? $options{p} : 0.5; my $significance = $options{'s'} ? $options{'s'} : 0.05; my $prob = &probability_cumulative($p, $total, $win); printf "%4d / %4d \t... %f %s\n", $win, $total, $prob, ($prob < $significance) ? "*" : ""; printf "%4d / %4d \tfor significance %f\n", &significant_win($p, $total, $significance), $total, $significance; printf "[%f : %f ]\tfor significance %f\n", &significant_prob($total, $win, $significance), 1.0 - &significant_prob($total, $total-$win, $significance), $significance; # foreach my $s (0.01, 0.05, 0.1) { # foreach my $t (10, 20, 50, 100, 200, 500, 1000) { # printf "%4d / %5d \tfor significance %f\n", # &significant_win($p, $t, $s), $t, $s; # } # } sub pow($$){ my ($p, $n) = @_; my $result = 1.0; foreach my $i (1..$n) { $result *= $p; } return $result; } sub significant_win($$$) { my ($p, $total, $significance) = @_; my $sum = 0.0; my $win = $total; while ($sum < $significance) { $sum += &probability($p, $total, $win); $win--; } return $win+2; } my %probability_memoize; sub probability_cumulative($$$){ my ($p, $total, $win) = @_; my $key = $p."-".$total."-".$win; return $probability_memoize{$key} if ($probability_memoize{$key}); my $sum = 0.0; foreach my $i ($win .. $total) { my $key_i = $p."-".$total."-".$i; if ($probability_memoize{$key}) { $sum += $probability_memoize{$key}; last; } $sum += probability($p, $total, $i) } return $probability_memoize{$key} = $sum; } sub probability($$$){ my ($p, $total, $win) = @_; return exp(log_probability($p, $total, $win)); } sub log_probability($$$){ my ($p, $total, $win) = @_; return log_cnr($total, $win) + $win * log($p) + ($total-$win) * log(1-$p); } sub log_factorial($){ # Stirling's formula my ($n) = @_; my $pi = 3.1415926535897932; return ($n+0.5)*log($n) - $n+0.5*log(2*$pi) + 1.0/12/$n - 1.0/360/$n/$n/$n + 1.0/1260/$n/$n/$n/$n/$n; } sub log_cnr($$){ my ($n, $r) = @_; return 0 if (($n == $r) || ($r == 0)); return log_factorial($n)-log_factorial($r)-log_factorial($n-$r); } sub cnr($$){ my ($n, $r) = @_; return 1 if (($n == $r) || ($r == 0)); return exp(log_cnr($n,$r)); } sub significant_prob ($$$) { my ($total, $win, $significance) = @_; my $last_significant = 0.0; my $step = 1; # 1.0/$step is used while ($step <= 128) { for (my $i=1; $last_significant*$step+$i<$step; ++$i) { my $p=($step*$last_significant + $i) / $step; my $prob = &probability_cumulative($p, $total, $win); last if ($prob > $significance); $last_significant = $p; } $step *= 2; } return $last_significant; } libosl-0.8.0.orig/tools/kanji2csa/0000755000000000000000000000000010237166571015455 5ustar rootrootlibosl-0.8.0.orig/tools/kanji2csa/sample.txt0000644000000000000000000000071610227657623017505 0ustar rootroot¼ê¹ç³ä¡§Ê¿¼ê ¸å¼ê¤Î»ý¶ð¡§Êâ»° £¹ £¸ £· £¶ £µ £´ £³ £² £± +---------------------------+ |v¶Ìv·Ëv¶âv¶ä ¡¦ ¡¦ ¡¦ ζv¹á|°ì |v¹áv¶ä ¡¦ ¡¦ ¡¦ ¡¦ ¡¦ ¡¦ ¡¦|Æó | ¡¦vÊâvÊâ Á´ ÊâvÊâ ¡¦ ¡¦ ¡¦|»° |vÊâ ¡¦v·Ë ¡¦ ¡¦ ¡¦vÊâ ¡¦ ¡¦|»Í | ÇÏ ¡¦ ¡¦ ¡¦ ¡¦v·Ë ¡¦ ¡¦vÊâ|¸Þ | Êâ ¡¦ Êâ Êâ ¡¦v³Ñ Êâ ¡¦ ¡¦|Ï» | ¡¦ Êâ ¶ävÊâ ¡¦ ¡¦ ¡¦ ¡¦ Êâ|¼· | ¹á ¶â ¡¦ ¡¦ ¡¦ ¡¦ ¡¦ ¡¦ ¡¦|Ȭ | ¶Ì ·Ëv¶â ¡¦ ¡¦ ¡¦ ¡¦ ¡¦ ¹á|¶å +---------------------------+ Àè¼ê¤Î»ý¶ð¡§Èô¡¡¶â¡¡Êâ¡¡ Àè¼êÈÖ Àè¼ê¡§IS¾­´ý ¸å¼ê¡§YSS libosl-0.8.0.orig/tools/kanji2csa/kanji2csa.rb0000755000000000000000000000513310237166571017654 0ustar rootroot#!/usr/bin/env ruby require "jcode" require 'nkf' $KCODE = "e" #-- Tables PtypeConvert = { "¡¦" => nil, "¶Ì" => "OU", "Èô" => "HI", "³Ñ" => "KA", "¶â" => "KI", "¶ä" => "GI", "·Ë" => "KE", "¹á" => "KY", "Êâ" => "FU", "ζ" => "RY", "ÇÏ" => "UM", "Á´" => "NG", "·½" => "NK", "°É" => "NY", "¤È" => "TO" } NumberConvert = { "Æó" => 2, "»°" => 3, "»Í" => 4, "¸Þ" => 5, "Ï»" => 6, "¼·" => 7, "Ȭ" => 8, "¶å" => 9 #¤½¤ì¤è¤ê¿¤¤¤Î¤Ï̵»ë } BLACK = 0 WHITE = 1 PlayerString = [ "+", "-" ] #-- Convert functions def convert_line line ret = "" while line piece = line ret << piece.to_s line = nil end return ret end def convert_player line if /Àè/.match(line) || / /.match(line) return BLACK elsif /¸å/.match(line) || /v/.match(line) return WHITE else STDERR.print "which player? :#{line}\n" return end end def convert_line line ret = "" while piece = /([ |v])(.)/.match(line) line.sub!(/([ |v])(.)/, "") pplayer = PlayerString[convert_player(piece[1])] ptype = PtypeConvert[piece[2]] if ptype == nil ret << " * " else ret << pplayer << ptype end end return ret end def convert_mochigoma line ret = [] last_ptype = nil while piece = /(.)/.match(line) line.sub!(/(.)/, "") if ptype = PtypeConvert[piece[1]] ret.push ptype last_ptype = ptype elsif pcount = NumberConvert[piece[1]] if last_ptype == nil STDERR.print "Piece not set and count of it found\n" STDERR.print [piece[1]] STDERR.print pcount STDERR.print "\n" return end while pcount > 1 ret.push last_ptype pcount -= 1 end end end return ret end #-- Main #- Values bancount = 0 #banmen's line number banmen = [] mochigoma = [[],[]] comments = [] turn = -1 #- Input while !STDIN.eof? line = NKF.nkf("-e", STDIN.readline) if banline = /\|(.+)\|/.match(line) banmen[bancount] = convert_line(banline[1]) bancount+=1 elsif mochiline = /(.+)»ý¶ð¡§(.+)/.match(line) player = mochiline[1] komaline = mochiline[2] mochigoma[convert_player(player)] = convert_mochigoma(komaline) elsif turnline = /(.+)ÈÖ/.match(line) turn = convert_player(turnline[1]) else comments.push line end end comments.reverse! #- Output while !comments.empty? print "'#{comments.pop}" end print "\n" for i in 0...9 print "P#{i+1}#{banmen[i]}\n" end for i in 0..1 if !mochigoma[i].empty? print "P#{PlayerString[i]}" while !mochigoma[i].empty? piece = mochigoma[i].pop print "00#{piece}" end print "\n" end end print "#{PlayerString[turn]}\n" libosl-0.8.0.orig/tools/kanji2csa/200501.html0000644000000000000000000000601410230011712017046 0ustar rootroot --2005/1--
2005/1/15(“y)

blog‚ðì‚Á‚Ă݂܂µ‚½B‚±‚¿‚ç‚Å‚·B
¡‚܂ł̂â‚‚Íemacs‚©‚çange-ftp‚Å’¼Ú‘‚«ž‚ñ‚Å‚¢‚ÄA•¶Í‘‚­‚¾‚¯‚Ȃ瑬‚¢‚¯‚ÇŒ©‰h‚¦‚͈«‚¢‚µA‰æ‘œ“\‚Á‚½‚è‚·‚é‚̂͑å•ςłµ‚½B

2005/1/7(‹à)

Œ‹‹ÇV‚µ‚¢‹l«Šûƒ‹[ƒ`ƒ“ŒÄ‚Ño‚µ•ûŽ®‚ÍAŒ³‚̂₂ɑ΂µ‚Ä491.5-408.5(.546)‚Æ—LˆÓ‚ÉŸ‚¿‰z‚µB
ÅI”Ղł̂ݎw‚µŽè‚ª•Ï‚í‚邿‚¤‚È•ÏX‚Å‚±‚ꂾ‚¯·‚ª‚‚¯‚Έ«‚­‚È‚¢BI”Õ‚ÌM—Š“x‚͈ȑO‚æ‚è‘‚µ‚½‚Í‚¸B
‚ ‚Æ‚ÍGPW‚Å”­•\‚³‚ê‚Ä‚¢‚½‚悤‚É‹l‚ß‚ë‚̉”\«‚ª‚‚¢‹Ç–Ê‚©‚Ç‚¤‚©‚𔻒肵‚Ä‚»‚ê‚ɉž‚¶‚ħŒÀƒm[ƒh”‚ð㉺‚³‚¹‚邯‚¢‚¤‚Ì‚à‚»‚Ì‚¤‚¿ŽŽ‚µ‚Ă݂鉿’l‚ª‚ ‚è‚»‚¤‚¾‚ªA‘¼‚É‚â‚邱‚Æ‚ª‚ ‚é‚̂Ōã‰ñ‚µB

2005/1/4(‰Î)

ð“ú‚ÍŠÛ‚R”N‚̃uƒ‰ƒ“ƒN‚ðŒo‚ÄA”ÑjƒŠƒ][ƒg‚Æ‚¢‚¤ƒXƒL[ê‚̃iƒCƒ^[‚ŃXƒL[‚ð‚µ‚½B¡“ú‚͋ؓ÷’É‚ª‚Ђǂ¢B
ƒS[ƒOƒ‹‚È‚µ‚Å•’ʂɂ߂ª‚Ë‚Ì‚Ü‚ÜŠŠ‚Á‚½‚Ì‚ÅI‚í‚Á‚½‚ ‚Æ–Ú‚ª‚©‚È‚è[ŒŒ‚µ‚½B

2005/1/2(“ú)

‚ ‚¯‚Ü‚µ‚Ä‚¨‚߂łƂ¤‚²‚´‚¢‚Ü‚·B
¡“ú”N‰ê󂪂P’Ê—Fl‚©‚ç—ˆ‚Ü‚µ‚½B
‚±‚±‚P‚O”N‚­‚ç‚¢”N‰êó‚ð‚P’Ê‚à‘‚¢‚ĂȂ¢‚½‚ßi—ˆ‚Ä‚à•ÔŽ–‚ð‘‚©‚È‚¢‚Æ‚¢‚¤Ž¸—ç‚È‚±‚Æ‚à‚µ‚Ä‚«‚Ü‚µ‚½j—ˆ‚é•û‚à’iX‚Æ×‚Á‚Ä‚«‚ÄA‚±‚±””Né“`‚ª‚ç‚݂Ƃ©‚µ‚©—ˆ‚ĂȂ©‚Á‚½‚ÆŽv‚¤‚̂ł¿‚å‚Á‚Æ‹Á‚«‚Ü‚µ‚½B

‚³‚ÄAŽ„‚ÍVt‚©‚猋\“­‚¢‚Ä‚¢‚ÄA¡“ú‚Í•KŽ€‚ÆŽv‚¢ž‚ñ‚ÅŽÀ‚Í‘ŠŽè‚ÌŠæ’£‚è‚ðŒ©“¦‚µ‚Ä‚¢‚邾‚¯‚Æ‚¢‚¤¡‚܂ŎžXoŒ»‚µ‚Ä‚¢‚½ƒpƒ^[ƒ“‚ð‚Ù‚Úo‚È‚­‚µ‚½‚ÆŽv‚¤‚Ì‚¾‚ªAFXƒeƒXƒg‚µ‚Ä‚¢‚½‚çuƒRƒ“ƒsƒ…[ƒ^«Šû‚Ìi•à‚Qv‚Ì–â‘èW‚Ì‚P‚T”Ԃɖ͔͉𓚂æ‚è‚à—Ç‚¢‰ð‚ð”­Œ©‚µ‚½B

Žè‡Š„F•½Žè@@
ŒãŽè‚ÌŽ‹îFŠp@‹âŽO@•à“ñ@
  ‚X ‚W ‚V ‚U ‚T ‚S ‚R ‚Q ‚P
+---------------------------+
| Œ\ E E E E E EvŒjv|ˆê
| E —´ E Ev•à ‹àv‹àv‹Ê E|“ñ
| E E E E E •àv‹àv•à E|ŽO
|v•à E Ev•à Ev‹âv•à E E|Žl
| E E E Šp Ev•à E Ev•à|ŒÜ
| •à Ev•à •à E E E E •à|˜Z
| E E E E E E •à •à E|޵
|  E E E ‹à E ‹Ê E E|”ª
| E E E E E E E Œj |‹ã
+---------------------------+
æŽè‚ÌŽ‹îF”ò@Œj@@•à“ñ@
æŽè”Ô
–͔͉𓚂ͣ‚T“ñ—³‚Å—v‚Í¢‚UŒÜ•à‚ÆŽæ‚点‚Ä‚à‚»‚±‚Å‹l‚Þ‚Æ‚¢‚¤‚±‚Æ‚ª•ª‚©‚Á‚Ä‚¢‚é‚©‚Ç‚¤‚©A‚Æ‚¢‚¤–â‘èB
i•à‚Q‚ł̃eƒXƒgŒ‹‰Ê‚ł͊m‚©“–Žž‚̃\ƒtƒg‚Í‚ ‚܂肢‚¢Œ‹‰Ê‚ðŽc‚µ‚ĂȂ©‚Á‚½–â‘肾‚ÆŽv‚¤‚ªA¡‚ł͊ȒP‚È–â‘肾‚ÆŽv‚¤B
IS«Šû‚ÅŽŽ‚µ‚Ä‚à‚·‚®‚É£‚T“ñ—³‚É‹C‚¢‚Ä‚»‚̂܂ܑ¼‚̎肪ã‰ñ‚邱‚Ƃ͂Ȃ©‚Á‚½‚Ì‚¾‚ª¡“ú‰‚߂đ¼‚̎肪ã‰ñ‚é‚Ì‚ðŒ©‚½B
‚»‚ÌŽè‚Í£‚R“ñ‹àB
£‚T“ñ—³‚É”ä‚ׂÂ܂ç‚È‚¢Žè‚̂悤‚É‚àŒ©‚¦‚邪‚±‚ꂪ£‚T“ñ—³‚æ‚è‚à‚͂邩‚É–¾‰õ‚ÅA£‚R“ñ‹à‚É¢“¯‹àˆÈŠO‘S‚Ä‹l‚݂Ȃ̂Ţ“¯‹àB
‚»‚±‚Å£‚S“ñ•ଂÆs‚­B‚È‚ñ‚Æ‚±‚̈ꌩ•ςȎè‚ɑ΂µ‚Ä¢‚PŽlŠp‘łƂ¢‚¤ˆÓ–¡•s–¾‚ÈŽèˆÈŠO‘S‚Äi‚à‚¿‚ë‚ñ‰¤Žè‚𜂭j‹l‚ÝB‚±‚±‚ªŽÀ‚É–Ê”’‚¢‚Æ‚±‚ëB
Œ‹‹Ç[3605]£‚R“ñ‹à¢“¯‹à£‚S“ñ•ଢ‚PŽlŠp£‚R“ñŠp¬¢‚PŽO‹Ê£‚PŒÜ•ࢂS޵‹â£“¯‹à¢“¯Šp¬£“¯‹Ê¢‚S˜Z‹â£‚R”ª‹Ê¢‚S޵‹â‘Å£‚Q”ª‹Ê
‚Æ‚¢‚¤‚Ì‚ªIS«Šû‚̓ǂ݂ÅA’Tõ’†‚Ì‹l«ŠûŒÄ‚Ño‚µ•û–@‚ð•Ï‚¦‚½‚Ì‚ªŒ÷‚ð‘t‚µ‚ĂȂ©‚È‚©³Šm‚ȓǂ݂ɂȂÁ‚Ä‚¢‚éB
‚¿‚Ȃ݂ɣ‚T“ñ—³‚Í1500“_‚­‚ç‚¢‚µ‚©‚¢‚©‚È‚¢B‚à‚¿‚ë‚ñ‚±‚Á‚¿‚àŒ‹‹Ç‚ÍæŽè‚ÌŸ‚¿‚ɕςí‚è‚͂Ȃ¢‚Ì‚¾‚ªB

libosl-0.8.0.orig/tools/multi-mtdfstat/0000755000000000000000000000000010712127510016552 5ustar rootrootlibosl-0.8.0.orig/tools/multi-mtdfstat/run.sh0000755000000000000000000000046210465663265017740 0ustar rootroot#! /bin/sh BASE=/opt/gps/$USER/gpsshogi-nodist/data/problems name=test1 for problem in tesuji/1 tesuji/2 rakuraku/1 rakuraku/2 amateur/1 100/1 100/3 100/2 100/4 kakoi seme-uke; do dir=$BASE/$problem problem_name=`echo $problem | sed -e 's!/!-!g'` $HOME/run.rb $dir > $HOME/$name-$problem_name done libosl-0.8.0.orig/tools/multi-mtdfstat/compare.rb0000755000000000000000000000207610712127510020535 0ustar rootroot#! /usr/bin/env ruby left = ARGV[0] right = ARGV[1] result1 = nil result2 = nil File.open(left) {|f1| File.open(right) {|f2| result1 = f1.readlines.sort result2 = f2.readlines.sort } } left_only = Array.new right_only = Array.new left_nodes = Array.new right_nodes = Array.new 0.upto(result1.length - 1) {|i| r1 = result1[i].split(/\t/) r2 = result2[i].split(/\t/) nodes1 = r1[3].to_i nodes2 = r2[3].to_i if (r1[1] == 'OK' && r2[1] != 'OK') then left_only.push("#{r1[0]} #{nodes1 - nodes2}") elsif (r1[1] != 'OK' && r2[1] == 'OK') then right_only.push("#{r1[0]} #{nodes2 - nodes1}") elsif (r1[1] == 'OK' && r2[1] == 'OK') then if (nodes1 > nodes2) then left_nodes.push("#{r1[0]} #{nodes1 - nodes2}") elsif (nodes1 < nodes2) then right_nodes.push("#{r1[0]} #{nodes2 - nodes1}") end end } puts 'Left:' left_only.each {|x| puts x } puts 'Right:' right_only.each {|x| puts x } puts "Left More: #{left_nodes.length}" left_nodes.each {|x| puts x } puts "Right More: #{right_nodes.length}" right_nodes.each {|x| puts x } libosl-0.8.0.orig/tools/multi-mtdfstat/machine-conf.rb0000644000000000000000000000045310465661502021441 0ustar rootrootMACHINES = ["gopteron8", "gopteron8", "gopteron7", "gopteron7", "gopteron6", "gopteron6"] #COMMAND = '/opt/gps/yoshiki/gpsshogi/bin/mtdfstat' COMMAND = 'env OSL_HOME=/home/users/yoshiki /home/users/yoshiki/mtdfstat' ARG = '-l 1600 -e progress -O - -v 0' #ARG = '-l 1600 -S 30 -e progress -O - -v 0' libosl-0.8.0.orig/tools/multi-mtdfstat/stat.rb0000755000000000000000000000053410712127510020057 0ustar rootroot#! /usr/bin/env ruby ok_count = 0 total_nodes = 0 ok_nodes = 0 while l = gets result = l.chomp.split(/\t/) nodes = result[3].to_i if result[1] == 'OK' then ok_count += 1 ok_nodes += nodes end total_nodes += nodes end puts "OK: #{ok_count} OK nodes: #{ok_nodes}, average: #{ok_nodes.to_f / ok_count} Total nodes: #{total_nodes}" libosl-0.8.0.orig/tools/multi-mtdfstat/run.rb0000755000000000000000000000062410465657467017740 0ustar rootroot#! /usr/bin/env ruby require 'thread' require './machine-conf.rb' files = Dir[ARGV[0] + "/*.csa"] mutex = Mutex.new threads = [] MACHINES.each {|machine| threads << Thread.new(machine) {|x| while true file = nil mutex.synchronize do file = files.shift end break unless file system("rsh #{x} '#{COMMAND} #{ARG} #{file}'") end } } threads.each {|x| x.join } libosl-0.8.0.orig/tools/checkstat-summary.pl0000755000000000000000000000234211120343654017604 0ustar rootroot#!/usr/bin/perl -w # summary.pl checkstat results use File::Basename; use strict; my $problems = (); sub parse ($) { my ($filename) = @_; my $result = (); unless (open(FILE, $filename)) { warn "open $! $filename"; return undef; } while () { chomp; next unless /solving (.+)/; my $problem = basename $1; $_ = while (!/total/); /^total : take (\d+) clocks, loop= (\d+)/ || die "unknown syntax $_"; my $cycles = $1; my $total = $2; $_ = ; /^unique : take \d+ clocks, loop= (\d+)/ || die "unknown syntax $_"; my $uniq = $1; $_ = ; /^real ([0-9.]+) sec./; my $real = $1; $problems->{$problem} = 1; $result->{$problem} = [$cycles, $total, $uniq, $real]; } close FILE; return $result; } my $tables = (); my @files; foreach my $file (@ARGV){ my $contents = parse($file); if (defined $contents) { $tables->{$file} = $contents; push(@files, $file); } } print "# problem"; foreach my $config (@files) { print "\t",$config; } print "\n"; foreach my $problem (sort keys %$problems){ print $problem, "\t"; foreach my $config (@files) { my $tuple = $tables->{$config}->{$problem}; print join("\t",@$tuple), "\t"; } print "\n"; } libosl-0.8.0.orig/tools/false-brinkmate.pl0000755000000000000000000000423411117002011017167 0ustar rootroot#!/usr/bin/perl -w use FileHandle; use strict; # usage: ./false-brinkmate.pl dir0 [dir1] ... # csa files in dir* will be processed. my $program = "gps_l"; my $threshold = 10000; my ($total, $target, $brinkmate, $false_brinkmate, $blunder)=0; sub analyze ($$) { my ($file,$sente) = @_; my $prefix = $sente ? "+" : "-"; open (CSA, $file) || die "open $file !"; ++$target; my @lines = grep { my $l=$_; ($l =~ /^[+-][0-9]/ || substr($l,0,3) eq "'**") } ; close CSA; my ($almost_win, $move, $lasteval) = 0; for (my $i=0; $i<=$#lines; ++$i) { my $line = $lines[$i]; ++$move if ($line =~ /^[+-][0-9]/); next unless (substr($line,0,1) eq $prefix); next unless (substr($lines[$i+1], 0, 3) eq "'**" && substr($lines[$i+1], 4) =~ /(-*[0-9]+)/); my $eval = $sente ? $1 : -$1; if ($eval > $threshold) { $almost_win = $move; } elsif ($almost_win && $eval < 0) { ++$false_brinkmate; print $file." ".$almost_win." ".$eval."\n"; last; } elsif ($lasteval && $eval && $eval +3000 < $lasteval && $eval > -$threshold && $lasteval > 0 && $lasteval < $threshold) { ++$blunder; print $file." ".$move." ".$eval." <= ".$lasteval."\n"; last; } $lasteval = $eval; } ++$brinkmate if ($almost_win); } my $ire = '[A-Za-z0-9_@.-]+'; sub find ($) { my ($dir) = @_; opendir (DIR, $dir) || die "opendir $dir !"; while (my $file=readdir(DIR)) { next unless $file =~ /floodgate-900-0.*\.csa$/; next unless $file =~ /^($ire)\+($ire\-[0-9]+-[0-9]+)[\+:]($ire)[\+:]($ire)[\+:]([0-9]{4})([0-9]{2})([0-9]{2})([0-9]{2})([0-9]{2})([0-9]{2})\.csa$/; my $record = { event => $1, game => $2, sente => $3, gote => $4, year => $5, month => $6, date => $7, hour => $8, minute => $9, second => $10, file => "$file" }; ++$total; if ($record->{sente} eq $program) { analyze($dir."/".$file, 1); } elsif ($record->{gote} eq $program) { analyze($dir."/".$file, 0); } } closedir DIR; } foreach my $dir (@ARGV) { find($dir); } print STDERR "total $total, $program $target, brinkmate $brinkmate, false_brinkmate $false_brinkmate, blunder $blunder\n"; libosl-0.8.0.orig/tools/same-opening.pl0000755000000000000000000000217310430132762016523 0ustar rootroot#!/usr/bin/perl -w use strict; use Getopt::Std; # usage ./same-opening.pl [-d] -n 15 -m 3 *.csa # -d ¹çή¸¡ÃÎ # -n ²¿¼êÌܤޤÇÄ´¤Ù¤ë¤« # -m ½ÐÎϤ¹¤ëºÇ¾®ÉÑÅÙ my %opts=(); getopts("dm:n:",\%opts); my $dag = $opts{d}; my $num_moves = $opts{n} ? $opts{n} : 3; my $minimum = $opts{m} ? $opts{m} : 0; my %data; sub parse ($$) { my ($file, $num) = @_; open FILE, $file || die "open $! $file"; my @moves; while () { next unless (/^([+-][0-9]{4}[A-Z]{2})/); push(@moves, $1); last if (@moves+0 >= $num); } close FILE; my $key = join(',', ($dag ? (sort @moves) : @moves)); if (defined $data{$key}) { $data{$key}++; } else { $data{$key} = 1; } } foreach my $file (@ARGV) { parse($file, $num_moves); } my %reverse; foreach my $key (keys %data) { my $frequency = $data{$key}; if (defined $reverse{$frequency}) { push (@{$reverse{$frequency}}, $key); } else { $reverse{$frequency} = [$key]; } } foreach my $freq (sort {$b <=> $a} keys %reverse) { last if ($freq < $minimum); foreach my $state (@{$reverse{$freq}}) { print $freq . "\t" . $state . "\n"; } } libosl-0.8.0.orig/tools/boardscan/0000755000000000000000000000000010341362677015545 5ustar rootrootlibosl-0.8.0.orig/tools/boardscan/pgm.rb0000644000000000000000000000247710241374741016661 0ustar rootroot#! /usr/bin/env ruby class Pgm def initialize(width, height, data) @width = width @height = height @data = data end def get(x, y) return @data[y * @width + x] end def to_s() return "P5\n" + "#{width} #{height}\n" + "255\n" + @data end def sub(x, y, width, height) data = "" y.upto(y + height - 1) {|j| x.upto(x + width - 1) {|i| data << get(i, j) } } return Pgm.new(width, height, data) end def Pgm.create(file) pnm = nil File.open(file) {|f| if (f.readline.chomp != 'P5') puts "Unsupported file" exit 1 end width, height = f.readline.chomp.split if (f.readline.chomp != '255') puts "Unknown depth" exit 1 end width = width.to_i height = height.to_i data = f.read(width * height) pnm = Pgm.new(width, height, data) } return pnm end def rotate() PgmRotated.new(@width, @height, @data) end attr_reader :width, :height end class PgmRotated < Pgm def initialize(width, height, data) super(width, height, data) end def get(x, y) super(@width - x - 1, @height - y - 1) end end # 1200 x 1500 # width = 1200 # height = 1500 # puts 'P5' # puts "#{width} #{height}" # puts 255 # 0.upto(height - 1){|y| # 0.upto(width - 1) {|x| # printf "%c", pnm.get(x, y) # } # } libosl-0.8.0.orig/tools/boardscan/piece.sh0000755000000000000000000000023710241374741017165 0ustar rootroot#! /bin/sh for file in *s.pnm; do ./detect.rb $file dir=${file/s.pnm/} if [ ! -d $dir ]; then mkdir $dir fi echo $dir mv test??.pnm $dir done libosl-0.8.0.orig/tools/boardscan/detect.rb0000755000000000000000000000727110243106655017345 0ustar rootroot#! /usr/bin/env ruby require 'pgm.rb' require 'util.rb' if ARGV.length != 1 puts "Usage: ./detect.rb FILE" exit 1 end pnm = Pgm.create(ARGV[0]) # look for about 400 pixel wide horizontal line def is_black(pnm, x, y) if 0 <= x && x < pnm.width && 0 <= y && y < pnm.height then return pnm.get(x, y) < 128 else false end end lines = Array.new() 10.upto(pnm.width - 1) {|i| in_line = false start = 0 while true while (! is_black(pnm, i, start) && start < pnm.height) start += 1 end if start == pnm.height break end x = i y = start start_point = Point.new(x, y) while true if is_black(pnm, x, y + 1) then nil elsif is_black(pnm, x + 1, y + 1) then x = x + 1 elsif is_black(pnm, x - 1, y + 1) then x = x - 1 else y += 1 break end y += 1 end end_point = Point.new(x, y) if end_point.y - start_point.y > 400 \ && start_point.y != 0 && end_point.y != pnm.height then lines.push(Line.new(start_point, end_point)) end start = y end } if lines.length > 10 then i = 1 while true a = lines[i-1] b = lines[i] if a.end_point == b.end_point then lines.delete_at(if a.start_point.y < b.start_point.y then i else i-1 end) elsif a.end_point.y + 20 >= pnm.height then lines.delete_at(i-1) else i += 1 end break if i >= lines.length end end if lines.length != 10 then width = (lines.last.start_point.x - lines[0].start_point.x) / 9 i = 1 while true a = lines[i-1] b = lines[i] if b.start_point.x - a.start_point.x < width / 2 then lines.delete_at(i) elsif b.start_point.x - a.start_point.x > width * 3 / 2 then lines[i, 0] = Line.new(Point.new(a.start_point.x + width, (a.start_point.y + b.start_point.y / 2)), Point.new(a.end_point.x + width, (a.end_point.y + b.end_point.y / 2))) i += 1 else i += 1 end break if i >= lines.length end end 0.upto(lines.length - 2) {|i| a = lines[i] b = lines[i+1] if a.start_point.y >= b.start_point.y + 100 then a.end_point.y = b.end_point.y elsif a.start_point.y + 100 <= b.start_point.y then b.start_point.y = a.start_point.y end if a.end_point.y >= b.end_point.y + 100 then a.end_point.y = b.end_point.y elsif a.end_point.y + 100 <= b.end_point.y then b.end_point.y = a.end_point.y end } width = (lines.last.start_point.x - lines[0].start_point.x) * 9 / 10 new_y = lines[0].start_point.y while true x = lines[0].start_point.x + 5 y = new_y while true if is_black(pnm, x + 1, y) then x += 1 elsif is_black(pnm, x + 1, y - 1) then x += 1 y -= 1 elsif is_black(pnm, x + 1, y + 1) then x += 1 y += 1 else break end end if x - lines[0].start_point.x > width then new_y += 1 else break end end if new_y != lines[0].start_point.y then diff = new_y - lines[0].start_point.y 0.upto(lines.length - 1) {|i| lines[i] = Line.new(Point.new(lines[i].start_point.x, lines[i].start_point.y + diff), Point.new(lines[i].end_point.x, lines[i].end_point.y + diff / 2)) } end puts lines 0.upto(8) {|i| 0.upto(8) {|j| filename = "test" + "%d" % i + "%d" % j + ".pnm" File.open(filename, "w+") {|f| width = lines[j+1].start_point.x - lines[j].start_point.x height = (lines[j].end_point.y - lines[j].start_point.y) / 9 x_compensation = (lines[j].end_point.x.to_f - lines[j].start_point.x) / (lines[j].end_point.y - lines[j].start_point.y) * height * i f.print(pnm.sub((lines[j].start_point.x + x_compensation).to_i, (lines[j].start_point.y + height * i).to_i, width, height)) } } } libosl-0.8.0.orig/tools/boardscan/util.rb0000644000000000000000000000065610241374741017050 0ustar rootrootclass Point def initialize(x, y) @x = x @y = y end def to_s return "(#{x}, #{y})" end def ==(a) return a.x == x && a.y == y end attr_reader :x, :y attr_writer :x, :y end class Line def initialize(start_point, end_point) @start_point = start_point @end_point = end_point end def to_s return "#{@start_point}---#{@end_point}" end attr_reader :start_point, :end_point end libosl-0.8.0.orig/tools/boardscan/extract.rb0000755000000000000000000000035510341362677017552 0ustar rootroot#! /usr/bin/env ruby require 'pgm.rb' 1.upto(100) {|i| filename = "default-" + "%03d" % i + ".pnm" puts filename pnm = Pgm.create(filename) File.open(i.to_s + "s.pnm", "w+") {|f| f.puts(pnm.sub(100, 500, 1200, 1200)) } } libosl-0.8.0.orig/tools/boardscan/csa.sh0000755000000000000000000000016210241374741016643 0ustar rootroot#! /bin/sh for file in *s.pnm; do number=${file/s.pnm/} echo $number ./board.rb $number > $number.csa done libosl-0.8.0.orig/tools/boardscan/board.rb0000755000000000000000000004357510341362677017202 0ustar rootroot#! /usr/bin/env ruby require 'pgm.rb' require 'util.rb' def is_black(pnm, x, y) if 0 <= x && x < pnm.width && 0 <= y && y < pnm.height then return pnm.get(x, y) < 128 else false end end def point_is_black(pnm, point) return is_black(pnm, point.x, point.y) end def move(pnm, point, first, second) return unless point_is_black(pnm, point) while true if point_is_black(pnm, first.call(point)) then point = first.call(point) elsif point_is_black(pnm, second.call(point)) then point = second.call(point) else break end end return point end def southwest(pnm, x, y) return unless is_black(pnm, x, y) while true if is_black(pnm, x - 1, y + 1) then x -= 1 y += 1 elsif is_black(pnm, x, y + 1) then y += 1 else break end end return Point.new(x, y) end def southwest_west(pnm, x, y) return unless is_black(pnm, x, y) while true if is_black(pnm, x - 1, y + 1) then x -= 1 y += 1 elsif is_black(pnm, x - 1, y) then x -= 1 else break end end return Point.new(x, y) end def east(pnm, x, y) return unless is_black(pnm, x, y) while true if is_black(pnm, x + 1, y) then x += 1 elsif is_black(pnm, x + 1, y - 1) then x += 1 y -= 1 else break end end return Point.new(x, y) end def east_south(pnm, x, y) return unless is_black(pnm, x, y) while true if is_black(pnm, x + 1, y) then x += 1 elsif is_black(pnm, x + 1, y + 1) then x += 1 y += 1 else break end end return Point.new(x, y) end def southeast(pnm, x, y) return unless is_black(pnm, x, y) while true if is_black(pnm, x + 1, y + 1) then x += 1 y += 1 elsif is_black(pnm, x, y + 1) then y += 1 else break end end return Point.new(x, y) end def detect_kin(pnm) #±¦¾å ¤«¤é º¸²¼ ¤Î¼ÐÀþ¤òõ¤¹ line1 = line_exist?(pnm, pnm.width * 2 / 5, pnm.width * 3 / 5, 5, pnm.height / 4, lambda {|start_point, point| point.x < pnm.width / 4 && point.y > pnm.height * 2 / 5}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x - 1, p.y + 1)}, lambda{|p| Point.new(p.x - 1, p.y)})}) return false unless line1 line2 = line_exist?(pnm, pnm.width * 2 / 5, pnm.width * 3 / 5, 5, pnm.height / 4, lambda {|start_point, point| point.x > pnm.width * 3 / 4 && point.y > pnm.height * 7 / 20}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y)})}) return false unless line2 kyo_line = line_exist?(pnm, line1.start_point.x, line1.start_point.x + 1, line1.start_point.y, line1.start_point.y + 1, lambda {|start_point, point| point.x > pnm.width * 5 / 8}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) if kyo_line then return false else return true end end def detect_kyo(pnm) puts "DETECTING KY" if DEBUG_DETECT #±¦¾å ¤«¤é º¸²¼ ¤Î¼ÐÀþ¤òõ¤¹ line1 = line_exist?(pnm, pnm.width * 2 / 5, pnm.width * 3 / 5, 5, pnm.height / 2, lambda {|start_point, point| # point.x < pnm.width * 3 / 11 && point.y > pnm.height * 5 / 12 start_point.x - point.x > pnm.width / 4 && point.y - start_point.y > pnm.height / 4 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x - 1, p.y + 1)}, lambda{|p| Point.new(p.x, p.y + 1)})}) return false unless line1 puts "line1 found" if DEBUG_DETECT line2 = line_exist?(pnm, line1.start_point.x, line1.start_point.x + 5, line1.start_point.y, line1.start_point.y + 10, lambda {|start_point, point| point.x > pnm.width * 5 / 8 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line2 puts "line2 found" if DEBUG_DETECT line3 = line_exist?(pnm, 5, pnm.width / 4, 5, pnm.height / 3, lambda {|start_point, point| point.x > pnm.width * 5 / 8 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y - 1)})}) if line3 then puts "line3 found" if DEBUG_DETECT return true end return false end def detect_gyoku(pnm) lines = Array.new # º¸ 1/4 ¤Î½ÄÎΰ褫¤é¤Î²£ËÀ»°¤Ä 5.upto(pnm.height - 5 - 1) {|j| 5.upto(pnm.width / 4) {|i| if (is_black(pnm, i, j)) then point = east(pnm, i, j) if point.x > pnm.width * 3 / 4 then if lines.empty? || point.y - lines.last.y > pnm.height / 6 then lines.push(point) end end end } } if lines.length == 3 && lines[0].y < pnm.height / 3 \ && lines.last.y > pnm.height * 3 / 4 \ && ((lines[2].y - lines[1].y) - (lines[1].y - lines[0].y)).abs < 10 \ && (lines[2].y - lines[1].y) > (lines[1].y - lines[0].y) then return true end return false end def line_exist?(pnm, start_x, end_x, start_y, end_y, predicate, move) start_y.upto(end_y - 1) {|j| start_x.upto(end_x - 1) {|i| if (is_black(pnm, i, j)) then point = move.call(pnm, i, j) if predicate.call(Point.new(i, j), point) then # print i, " ", j, " " # puts point return Line.new(Point.new(i, j), point) end end } } return false end def detect_fu(pnm) puts "DETECTING FU" if DEBUG_DETECT # ¿¿Ãæ¤Î½ÄËÀ¤È±¦²¼¤«¤éº¸²¼¤Ø¤Î¤Ï¤é¤¤ line1 = line_exist?(pnm, pnm.width * 2 / 5, pnm.width * 3 / 5, 5, pnm.height / 4, lambda {|start_point, point| point.y > pnm.height * 5 / 8 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line1 puts "line1 found" if DEBUG_DETECT line2 = line_exist?(pnm, pnm.width * 5 / 8, pnm.width - 5, pnm.height / 2, pnm.height - 5, lambda {|start_point, point| point.x < pnm.width * 7 / 20 && point.y > pnm.height * 3 / 4 }, lambda {|pnm, i, j| return southwest_west(pnm, i, j) }) return false unless line2 puts "line2 found" if DEBUG_DETECT # ±¦¾å¤Î²£ËÀ line3 = line_exist?(pnm, pnm.width / 2, pnm.width - 5, 5, pnm.height / 3, lambda {|start_point, point| point.x > pnm.width / 3 && start_point.x - point.x > pnm.width / 6}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x - 1, p.y)}, lambda{|p| Point.new(p.x - 1, p.y + 1)})}) if line3 then puts "line3 found" if DEBUG_DETECT return true end return false end def detect_kei(pnm) # ½ÄËÀÆóËÜ line1 = line_exist?(pnm, 5, pnm.width / 3, 5, pnm.height / 4, lambda {|start_point, point| point.y > pnm.height * 3 / 4 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line1 line2 = line_exist?(pnm, pnm.width / 2, pnm.width - 5, 5, pnm.height / 4, lambda {|start_point, point| point.y > pnm.height * 3 / 4 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) # ¸þ¤­ if !line2 then line2 = line_exist?(pnm, pnm.width / 2, pnm.width - 5, 5, pnm.height / 4, lambda {|start_point, point| point.y - start_point.y > pnm.height / 4 && \ line_exist?(pnm, point.x, point.x + 1, point.y, point.y + 5, lambda {|start_point, point| point.y > pnm.height * 3 / 4 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) end if line2 && line1.end_point.x < pnm.width - line2.end_point.x then return true end return false end def detect_kaku(pnm) line1 = line_exist?(pnm, 5, pnm.width / 3, pnm.height / 4, pnm.height / 2, lambda {|start_point, point| point.x < start_point.x && point.y > pnm.height * 3 / 4 \ && (point.y - start_point.y) / (start_point.x - point.x) < 10}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x - 1, p.y + 1)})}) return false unless line1 line2 = line_exist?(pnm, line1.start_point.x, line1.start_point.x + 3, line1.start_point.y, line1.start_point.y + 10, lambda {|start_point, point| point.x > pnm.width * 3 / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y - 1)})}) return false unless line2 line3 = line_exist?(pnm, line2.end_point.x - 5, line2.end_point.x, line2.end_point.y, line2.end_point.y + 5, lambda {|start_point, point| point.y > pnm.height * 3 / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) if line3 then return true end return false end def detect_hisha(pnm) puts "DETECTING HI" if DEBUG_DETECT # º¸Â¦¤Î¤Ï¤é¤¤ line1 = line_exist?(pnm, 5, pnm.width / 2, pnm.height / 4, pnm.height / 2, lambda {|start_point, point| point.x < start_point.x && point.y > pnm.height * 3 / 4 \ && (point.y - start_point.y) / (start_point.x - point.x) < 25}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x - 1, p.y + 1)}, lambda{|p| Point.new(p.x, p.y + 1)})}) # Í¥À褹¤ë·¹¤­¤òÊѤ¨¤Æ¤â¤¦°ì²ó if !line1 then line1 = line_exist?(pnm, 5, pnm.width / 2, pnm.height / 4, pnm.height / 2, lambda {|start_point, point| point.x < start_point.x && point.y > pnm.height * 3 / 4 \ && (point.y - start_point.y) / (start_point.x - point.x) < 25}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x - 1, p.y + 1)})}) end return false unless line1 puts "line1 found" if DEBUG_DETECT #¿¿Ãæ¤Î½ÄËÀ line2 = line_exist?(pnm, pnm.width * 2 / 5, pnm.width * 3 / 5, 5, pnm.height / 3, lambda {|start_point, point| point.y > pnm.width * 3 / 4 && point != line1.end_point}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) puts "line2 found" if DEBUG_DETECT return false unless line2 if line_exist?(pnm, 5, pnm.width / 4, 5, line2.start_point.y + 5, lambda {|start_point, point| point.x > pnm.width / 2}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y - 1)})}) then puts "line3 found" if DEBUG_DETECT return true end return false end def detect_gin(pnm) line1 = line_exist?(pnm, pnm.width / 3, pnm.width * 2 / 3, 5, pnm.height / 4, lambda {|start_point, point| point.y > pnm.width * 3 / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line1 line2 = line_exist?(pnm, line1.start_point.x, line1.start_point.x + 1, line1.start_point.y, line1.start_point.y + 5, lambda {|start_point, point| point.x > pnm.width * 3 / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y - 1)})}) return false unless line2 line3 = line_exist?(pnm, line2.end_point.x - 5, line2.end_point.x, line2.end_point.y, line2.end_point.y + 5, lambda {|start_point, point| point.y - start_point.y > pnm.height / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) if line3 then return true end return false end def detect_to(pnm) line1 = line_exist?(pnm, pnm.width * 2 / 3, pnm.width - 5, pnm.height / 3, pnm.height / 2, lambda {|start_point, point| point.x < pnm.width / 3 && point.y > pnm.height * 2 / 3 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x - 1, p.y + 1)}, lambda{|p| Point.new(p.x - 1, p.y)})}) return false unless line1 line2 = line_exist?(pnm, line1.end_point.x, line1.end_point.x + 5, line1.end_point.y, line1.end_point.y + 5, lambda {|start_point, point| line_exist?(pnm, point.x, point.x + 1, point.y, point.y + 1, lambda {|start_point, point| point.x > pnm.width * 2 / 3 && point.y > pnm.height * 3 / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y - 1)})})}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y)})}) if line2 then return true end return false end def detect_nari(pnm) line1 = line_exist?(pnm, 5, pnm.width / 2, 5, pnm.height / 2, lambda {|start_point, point| point.x < pnm.width / 2 \ && point.x - start_point.x > pnm.height / 4 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line1 line2 = line_exist?(pnm, line1.start_point.x, line1.end_point.x, 5, line1.start_point.y, lambda {|start_point, point| point.y < pnm.height / 2 \ && point.y - start_point.y > pnm.height / 4 }, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x - 1, p.y + 1)})}) return line2 end def detect_narikyo(pnm) return detect_nari(pnm) && detect_kyo(pnm) end def detect_ryu(pnm) line1 = line_exist?(pnm, 5, pnm.width / 3, pnm.height / 3, pnm.height * 2 / 3, lambda {|start_point, point| point.y - start_point.y > pnm.height / 4}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line1 line2 = line_exist?(pnm, line1.start_point.x, line1.start_point.x + 5, line1.start_point.y, line1.start_point.y + 5, lambda {|start_point, point| point.x > pnm.width * 2 / 3}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y - 1)})}) return false unless line2 line3 = line_exist?(pnm, line2.end_point.x - 5, line2.end_point.x, line2.end_point.y, line2.end_point.y + 5, lambda {|start_point, point| point.y - start_point.y > pnm.height / 5}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line3 line4 = line_exist?(pnm, line2.start_point.x, line2.end_point.x, line2.start_point.y, line2.start_point.y + 5, lambda {|start_point, point| point.y > line1.end_point.y}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) if line4 then return true end return false end def detect_uma(pnm) line1 = line_exist?(pnm, 5, pnm.width / 3, 5, pnm.height / 4, lambda {|start_point, point| point.y > pnm.height / 2 && point.y < pnm.height * 5 / 6}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x, p.y + 1)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) return false unless line1 line2 = line_exist?(pnm, line1.start_point.x, line1.start_point.x + 5, line1.start_point.y, line1.start_point.y + 5, lambda {|start_point, point| point.x > pnm.width * 2 / 3}, lambda {|pnm, x, y| move(pnm, Point.new(x,y), lambda{|p| Point.new(p.x + 1, p.y)}, lambda{|p| Point.new(p.x + 1, p.y + 1)})}) if line2 then return true end return false end def detect(pnm) if detect_gyoku(pnm) then return "+OU" elsif detect_gyoku(pnm.rotate()) then return "-OU" elsif detect_kei(pnm) then return "+KE" elsif detect_kei(pnm.rotate()) then return "-KE" elsif detect_hisha(pnm) then return "+HI" elsif detect_hisha(pnm.rotate()) then return "-HI" elsif detect_kaku(pnm) then return "+KA" elsif detect_kaku(pnm.rotate()) then return "-KA" elsif detect_kin(pnm) then return "+KI" elsif detect_kin(pnm.rotate()) then return "-KI" elsif detect_gin(pnm) then return "+GI" elsif detect_gin(pnm.rotate()) then return "-GI" elsif detect_kyo(pnm) then return "+KY" elsif detect_kyo(pnm.rotate()) then return "-KY" elsif detect_fu(pnm) then return "+FU" elsif detect_fu(pnm.rotate()) then return "-FU" elsif detect_to(pnm) then return "+TO" elsif detect_to(pnm.rotate()) then return "-TO" elsif detect_narikyo(pnm) then return "+NY" elsif detect_narikyo(pnm.rotate()) then return "-NY" elsif detect_ryu(pnm) then return "+RY" elsif detect_ryu(pnm.rotate()) then return "-RY" elsif detect_uma(pnm) then return "+UM" elsif detect_uma(pnm.rotate()) then return "-UM" else return " * " end end if (ARGV[0][-4, 4] == ".pnm") then DEBUG_DETECT = true puts detect(Pgm.create(ARGV[0])) else DEBUG_DETECT = false 0.upto(8) {|y| print "P", y + 1 0.upto(8) {|x| filename = ARGV[0] + "/test" + "%d%d" % [y, x] + ".pnm" print detect(Pgm.create(filename)) } puts } puts "+" end libosl-0.8.0.orig/tools/csa2myshogi.rb0000755000000000000000000000750510236057164016373 0ustar rootroot#!/usr/local/bin/ruby NormalPtypeList = ["HI", "KA", "KI", "GI", "KE", "KY" ,"FU"] PtypeList = ["FU", "KY", "KE", "GI", "KI", "KA", "HI", "OU", "RY", "UM", "NG", "NK", "NY", "TO"] PlayerList = ["+", "-"] class PtypeO def initialize player, ptype unless PlayerList.index player raise Exception.new("\"#{player}\" not a player") end unless PtypeList.index ptype raise Exception.new("\"#{ptype}\" not a ptype") end @player = player @ptype = ptype end def owner return @player end def ptype return @ptype end def to_s return "#{@player}#{@ptype}" end end class ShogiState def initialize @board = Array.new (1..9).each {|x| @board[x] = Array.new (1..9).each {|y| @board[x][y] = nil } } @mochigoma = Hash.new PlayerList.each { |player| @mochigoma[player] = Hash.new NormalPtypeList.each {|ptype| @mochigoma[player][ptype] = 0 } } end def addPiece x, y, ptypeO @board[x][y]=ptypeO end def getPiece x, y return @board[x][y] end def addMochigoma player, ptype @mochigoma[player][ptype] += 1 end def getMochigoma player, ptype return @mochigoma[player][ptype] end end module PrintMyshogi SenteGote = { "+" => "\\sente", "-" => "\\gote" } PtypeConvert = { "FU" => "\\fu", "KY" => "\\kyou", "KE" => "\\kei", "GI" => "\\gin", "KI" => "\\kin", "KA" => "\\kaku", "HI" => "\\hi", "OU" => "\\ou", "RY" => "\\ryu", "UM" => "\\uma", "NG" => "\\narigin", "NK" => "\\narikei", "NY" => "\\narikyou", "TO" => "\\tokin", } def to_s ret = " \\begin{myshogi}\n \\banmen\n" PlayerList.each { |player| ret << " \\mochigoma{#{SenteGote[player]}}" NormalPtypeList.each { |ptype| ret << "{#{getMochigoma player, ptype}}" } ret << "\n" } (1..9).each {|y| (1..9).each {|x| ptypeO = getPiece x, y if ptypeO player = SenteGote[ptypeO.owner] ptype = PtypeConvert[ptypeO.ptype] ret << " \\koma{#{x}#{y}}{#{player}}{#{ptype}}\n" end } } ret << " \\end{myshogi}\n" return ret end end module ParseCsa private def readline return nil if @input.eof? begin line = @input.readline end while line =~ /^\'/ line.chomp! return line end def parseBoard (1..9).each {|y| line = readline if !line.sub! /P#{y}/, "" throw Exception.new("While parsing line:#{y} of board got invalid input: \"#{line}\"") end (1..9).each {|invx| x = 10 - invx line.sub! /(.)(..?)/, "" if $1 == " " && $2 == "* " addPiece x, y, nil elsif $1 == " " && $2 == "*" STDERR.print "line ending with \" *\" found, for #{y}, #{x}\n" addPiece x, y, nil else begin ptypeO = PtypeO.new($1, $2) addPiece x, y, ptypeO rescue raise end end } } end def parseMochigomaAndTeban while true line = readline break if line =~ /^[\-|\+]$/ if !line.sub! /^P([\+|\-])/, "" throw Exception.new("#got invalid input \"#{line}\"") end player = $1 while line.sub! /(\d\d)(..)/, "" if $1 != "00" throw Exception.new("#got invalid input \"#{line}\"") end addMochigoma player, $2 end end @teban = line end def parseMoves @moves = Array.new begin line = readline return if line == nil @moves.push line end while !line.sub! /^P([\+|\-])/, "" end public def parse input @input = input parseBoard parseMochigomaAndTeban parseMoves end end class ReadCsaOutputMyshogi < ShogiState include ParseCsa include PrintMyshogi def initialize super end end shogiState = ReadCsaOutputMyshogi.new shogiState.parse STDIN print shogiState libosl-0.8.0.orig/tools/chi.pl0000755000000000000000000000351511702205404014702 0ustar rootroot#!/usr/bin/perl -w use strict; use Getopt::Std; my %options=(); getopts("t:w:p:s:",\%options); my $total = $options{t} ? $options{t} : 20; my $win = defined $options{w} ? $options{w} : $total/2; my $p = defined $options{p} ? $options{p} : 0.5; #my $significance = $options{'s'} ? $options{'s'} : 0.05; # XXX: must be compatible with $chi2_threshold my $significance = 0.05; #my $chi2_threshold = 6.63490; # for 1% my $chi2_threshold = 3.84146; # for 5% #my $chi2_threshold = 2.70554; # for 10% printf "%4d / %4d \t... %s\n", $win, $total, (&is_significant($win, $p, $total) ? "*" : ""); printf "%4d / %4d\tfor significance %f\n", &significant_win($p, $total), $total, $significance; printf "[%f : %f ]\tfor significance %f\n", &significant_prob($total, $win, $significance), 1.0 - &significant_prob($total, $total-$win, $significance), $significance; sub significant_win($$) { my ($p, $total) = @_; for (my $i=$total; $i>=($total*$p); --$i) { if (! &is_significant($i, $p, $total)) { return $i+1; } } return $total; } sub is_significant($$$) { my ($win, $p, $total) = @_; my $expected_win = $total*$p; my $expected_lose = $total - $expected_win; my $lose = $total - $win; my $chi = 1.0*($expected_win - $win)*($expected_win - $win)/$expected_win + 1.0*($expected_lose - $lose)*($expected_lose - $lose)/$expected_lose; return $chi > $chi2_threshold; } sub significant_prob ($$$) { my ($total, $win, $significance) = @_; my $last_significant = 0.0; my $step = 1; # 1.0/$step is used while ($step <= 128) { for (my $i=1; $last_significant*$step+$i<$step; ++$i) { my $p=($step*$last_significant + $i) / $step; last if (($win/$total < $p) || ! is_significant($win, $p, $total)); $last_significant = $p; } $step *= 2; } return $last_significant; } libosl-0.8.0.orig/LICENSE0000644000000000000000000000540712321270310013442 0ustar rootrootCopyright (C) 2003-2014 Team GPS. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. THIS SOFTWARE IS PROVIDED BY THE TEAM GPS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE TEAM GPS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. The views and conclusions contained in the software and documentation are those of the authors and should not be interpreted as representing official policies, either expressed or implied, of the Team GPS. ---------------------------------------------------------------------- Copyright (C) 2003-2014 Team GPS. ¥½¡¼¥¹¥³¡¼¥É·Á¼°¤Ç¤¢¤ì¥Ð¥¤¥Ê¥ê·Á¼°¤Ç¤¢¤ì¡¢Êѹ¹¤Î̵ͭ¤Ë ´Ø¤ï¤é¤º¡¢°Ê²¼ ¤Î¾ò·ï¤òËþ¤¿¤¹¸Â¤ê¤Ë¤ª¤¤¤Æ¡¢ºÆÇÛÉÛ¤·¤Æ¤«¤Þ¤¤¤Þ¤»¤ó: ¥½¡¼¥¹¥³¡¼¥É·Á¼°¤ÇºÆÇÛÉÛ¤¹¤ë¾ì¹ç¡¢¾åµ­Ãøºî¸¢É½¼¨¡¢ Ëܾò·ï½ñ¤ª¤è¤Ó²¼µ­ ÀÕǤ¸ÂÄ구Äê¤òɬ¤º´Þ¤á¤Æ¤¯¤À¤µ¤¤¡£ ¥Ð¥¤¥Ê¥ê·Á¼°¤ÇºÆÇÛÉÛ¤¹¤ë¾ì¹ç¡¢¾åµ­Ãøºî¸¢É½¼¨¡¢ Ëܾò·ï½ñ¤ª¤è¤Ó²¼µ­ÀÕǤ ¸ÂÄ구Äê¤ò¡¢ÇÛÉÛʪ¤È¤È¤â¤ËÄ󶡤µ¤ì¤ëʸ½ñ ¤ª¤è¤Ó/¤Þ¤¿¤Ï ¾¤Î»ñÎÁ¤Ëɬ¤º ´Þ¤á¤Æ¤¯¤À¤µ¤¤¡£ ËÜ¥½¥Õ¥È¥¦¥§¥¢¤Ï Team GPS ¤Ë¤è¤Ã¤Æ¡¢¡É¸½¾õ¤Î¤Þ¤Þ¡É Ä󶡤µ¤ì¤ë¤â¤Î¤È¤· ¤Þ¤¹¡£ ËÜ¥½¥Õ¥È¥¦¥§¥¢¤Ë¤Ä¤¤¤Æ¤Ï¡¢ÌÀ¼¨ÌÛ¼¨¤òÌä¤ï¤º¡¢ ¾¦ÍÑÉʤȤ·¤ÆÄ̾綠 ¤Ê¤¨¤ë¤Ù¤­ÉʼÁ¤ò¤½¤Ê¤¨¤Æ¤¤¤ë¤È¤ÎÊݾڤ⡢ ÆÃÄê¤ÎÌÜŪ¤ËŬ¹ç¤¹¤ë¤È¤ÎÊÝ¾Ú ¤ò´Þ¤á¡¢²¿¤ÎÊݾڤâ¤Ê¤µ¤ì¤Þ¤»¤ó¡£ »öͳ¤Î¤¤¤«¤ó¤òÌä¤ï¤º¡¢ »³²È¯À¸¤Î¸¶°ø ¤¤¤«¤ó¤òÌä¤ï¤º¡¢³î¤Ä¡¢ ÀÕǤ¤Îº¬µò¤¬·ÀÌó¤Ç¤¢¤ë¤«¸·³ÊÀÕǤ¤Ç¤¢¤ë¤« (²á¼º ¤½¤Î¾) ÉÔË¡¹Ô°Ù¤Ç¤¢¤ë¤«¤òÌä¤ï¤º¡¢ Team GPS ¤â´óÍ¿¼Ô¤â¡¢ ²¾¤Ë¤½¤Î¤è¤¦ ¤Ê»³²¤¬È¯À¸¤¹¤ë²ÄǽÀ­¤òÃΤ餵¤ì¤Æ¤¤¤¿¤È¤·¤Æ¤â¡¢ ËÜʸ½ñ¤Î»ÈÍѤ«¤éȯÀ¸ ¤·¤¿Ä¾ÀÜ»³²¡¢´ÖÀÜ»³²¡¢¶öȯŪ¤Ê»³²¡¢ÆÃÊÌ»³²¡¢ ĨȳŪ»³²¤Þ¤¿¤Ï·ë²Ì »³²¤Î¤¤¤º¤ì¤ËÂФ·¤Æ¤â (ÂåÂØÉʤޤ¿¤Ï ¥µ¡¼¥Ó¥¹¤ÎÄó¶¡; »ÈÍѵ¡²ñ¡¢¥Ç¡¼¥¿ ¤Þ¤¿¤ÏÍø±×¤Î»¼º¤ÎÊä½þ; ¤Þ¤¿¤Ï¡¢¶È̳¤ÎÃæÃǤËÂФ¹¤ëÊä½þ¤ò´Þ¤á) ÀÕǤ¤ò¤¤¤Ã ¤µ¤¤É餤¤Þ¤»¤ó¡£ ¤³¤Î¥½¥Õ¥È¥¦¥§¥¢¤Èʸ½ñ¤Ë´Þ¤Þ¤ì¤ë°Õ¸«¤ä·ëÏÀ¤Ï¤½¤ì¤é¤ÎÃøºî¼Ô¤Ë¤è¤ë ¤â¤Î ¤Ç¤¢¤Ã¤Æ¡¢Team GPS ¤Î ¸ø¼°¤ÊÊý¿Ë¤ò¡¢ÌÀ¼¨ÌÛ¼¨¤òÌä¤ï¤º¡¢¤¢¤é¤ï¤·¤Æ¤¤¤ë¤â ¤Î¤È ¤È¤Ã¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£ libosl-0.8.0.orig/.gitignore0000644000000000000000000000251611717610410014432 0ustar rootrootmakefile.local release .svn *.diff *.log *.swp *.vim *.o *.lo *.a *.pb.h *.pb.cc .deps build dist dist-smp install-lib tags # executables in test/ test/**/*.t test/testAll test/testBoard test/testCategory test/testOpening test/testSearch *.testProblems* *.testShow # executables in sample/ sample/category/generatorstat sample/category/make_move sample/category/generate sample/debug/printPdp sample/debug/printPosition sample/debug/printMove sample/debug/printPiece sample/debug/printPtypeO sample/debug/printNcores sample/eval/ppair/pairdiff sample/eval/ppair/pairedit sample/eval/ppair/pairstat sample/eval/show-state sample/opening/convert sample/opening/showOpening sample/opening/opening-validator sample/performance/checkHashPerf sample/performance/generatorPerf sample/performance/isCheckPerf sample/performance/pin_perf sample/performance/mtdfPerf sample/performance/category_perf sample/performance/progress_perf sample/performance/rating-perf sample/progress/show-state sample/quiescence/quiescencestat sample/quiescence/range-vs-nodes sample/quiescence/quiescence2stat sample/record/check-kisen sample/record/show-ipx sample/record/show-ki2 sample/record/bad-moves sample/record/all-states sample/legal_moves sample/sort sample/random_play sample/show_repetition sample/showRecord sample/checkstat sample/fixed-checkmate sample/rating/ratingstat libosl-0.8.0.orig/core/0000755000000000000000000000000012566322565013404 5ustar rootrootlibosl-0.8.0.orig/core/osl/0000755000000000000000000000000012566322565014201 5ustar rootrootlibosl-0.8.0.orig/core/osl/simpleState.cc0000644000000000000000000003633512316770314017004 0ustar rootroot/* simpleState.cc */ #include "osl/simpleState.h" #include "osl/simpleState.tcc" #include "osl/csa.h" #include "osl/bits/pieceTable.h" #include "osl/bits/pieceStand.h" #include #include osl::SimpleState::SimpleState() { init(); } osl::SimpleState::SimpleState(Handicap h) { init(h); } void osl::SimpleState::initPawnMask(){ for (Ptype ptype: PieceStand::order) { stand_count[BLACK][ptype - PTYPE_BASIC_MIN] = countPiecesOnStandBit(BLACK, ptype); stand_count[WHITE][ptype - PTYPE_BASIC_MIN] = countPiecesOnStandBit(WHITE, ptype); } pawnMask[0].clearAll(); pawnMask[1].clearAll(); for(int num=PtypeTraits::indexMin; num< PtypeTraits::indexLimit; num++){ Piece p=pieceOf(num); Player player=p.owner(); Square pos=p.square(); if(!pos.isPieceStand() && !p.isPromotedNotKingGold()){ if (isPawnMaskSet(player,pos.x())) { throw CsaIOError("2FU!"); } pawnMask[player].set(pos); } } assert(isConsistent(true)); } void osl::SimpleState::init() { player_to_move=BLACK; for (int ipos=0;ipos0;x--) { setBoard(Square(x,y),Piece::EMPTY()); } // promoteMask.clearAll(); stand_mask[BLACK].resetAll(); stand_mask[WHITE].resetAll(); stand_count[BLACK].fill(0); stand_count[WHITE].fill(0); used_mask.resetAll(); pawnMask[0].clearAll(); pawnMask[1].clearAll(); for (int num=0;num0;x--) { setPiece(BLACK,Square(x,7),PAWN); setPiece(WHITE,Square(x,3),PAWN); } // setPiece(BLACK,Square(1,9),LANCE); setPiece(BLACK,Square(9,9),LANCE); setPiece(WHITE,Square(1,1),LANCE); setPiece(WHITE,Square(9,1),LANCE); // setPiece(BLACK,Square(2,9),KNIGHT); setPiece(BLACK,Square(8,9),KNIGHT); setPiece(WHITE,Square(2,1),KNIGHT); setPiece(WHITE,Square(8,1),KNIGHT); // setPiece(BLACK,Square(3,9),SILVER); setPiece(BLACK,Square(7,9),SILVER); setPiece(WHITE,Square(3,1),SILVER); setPiece(WHITE,Square(7,1),SILVER); // setPiece(BLACK,Square(4,9),GOLD); setPiece(BLACK,Square(6,9),GOLD); setPiece(WHITE,Square(4,1),GOLD); setPiece(WHITE,Square(6,1),GOLD); // setPiece(BLACK,Square(5,9),KING); setPiece(WHITE,Square(5,1),KING); // setPiece(BLACK,Square(8,8),BISHOP); setPiece(WHITE,Square(2,2),BISHOP); // setPiece(BLACK,Square(2,8),ROOK); setPiece(WHITE,Square(8,2),ROOK); initPawnMask(); } osl::SimpleState::~SimpleState() {} void osl::SimpleState::setPiece(Player player,Square pos,Ptype ptype) { int num; for (num=0;num<40;num++) { if (!used_mask.test(num) && Piece_Table.getPtypeOf(num)==unpromote(ptype) && (ptype!=KING || num==PtypeTraits::indexMin+playerToIndex(player))) { used_mask.set(num); Piece p(player,ptype,num,pos); setPieceOf(num,p); if (pos.isPieceStand()) stand_mask[player].set(num); else{ setBoard(pos,p); if (ptype==PAWN) pawnMask[player].set(pos); } return; } } std::cerr << "osl::SimpleState::setPiece! maybe too many pieces " << ptype << " " << pos << " " << player << "\n"; abort(); } void osl::SimpleState::setPieceAll(Player player) { for (int num=0;num<40;num++) { if (!used_mask.test(num)) { used_mask.set(num); stand_mask[player].set(num); Player pplayer = player; /* 片玉ã—ã‹ãªã„å•題ã®ãŸã‚ */ if (num==PtypeTraits::indexMin+playerToIndex(alt(player))) { pplayer=alt(player); } Piece p(pplayer,Piece_Table.getPtypeOf(num),num,Square::STAND()); setPieceOf(num,p); } } } // check bool osl::SimpleState::isConsistent(bool show_error) const { // board上ã®è¦ç´ ã®consistency for (int y=1;y<=9;y++) { for (int x=9;x>=1;x--) { const Square pos(x,y); const Piece p0=pieceAt(pos); if (p0.isPiece()) { if (p0.square()!=pos) { if (show_error) { std::cerr << p0 << " must be put at " << pos << std::endl; } return false; } int num=p0.number(); if (! PieceTable::validNumber(num) || !used_mask.test(num)) { if (show_error) std::cerr << "NotUsed, num=" << num << std::endl; return false; } Piece p1=pieceOf(num); if (p0!=p1) { if (show_error) std::cerr << "board[" << pos << "]!=" << "piece[" << num << "]" << std::endl; return false; } } } } // piecesã®consistency for (int num0=0; num0 pawnMask1; pawnMask1[0].clearAll(); pawnMask1[1].clearAll(); for (int num=PtypeTraits::indexMin; num::indexLimit;num++){ if (isOnBoard(num)){ Piece p=pieceOf(num); if (!p.isPromotedNotKingGold()){ pawnMask1[playerToIndex(p.owner())].set(p.square()); } } } if ((pawnMask[0]!=pawnMask1[0]) || (pawnMask[1]!=pawnMask1[1])) { if (show_error) std::cerr << "pawnMask " << pawnMask[0] << "!=" << pawnMask1[0] << " || " << pawnMask[1] << "!=" << pawnMask1[1] << std::endl; return false; } } // illegal position for piece for (int i=0; i(); ++i) { const Piece pawn = nth(i); if (! pawn.isPromoted() && pawn.isOnBoard() && pawn.square().squareForBlack(pawn.owner()).y() == 1) { if (show_error) std::cerr << "pawn " << pawn << std::endl; return false; } } for (int i=0; i(); ++i) { const Piece lance = nth(i); if (! lance.isPromoted() && lance.isOnBoard() && lance.square().squareForBlack(lance.owner()).y() == 1) { if (show_error) std::cerr << "lance " << lance << std::endl; return false; } } for (int i=0; i(); ++i) { const Piece knight = nth(i); if (! knight.isPromoted() && knight.isOnBoard() && knight.square().squareForBlack(knight.owner()).y() == 1) { if (show_error) std::cerr << "knight " << knight << std::endl; return false; } } return true; } bool osl::SimpleState::isAlmostValidMove(Move move,bool show_error) const { if (show_error) { const bool valid = isAlmostValidMove(move); if (! valid) std::cerr << *this << " " << move << std::endl; return valid; } else return isAlmostValidMove(move); } template bool osl::SimpleState::isAlmostValidMove(Move move) const { assert(move.isValid()); assert(turn() == move.player()); assert(isValidMoveByRule(move, true)); const Square from=move.from(); if (from.isPieceStand()) // æ‰“ã¤æ‰‹ return isAlmostValidDrop(move); const Square to=move.to(); if (! testValidityOtherThanEffect(move)) return false; const Piece from_piece = pieceAt(from); // ãã® offsetã®å‹•ããŒptypeã«é–¢ã—ã¦validã‹? EffectContent effect=Ptype_Table.getEffect(from_piece.ptypeO(),from,to); if (!effect.hasUnblockableEffect()) { const Offset o=effect.offset(); if (o.zero()) { if (show_error) { std::cerr << " No such move2 : " << move << std::endl; } return false; } // 離れãŸå‹•ãã®æ™‚ã«é–“ãŒå…¨éƒ¨ç©ºã„ã¦ã„ã‚‹ã‹? for (Square p=from+o;p!=to;p+=o) { if (! pieceAt(p).isEmpty()) { if (show_error) std::cerr << " Not space to move : " << move << std::endl; return false; } } } assert(isValidMoveByRule(move, true)); return true; } bool osl::SimpleState::isValidMoveByRule(Move move,bool show_error) { assert(move.isNormal()); const Square from=move.from(); const Square to=move.to(); const Ptype ptype=move.ptype(); const Player turn = move.player(); if (from.isPieceStand()) // æ‰“ã¤æ‰‹ { // å‹•ã‘ãªã„場所ã§ã¯ãªã„ã‹? if (! Ptype_Table.canDropTo(turn,ptype,to)) { if (show_error) std::cerr << " can't drop to : " << move << std::endl; return false; } } else { if (isBasic(move.ptype()) && move.isPromotion()) { if (show_error) std::cerr << " inconsistent promote " << move << std::endl; return false; } const PtypeO old_ptypeo = move.oldPtypeO(); const EffectContent effect = Ptype_Table.getEffect(old_ptypeo, Offset32(to,from)); // ãã® offsetã®å‹•ããŒptypeã«é–¢ã—ã¦validã‹? if (!effect.hasUnblockableEffect()) { const Offset o = effect.offset(); if (o.zero()) { if (show_error) { std::cerr << " No such move1 : " << move << std::endl; } return false; } } // promoteã—ã¦ã„る時ã«promoteå¯èƒ½ã‹ if (move.isPromotion()) { if (! (canPromote(unpromote(move.ptype())) && (to.canPromote(move.player()) || from.canPromote(move.player())))) { if (show_error) std::cerr << " illegal promote type or position : " << move << std::endl; return false; } } // promoteã—ã¦ã„ãªã„時ã«å¼·åˆ¶promoteã§ãªã„ã‹? if ((! isPromoted(ptype) && ! Ptype_Table.canDropTo(turn,getPtype(old_ptypeo),to)) && !move.isPromotion()) { if (show_error) std::cerr << " must promote to this position : " << move << std::endl; return false; } } return true; } bool osl::SimpleState::isValidMove(Move move,bool show_error) const { if (turn() != move.player()) { if (show_error) { std::cerr << "invalid player move : " << move << std::endl; std::cerr << *this; } return false; } if (! isValidMoveByRule(move, show_error) || ! move.isValid()) return false; return isAlmostValidMove(move, show_error); } #ifndef MINIMAL bool osl::SimpleState::dump() const { return static_cast(std::cerr << *this << "\n"); } #endif /** * from ã§è¡¨ç¾ã•れãŸPieceã‚’new_ownerã®æŒé§’ã«ã—ãŸå±€é¢ã‚’作る. */ const osl::SimpleState osl::SimpleState::emulateCapture(Piece from, Player new_owner) const { osl::SimpleState newState; for(int i=0;i<40;i++){ Piece p=pieceOf(i); if(p==from){ newState.setPiece(new_owner,Square::STAND(),unpromote(p.ptype())); } else{ newState.setPiece(p.owner(),p.square(),p.ptype()); } } newState.setTurn(turn()); newState.initPawnMask(); return newState; } /** * from ã‹ã‚‰to ã« ptypeã®æŒé§’を一枚渡ã—ãŸå±€é¢ã‚’作る. */ const osl::SimpleState osl::SimpleState::emulateHandPiece(Player from, Player to, Ptype ptype) const { assert(hasPieceOnStand(from, ptype)); assert(from==alt(to)); osl::SimpleState newState; bool done=false; for(int i=0;i<40;i++){ if(!usedMask().test(i)) continue; Piece p=pieceOf(i); if(!done && p.owner()==from && !p.isOnBoard() && p.ptype()==ptype){ newState.setPiece(to,Square::STAND(),ptype); done=true; } else{ newState.setPiece(p.owner(),p.square(),p.ptype()); } } assert(done); newState.setTurn(turn()); newState.initPawnMask(); return newState; } const osl::SimpleState osl::SimpleState::rotate180() const { SimpleState ret; for (int i=0; i<40; ++i) { if(!usedMask().test(i)) continue; const Piece p = pieceOf(i); ret.setPiece(alt(p.owner()), p.square().rotate180Safe(), p.ptype()); } ret.setTurn(alt(turn())); ret.initPawnMask(); return ret; } const osl::SimpleState osl::SimpleState::flipHorizontal() const { SimpleState ret; for (int i=0; i<40; ++i) { if(!usedMask().test(i)) continue; const Piece p = pieceOf(i); ret.setPiece(p.owner(), p.square().flipHorizontal(), p.ptype()); } ret.setTurn(turn()); ret.initPawnMask(); return ret; } bool osl::operator==(const SimpleState& st1,const SimpleState& st2) { assert(st1.isConsistent(false)); assert(st2.isConsistent(false)); if (st1.turn()!=st2.turn()) return false; if (st1.pawnMask[0]!=st2.pawnMask[0]) return false; if (st1.pawnMask[1]!=st2.pawnMask[1]) return false; for (int y=1;y<=9;y++) for (int x=9;x>0;x--) { Piece p1=st1.pieceAt(Square(x,y)); Piece p2=st2.pieceAt(Square(x,y)); if (p1.ptypeO()!=p2.ptypeO()) return false; } return true; } namespace osl { namespace { void showStand(std::ostream& os, Player player, PieceStand stand) { if (! stand.any()) return; os << "P" << csa::show(player); for (Ptype ptype: PieceStand::order) { for (unsigned int j=0; j0;x--) { os << csa::show(state.pieceOnBoard(Square(x,y))); } os << std::endl; } // æŒã¡é§’ã®è¡¨ç¤º const PieceStand black_stand(BLACK, state); const PieceStand white_stand(WHITE, state); showStand(os, BLACK, black_stand); showStand(os, WHITE, white_stand); os << state.turn() << std::endl; return os; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/additionalEffect.cc0000644000000000000000000000604112316770314017726 0ustar rootroot#include "osl/additionalEffect.h" #include "osl/bits/additionalOrShadow.h" bool osl::effect_util:: AdditionalEffect::hasEffect(const NumEffectState& state, Square target, Player attack) { PieceMask direct = state.effectSetAt(target) & state.piecesOnBoard(attack); PieceMask mask; mask.setAll(); mask.clearBit(); direct &= (state.promotedPieces() | mask); while (direct.any()) { const int num = direct.takeOneBit(); const Square p = state.pieceOf(num).square(); const Direction d=Board_Table.getShort8(p,target); const int num1=state.longEffectNumTable()[num][d]; if(!Piece::isEmptyNum(num1) && state.pieceOf(num1).owner()==attack) return true; } return false; } template int osl::effect_util:: AdditionalEffect::count(const NumEffectState& state, Square target, Player attack) { PieceVector direct_pieces; state.findEffect(attack, target, direct_pieces); return AdditionalOrShadow::count (direct_pieces, state, target, attack); } bool osl::effect_util:: AdditionalEffect::hasEffectStable(const NumEffectState& state, Square target, Player attack) { return count<1>(state, target, attack); } int osl::effect_util:: AdditionalEffect::count2(const NumEffectState& state, Square target, Player attack) { return count<2>(state, target, attack); } void osl::effect_util:: AdditionalEffect::find(const NumEffectState& state, Square target, const PieceVector& direct_effects, PieceVector& black, PieceVector& white) { for (Piece p: direct_effects) { const Square from = p.square(); const Offset32 diff32 = Offset32(from, target); const Offset step = Board_Table.getShortOffsetNotKnight(diff32); if (step.zero()) continue; // 利ããŒ8æ–¹å‘ã®å ´åˆ Piece candidate=state.nextPiece(from, step); if (! candidate.isPiece()) continue; const Offset32 diff_reverse = Offset32(target,candidate.square()); for (; candidate.isPiece(); candidate=state.nextPiece(candidate.square(), step)) { const EffectContent effect = Ptype_Table.getEffect(candidate.ptypeO(), diff_reverse); if (! effect.hasEffect()) break; if (candidate.owner() == BLACK) black.push_back(candidate); else white.push_back(candidate); } } } void osl::effect_util:: AdditionalEffect::find(const NumEffectState& state, Square target, PieceVector& black, PieceVector& white) { PieceVector direct_pieces; state.findEffect(BLACK, target, direct_pieces); find(state, target, direct_pieces, black, white); direct_pieces.clear(); state.findEffect(WHITE, target, direct_pieces); find(state, target, direct_pieces, black, white); } void osl::effect_util:: AdditionalEffect::count(const NumEffectState& state, Square target, int& black, int& white) { PieceVector black_pieces, white_pieces; find(state, target, black_pieces, white_pieces); black = black_pieces.size(); white = white_pieces.size(); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/enterKing.cc0000644000000000000000000001111412316770314016424 0ustar rootroot/* enterKing.cc */ #include "osl/enterKing.h" bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState& state) { if (state.turn() == BLACK) return canDeclareWin(state); else return canDeclareWin(state); } template bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState& state) { //手番, æŒæ™‚é–“ã¯çœç•¥ assert(Turn == state.turn()); const Square myKingSquare = state.kingSquare(Turn); //王手ãŒã‹ã‹ã£ã¦ã„ãªã„ã‹ if ( state.hasEffectAt(alt(Turn), myKingSquare) ) return false; //è‡ªçŽ‰ãŒæ•µé™£ã«ã„ã‚‹ã‹ //先手ãªã‚‰1~3 //後手ãªã‚‰7~9 const int y = myKingSquare.y(); const int enemyCampMin = (Turn==BLACK) ? 1 : 7; const int enemyCampMax = enemyCampMin + 2; if( (y < enemyCampMin) || (y > enemyCampMax) ) return false; // 敵陣ã«è‡ªåˆ†ã®é§’ãŒ10枚以上 (自玉を除ã„ã¦) ã‚ã‚‹ã‹ // é§’ã®ç‚¹æ•°ã‚’勘定ã™ã‚‹. (対象: 敵陣ã®é§’ + æŒé§’) // 大駒を5点ã¨ã—ã¦, 先手ã¯28点, 後手ãªã‚‰27ç‚¹å¿…è¦ int countPiece = 0; int onEnemyCamp = -1; // 自玉ã®åˆ†ã‚’予ã‚引ã„ã¦ãŠã for (int i = enemyCampMin; i <= enemyCampMax; i++) for (int j=1; j<=9; j++){ Piece pieceOnEnemyCamp = state.pieceOnBoard(Square(j,i)); if (pieceOnEnemyCamp.isOnBoardByOwner()) { ++countPiece; onEnemyCamp += 1 + 4 * isMajor(pieceOnEnemyCamp.ptype()); } } if (countPiece < 11) return false; int onStand = 5 * state.countPiecesOnStand(Turn) + 5 * state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn); if ( onEnemyCamp + onStand < 27 + (Turn==BLACK) ) return false; return true; } bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState& state, int &distance) { if (state.turn() == BLACK) return canDeclareWin(state, distance); else return canDeclareWin(state, distance); } template bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState& state, int &drops) { // 宣言å‹ã¡ã®æ¡ä»¶ã‚’ //「敵陣ã«ï¼ˆè‡ªçŽ‰ã‚’é™¤ã„ã¦ï¼‰10枚以上ã„る〠// 以外満ãŸã—ã¦ã„る時㫠// 敵陣ã«ã‚ã¨ä½•枚駒を打ã¦ã°è‰¯ã„ã‹ã‚’drops ã§è¿”ã™ // ä»–ã®æ¡ä»¶ã‚’満ãŸã—ã¦ã„ãªã„å ´åˆä½•枚打ã£ã¦ã‚‚å‹ã¦ãªã„ã®ã§41を返㙠//手番, æŒæ™‚é–“ã¯çœç•¥ assert(Turn == state.turn()); const Square myKingSquare = state.kingSquare(Turn); drops = 41; //王手ãŒã‹ã‹ã£ã¦ã„ãªã„ã‹ if ( state.hasEffectAt(alt(Turn), myKingSquare) ) return false; //è‡ªçŽ‰ãŒæ•µé™£ã«ã„ã‚‹ã‹ //先手ãªã‚‰1~3 //後手ãªã‚‰7~9 const int y = myKingSquare.y(); const int enemyCampMin = (Turn==BLACK) ? 1 : 7; const int enemyCampMax = enemyCampMin + 2; if( (y < enemyCampMin) || (y > enemyCampMax) ) return false; // 敵陣ã«è‡ªåˆ†ã®é§’ãŒ10枚以上 (自玉を除ã„ã¦) ã‚ã‚‹ã‹ // é§’ã®ç‚¹æ•°ã‚’勘定ã™ã‚‹. (対象: 敵陣ã®é§’ + æŒé§’) // 大駒を5点ã¨ã—ã¦, 先手ã¯28点, 後手ãªã‚‰27ç‚¹å¿…è¦ int countPiece = 0; int onEnemyCamp = -1; // 自玉ã®åˆ†ã‚’予ã‚引ã„ã¦ãŠã for (int i = enemyCampMin; i <= enemyCampMax; i++) for (int j=1; j<=9; j++){ Piece pieceOnEnemyCamp = state.pieceOnBoard(Square(j,i)); if (pieceOnEnemyCamp.isOnBoardByOwner()) { ++countPiece; onEnemyCamp += 1 + 4 * isMajor(pieceOnEnemyCamp.ptype()); } } int onStand = 5 * state.countPiecesOnStand(Turn) + 5 * state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn) + state.countPiecesOnStand(Turn); if ( onEnemyCamp + onStand < 27 + (Turn==BLACK) ) return false; if (countPiece < 11) { drops = 11 - countPiece; return false; } else { drops = 0; } return true; } namespace osl { namespace enter_king { template bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState&); template bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState&); template bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState&, int &drops); template bool osl::enter_king::EnterKing::canDeclareWin(const NumEffectState&, int &drops); } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/book/0000755000000000000000000000000012317712235015122 5ustar rootrootlibosl-0.8.0.orig/core/osl/book/compactBoard.h0000644000000000000000000000444312316770314017677 0ustar rootroot#ifndef _COMPACT_BOARD_H #define _COMPACT_BOARD_H #include "osl/simpleState.h" #include #include namespace osl { namespace book { class OPiece { public: OPiece(Piece p) { const Square pos = p.square(); const int bitPos = position2Bits(pos); value = (static_cast(p.owner()) << 20 | static_cast(p.ptype()) << 16 | bitPos); } OPiece(int i) { value = i; } Square square() const { return bits2Square(value); } Ptype ptype() const { return static_cast((value >> 16) & 0xf); } Player owner() const { return static_cast(value >> 20); } operator int() const { return value; } /** Converts a position to an integer (bits) */ static int position2Bits(const Square& pos); /** Converts an integer (bits) to Square */ static Square bits2Square(const int bit_position); private: int value; }; class CompactBoard; /** * å±€é¢ã‚’比較ã™ã‚‹. * 将棋ã¨ã—ã¦ã®å±€é¢ï¼ˆæ‰‹ç•ªã‚„æŒã¡é§’ã‚’å«ã‚€ï¼‰ã‚’比較ã™ã‚‹. * NumEffectStateç­‰ã¨ç•°ãªã‚Šé§’番å·ã¯è€ƒæ…®ã•れãªã„. */ bool operator==(const CompactBoard&, const CompactBoard&); std::ostream& operator<<(std::ostream& os, const CompactBoard& c); std::istream& operator>>(std::istream& os, CompactBoard& c); /** * SimpleStateよりcompactãªå±€é¢ã®è¡¨ç¾ */ class CompactBoard { public: CompactBoard() {} explicit CompactBoard(const SimpleState& state); SimpleState state() const; const std::vector& pieces() const {return piece_vector;}; Player turn() const {return player_to_move;} friend std::ostream& operator<<(std::ostream& os, const CompactBoard& c); friend std::istream& operator>>(std::istream& os, CompactBoard& c); friend bool operator==(const CompactBoard&, const CompactBoard&); private: std::vector piece_vector; Player player_to_move; }; int readInt(std::istream& is); void writeInt(std::ostream& os, int n); } } #endif // _COMPACT_BOARD_H /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/book/openingBook.h0000644000000000000000000001527112316770314017554 0ustar rootroot#ifndef _OPENING_BOOK_H #define _OPENING_BOOK_H #include "osl/book/compactBoard.h" #include "osl/basic_type.h" #include "osl/numEffectState.h" #include #include namespace osl { namespace book { class OMove { public: OMove(int i) { value = i; } OMove(Move m) { const Square from = m.from(); const Square to = m.to(); const int bitFrom = (from.isPieceStand() ? 0 : (from.x() << 4 | from.y())); const int bitTo = (to.isPieceStand() ? 0 : (to.x() << 12 | to.y() << 8)); value = (bitFrom | bitTo | static_cast(m.isPromotion()) << 19 | static_cast(m.capturePtype()) << 20 | static_cast(m.ptype()) << 24 | static_cast(m.player()) << 28); } Square from() { if ((value & 0xff) == 0) return Square::STAND(); else return Square((value >> 4) & 0xf, value & 0xf); } Square to() { if (((value >> 8) & 0xff) == 0) return Square::STAND(); else return Square((value >> 12) & 0xf, (value >> 8) & 0xf); } bool isPromotion() { return (value >> 19) & 1; } Ptype capturePtype() { return static_cast((value >> 20) & 0xf); } Ptype ptype() { return static_cast((value >> 24) & 0xf); } Player player() { return static_cast((value) >> 28); } operator Move() { return Move(from(), to(), ptype(), capturePtype(), isPromotion(), player()); } operator int() { return value; } private: int value; }; struct OBMove { Move move; int state_index; int stateIndex() const { return state_index; } }; /** * Stateã¨OBMoveã‚’ä¿æŒã™ã‚‹. * Stateã¯vectorã¨é»’ã‹ã‚‰è¦‹ãŸwinCount, loseCountã‚’ä¿æŒã™ã‚‹ * OBMoveã¯Moveã¨ãã®Moveを採用ã—ãŸæ™‚ã®Stateã®index * ãƒ•ã‚¡ã‚¤ãƒ«å½¢å¼ * stateæ•° - 4byte * State - 16byte * stateæ•° * + é»’ã®winCount * + 白ã®winCount * + OBMoveã®æ•° * + OBMoveã®é–‹å§‹index * OBMove - 8byte * OBMoveæ•° * + Move (4byte) * + Stateã®index */ class WinCountBook { int nStates; std::ifstream ifs; public: WinCountBook(const char *filename); ~WinCountBook(); int winCount(int stateIndex); int loseCount(int stateIndex); std::vector moves(int stateIndex); private: int readInt(); void seek(int offset); }; struct WMove { Move move; int state_index; int weight; int stateIndex() const { return state_index; } void setWeight(const int w) { weight = w; }; }; std::ostream& operator<<(std::ostream&, const WMove& w); std::istream& operator>>(std::istream&, WMove& w); inline bool operator==(const WMove& l, const WMove& r) { return l.move == r.move && l.stateIndex() == r.stateIndex() && l.weight == r.weight; } /** * WMoveã®Weightã«ã‚ˆã‚‹sort */ struct WMoveSort : public std::binary_function { bool operator()(const WMove& l, const WMove& r) const { return l.weight > r.weight; } }; /** * WMoveã®Moveã«ã‚ˆã‚‹sort */ struct WMoveMoveSort : public std::binary_function { bool operator()(const WMove& l, const WMove& r) const { return l.move.intValue() < r.move.intValue(); } }; /** * WMoveã®Weightã¨Moveã«ã‚ˆã‚‹sort */ struct WMoveWeightMoveSort : public std::binary_function { bool operator()(const WMove& l, const WMove& r) const { if (l.weight != r.weight) return l.weight > r.weight; return l.move.intValue() < r.move.intValue(); } }; /** * Stateã¨WMoveã‚’ä¿æŒã™ã‚‹. * Stateã¯vectorã‚’ä¿æŒã™ã‚‹ * WMoveã¯Moveã¨ãã®Moveを採用ã—ãŸæ™‚ã®Stateã®indexã¨æ‰‹ç•ªã‹ã‚‰è¦‹ãŸ * Moveã®é‡ã¿(0-1000)をも㤠* ãƒ•ã‚¡ã‚¤ãƒ«å½¢å¼ * versionç•ªå· - 4byte * stateæ•° - 4byte * moveæ•° - 4byte * é–‹å§‹state index - 4byte * State - 16byte * stateæ•° * + WMoveã®é–‹å§‹index * + WMoveã®æ•° * + 先手ã®å‹æ•° * + 後手ã®å‹æ•° * WMove - 12byte * WMoveæ•° * + Move (4byte) * + Stateã®index * + Weight * CompactBoardå½¢å¼ã®ç›¤é¢ - 164byte * stateæ•° */ class WeightedBook { int n_states; int n_moves; int start_state; std::ifstream ifs; public: typedef std::vector WMoveContainer; WeightedBook(const char *filename); ~WeightedBook(); /** * Return moves from the state of the stateIndex. If the zero_include is * true, all of the moves are returned. Otherwise, the moves that * have some weights (i.e. non-zero value) are returned. */ WMoveContainer moves(int stateIndex, const bool zero_include = true); int whiteWinCount(int stateIndex); int blackWinCount(int stateIndex); CompactBoard compactBoard(int stateIndex); SimpleState board(int stateIndex); int totalState() const { return n_states; } int startState() const { return start_state; } void validate(); /** * As traversing the 'tree', return all state indices of the state's * parents. * @return state indexes; empty if there is none. */ std::vector parents(const int stateIndex); /** * As traversing the 'tree', find a state index of the state. If * the visit_zero is true zero-weighted moves are visited (in this * case, player is ignored). Otherwise, the palyer's zero-weighted * moves are not visited. * * @param state to find * @param visit_zero * @param player * @return a state index of the state; if it is not found, return -1. */ int stateIndex(const SimpleState& state, const bool visit_zero = true, const Player player = BLACK); /** * As traversing the 'tree', find a state index of the state reached * by applying the moves from the initial state. * Note that zero-weighted moves are visited. * * @param moves to apply * @return state index; if it is not found, return -1. */ int stateIndex(const std::vector& moves); private: void seek(int offset); static const int HEADER_SIZE = 16; static const int STATE_SIZE = 16; static const int MOVE_SIZE = 12; static const int BOARD_SIZE = 41 * 4; }; } // book using book::CompactBoard; using book::WeightedBook; } // namespace osl #endif // _OPENING_BOOK_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/book/bookInMemory.h0000644000000000000000000000166612316770314017717 0ustar rootroot/* bookInMemory.h */ #ifndef OSL_BOOKINMEMORY_H #define OSL_BOOKINMEMORY_H #include "osl/hashKey.h" #include #include namespace osl { namespace book { class WeightedBook; class BookInMemory { typedef CArray moves_t; typedef std::unordered_map> table_t; table_t table; public: ~BookInMemory(); void find(const HashKey& key, MoveVector& out) const; size_t size() const { return table.size(); } static const BookInMemory& instance(const std::string& filename=""); private: explicit BookInMemory(const std::string& filename); void readAll(const std::string& filename); int readRecursive(const HashKey& key, int index, WeightedBook& book, int, int); }; } using book::BookInMemory; } #endif /* OSL_BOOKINMEMORY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/book/openingBook.cc0000644000000000000000000001707312317712235017713 0ustar rootroot#include "osl/book/openingBook.h" #include "osl/book/compactBoard.h" #include #include #include int osl::book::readInt(std::istream& is) { int ret=0; CArray cs; is.read(&cs[0],4); for (int i=0;i<4;i++) { ret = (ret<<8)|(cs[i]&255); } return ret; } void osl::book::writeInt(std::ostream& os, int n) { CArray buf; for (int i = 0; i < 4; i++) { buf[i] = (n >> (8 * (4 - i - 1))) & 255; } os.write(&buf[0], 4); } #ifndef MINIMAL osl::book:: WinCountBook::WinCountBook(const char *filename) : ifs(filename, std::ios_base::binary) { if (! ifs) { const char *message = "WinCountBook: open failed "; std::cerr << message << filename << std::endl; throw std::runtime_error(std::string(message) + filename); } nStates=readInt(); } osl::book:: WinCountBook::~WinCountBook() { } int osl::book:: WinCountBook::readInt() { int ret=0; CArray cs; ifs.read(&cs[0],4); for (int i=0;i<4;i++) { ret = (ret<<8)|(cs[i]&255); } return ret; } void osl::book:: WinCountBook::seek(int offset) { ifs.seekg(offset,std::ios::beg); } std::vector osl::book:: WinCountBook::moves(int stateIndex) { assert(stateIndex >= 0); seek(4+16*stateIndex+8); int nMoves=readInt(); int moveIndex=readInt(); seek(4+16*nStates+8*moveIndex); std::vector moves; moves.reserve(nMoves); for(int i=0;i>(std::istream& is, WMove& w) { w.move = OMove(readInt(is)).operator Move(); w.state_index = readInt(is); w.weight = readInt(is); return is; } osl::book:: WeightedBook::WeightedBook(const char *filename) : ifs(filename, std::ios_base::binary) { if (! ifs) { const char *message = "WeightedBook: open failed "; std::cerr << message << filename << std::endl; throw std::runtime_error(std::string(message) + filename); } #ifndef NDEBUG int version = #endif readInt(ifs); assert(version == 1); n_states = readInt(ifs); n_moves = readInt(ifs); start_state = readInt(ifs); } osl::book:: WeightedBook::~WeightedBook() { } void osl::book:: WeightedBook::seek(int offset) { ifs.seekg(offset,std::ios::beg); } osl::book::WeightedBook::WMoveContainer osl::book:: WeightedBook::moves(int stateIndex, const bool visit_zero) { assert(stateIndex >= 0); seek(HEADER_SIZE + STATE_SIZE * stateIndex); int moveIndex=readInt(ifs); int nWMoves=readInt(ifs); seek(HEADER_SIZE + STATE_SIZE * n_states + MOVE_SIZE * moveIndex); std::vector moves; moves.reserve(nWMoves); for(int i=0;i> wm; if (!visit_zero && wm.weight == 0) continue; moves.push_back(wm); } return moves; } osl::book::CompactBoard osl::book:: WeightedBook::compactBoard(int stateIndex) { seek(HEADER_SIZE + STATE_SIZE * n_states + MOVE_SIZE * n_moves + BOARD_SIZE * stateIndex); CompactBoard board; ifs >> board; return board; } osl::SimpleState osl::book:: WeightedBook::board(int stateIndex) { const CompactBoard board = compactBoard(stateIndex); return board.state(); } int osl::book:: WeightedBook::whiteWinCount(int stateIndex) { seek(HEADER_SIZE + STATE_SIZE * stateIndex); readInt(ifs); readInt(ifs); readInt(ifs); return readInt(ifs); } int osl::book:: WeightedBook::blackWinCount(int stateIndex) { seek(HEADER_SIZE + STATE_SIZE * stateIndex); readInt(ifs); readInt(ifs); return readInt(ifs); } void osl::book:: WeightedBook::validate() { #ifndef NDEBUG { SimpleState state(HIRATE); SimpleState start = board(start_state); assert(state == start); } #endif std::vector visited(n_states); std::fill(visited.begin(), visited.end(), false); std::vector stateToCheck; stateToCheck.push_back(start_state); visited[start_state] = true; while (!stateToCheck.empty()) { const int index = stateToCheck.back(); stateToCheck.pop_back(); SimpleState state = board(index); for (WMove move: moves(index)) { NumEffectState newState(state); newState.makeMove(move.move); const int nextIndex = move.stateIndex(); SimpleState stateInFile = board(nextIndex); assert(newState == stateInFile); if (!visited[nextIndex]) { stateToCheck.push_back(nextIndex); visited[nextIndex] = true; } } } } int osl::book:: WeightedBook::stateIndex(const SimpleState& state_to_look_for, const bool visit_zero, const Player player) { int ret = -1; const CompactBoard board_to_look_for(state_to_look_for); const CompactBoard start_state = compactBoard(startState()); if (start_state == board_to_look_for) { ret = startState(); return ret; } std::vector states(totalState(), false); // mark states that have been visited. std::vector stateToVisit; stateToVisit.push_back(startState()); while (!stateToVisit.empty()) { const int stateIndex = stateToVisit.back(); stateToVisit.pop_back(); states[stateIndex] = true; WMoveContainer v; if (visit_zero) v = moves(stateIndex); else { const CompactBoard stateIndexCB = compactBoard(stateIndex); const Player turn = stateIndexCB.turn(); const bool zero_include = turn == player ? false : true; v = moves(stateIndex, zero_include); } for (WMove move: v) { const int nextIndex = move.stateIndex(); if (! states[nextIndex]) { const CompactBoard state = compactBoard(nextIndex); if (state == board_to_look_for) { ret = nextIndex; return ret; } stateToVisit.push_back(nextIndex); } } // each wmove } // while loop return ret; } int osl::book:: WeightedBook::stateIndex(const std::vector& moves) { int state_index = startState(); for (Move move: moves) { const WMoveContainer wmoves = this->moves(state_index); WMoveContainer::const_iterator it = wmoves.begin(); for (; it != wmoves.end(); ++it) if (it->move == move) break; if (it != wmoves.end()) { state_index = it->stateIndex(); // next state to visit continue; } return -1; // not found } return state_index; } std::vector osl::book:: WeightedBook::parents(const int target_state_index) { std::vector ret; if (startState() == target_state_index) return ret; std::vector states(totalState(), false); // mark states that have been visited. std::vector stateToVisit; stateToVisit.push_back(startState()); while (!stateToVisit.empty()) { const int stateIndex = stateToVisit.back(); stateToVisit.pop_back(); states[stateIndex] = true; const WMoveContainer moves = this->moves(stateIndex); for (WMove move: moves) { const int nextIndex = move.stateIndex(); if (nextIndex == target_state_index) ret.push_back(stateIndex); if (! states[nextIndex]) stateToVisit.push_back(nextIndex); } // each wmove } // while loop return ret; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/book/compactBoard.cc0000644000000000000000000000453412316770314020036 0ustar rootroot#include "osl/book/compactBoard.h" #include #include #include int osl::book:: OPiece::position2Bits(const Square& pos) { return pos.isPieceStand() ? 0 : ((pos.x() << 4) | pos.y()); // 8 bits } osl::Square osl::book:: OPiece::bits2Square(const int bit_position) { if ((bit_position & 0xff) == 0) return Square::STAND(); else return Square((bit_position >> 4) & 0xf, bit_position & 0xf); } namespace osl { namespace book { struct opiece_sort { bool operator()(const OPiece& l, const OPiece& r) { if (l.square() == Square::STAND() || r.square() == Square::STAND()) { if (l.square() != r.square()) return l.square() == Square::STAND(); if (l.owner() != r.owner()) return l.owner() == WHITE; return l.ptype() < r.ptype(); } if (l.square().x() != r.square().x()) return l.square().x() < r.square().x(); return l.square().y() < r.square().y(); } }; } } osl::book:: CompactBoard::CompactBoard(const SimpleState& state) { piece_vector.reserve(40); for (int i = 0; i < 40; i++) { if(state.usedMask().test(i)) piece_vector.push_back(OPiece(state.pieceOf(i))); } std::sort(piece_vector.begin(), piece_vector.end(), opiece_sort()); player_to_move = state.turn(); } osl::SimpleState osl::book:: CompactBoard::state() const { SimpleState state; state.init(); for (const OPiece& p: piece_vector) { state.setPiece(p.owner(), p.square(), p.ptype()); } state.setTurn(turn()); state.initPawnMask(); return state; } bool osl::book:: operator==(const CompactBoard& lhs, const CompactBoard& rhs) { return (lhs.turn() == rhs.turn()) && (lhs.pieces() == rhs.pieces()); } std::ostream& osl::book:: operator<<(std::ostream& os, const CompactBoard& c) { for (unsigned int i = 0; i < c.pieces().size(); i++) { writeInt(os, static_cast(c.pieces()[i])); } writeInt(os, static_cast(c.turn())); return os; } std::istream& osl::book:: operator>>(std::istream& is, CompactBoard& c) { assert(c.piece_vector.size() == 0); for (unsigned int i = 0; i < 40; i++) { c.piece_vector.push_back(OPiece(readInt(is))); } c.player_to_move = static_cast(readInt(is)); return is; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/book/bookInMemory.cc0000644000000000000000000000454412316770314020053 0ustar rootroot/* bookInMemory.cc */ #include "osl/book/bookInMemory.h" #include "osl/book/openingBook.h" #include "osl/numEffectState.h" #include "osl/oslConfig.h" #include #include osl::book:: BookInMemory::BookInMemory(const std::string& filename) { readAll(filename); } osl::book:: BookInMemory::~BookInMemory() { } int osl::book:: BookInMemory::readRecursive(const HashKey& key, int index, WeightedBook& book, int depth, int /*parent_visit*/) { const int depth_threshold = 60, visit_threshold = 4, scale = 16; const int visit = book.blackWinCount(index)+book.whiteWinCount(index); if (depth > depth_threshold || table.find(key) != table.end() || visit < visit_threshold) return visit; const std::vector& moves = book.moves(index); FixedCapacityVector, 40> children; for (WMove move: moves) { const HashKey child = key.newMakeMove(move.move); const int cv = readRecursive(child, move.stateIndex(), book, depth+1, visit); if (cv < visit_threshold || cv*scale < visit || move.weight == 0) continue; children.push_back(std::make_pair(cv, move.move)); if (children.size() == children.capacity()) break; } std::sort(children.begin(), children.end()); std::reverse(children.begin(), children.end()); if (! children.empty()) { moves_t& store = table[key]; store.fill(Move()); for (size_t i=0; isecond) if (move.isNormal()) out.push_back(move); } const osl::book::BookInMemory& osl::book:: BookInMemory::instance(const std::string& filename) { static std::map > table; std::shared_ptr &book = table[filename]; if (! book) book.reset(new BookInMemory(filename)); return *book; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/csa.cc0000644000000000000000000002010412316770314015243 0ustar rootroot#include "osl/csa.h" #include "osl/simpleState.h" #include "osl/bits/pieceTable.h" #include "osl/oslConfig.h" #include #include #include #include #include #include #include #include #include /* ------------------------------------------------------------------------- */ osl::Player osl::csa:: charToPlayer(char c) { if(c=='+') return BLACK; if(c=='-') return WHITE; throw CsaIOError("not a csa PlayerCharacter "+std::string(1,c)); } const osl::Square osl::csa:: strToPos(const std::string& s) { int x=s.at(0)-'0'; int y=s.at(1)-'0'; if(x==0 && y==0) return Square::STAND(); return Square(x,y); } osl::Ptype osl::csa:: strToPtype(const std::string& s) { for(int i=0;i<16;i++){ if(s == Ptype_Table.getCsaName(static_cast(i))) return static_cast(i); } throw CsaIOError("unknown std::string in csa::strToPtype "+s); } const osl::Move osl::csa:: strToMove(const std::string& s,const SimpleState& state) { if (s == "%KACHI") return Move::DeclareWin(); if (s == "%TORYO") return Move::INVALID(); if (s == "%PASS") // FIXME: not in CSA protocol return Move::PASS(state.turn()); Player pl=csa::charToPlayer(s.at(0)); Square fromPos=csa::strToPos(s.substr(1,2)); Square toPos=csa::strToPos(s.substr(3,2)); Ptype ptype=csa::strToPtype(s.substr(5,2)); if(fromPos==Square::STAND()){ if (isPromoted(ptype)) throw CsaIOError("drop with promote ?! in csa::strToMove "+s); return Move(toPos,ptype,pl); } else{ Piece p0=state.pieceAt(fromPos); Piece p1=state.pieceAt(toPos); Ptype capturePtype=p1.ptype(); bool isPromote=(p0.ptype()!=ptype); if (! ((p0.ptype()==ptype)||(p0.ptype()==unpromote(ptype)))) throw CsaIOError("bad promotion in csa::strToMove "+s); return Move(fromPos,toPos,ptype, capturePtype,isPromote,pl); } } /* ------------------------------------------------------------------------- */ const std::string osl::csa:: show(Player player, std::string& buf, size_t offset) { assert(buf.size() >= offset+1); buf[offset] = (player==BLACK) ? '+' : '-'; return buf; } const std::string osl::csa:: show(Move move, std::string& buf) { assert(buf.capacity() >= 7); buf.resize(7); if (move == Move::DeclareWin()) return buf = "%KACHI"; if (move.isInvalid()) return buf = "%TORYO"; if (move.isPass()) return buf = "%PASS"; // FIXME: not in CSA protocol show(move.player(), buf); show(move.from(), buf, 1); show(move.to(), buf, 3); show(move.ptype(), buf, 5); return buf; } const std::string osl::csa:: show(Square pos, std::string& buf, size_t offset) { assert(buf.size() >= offset+2); if (pos.isPieceStand()) { buf[0+offset] = '0'; buf[1+offset] = '0'; return buf; } const int x = pos.x(); const int y = pos.y(); buf[offset+0] = x + '0'; buf[offset+1] = y + '0'; return buf; } const std::string osl::csa:: show(Ptype ptype, std::string& buf, size_t offset) { assert(buf.size() >= offset+2); const char *name = Ptype_Table.getCsaName(ptype); buf[0+offset] = name[0]; buf[1+offset] = name[1]; return buf; } const std::string osl::csa:: show(Move move) { // NOTE: copy コピーを返ã™ã®ã§ dangling pointer ã§ã¯ãªã„ std::string buf("+7776FU"); return show(move, buf); } const std::string osl::csa:: fancyShow(Move move) { std::string ret = show(move); if (move.isNormal()) { if (move.capturePtype() != PTYPE_EMPTY) ret += "x" + show(move.capturePtype()); if (move.isPromotion()) ret += '+'; } return ret; } const std::string osl::csa:: show(Player player) { std::string buf("+"); return show(player, buf); } const std::string osl::csa:: show(Square position) { std::string buf("00"); return show(position, buf); } const std::string osl::csa:: show(Ptype ptype) { std::string buf("OU"); return show(ptype, buf); } const std::string osl::csa:: show(Piece piece) { if (piece.isEdge()) return " "; if (piece.isEmpty()) return " * "; assert(piece.isPiece() && isPiece(piece.ptype())); assert(unpromote(piece.ptype()) == Piece_Table.getPtypeOf(piece.number())); return show(piece.owner()) + show(piece.ptype()); } const std::string osl::csa:: show(const Move *first, const Move *last) { std::ostringstream out; for (; first != last; ++first) { if (first->isInvalid()) break; out << show(*first); } return out.str(); } /* ------------------------------------------------------------------------- */ osl::csa::CsaFileMinimal::CsaFileMinimal(const std::string& filename) { std::ifstream is(filename); if (! is) { const std::string msg = "CsaFileMinimal::CsaFileMinimal file open failed "; std::cerr << msg << filename << "\n"; throw CsaIOError(msg + filename); } load(is); } osl::csa::CsaFileMinimal::CsaFileMinimal(std::istream& is) { load(is); } osl::csa::CsaFileMinimal::~CsaFileMinimal() { } void osl::csa::CsaFileMinimal::load(std::istream& is) { SimpleState work; work.init(); std::string line; CArray board_parsed = {{ false }}; while (std::getline(is, line)) { // quick hack for \r if ((! line.empty()) && (line[line.size()-1] == 13)) line.erase(line.size()-1); std::vector elements; boost::algorithm::split(elements, line, boost::algorithm::is_any_of(",")); for (auto& e: elements) { boost::algorithm::trim(e); boost::algorithm::trim_left(e); parseLine(work, record, e, board_parsed); } } if (*std::min_element(board_parsed.begin(), board_parsed.end()) == false) throw CsaIOError("incomplete position description in csaParseLine"); assert(record.initial_state.isConsistent()); } bool osl::csa:: CsaFileMinimal::parseLine(SimpleState& state, RecordMinimal& record, std::string s, CArray& board_parsed) { while (! s.empty() && isspace(s[s.size()-1])) // ignore trailing garbage s.resize(s.size()-1); if (s.length()==0) return true; switch(s.at(0)){ case 'P': /* é–‹å§‹ç›¤é¢ */ switch(s.at(1)){ case 'I': /* å¹³æ‰‹åˆæœŸé…ç½® */ board_parsed.fill(true); state.init(HIRATE); break; case '+': /* 先手ã®é§’ */ case '-':{ /* 後手ã®é§’ */ Player pl=csa::charToPlayer(s.at(1)); for(int i=2;i<=(int)s.length()-4;i+=4){ Square pos=csa::strToPos(s.substr(i,2)); if(s.substr(i+2,2) == "AL"){ state.setPieceAll(pl); } else{ Ptype ptype=csa::strToPtype(s.substr(i+2,2)); state.setPiece(pl,pos,ptype); } } break; } default: if(isdigit(s.at(1))){ const int y=s.at(1)-'0'; board_parsed[y-1] = true; for(unsigned int x=9,i=2;i pieces_onboard; /** æˆé§’一覧 */ PieceMask promoted; CArray pin_or_open; KingMobility king_mobility; CArray king8infos; friend bool operator==(const NumEffectState& st1,const NumEffectState& st2); typedef NumEffectState state_t; public: // ---------------------------------------------------------------------- // 0. å°†æ£‹ä»¥å¤–ã®æ“作 // ---------------------------------------------------------------------- explicit NumEffectState(const SimpleState& st=SimpleState(HIRATE)); ~NumEffectState(); /** 主è¦éƒ¨åˆ†ã‚’高速ã«ã‚³ãƒ”ーã™ã‚‹. 盤ã®å¤–ã¯ã‚³ãƒ”ーã•れãªã„*/ void copyFrom(const NumEffectState& src); void copyFrom(const SimpleState& src); bool isConsistent(bool showError=true) const; /** 局颿›´æ–°ã«é–¢ã™ã‚‹ä¸€è²«æ€§ã‚’テスト */ bool isConsistent(const NumEffectState& prev, Move moved, bool show_error=true) const; void showEffect(std::ostream& os) const; // ---------------------------------------------------------------------- // 1. 盤é¢å…¨ä½“ã®æƒ…å ± // ---------------------------------------------------------------------- const PieceMask& piecesOnBoard(Player p) const { return pieces_onboard[p]; } const PieceMask promotedPieces() const { return promoted; } const PieceMask pin(Player king) const { return pin_or_open[king]&piecesOnBoard(king); } /** attack ã®é§’ã§å‹•ãã¨é–‹ã王手ã«ãªã‚‹å¯èƒ½æ€§ãŒã‚ã‚‹é›†åˆ */ const PieceMask checkShadow(Player attack) const { return pin_or_open[alt(attack)]&piecesOnBoard(attack); } PieceMask pinOrOpen(Player king) const { return pin_or_open[king]; } uint64_t Iking8Info(Player king) const { return king8infos[king]; } const checkmate::King8Info #ifdef __GNUC__ __attribute__ ((pure)) #endif king8Info(Player king) const; /** Pã®çމãŒçŽ‹æ‰‹çŠ¶æ…‹ */ bool inCheck(Player P) const { const Square king = kingSquare(P); #ifdef ALLOW_KING_ABSENCE if (king.isPieceStand()) return false; #endif return hasEffectAt(alt(P), king); } /** 手番ã®çމãŒçŽ‹æ‰‹çŠ¶æ…‹ */ bool inCheck() const { return inCheck(turn()); } /** * target ã®çŽ‹ã«åˆé§’å¯èƒ½ã§ãªã„王手ãŒã‹ã‹ã£ã¦ã„ã‚‹ã‹ã©ã†ã‹. * - 両王手 => 真 * - unblockable ãªåˆ©ãã ã‘ => 真 * - blockable ãªåˆ©ãã ã‘ => å½ * - 王手ã§ãªã„ => å½ * 2014/03 */ bool inUnblockableCheck(Player target) const { const Square king_position = kingSquare(target); Piece attacker_piece; if (hasEffectAt(alt(target), king_position, attacker_piece)) { if (attacker_piece == Piece::EMPTY()) return true; // multiple pieces // sigle check const Square from = attacker_piece.square(); const EffectContent effect = Ptype_Table.getEffect(attacker_piece.ptypeO(), from, king_position); return effect.hasUnblockableEffect(); } // no check return false; } const EffectedNumTable& longEffectNumTable() const { return effects.effectedNumTable; } /** pl ã‹ã‚‰ã®åˆ©ããŒ(1ã¤ä»¥ä¸Š)ã‚る駒一覧 */ const PieceMask effectedMask(Player pl) const { return effects.effected_mask[pl]; } /** å‰ã®æŒ‡æ‰‹ã§effectedMask(pl)ãŒå¤‰åŒ–ã—ãŸã‹. * å–られãŸé§’ã¯ç¾åœ¨ã®å®Ÿè£…ã§ã¯ãƒªã‚¹ãƒˆã•れãªã„よã†ã . */ const PieceMask effectedChanged(Player pl) const { return effects.effected_changed_mask[pl]; } bool hasChangedEffects() const { return ! effects.changedEffects(BLACK).isInvalid(); } const BoardMask changedEffects(Player pl) const{ assert(hasChangedEffects()); return effects.changedEffects(pl); } const BoardMask changedEffects() const{ BoardMask ret = changedEffects(BLACK); return ret |= changedEffects(WHITE); } const NumBitmapEffect changedPieces() const{ return effects.changedPieces(); } template bool longEffectChanged() const { return changedPieces().template hasLong(); } template bool anyEffectChanged() const { return changedPieces().template hasAny(); } /** å–られãã†ãªPã®é§’ã§ä¾¡å€¤ãŒæœ€å¤§ã®ã‚‚ã® */ const Piece findThreatenedPiece(Player P) const; // ---------------------------------------------------------------------- // 2. é§’ã«é–¢ã™ã‚‹æƒ…å ± // ---------------------------------------------------------------------- bool isOnBoardNum(int num) const { return piecesOnBoard(BLACK).test(num) || piecesOnBoard(WHITE).test(num); } Square mobilityOf(Direction d,int num) const { return effects.mobilityTable.get(d,num); } Square mobilityOf(Direction d, Piece p) const { return mobilityOf(d, p.number()); } Square kingMobilityAbs(Player p, Direction d) const { return Square::makeDirect(king_mobility[p][d]); } /** * 玉ãŒdæ–¹å‘ã«ã©ã“ã¾ã§å‹•ã‘ã‚‹ã‹ã‚’返㙠* @param p 注目ã™ã‚‹çމã®ãƒ—レイヤ * @param d piece ã‹ã‚‰ã¿ãŸå‘ã */ Square kingMobilityOfPlayer(Player p, Direction d) const { if (p == BLACK) d = inverse(d); return kingMobilityAbs(p, d); } /** * pinã•れãŸé§’ãŒPã®Kingã‹ã‚‰è¦‹ã¦ã©ã®æ–¹å‘ã‹? * Pã‹ã‚‰è¦‹ãŸdirectionを返㙠*/ template Direction pinnedDir(Piece p) const { assert(p.owner() == P); assert(pinOrOpen(P).test(p.number())); Square king=kingSquare

(); return Board_Table.getShort8

(p.square(),king); } Direction pinnedDir(Piece p) const { if (p.owner() == BLACK) return pinnedDir(p); else return pinnedDir(p); } /** * pinã•れãŸé§’pãŒtoã«å‹•ã‘ã‚‹ã‹? * pinã«é–¢ä¿‚ãŒãªã‘れã°toã¸å‹•ã‘ã‚‹ã¨ã„ã†å‰æ */ template bool pinnedCanMoveTo(Piece p,Square to) const { assert(p.owner() == P); Direction d=pinnedDir

(p); Square from=p.square(); return primDir(d)==primDirUnsafe(Board_Table.getShort8Unsafe

(from,to)); } bool pinnedCanMoveTo(Piece p,Square to) const { if (p.owner() == BLACK) return pinnedCanMoveTo(p, to); else return pinnedCanMoveTo(p, to); } /** * Pã®pinã•れãŸé§’ã‹ã‚‰ï¼Œãã®pinã®åŽŸå› ã¨ãªã£ã¦ã„ã‚‹é•·ã„利ãã‚’æŒã¤é§’を得る. */ template Piece pinAttacker(Piece pinned) const { assert(pinned.owner() == P); assert(pinOrOpen(P).test(pinned.number())); Direction d=pinnedDir

(pinned); int attacker_num=longEffectNumTable()[pinned.number()][(P==BLACK ? d : inverseUnsafe(d))]; return pieceOf(attacker_num); } Piece pinAttacker(Piece pinned) const { if (pinned.owner() == BLACK) return pinAttacker(pinned); else return pinAttacker(pinned); } // ---------------------------------------------------------------------- // 3. ã‚ã‚‹Squareã¸ã®åˆ©ã // ---------------------------------------------------------------------- const NumBitmapEffect effectSetAt(Square sq) const { return effects.effectSetAt(sq); } /** * 利ãã®æ•°ã‚’æ•°ãˆã‚‹. * targetãŒç›¤ã‚’ã¯ã¿å‡ºã—ã¦ã¯ã„ã‘ãªã„ */ int countEffect(Player player,Square target) const { assert(target.isOnBoard()); return effectSetAt(target).countEffect(player); } /** * 利ãã®æ•°ã‚’æ•°ãˆã‚‹. * targetãŒç›¤ã‚’ã¯ã¿å‡ºã—ã¦ã¯ã„ã‘ãªã„ * @param pins ã“ã®é§’ã®åˆ©ãã¯æ•°ãˆãªã„ */ int #ifdef __GNUC__ __attribute__ ((pure)) #endif countEffect(Player player,Square target, PieceMask pins) const { assert(target.isOnBoard()); const NumBitmapEffect effect = effectSetAt(target); const int all = effect.countEffect(player); pins &= effect; return all - pins.countBit(); } // ---------------------------------------------------------------------- // 3.1 集åˆã‚’返㙠// ---------------------------------------------------------------------- template const mask_t allEffectAt(Player P, Square target) const { return effectSetAt(target).template selectBit() & piecesOnBoard(P).template getMask(); } const mask_t allEffectAt(Player P, Ptype ptype, Square target) const; template const mask_t longEffectAt(Square target) const { return effectSetAt(target).selectLong() >> 8; } template const mask_t longEffectAt(Square target, Player owner) const { return longEffectAt(target) & piecesOnBoard(owner).getMask(1); } const mask_t longEffectAt(Square target) const { return effectSetAt(target).selectLong() >> 8; } const mask_t longEffectAt(Square target, Player owner) const { return longEffectAt(target) & piecesOnBoard(owner).getMask(1); } // ---------------------------------------------------------------------- // 3.2 bool を返㙠// ---------------------------------------------------------------------- /** * 対象ã¨ã™ã‚‹ãƒžã‚¹ã«ã‚るプレイヤーã®åˆ©ããŒã‚ã‚‹ã‹ã©ã†ã‹. * @param player æ”»æ’ƒå´ * @param target 対象ã®ãƒžã‚¹ */ template bool hasEffectAt(Square target) const { assert(target.isOnBoard()); mask_t mask=effectSetAt(target).getMask(1); mask&=NumBitmapEffect::playerEffectMask

(); return !mask.none(); } /** * 対象ã¨ã™ã‚‹ãƒžã‚¹ã«ã‚るプレイヤーã®åˆ©ããŒã‚ã‚‹ã‹ã©ã†ã‹. * @param player æ”»æ’ƒå´ * @param target 対象ã®ãƒžã‚¹ */ bool hasEffectAt(Player player,Square target) const { assert(target.isOnBoard()); mask_t mask=effectSetAt(target).getMask(1); mask&=NumBitmapEffect::playerEffectMask(player); return !mask.none(); } /** * ã‚るマスã«PTYPEã®é•·ã„利ããŒã‚ã‚‹ã‹ã©ã†ã‹. */ template bool hasLongEffectAt(Player P, Square to) const { static_assert((PTYPE == LANCE || PTYPE == BISHOP || PTYPE == ROOK), "ptype"); return longEffectAt(to, P).any(); } /** * target ã« ptype ã®åˆ©ããŒã‚ã‚‹ã‹? æˆä¸æˆã‚’区別ã—ãªã„ */ template bool hasEffectByPtype(Player attack, Square target) const { return allEffectAt(attack, target).any(); } /** * target ã« ptype ã®åˆ©ããŒã‚ã‚‹ã‹? æˆä¸æˆã‚’区別 */ template bool hasEffectByPtypeStrict(Player attack, Square target) const { mask_t mask=allEffectAt(attack, target); if (isPromoted(PTYPE)) mask &= promoted.getMask(); else mask &= ~(promoted.getMask()); return mask.any(); } /** * ã‚るマスã«ã‚ã‚‹Directionã§ã®é•·ã„利ããŒã‚ã‚‹ã‹ã©ã†ã‹. * 64bit版対応済㿠*/ template bool hasEffectInDirection(Square to) const { static_assert((DirectionTraits

::isLong), "Dir"); const PieceMask& pieces_onboard=piecesOnBoard(P); mask_t mask1=pieces_onboard.getMask(1); mask1 &= ((PtypeDirectionTraits::canMove ? mask_t::makeDirect(PtypeFuns::indexMask) : mask_t::makeDirect(0)) | (PtypeDirectionTraits::canMove ? mask_t::makeDirect(PtypeFuns::indexMask) : mask_t::makeDirect(0)) | (PtypeDirectionTraits::canMove ? mask_t::makeDirect(PtypeFuns::indexMask) : mask_t::makeDirect(0))); mask1 <<= 8; // 短ã„利ãを排除 mask1&=effectSetAt(to).getMask(1)& NumBitmapEffect::longEffectMask(); while (mask1.any()) { int num=mask1.takeOneBit()+NumBitmapEffect::longToNumOffset; Square from = pieceOf(num).square(); Direction dir=Board_Table.getLongDirection(Offset32(to,from)); if (dir==DirectionPlayerTraits::directionByBlack) return true; } return false; } /** * 対象ã¨ã™ã‚‹ãƒžã‚¹ã«ã‚るプレイヤーã®(ãŸã ã—ã‚る駒以外)利ããŒã‚ã‚‹ã‹ã©ã†ã‹. * @param player æ”»æ’ƒå´ * @param piece 攻撃å´ã®é§’ * @param target 対象ã®ãƒžã‚¹ */ bool hasEffectNotBy(Player player,Piece piece,Square target) const { assert(piece.owner()==player); PieceMask pieces_onboard=piecesOnBoard(player); int num=piece.number(); pieces_onboard.reset(num); return (pieces_onboard&effectSetAt(target)).any(); } /** * {pinã•れã¦ã„ã‚‹é§’, 玉以外}ã‹ã‚‰ã®åˆ©ããŒã‚ã‚‹. */ bool hasEffectByNotPinnedAndKing(Player pl,Square target) const{ assert(target.isOnBoard()); PieceMask m=piecesOnBoard(pl)& ~pinOrOpen(pl) & effectSetAt(target); m.clearBit(); return m.any(); } /** * pinã•れã¦ã„る駒以外ã‹ã‚‰ã®åˆ©ããŒã‚ã‚‹. */ bool hasEffectByNotPinned(Player pl,Square target) const{ assert(target.isOnBoard()); PieceMask m=piecesOnBoard(pl)& ~pinOrOpen(pl) & effectSetAt(target); return m.any(); } /** * 二ã¤ä»¥ä¸Šã®é§’ã‹ã‚‰åˆ©ããŒã‚ã‚‹. * ãã‚‚ãも利ããŒãªã„å ´åˆã‚‚呼ã°ã‚Œã‚‹ * @param player æ”»æ’ƒå´ * @param target 対象ã®ãƒžã‚¹ */ bool hasMultipleEffectAt(Player player,Square target) const { mask_t mask=effectSetAt(target).getMask(1); mask&=NumBitmapEffect::playerEffectMask(player); return NumBitmapEffect::playerEffect(player).getMask(1) < mask; } /** * é§’attack ㌠target ã«åˆ©ãã‚’æŒã¤ã‹ (æ—§hasEffectToã¨çµ±åˆ) * @param target 対象ã®ãƒžã‚¹ */ bool hasEffectByPiece(Piece attack, Square target) const { assert(attack.isPiece()); assert(target.isOnBoard()); return effectSetAt(target).test(attack.number()); } /** * attackerã«ptypeoã®é§’ãŒã„ã‚‹ã¨ä»®å®šã—ãŸå ´åˆã«targetã«åˆ©ããŒã‚ã‚‹ã‹ã©ã†ã‹ * ã‚’ stateã‚’updateã—ãªã„ã§ç¢ºã‹ã‚ã‚‹. * targetSquareã¯ç©ºç™½ã§ã‚‚良ㄠ* 盤上ã®é§’ã‚’å‹•ã‹ã™äº‹ã‚’検討ã—ã¦ã„ã‚‹ã¨ãã¯ã«ï¼Œ * 自分自身ã®é™°ã«å…¥ã£ã¦åˆ©ã‹ãªã„ã¨è¦‹ãªã•れるã“ã¨ãŒã‚ã‚‹ */ bool hasEffectIf(PtypeO ptypeo,Square attacker, Square target) const #ifdef __GNUC__ __attribute__ ((pure)) #endif { Offset32 offset32=Offset32(target,attacker); EffectContent effect=Ptype_Table.getEffect(ptypeo,offset32); if (! effect.hasEffect()) return false; if (effect.hasUnblockableEffect()) return true; assert(Board_Table.getShortOffset(offset32) == effect.offset()); return this->isEmptyBetween(attacker,target,effect.offset()); } /** * */ template bool #ifdef __GNUC__ __attribute__ ((pure)) #endif hasEffectByWithRemove(Square target,Square removed) const; bool hasEffectByWithRemove(Player player, Square target,Square removed) const{ if (player==BLACK) return hasEffectByWithRemove(target,removed); else return hasEffectByWithRemove(target,removed); } // ---------------------------------------------------------------------- // 3.3 pieceを探㙠// ---------------------------------------------------------------------- /** return a piece s.t. owner == attack, ptype == PTYPE, has effect on target. return Piece::EMPTY() otherwise */ template const Piece findAttackAt(Player attack, Square target) const { mask_t mask=allEffectAt(attack, target); if (mask.none()) return Piece::EMPTY(); return pieceOf(mask.takeOneBit()+PtypeFuns::indexNum*32); } template const Piece findAttackAtStrict(Player attack, Square target) const { mask_t mask=allEffectAt(attack, target); if (isPromoted(PTYPE)) mask &= promoted.getMask(); else mask &= ~(promoted.getMask()); if (mask.none()) return Piece::EMPTY(); return pieceOf(mask.takeOneBit()+PtypeFuns::indexNum*32); } /** * pieceã®dæ–¹å‘ã‹ã‚‰é•·ã„利ããŒã‚ã‚‹å ´åˆã«ãã®é§’ã‚’è¿”ã™ã€‚ * @param d piece ã‹ã‚‰ã¿ãŸå‘ã */ const Piece findLongAttackAt(Player owner, int piece, Direction d) const { assert(pieceOf(piece).isOnBoardByOwner(owner)); if (owner == BLACK) d = inverse(d); const int num = effects.effectedNumTable[piece][d]; if (num == EMPTY_NUM) return Piece::EMPTY(); return pieceOf(num); } const Piece findLongAttackAt(Player owner, Piece piece, Direction d) const { assert(piece.isPiece()); assert(piece.owner() == owner); return findLongAttackAt(owner, piece.number(), d); } const Piece findLongAttackAt(Piece piece, Direction d) const { assert(piece.isPiece()); return findLongAttackAt(piece.owner(), piece, d); } const Piece findLongAttackAt(Square square, Direction d) const { return findLongAttackAt(pieceOnBoard(square), d); } /** * 利ãã®ä¸­ã‹ã‚‰å®‰ãã†ãªé§’ã‚’é¸ã¶ */ const Piece selectCheapPiece(PieceMask effect) const; /** * @param P - 利ãã‚’ã¤ã‘ã¦ã„ã‚‹å´ã®ãƒ—レイヤ * @param square - 調査ã™ã‚‹å ´æ‰€ * @return 利ãを付ã‘ã¦ã„る中ã§å®‰ãã†ãªé§’ (複数ã®å ´åˆã§ã‚‚EMPTYã«ã¯ã—ãªã„) */ const Piece findCheapAttack(Player P, Square square) const { return selectCheapPiece(piecesOnBoard(P) & effectSetAt(square)); } /** * @param P - 利ãã‚’ã¤ã‘ã¦ã„ã‚‹å´ã®ãƒ—レイヤ * @param square - 調査ã™ã‚‹å ´æ‰€ * @return 利ãを付ã‘ã¦ã„る中ã§å®‰ãã†ãªé§’ (複数ã®å ´åˆã§ã‚‚EMPTYã«ã¯ã—ãªã„) */ const Piece findCheapAttackNotBy(Player P, Square square, const PieceMask& ignore) const { PieceMask pieces = piecesOnBoard(P); pieces &= ~ignore; return selectCheapPiece(pieces & effectSetAt(square)); } const Piece findAttackNotBy(Player P, Square square, const PieceMask& ignore) const { PieceMask pieces = piecesOnBoard(P); pieces &= ~ignore; pieces &= effectSetAt(square); if (pieces.none()) return Piece::EMPTY(); return pieceOf(pieces.takeOneBit()); } /** * 王手駒を探㙠* @return 王手ã‹ã©ã†ã‹ * @param attack_piece * 一ã¤ã®é§’ã«ã‚ˆã‚‹çŽ‹æ‰‹ã®å ´åˆã¯attck_pieceã«ãã®é§’を入れる * 複数ã®é§’ã«ã‚ˆã‚‹çŽ‹æ‰‹ã®å ´åˆã¯Piece::EMPTY()を入れる * @param P(template) 玉 */ template bool findCheckPiece(Piece& attack_piece) const { return hasEffectAt(kingSquare(P),attack_piece); } bool hasEffectAt(Player P, Square target,Piece& attackerPiece) const { if (P == BLACK) return hasEffectAt(target, attackerPiece); else return hasEffectAt(target, attackerPiece); } /** * @param P(template) - 利ãã‚’ã¤ã‘ã¦ã„ã‚‹å´ã®ãƒ—レイヤ * @param target - 利ãã‚’ã¤ã‘られãŸå ´æ‰€ * @param attackerPiece - multiple attackã®å ´åˆã¯Piece::EMPTY() * ãã†ã§ãªã„ãªã‚‰åˆ©ãã‚’ã¤ã‘ã¦ã„る駒を返㙠*/ template bool hasEffectAt(Square target,Piece& attackerPiece) const { attackerPiece=Piece::EMPTY(); const PieceMask& pieceMask=piecesOnBoard(P)&effectSetAt(target); mask_t mask=pieceMask.getMask(0); if (mask.none()) return false; /** * mask|=0x8000000000000000ll; * if((mask&(mask-1))!=0x8000000000000000ll) ãªã‚‰1ã¤ã®ifæ–‡ã§æ¸ˆã‚€ */ if (mask.hasMultipleBit()) return true; int num=mask.bsf(); attackerPiece=pieceOf(num); return true; } // ---------------------------------------------------------------------- // 4. æŒ‡æ‰‹ã®æ¤œæŸ»ãƒ»ç”Ÿæˆãƒ»é©ç”¨ // ---------------------------------------------------------------------- // --- 2014/03 bool isSafeMove(Move move) const; bool isCheck(Move move) const; bool isPawnDropCheckmate(Move move) const; bool isDirectCheck(Move move) const; bool isOpenCheck(Move move) const; // --- /** * åˆæ³•手ã‹ã©ã†ã‹ã‚’ç°¡å˜ã«æ¤œæŸ»ã™ã‚‹ï¼Žå±€é¢ã«ä¾å­˜ã™ã‚‹ãƒã‚§ãƒƒã‚¯ã®ã¿ï¼Ž * ルール上指ã›ãªã„手ã§ã‚ã‚‹å¯èƒ½æ€§ãŒã‚ã‚‹å ´åˆã¯ï¼ŒisValidMove を用ã„る. * * Pã‚’template引数ã«ã§ãã‚‹ã¨å°‘ã—ã¯é€Ÿããªã‚Šãㆠ* å±€é¢ã«ä¾å­˜ã™ã‚‹æ¤œæŸ»ã§ã‚‚,玉ã®ç´ æŠœãや王手を防ã„ã§ã„ã‚‹ã‹ï¼Œ * åƒæ—¥æ‰‹ï¼Œæ‰“æ­©è©°ã‹ã©ã†ã‹ã¯æ¤œæŸ»ã—ãªã„. * @param showError(template) - falseã‚’è¿”ã™æ™‚ã«ã¯ä½•ã‹è¡¨ç¤ºã™ã‚‹. * @param move - 手 */ template bool isAlmostValidMove(Move move) const; bool isAlmostValidMove(Move move,bool show_error=true) const; /** * å…¨ã¦ã®åˆæ³•手を生æˆã™ã‚‹. 玉ã®ç´ æŠœãや打歩詰ã®ç¢ºèªã‚’ã™ã‚‹ï¼Ž * ãŸã ã—, 打歩詰ã‚絡ã¿ä»¥å¤–ã§ã¯æœ‰åˆ©ã«ã¯ãªã‚‰ãªã„手 * (Move::ignoredUnpromote)ã¯ç”Ÿæˆã—ãªã„. */ void generateLegal(MoveVector&) const; /** * 打歩詰ã‚絡ã¿ä»¥å¤–ã§ã¯æœ‰åˆ©ã«ã¯ãªã‚‰ãªã„手もå«ã‚, å…¨ã¦ã®åˆæ³•手を生æˆã™ * る(Move::ignoredUnpromoteも生æˆã™ã‚‹ï¼‰. 玉ã®ç´ æŠœãや打歩詰ã®ç¢ºèª * ã‚’ã™ã‚‹ï¼Ž */ void generateWithFullUnpromotions(MoveVector&) const; /** 自殺をå«ã‚ã¦ã™ã¹ã¦ã®æ‰‹ã‚’ç”Ÿæˆ */ void generateAllUnsafe(MoveVector&) const; void makeMove(Move move); void makeMovePass() { changeTurn(); effects.clearChangedEffects(); effects.clearEffectedChanged(); } template void makeUnmakePass(Function &f) { changeTurn(); f(Square::STAND()); changeTurn(); } template void makeUnmakeMove(Move move, Function &f) { if (move.player() == BLACK) makeUnmakeMove(Player2Type(), move, f); else makeUnmakeMove(Player2Type(), move, f); } template void makeUnmakeMove(Player2Type

player, Move move, Function &f) { if (move.isPass()) return makeUnmakePass(f); assert(move.isValid()); assert(isAlmostValidMove(move)); assert(P == move.player()); assert(P == turn()); Square from=move.from(); Square to=move.to(); if (from.isPieceStand()) { assert(pieceAt(to) == Piece::EMPTY()); doUndoDropMove(player,to,move.ptype(),f); } else { assert(pieceAt(from) != Piece::EMPTY()); Piece captured=pieceAt(to); if (captured != Piece::EMPTY()) { doUndoCaptureMove(player,from,to,captured,move.promoteMask(),f); } else { doUndoSimpleMove(player,from,to,move.promoteMask(),f); } } } bool wasCheckEvasion(Move last_move) const; // ---------------------------------------------------------------------- // 5. forEachXXX // ---------------------------------------------------------------------- /** T 㯠isBasic ã§ãªãã¦ã‚‚å‹•ã㌠unpromote(T) ã®çµæžœã¨åŒã˜. */ template void forEachOnBoard(F& func) const { mask_t onMask=piecesOnBoard(P).template selectBit() ; while (onMask.any()) { int num=onMask.takeOneBit()+((PtypeFuns::indexNum)<<5); Piece p = pieceOf(num); func(p); } } /** T ã®æˆä¸æˆã‚’区別 */ template void forEachOnBoardPtypeStrict(F& func) const { mask_t mask=piecesOnBoard(P).template selectBit() ; if (isPromoted(T)) mask &= promoted.getMask(); else mask &= ~(promoted.getMask()); while (mask.any()) { int num=mask.takeOneBit()+((PtypeFuns::indexNum)<<5); func(pieceOf(num)); } } private: template void forEachEffect(const PieceMask& pieces, Square sq,Action & action) const { #if OSL_WORDSIZE == 64 mask_t mask=pieces.getMask(0); while (mask.any()) { const int num=mask.takeOneBit(); action.template doAction

(pieceOf(num),sq); } #elif OSL_WORDSIZE == 32 mask_t mask0=pieces.getMask(0); while (mask0.any()) { const int num=mask0.takeOneBit(); action.template doAction

(pieceOf(num),sq); } mask_t mask1=pieces.getMask(1); while (mask1.any()) { const int num=mask1.takeOneBit()+32; action.template doAction

(pieceOf(num),sq); } #endif } public: /** * sq ã¸ã®åˆ©ãã‚’æŒã¤å„é§’ã«é–¢ã—ã¦å‡¦ç†ã‚’行ã†. * @param action ãŸã¨ãˆã° AlwaysMoveAction */ template void forEachEffect(Square sq,Action & action) const { const PieceMask pieceMask=piecesOnBoard(P)&effectSetAt(sq); forEachEffect(pieceMask, sq, action); } /** * sq ã«ã‚ã‚‹é§’ã‚’å–ã‚‹ move を生æˆã—㦠action ã® member を呼ã³å‡ºã™. * @param pin 無視ã™ã‚‹é§’ * @param action ãŸã¨ãˆã° AlwaysMoveAction */ template void forEachEffect(Square sq,Action & action,const PieceMask& pin) const { PieceMask pieceMask=piecesOnBoard(P)&effectSetAt(sq); pieceMask &= ~pin; forEachEffect(pieceMask, sq, action); } /** * sq ã«ç§»å‹•ã™ã‚‹ move を生æˆã—㦠action ã® member を呼ã³å‡ºã™ * @param action ãŸã¨ãˆã° AlwayMoveAction * @param piece ã“れ以外ã®é§’を使ㆠ*/ template void forEachEffectNotBy(Square sq,Piece piece,Action & action) const { PieceMask pieces=piecesOnBoard(P)&effectSetAt(sq); pieces.reset(piece.number()); forEachEffect(pieces, sq, action); } private: template void forEachEffectOfPieceDir(Square, Action&, Int2Type) const {} template void forEachEffectOfPieceDir(Square pieceSquare,Action & action,Int2Type) const { const Offset offset=DirectionPlayerTraits::offset(); action.template doAction

(this->pieceAt(pieceSquare),pieceSquare+offset); } template void forEachEffectOfPieceDir(Square pieceSquare,Action & action) const { forEachEffectOfPieceDir(pieceSquare,action,Int2Type<(PtypeTraits::moveMask & DirectionTraits

::mask)!=0>()); } template void forEachEffectOfPieceLongDir(Square, Action&, Int2Type) const {} template void forEachEffectOfPieceLongDir(Square pieceSquare,Action & action,Int2Type) const { Piece piece=this->pieceAt(pieceSquare); const Offset offset=DirectionPlayerTraits::offset(); assert(offset.intValue() != 35); Square sq=pieceSquare+offset; for (;this->pieceAt(sq).isEmpty();sq+=offset) action.template doAction

(piece,sq); action.template doAction

(piece,sq); } template void forEachEffectOfPieceLongDir(Square pieceSquare,Action & action) const { forEachEffectOfPieceLongDir(pieceSquare,action,Int2Type<(PtypeTraits::moveMask & DirectionTraits

::mask)!=0>()); } public: /** * pieceSquareã«ã‚ã‚‹é§’ã«ã‚ˆã£ã¦åˆ©ãã‚’å—ã‘ã‚‹ã™ã¹ã¦ã®square * (空白å«ã‚€)ã«ã¤ã„㦠* actionを実行ã™ã‚‹ * * SimpleState より移æ¤: ImmediateAddSupportãŒãªã‘ã‚Œã°æ¶ˆã›ã‚‹ */ template void forEachEffectOfPiece(Square pieceSquare,Action & action) const; template void forEachEffectOfPiece(Piece piece,Action & action) const; /** * PtypeO ㌠Square ã«ã„ã‚‹ã¨ä»®å®šã—ãŸæ™‚ã«ã®åˆ©ãを列挙. * 盤é¢ãŒå®Ÿéš›ã¨é•ã†ã¨é•·ã„利ããŒä¸æ­£ç¢ºã«ãªã‚‹ * @param InterestEmpty 空白ã®ãƒžã‚¹ã«èˆˆå‘³ãŒã‚ã‚‹ã‹ */ template void forEachEffectOfPtypeO(Square, PtypeO, Function& f) const; template void forEachEffectOfPtypeO(Square, Ptype, Function& f) const; /** * 玉ã®ç´ æŠœããªã—ã«åˆæ³•手ã§targetã«ç§»å‹•å¯èƒ½ã‹ã‚’判定 * @param king 玉 (玉ã§å–る手ã¯è€ƒãˆãªã„) * @return 移動å¯èƒ½ãªé§’ãŒã‚れã°ï¼Œå®‰å…¨ãªé§’を一ã¤ï¼Žãªã‘れ㰠Piece::EMPTY() * @see osl::move_classifier::PawnDropCheckmate */ template Piece safeCaptureNotByKing(Square target, Piece king) const; Piece safeCaptureNotByKing(Player P, Square target) const { const Piece king = kingPiece(P); if (P == BLACK) return this->safeCaptureNotByKing(target, king); else return this->safeCaptureNotByKing(target, king); } /** * forEachEffect ã® Player ã®template 引数を通常ã®å¼•æ•°ã«ã—ãŸãƒãƒ¼ã‚¸ãƒ§ãƒ³ * @param P 探ã™å¯¾è±¡ã®é§’ã®æ‰€æœ‰è€… * @param pos ã«åˆ©ãã®ã‚る駒を探㙠*/ template void forEachEffect(Player P, Square pos, Action& a) const { if (P == BLACK) this->template forEachEffect(pos,a); else this->template forEachEffect(pos,a); } /** * target ã«åˆ©ãã®ã‚ã‚‹Pieceã‚’outã«æ ¼ç´ã™ã‚‹ */ void findEffect(Player P, Square target, PieceVector& out) const; private: void doSimpleMove(Square from, Square to, int promoteMask); void doDropMove(Square to,Ptype ptype); void doCaptureMove(Square from, Square to, Piece target,int promoteMask); template void doUndoSimpleMove(Player2Type

player, Square from, Square to, int promoteMask,Function& func); template void prologueSimple(Player2Type

, Square from, Square to, int promoteMask, Piece& oldPiece, int& num, PtypeO& oldPtypeO, PtypeO& new_ptypeo, CArray& pin_or_open_backup, KingMobility& king_mobility_backup, PieceMask& promoted_backup, CArray& effected_mask_backup, CArray& effected_changed_mask_backup, CArray& king8infos_backup, MobilityTable &mobility_backup ); void epilogueSimple(Square from, Square to, Piece oldPiece, int num, PtypeO oldPtypeO, PtypeO newPtypeO, const CArray& pin_or_open_backup, const KingMobility& king_mobility_backup, const PieceMask& promoted_backup, const CArray& effected_mask_backup, const CArray& effected_changed_mask_backup, const CArray& king8infos_backup, const MobilityTable &mobility_backup ); template void doUndoDropMove(Player2Type

player, Square to, Ptype ptype, Function& func); template void prologueDrop(Player2Type

, Square to, Ptype ptype, Piece& oldPiece, int& num, PtypeO& ptypeO, int& numIndex, mask_t& numMask, CArray& pin_or_open_backup, KingMobility& king_mobility_backup, CArray& effected_mask_backup, CArray& effected_changed_mask_backup, CArray& king8infos_backup, MobilityTable &mobility_backup); template void epilogueDrop(Player2Type

, Square to, Ptype ptype, Piece oldPiece, int num, PtypeO ptypeO, int numIndex, mask_t numMask, const CArray& pin_or_open_backup, const KingMobility& king_mobility_backup, const CArray& effected_mask_backup, const CArray& effected_changed_mask_backup, const CArray& king8infos_backup, const MobilityTable &mobility_backup); template void doUndoCaptureMove(Player2Type

player, Square from,Square to, Piece target, int promoteMask,Function& func); template void prologueCapture(Player2Type

, Square from, Square to, Piece target, int promoteMask, Piece& oldPiece, PtypeO& oldPtypeO, PtypeO& capturePtypeO, PtypeO& new_ptypeo, int& num0, int& num1, int& num1Index, mask_t& num1Mask, CArray& pin_or_open_backup, KingMobility& king_mobility_backup, PieceMask& promoted_backup, CArray& effected_mask_backup, CArray& effected_changed_mask_backup, CArray& king8infos_backup, MobilityTable &mobility_backup); template void epilogueCapture(Player2Type

, Square from, Square to, Piece target, Piece oldPiece, PtypeO oldPtypeO, PtypeO capturePtypeO, PtypeO newPtypeO, int num0, int num1, int num1Index, mask_t num1Mask, const CArray& pin_or_open_backup, const KingMobility& king_mobility_backup, const PieceMask& promoted_backup, const CArray& effected_mask_backup, const CArray& effected_changed_mask_backup, const CArray& king8infos_backup, const MobilityTable &mobility_backup); // template void makePinOpenDir(Square target, PieceMask& pins, PieceMask const& onBoard,Player defense) { const Offset offset = DirectionTraits

::blackOffset(); Square sq=target-offset; int num; while(Piece::isEmptyNum(num=pieceAt(sq).number())) sq-=offset; king_mobility[defense][DIR]=static_cast(sq.uintValue()); if(Piece::isEdgeNum(num)) return; int num1=longEffectNumTable()[num][DIR]; if(Piece::isPieceNum(num1) && onBoard.test(num1)){ pins.set(num); } } void recalcPinOpen(Square changed, Direction &lastDir, Player defense) { Square target=kingSquare(defense); #ifdef ALLOW_KING_ABSENCE if (target.isPieceStand()) return; #endif const Direction longD=Board_Table.getLongDirection(changed,target); if(!isLong(longD) || (lastDir!=UL && longD==lastDir)) return; lastDir=longD; Direction shortD=longToShort(longD); { // reset old pins Square oldPos=Square::makeDirect(king_mobility[defense][shortD]); int oldNum=pieceAt(oldPos).number(); if(Piece::isPieceNum(oldNum)) pin_or_open[defense].reset(oldNum); } const Offset offset = Board_Table.getOffsetForBlack(longD); Square sq=target-offset; int num; while(Piece::isEmptyNum(num=pieceAt(sq).number())) sq-=offset; king_mobility[defense][shortD]=static_cast(sq.uintValue()); if(Piece::isEdgeNum(num)) return; int num1=longEffectNumTable()[num][shortD]; if(Piece::isPieceNum(num1) && piecesOnBoard(alt(defense)).test(num1)){ pin_or_open[defense].set(num); } } PieceMask makePinOpen(Square target,Player defense); void makePinOpen(Player defense); template void makeKing8Info(); }; inline bool operator!=(const NumEffectState& s1, const NumEffectState& s2) { return !(s1==s2); } } // namespace osl template void osl::NumEffectState:: doUndoSimpleMove(Player2Type

player, Square from, Square to, int promoteMask, Function& func) { Piece oldPiece; int num; PtypeO oldPtypeO, newPtypeO; CArray pin_or_open_backup; KingMobility king_mobility_backup; PieceMask promoted_backup; CArray effected_mask_backup; CArray effected_changed_mask_backup; CArray king8infos_backup; MobilityTable mobility_backup; prologueSimple(player, from, to, promoteMask, oldPiece, num, oldPtypeO, newPtypeO, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup, king8infos_backup, mobility_backup); if (promoteMask!=0 && num < PtypeTraits::indexLimit) { clearPawn(P,from); changeTurn(); func(to); changeTurn(); setPawn(P,from); } else { changeTurn(); func(to); changeTurn(); } epilogueSimple(from, to, oldPiece, num, oldPtypeO, newPtypeO, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup, king8infos_backup, mobility_backup); } template void osl::NumEffectState::doUndoDropMove(Player2Type

player, Square to, Ptype ptype, Function& func) { Piece oldPiece; PtypeO ptypeO; int num, numIndex; mask_t numMask; CArray pin_or_open_backup; KingMobility king_mobility_backup; CArray effected_mask_backup; CArray effected_changed_mask_backup; CArray king8infos_backup; MobilityTable mobility_backup; prologueDrop(player, to, ptype, oldPiece, num, ptypeO, numIndex, numMask, pin_or_open_backup, king_mobility_backup, effected_mask_backup,effected_changed_mask_backup, king8infos_backup, mobility_backup); if (ptype==PAWN) { setPawn(P,to); changeTurn(); func(to); changeTurn(); clearPawn(P,to); } else { changeTurn(); func(to); changeTurn(); } epilogueDrop(player, to, ptype, oldPiece, num, ptypeO, numIndex, numMask, pin_or_open_backup, king_mobility_backup, effected_mask_backup,effected_changed_mask_backup, king8infos_backup, mobility_backup); } template void osl::NumEffectState::doUndoCaptureMove(Player2Type

player, Square from,Square to, Piece target, int promoteMask,Function& func) { Piece oldPiece; PtypeO oldPtypeO, capturePtypeO, newPtypeO; int num0, num1, num1Index; mask_t num1Mask; CArray pin_or_open_backup; KingMobility king_mobility_backup; PieceMask promoted_backup; CArray effected_mask_backup; CArray effected_changed_mask_backup; CArray king8infos_backup; MobilityTable mobility_backup; prologueCapture(player, from, to, target, promoteMask, oldPiece, oldPtypeO, capturePtypeO, newPtypeO, num0, num1, num1Index,num1Mask, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup, king8infos_backup, mobility_backup); changeTurn(); const Ptype capturePtype=target.ptype(); if (capturePtype==PAWN) { clearPawn(alt(P),to); if (promoteMask!=0 && num0::indexLimit) { clearPawn(P,from); func(to); setPawn(P,from); } else { func(to); } setPawn(alt(P),to); } else if (promoteMask!=0 && num0::indexLimit) { clearPawn(P,from); func(to); setPawn(P,from); } else { func(to); } changeTurn(); epilogueCapture(player, from, to, target, oldPiece, oldPtypeO, capturePtypeO, newPtypeO, num0, num1, num1Index,num1Mask, pin_or_open_backup, king_mobility_backup, promoted_backup,effected_mask_backup, effected_changed_mask_backup, king8infos_backup, mobility_backup); } template void osl::NumEffectState:: forEachEffectOfPiece(Piece piece,Action & action) const { Square pieceSquare = piece.square(); switch ((int)piece.ptypeO()) { case NEW_PTYPEO(WHITE,PAWN): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,LANCE): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,KNIGHT): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,SILVER): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,PPAWN): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,PLANCE): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,PKNIGHT): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,PSILVER): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,GOLD): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,BISHOP): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,PBISHOP): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,ROOK): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,PROOK): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(WHITE,KING): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PAWN): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,LANCE): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,KNIGHT): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,SILVER): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PPAWN): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PLANCE): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PKNIGHT): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PSILVER): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,GOLD): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,BISHOP): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PBISHOP): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,ROOK): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,PROOK): forEachEffectOfPiece(pieceSquare,action); break; case NEW_PTYPEO(BLACK,KING): forEachEffectOfPiece(pieceSquare,action); break; default: assert(0); } } template void osl::NumEffectState:: forEachEffectOfPiece(Square pieceSquare,Action & action) const { forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); forEachEffectOfPieceLongDir(pieceSquare,action); } #include "osl/bits/pieceStand.h" #endif /* OSL_NUM_EFFECT_STATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/simpleState.tcc0000644000000000000000000000504512316770314017162 0ustar rootroot/* simpleState.tcc */ #ifndef OSL_SIMPLE_STATE_TCC #define OSL_SIMPLE_STATE_TCC #include "osl/simpleState.h" #include template bool osl::SimpleState::isAlmostValidDrop(Move move) const { assert(move.from().isPieceStand()); const Square to=move.to(); const Piece to_piece=pieceAt(to); const Ptype ptype=move.ptype(); const Player turn = move.player(); // ターゲットãŒç©ºç™½ã‹ if (! to_piece.isEmpty()) { if (show_error) std::cerr << "drop on to piece : " << move << std::endl; return false; } // ãã‚‚ãã‚‚ãã®é§’ã‚’æŒã£ã¦ã„ã‚‹ã‹? if (! hasPieceOnStand(turn,ptype)) { if (show_error) std::cerr << turn << " don't have : " << ptype << std::endl; return false; } // 二歩ã®ãƒã‚§ãƒƒã‚¯ if (ptype==PAWN && isPawnMaskSet(turn, to.x())) { if (show_error) std::cerr << " Double Pawn : " << move << std::endl; return false; } return true; } template bool osl::SimpleState::testValidityOtherThanEffect(Move move) const { const Square from=move.from(); const Piece from_piece = pieceAt(from); const Square to=move.to(); const Piece to_piece=pieceAt(to); // fromã«ã‚ã‚‹ã®ãŒãã®é§’ã‹ if (from_piece.isEmpty() || (from_piece.owner() != turn())) { if (show_error) std::cerr << " No such piece0 : " << move << std::endl; return false; } // promoteã—ã¦ã„る時ã«promoteå¯èƒ½ã‹ if (move.isPromotion()) { // fromã«ã‚ã‚‹ã®ãŒãã®é§’ã‹ if (from_piece.ptype() != unpromote(move.ptype())) { if (show_error) std::cerr << " No such piece1 : " << move << std::endl; return false; } if (from_piece.isPromotedNotKingGold()) { if (show_error) std::cerr << " can't promote promoted piece : " << move << std::endl; return false; } } else { // fromã«ã‚ã‚‹ã®ãŒãã®é§’ã‹ if (from_piece.ptype() != move.ptype()) { if (show_error) std::cerr << " No such piece2 : " << move << std::endl; return false; } } // toã«ã‚ã‚‹ã®ãŒï¼Œç›¸æ‰‹ã®é§’ã‹ç©ºç™½ã‹? if (!to_piece.isEmpty() && to_piece.owner()==turn()) { if (show_error) std::cerr << " No move on : " << move << std::endl; return false; } // capturePtypeãŒä¸€è‡´ã—ã¦ã„ã‚‹ã‹? if (to_piece.ptype()!=move.capturePtype()) { if (show_error) std::cerr << " Not such capture : " << move << std::endl << *this; return false; } return true; } #endif /* _SIMPLE_STATE_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/usi.cc0000644000000000000000000002077712316770314015315 0ustar rootroot/* usi.cc */ #include "osl/usi.h" #include #include #include const std::string osl::psn:: show(Square pos) { const int x = pos.x(); const int y = pos.y(); std::string result = "XX"; result[0] = x + '0'; result[1] = y + 'a' - 1; return result; } char osl::psn:: show(Ptype ptype) { switch (ptype) { case PAWN: return 'P'; case LANCE: return 'L'; case KNIGHT: return 'N'; case SILVER: return 'S'; case GOLD: return 'G'; case BISHOP: return 'B'; case ROOK: return 'R'; case KING: return 'K'; default: assert("unsupported ptype" == 0); return '!'; } } const std::string osl::psn:: show(Move m) { const Square from = m.from(); const Square to = m.to(); if (from.isPieceStand()) { std::string result = "X*"; result[0] = show(m.ptype()); result += show(to); return result; } std::string result = show(from); result += show(to); if (m.promoteMask()) result += '+'; return result; } const std::string osl::psn:: showXP(Move m) { if (m.isInvalid()) return "resign"; if (m.isPass()) return "pass"; const Square from = m.from(); const Square to = m.to(); if (from.isPieceStand()) { std::string result = "X*"; result[0] = show(m.ptype()); result += show(to); return result; } std::string result = show(from); if (m.capturePtype() != PTYPE_EMPTY) result += 'x'; result += show(to); if (m.isPromotion()) result += '+'; else if (canPromote(m.ptype()) && (from.canPromote(m.player()) || to.canPromote(m.player()))) result += '='; return result; } const osl::Move osl::psn:: strToMove(const std::string& str, const SimpleState& s) { if (str.size() < 4) throw ParseError("Invalid move string: " + str); const Square to = strToPos(str.substr(2,2)); if (str[1] == '*') { const Ptype ptype = charToPtype(str[0]); return Move(to, ptype, s.turn()); } const Square from = strToPos(str.substr(0,2)); const Ptype ptype = s.pieceOnBoard(from).ptype(); const Ptype captured = s.pieceOnBoard(to).ptype(); if (! isPiece(ptype)) throw ParseError("No piece on square: " + str); bool promotion = false; if (str.size() > 4) { assert(str[4] == '+'); promotion = true; } return Move(from, to, (promotion ? promote(ptype) : ptype), captured, promotion, s.turn()); } const osl::Square osl::psn:: strToPos(const std::string& str) { assert(str.size() == 2); const int x = str[0] - '0'; const int y = str[1] - 'a' + 1; if (x <= 0 || x > 9 || y <= 0 || y > 9) throw ParseError("Invalid square character: " + str); return Square(x, y); } osl::Ptype osl::psn:: charToPtype(char c) { switch (c) { case 'P': return PAWN; case 'L': return LANCE; case 'N': return KNIGHT; case 'S': return SILVER; case 'G': return GOLD; case 'B': return BISHOP; case 'R': return ROOK; case 'K': return KING; default: return PTYPE_EMPTY; } } /* ------------------------------------------------------------------------- */ const std::string osl::usi:: show(Move m) { if (m.isPass()) return "pass"; if (m == Move::DeclareWin()) return "win"; if (! m.isNormal()) return "resign"; return psn::show(m); } const std::string osl::usi:: show(PtypeO ptypeo) { if (! isPiece(ptypeo)) return ""; char c = psn::show(unpromote(getPtype(ptypeo))); if (getOwner(ptypeo) == WHITE) c = tolower(c); std::string ret(1,c); if (isPromoted(ptypeo)) ret = "+" + ret; return ret; } const std::string osl::usi:: show(Piece p) { return show(p.ptypeO()); } const std::string osl::usi:: show(const NumEffectState& state) { std::ostringstream ret; if (state == SimpleState(HIRATE)) { ret << "startpos"; return ret.str(); } ret << "sfen "; for (int y=1; y<=9; ++y) { int empty_count = 0; for (int x=9; x>=1; --x) { const Piece p = state.pieceOnBoard(Square(x,y)); if (p.isEmpty()) { ++empty_count; continue; } if (empty_count) { ret << empty_count; empty_count = 0; } ret << show(p); } if (empty_count) ret << empty_count; if (y < 9) ret << "/"; } ret << " " << "bw"[state.turn() == WHITE] << " "; bool has_any = false; for (int z=0; z<2; ++z) { const Player player = indexToPlayer(z); for (Ptype ptype: PieceStand::order) { const int count = state.countPiecesOnStand(player, ptype); if (count == 0) continue; if (count > 1) ret << count; ret << show(newPtypeO(player, ptype)); has_any = true; } } if (! has_any) ret << "-"; ret << " 1"; return ret.str(); } const osl::Move osl::usi:: strToMove(const std::string& str, const NumEffectState& s) { if (str == "win") return Move::DeclareWin(); if (str == "pass") return Move::PASS(s.turn()); if (str == "resign") return Move::INVALID(); try { return psn::strToMove(str, s); } catch (std::exception& e) { throw ParseError("usi::strToMove failed for " + str + " by "+ e.what()); } catch (...) { throw ParseError("usi::strToMove failed for " + str); } } osl::PtypeO osl::usi:: charToPtypeO(char c) { const Ptype ptype = psn::charToPtype(toupper(c)); if (ptype == PTYPE_EMPTY) throw ParseError("Invalid piece character: " + std::string(1,c)); const Player pl = isupper(c) ? BLACK : WHITE; return newPtypeO(pl, ptype); } void osl::usi::parseBoard(const std::string& word, NumEffectState& out) { if (word.empty()) throw ParseError(word); SimpleState state; state.init(); int x=9, y=1; for (size_t i=0; i= word.size() ) throw ParseError(word); const char next = word[i+1]; if (!isalpha(next)) throw ParseError(word); const PtypeO ptypeo = charToPtypeO(next); if (!canPromote(ptypeo)) throw ParseError(word); const PtypeO promoted = promote(ptypeo); state.setPiece(getOwner(promoted), Square(x,y), getPtype(promoted)); --x; ++i; } else if (c == '/') { if (x != 0) throw ParseError(word); x = 9; ++y; } else if (isdigit(c)) { const int n = c - '0'; if (n == 0) throw ParseError(word); x -= n; } else { throw ParseError("usi: unknown input " + std::string(1,c)); } if (x < 0 || x > 9 || y < 0 || y > 9) throw ParseError(word); } out = NumEffectState(state); } void osl::usi::parse(const std::string& line, NumEffectState& state) { NumEffectState board; std::vector moves; parse(line, board, moves); state.copyFrom(board); for (Move move: moves) { state.makeMove(move); } } osl::NumEffectState osl::usi::makeState(const std::string& line){ NumEffectState state; parse(line,state); return state; } void osl::usi::parse(const std::string& line, NumEffectState& state, std::vector& moves) { moves.clear(); std::istringstream is(line); std::string word; is >> word; if (word == "position") is >> word; if (word == "startpos") state.init(HIRATE); else { if (word != "sfen") throw ParseError("sfen not found "+word); is >> word; parseBoard(word, state); is >> word; if (word != "b" && word != "w") throw ParseError(" turn error "+word); state.setTurn((word == "b") ? BLACK : WHITE); is >> word; if (word != "-") { int prefix = 0; for (char c: word) { if (isalpha(c)) { PtypeO ptypeo = charToPtypeO(c); for (int j=0; j> move_number)) return; assert(is); } if (! (is >> word)) return; if (word != "moves") throw ParseError("moves not found "+word); NumEffectState state_copy(state); while (is >> word) { Move m = strToMove(word, state_copy); moves.push_back(m); if (! m.isNormal() || ! state_copy.isValidMove(m)) throw ParseError("invalid move "+word); state_copy.makeMove(m); } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/0000755000000000000000000000000012316770314016115 5ustar rootrootlibosl-0.8.0.orig/core/osl/checkmate/immediateCheckmateTable.cc0000644000000000000000000000741212316770314023143 0ustar rootroot/* immediateCheckmateTable.cc */ #include "osl/checkmate/immediateCheckmateTable.h" #include "osl/bits/boardTable.h" #include "osl/bits/ptypeTable.h" namespace { bool canCheckmate(osl::Ptype ptype,osl::Direction dir,unsigned int mask) { // 王ã¯dropã§ããªã„, æ‰“ã¡æ­©è©°ã‚ if(ptype==osl::KING || ptype==osl::PAWN) return false; // ptypeãŒdiræ–¹å‘ã«åˆ©ãã‚’æŒãŸãªã„ == 王手をã‹ã‘られãªã„ if(!(osl::Ptype_Table.getMoveMask(ptype)& (osl::dirToMask(dir) | osl::dirToMask(osl::shortToLong(dir))))) return false; int dx=osl::Board_Table.getDxForBlack(dir); int dy=osl::Board_Table.getDyForBlack(dir); for(int l=0;l<8;l++){ if((mask&(1<(l); int dx1=osl::Board_Table.getDxForBlack(dir1); int dy1=osl::Board_Table.getDyForBlack(dir1); osl::Offset32 o32(dx-dx1,dy-dy1); if(!osl::Ptype_Table.getEffect(osl::newPtypeO(osl::BLACK,ptype),o32).hasEffect()) return false; } return true; } } osl::checkmate::ImmediateCheckmateTable::ImmediateCheckmateTable() { // ptypeDropMaskã®åˆæœŸåŒ– for(int i=0;i<0x100;i++){ for(int k=PTYPE_BASIC_MIN;k<=PTYPE_MAX;k++){ unsigned char mask=0; Ptype ptype=static_cast(k); for(int j=0;j<8;j++){ // 玉ã®é€ƒã’é“ãŒã‚ã‚‹ if((i&(0x1<(j); if(canCheckmate(ptype,dir,i)) mask|=(1<(k); for(int j=0;j<8;j++){ // 空白ã§ãªã„ if((i&(0x1<(j); if(canCheckmate(ptype,dir,(i>>8)&0xff)){ ptypeMask|=1u<<(k-PTYPE_BASIC_MIN); goto nextPtype; } } nextPtype:; } dropPtypeMasks[i]=ptypeMask; } // blockingMaskã®åˆæœŸåŒ– for(int k=PTYPE_BASIC_MIN;k<=PTYPE_MAX;k++){ Ptype ptype=static_cast(k); for(int j=0;j<8;j++){ unsigned int mask=0; Direction dir=static_cast(j); if(Ptype_Table.getMoveMask(ptype)& (dirToMask(dir) | dirToMask(shortToLong(dir)))){ int dx=Board_Table.getDxForBlack(dir); int dy=Board_Table.getDyForBlack(dir); for(int l=0;l<8;l++){ Direction dir1=static_cast(l); int dx1=Board_Table.getDxForBlack(dir1); int dy1=Board_Table.getDyForBlack(dir1); Offset32 o32(dx-dx1,dy-dy1); if(!Ptype_Table.getEffect(newPtypeO(BLACK,ptype),o32).hasEffect()){ if(!Board_Table.getShortOffsetNotKnight(o32).zero() && !(dx==-dx1 && dy==-dy1) ){ mask|=1<(k); for(int j=0;j<8;j++){ unsigned int mask=0x1ff; Direction dir=static_cast(j); if(Ptype_Table.getMoveMask(ptype)& (dirToMask(dir) | dirToMask(shortToLong(dir)))){ // 王手をã‹ã‘られる mask=0; int dx=Board_Table.getDxForBlack(dir); int dy=Board_Table.getDyForBlack(dir); for(int l=0;l<8;l++){ Direction dir1=static_cast(l); int dx1=Board_Table.getDxForBlack(dir1); int dy1=Board_Table.getDyForBlack(dir1); Offset32 o32(dx-dx1,dy-dy1); if(dir!= dir1 && !Ptype_Table.getEffect(newPtypeO(BLACK,ptype),o32).hasEffect()){ mask|=1<(NumEffectState const&, King8Info, Square, Move&); template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const&, King8Info, Square, Move&); template bool ImmediateCheckmate:: hasCheckmateMove(NumEffectState const&, Move&); template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const&, Move&); template bool ImmediateCheckmate:: hasCheckmateMove(NumEffectState const&); template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const&); } } bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(Player pl,NumEffectState const& state) { if(pl==BLACK) return hasCheckmateMove(state); else return hasCheckmateMove(state); } bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(Player pl,NumEffectState const& state,Move& bestMove) { if(pl==BLACK) return hasCheckmateMove(state,bestMove); else return hasCheckmateMove(state,bestMove); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/proofDisproof.cc0000644000000000000000000000205112316770314021255 0ustar rootroot#include "osl/checkmate/proofDisproof.h" #include void osl::checkmate:: ProofDisproof::testConsistency() { static_assert((ProofDisproof::BigProofNumber > ProofDisproof::PAWN_CHECK_MATE_PROOF),""); static_assert((ProofDisproof::NO_CHECK_MATE_PROOF > ProofDisproof::PAWN_CHECK_MATE_PROOF),""); } std::ostream& osl::checkmate:: operator<<(std::ostream& os, const ProofDisproof& pdp) { if (pdp == ProofDisproof::Checkmate()) os << "Checkmate"; else if (pdp == ProofDisproof::NoEscape()) os << "NoEscape"; else if (pdp == ProofDisproof::NoCheckmate()) os << "NoCheckmate"; else if (pdp == ProofDisproof::PawnCheckmate()) os << "PawnCheckmate"; else if (pdp == ProofDisproof::LoopDetection()) os << "LoopDetection"; else if (pdp == ProofDisproof::AttackBack()) os << "AttackBack"; else os << "pdp-" << pdp.proof() << "," << pdp.disproof(); return os; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/fixedDepthSearcher.tcc0000644000000000000000000003002212316770314022346 0ustar rootroot/* fixedDepthSearcher.tcc */ #ifndef OSL_CHECKMATE_FIXED_DEPTH_SERCHER_TCC #define OSL_CHECKMATE_FIXED_DEPTH_SERCHER_TCC #include "osl/checkmate/fixedDepthSearcher.h" #include "osl/checkmate/immediateCheckmate.h" #include "osl/numEffectState.h" #include "osl/move_generator/move_action.h" #include "osl/move_generator/addEffectWithEffect.h" #include "osl/move_generator/escape_.h" #include "osl/move_classifier/check_.h" namespace osl { namespace checkmate { template struct FixedAttackHelper{ FixedDepthSearcher &searcher; Move move; int depth; ProofDisproof& pdp; PieceStand& pieces; FixedAttackHelper(FixedDepthSearcher &s,int d,ProofDisproof& p, PieceStand& pi) : searcher(s), depth(d), pdp(p), pieces(pi) { } void operator()(Square) { assert(move.isNormal()); pdp=searcher.defense(move,depth-1,pieces); } }; /** * Pã¯å‹•ã‹ã™å´ã§ã¯ãªãæ”»æ’ƒå´ */ template struct FixedDefenseHelper{ FixedDepthSearcher &searcher; int depth; ProofDisproof& pdp; PieceStand& pieces; Move best_move; FixedDefenseHelper(FixedDepthSearcher &s,int d,ProofDisproof& p, PieceStand& pi) : searcher(s), depth(d), pdp(p), pieces(pi) { } void operator()(Square) { if (MayUnsafe) pdp=searcher.attackMayUnsafe(depth-1, best_move, pieces); else pdp=searcher.attack(depth-1, best_move, pieces); } }; } } template const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: attackMayUnsafe(int depth, Move& best_move, PieceStand& proof_pieces) { assert(state->turn() == P); const Square target_king = state->template kingSquare(); if (state->hasEffectAt

(target_king)) return ProofDisproof::NoEscape(); return attack(depth, best_move, proof_pieces); } template const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: attack(int depth, Move& best_move, PieceStand& proof_pieces) { assert(state->turn() == P); assert ((! HasGuide) || (state->isAlmostValidMove(best_move) && move_classifier:: Check

::isMember(*state, best_move.ptype(), best_move.from(), best_move.to()))); addCount(); const Square target_king = state->template kingSquare(); assert(! state->hasEffectAt

(target_king)); const King8Info info(state->Iking8Info(alt(P))); if ((! state->inCheck()) && ImmediateCheckmate::hasCheckmateMove

(*state, info, target_king, best_move)) { SetPieces::setAttackLeaf(best_move, proof_pieces); return ProofDisproof::Checkmate(); } if (depth <= 0) { return SetPieces::attackEstimation(*state, P, info); } ProofDisproof pdp; typedef FixedAttackHelper helper_t; helper_t helper(*this,depth,pdp,proof_pieces); int minProof = ProofDisproof::PROOF_MAX; int sumDisproof=0; if (HasGuide) { helper.move=best_move; state->makeUnmakeMove(Player2Type

(),best_move,helper); if (pdp.isCheckmateSuccess()) { SetPieces::attack(best_move, PieceStand(P,*state), proof_pieces); return ProofDisproof::Checkmate(); } minProof = pdp.proof(); sumDisproof += pdp.disproof(); } const Square targetKing = state->template kingSquare(); CheckMoveVector moves; bool has_pawn_checkmate=false; { move_action::Store store(moves); move_generator::AddEffectWithEffect::template generate (*state,targetKing,store,has_pawn_checkmate); } if (moves.size()==0){ if(has_pawn_checkmate) return ProofDisproof::PawnCheckmate(); else return ProofDisproof::NoCheckmate(); } if(has_pawn_checkmate) minProof=std::min(minProof,(int)ProofDisproof::PAWN_CHECK_MATE_PROOF); for (Move move: moves) { if (HasGuide && move == best_move) continue; helper.move=move; state->makeUnmakeMove(Player2Type

(), move,helper); int proof=pdp.proof(); if (proof= 3 ã§ã¯ PawnCheckmateã®éš›ã«unpromoteを試ã™å¿…è¦ã‚り return ProofDisproof(minProof,sumDisproof); } template inline const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: defenseEstimation(Move last_move, PieceStand& proof_pieces, Piece attacker_piece, Square target_position) const { assert(state->turn() == alt(P)); const Player Opponent = alt(P); int count=King8Info(state->Iking8Info(Opponent)).libertyCount(); // multiple checkãªã®ã§ï¼Œpawn dropã§ã¯ãªã„ if (attacker_piece.isEmpty()) { if (count>0){ return ProofDisproof(count,1); } return ProofDisproof::NoEscape(); } const Square attack_from=attacker_piece.square(); count += state->countEffect(alt(P), attack_from); if (attack_from.isNeighboring8(target_position)) --count; const EffectContent effect = Ptype_Table.getEffect(attacker_piece.ptypeO(), attack_from, target_position); if (! effect.hasUnblockableEffect()) { // this is better approximation than naive enumeration of blocking moves, // for counting of disproof number in df-pn, ++count; } if (count==0){ if (last_move.isValid() && last_move.isDrop() && last_move.ptype()==PAWN) return ProofDisproof::PawnCheckmate(); SetPieces::setLeaf(*state, P, stand(P), proof_pieces); return ProofDisproof::NoEscape(); } return ProofDisproof(count, 1); } template void osl::checkmate::FixedDepthSearcher:: generateBlockingWhenLiberty0(Piece defense_king, Square attack_from, CheckMoveVector& moves) const { assert(state->kingPiece(Defense) == defense_king); using namespace move_generator; using namespace move_action; CheckMoveVector all_moves; { Store store(all_moves); Escape:: generateBlockingKing(*state, defense_king, attack_from,store); } for (Move move: all_moves) { if (move.isDrop()) { if (! state->hasEffectAt(move.to())) continue; } else { // move if (! move.from().isNeighboring8(defense_king.square())) { if (! state->hasMultipleEffectAt(Defense, move.to())) continue; } } moves.push_back(move); } } template inline int osl::checkmate::FixedDepthSearcher:: blockEstimation(Square /*attack_from*/, Square /*defense_king*/) const { // 利ãã®ã‚るマスを数ãˆã‚ˆã†ã¨æ€ã£ãŸã‚‰åŠ¹æžœãŒãªã‹ã£ãŸ return 1; } template const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: defense(Move last_move, int depth, PieceStand& proof_pieces) { assert(state->turn() == alt(P)); addCount(); const Player Defense = alt(P); const Square attackerKing = state->template kingSquare

(); /** * ç›´å‰ã®æ”»ã‚æ–¹ã®æ‰‹ãŒè‡ªæ®ºæ‰‹ */ if (attackerKing.isOnBoard() && state->hasEffectAt(attackerKing)) return ProofDisproof::NoCheckmate(); const Piece target_king = state->template kingPiece(); const Square target_position = target_king.square(); assert(state->hasEffectAt

(target_position)); Piece attacker_piece; state->template findCheckPiece(attacker_piece); if (depth <= 0) { return defenseEstimation (last_move, proof_pieces, attacker_piece, target_position); } assert(depth > 0); CheckMoveVector moves; bool blockable_check = false; int nonblock_moves; { using namespace move_generator; using namespace move_action; if (attacker_piece.isEmpty()) { move_action::Store store(moves); Escape::template generateEscape(*state,target_king,store); nonblock_moves = moves.size(); } else { const Square attack_from=attacker_piece.square(); { move_action::Store store(moves); Escape:: generateCaptureKing(*state, target_king, attack_from, store); } const int num_captures = moves.size(); { move_action::Store store(moves); Escape::template generateEscape(*state, target_king, store); } nonblock_moves = moves.size(); blockable_check = ! state->inUnblockableCheck(alt(P)); if ((depth <= 1) && num_captures && (nonblock_moves > 2)) { if (nonblock_moves > 3) { const int block_estimate = blockable_check ? blockEstimation(attack_from, target_position) : 0; return ProofDisproof(nonblock_moves + block_estimate, 1); } } if (moves.empty()) generateBlockingWhenLiberty0(target_king, attack_from, moves); } } const size_t initial_moves = moves.size(); if (moves.empty() && !blockable_check) { if (last_move.isValid() && last_move.isDrop() && last_move.ptype()==PAWN) return ProofDisproof::PawnCheckmate(); SetPieces::setLeaf(*state, P, PieceStand(P,*state), proof_pieces); return ProofDisproof::NoEscape(); } const bool cut_candidate = (depth <= 1) && (nonblock_moves - (state->hasPieceOnStand(P) || state->hasPieceOnStand(P)) > 4); if (cut_candidate) return ProofDisproof(nonblock_moves, 1); typedef FixedDefenseHelper helper_t; SetPieces::clear(proof_pieces); PieceStand child_proof; ProofDisproof pdp; helper_t helper(*this, depth, pdp, child_proof); int minDisproof = ProofDisproof::DISPROOF_MAX; int sumProof = 0; size_t i=0, no_promote_moves=0; start_examine: for (;imakeUnmakeMove(Player2Type(),moves[i],helper); const int disproof=pdp.disproof(); if (disproof:: generateBlockingKing(*state, target_king, attack_from,store); } if ((int)moves.size() > nonblock_moves) goto start_examine; if (moves.empty()) { assert(! (last_move.isValid() && last_move.isDrop() && last_move.ptype()==PAWN)); SetPieces::setLeaf(*state, P, PieceStand(P,*state), proof_pieces); return ProofDisproof::NoEscape(); } } if (no_promote_moves == 0) { no_promote_moves = moves.size(); for (size_t i=0; i()) moves.push_back(moves[i].unpromote()); if (moves.size() > no_promote_moves) goto start_examine; } if (blockable_check) SetPieces::addMonopolizedPieces(*state, P, stand(P), proof_pieces); } // depth >= 2 ã§ã¯ unprmote も試ã™å¿…è¦ã‚り return ProofDisproof(sumProof,minDisproof); } template const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: hasEscapeByMove(Move next_move, int depth) { typedef FixedDefenseHelper helper_t; PieceStand proof_pieces; ProofDisproof pdp; helper_t helper(*this, depth+1, pdp, proof_pieces); state->makeUnmakeMove(Player2Type(),next_move,helper); return pdp; } #endif /* OSL_CHECKMATE_FIXED_DEPTH_SERCHER_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/fixedDepthSearcher.cc0000644000000000000000000000223312316770314022165 0ustar rootroot/* fixedDepthSearcher.cc */ #include "osl/checkmate/fixedDepthSearcher.h" #include "osl/checkmate/fixedDepthSearcher.tcc" #include "osl/move_generator/addEffectWithEffect.tcc" #include "osl/numEffectState.tcc" const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: hasCheckmateMoveOfTurn(int depth, Move& best_move) { if (state->turn() == BLACK) return hasCheckmateMove(depth, best_move); else return hasCheckmateMove(depth, best_move); } const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: hasEscapeMoveOfTurn(Move last_move, int depth) { if (state->turn() == BLACK) return hasEscapeMove(last_move, depth); else return hasEscapeMove(last_move, depth); } const osl::checkmate::ProofDisproof osl::checkmate::FixedDepthSearcher:: hasEscapeByMoveOfTurn(Move next_move, int depth) { if (state->turn() == BLACK) return hasEscapeByMove(next_move, depth); else return hasEscapeByMove(next_move, depth); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/immediateCheckmateTable.h0000644000000000000000000000272612316770314023010 0ustar rootroot/* immediateCheckmateTable.h */ #ifndef OSL_CHECKMATE_IMMEDIATE_CHECKMATE_TABLE_H #define OSL_CHECKMATE_IMMEDIATE_CHECKMATE_TABLE_H #include "osl/basic_type.h" #include "osl/bits/king8Info.h" namespace osl { namespace checkmate { class ImmediateCheckmateTable { private: CArray dropPtypeMasks; CArray2d ptypeDropMasks; CArray2d blockingMasks; CArray2d noEffectMasks; public: ImmediateCheckmateTable(); unsigned char dropPtypeMaskOf(unsigned int liberty_drop_mask) const { return dropPtypeMasks[liberty_drop_mask]; } unsigned char dropPtypeMask(King8Info canMoveMask) const { return dropPtypeMaskOf(canMoveMask.libertyDropMask()); } unsigned int ptypeDropMask(Ptype ptype,King8Info canMoveMask) const { return ptypeDropMasks[canMoveMask.liberty()][ptype]; } unsigned int blockingMask(Ptype ptype,Direction dir) const { assert(static_cast(dir)<8); return blockingMasks[ptype][dir]; } unsigned int noEffectMask(Ptype ptype,Direction dir) const { assert(static_cast(dir)<8); return noEffectMasks[ptype][dir]; } }; extern const ImmediateCheckmateTable Immediate_Checkmate_Table; } } #endif /* OSL_CHECKMATE_IMMEDIATE_CHECKMATE_TABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/immediateCheckmate.h0000644000000000000000000000552412316770314022037 0ustar rootroot/* immediateCheckmate.h */ #ifndef OSL_CHECKMATE_IMMEDIATE_CHECKMATE_H #define OSL_CHECKMATE_IMMEDIATE_CHECKMATE_H #include "osl/numEffectState.h" namespace osl { namespace checkmate { class ImmediateCheckmate { private: template static bool hasCheckmateDrop(NumEffectState const& state,Square target, King8Info mask,Move& bestMove); public: template static bool slowHasCheckmateMoveDirPiece(NumEffectState const& state,Square target, King8Info mask,Direction d,Square pos,Piece p,Ptype ptype,Move& bestMove); template static bool hasCheckmateMoveDirPiece(NumEffectState const& state,Square target, King8Info mask,Direction d,Square pos,Piece p,Move& bestMove); template static bool hasCheckmateMoveDir(NumEffectState const& state,Square target, King8Info mask,Direction d,Move& bestMove); template static bool hasCheckmateMove(NumEffectState const& state,Square target, King8Info mask,Move& bestMove); /** * 一手詰ã‚ãŒã‚ã‚‹å±€é¢ã‹ã©ã†ã‹åˆ¤å®š(move). * 手番ã®å´ã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã¯é™¤ã * é•·ã„利ãã«ã‚ˆã‚‹çŽ‹æ‰‹ã¯ç”Ÿæˆã—ãªã„. * pinã•れã¦ã„ã‚‹é§’ã®åˆ©ããŒãªã„ãŸã‚ã«è©°ã¿ã«ãªã‚‹ä¾‹ã‚‚扱ã‚ãªã„. * @param P(template) - 攻撃å´(手番å´)ã®ãƒ—レイヤー * @param state - å±€é¢ */ template static bool hasCheckmateMove(NumEffectState const& state); template static bool hasCheckmateMove(NumEffectState const& state, King8Info); /** * 一手詰ã‚ãŒã‚ã‚‹å±€é¢ã‹ã©ã†ã‹åˆ¤å®š(move). * 手番ã®å´ã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã¯é™¤ã * é•·ã„利ãã«ã‚ˆã‚‹çŽ‹æ‰‹ã¯ç”Ÿæˆã—ãªã„. * pinã•れã¦ã„ã‚‹é§’ã®åˆ©ããŒãªã„ãŸã‚ã«è©°ã¿ã«ãªã‚‹ä¾‹ã‚‚扱ã‚ãªã„. * @param P(template) - 攻撃å´(手番å´)ã®ãƒ—レイヤー * @param state - å±€é¢ * @param best_move - ã‚ã‚‹å ´åˆã«è©°ã‚ã®æ‰‹ã‚’返㙠*/ template static bool hasCheckmateMove(NumEffectState const& state,Move &bestMove); template static bool hasCheckmateMove(NumEffectState const& state, King8Info canMoveMask, Square king, Move& bestMove); /** * */ static bool hasCheckmateMove(Player pl,NumEffectState const& state); static bool hasCheckmateMove(Player pl,NumEffectState const& state,Move& bestMove); }; } // namespace checkmate using checkmate::ImmediateCheckmate; } // namespace osl #endif /* _CHECKMATE_IMMEDIATE_CHECKMATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/proofDisproof.h0000644000000000000000000001255212316770314021126 0ustar rootroot#ifndef _PROOF_DISPROOF_H #define _PROOF_DISPROOF_H #include "osl/basic_type.h" #include #include namespace osl { namespace checkmate { /** * 証明数(proof number)ã¨å証数(disproof number). * è©°ã¿å±€é¢ã¨ç¢ºå®šã—ãŸæ™‚㯠proofNumber=0 * ä¸è©°ã¿å±€é¢ã¨ç¢ºå®šã—ãŸæ™‚㯠disproofNumber=0 */ class ProofDisproof { unsigned long long pdp; public: enum { PROOF_SHIFT = 32, DISPROOF_MASK = 0xffffffffu, PROOF_MAX = (0xffffffffu / 16), DISPROOF_MAX = (0xffffffffu / 16), /** å証数ã®å®šæ•°: è©°ã‚“ã æ™‚ã«ã¯ï¼Œè©°ã®ç¨®é¡žã®åŒºåˆ¥ã«åˆ©ç”¨ */ NO_ESCAPE_DISPROOF = (DISPROOF_MAX - 1), CHECK_MATE_DISPROOF = (DISPROOF_MAX - 2), /** 証明数ã®å®šæ•°: å証ã•ã‚ŒãŸæ™‚ã«ã¯ï¼Œä¸è©°ã®ç¨®é¡žã®åŒºåˆ¥ã«åˆ©ç”¨ */ NO_CHECK_MATE_PROOF = (PROOF_MAX - 1), PAWN_CHECK_MATE_PROOF = (PROOF_MAX - 2), LOOP_DETECTION_PROOF = (PROOF_MAX - 3), ATTACK_BACK_PROOF = (PROOF_MAX - 4), }; private: static void testConsistency(); public: enum { /** 通常ã®å証数ã®ä¸Šé™ */ DISPROOF_LIMIT = (DISPROOF_MAX - 3), /** 通常ã®è¨¼æ˜Žæ•°ã®ä¸Šé™ */ PROOF_LIMIT = (PROOF_MAX - 5), }; private: static unsigned long long compose(unsigned long long proof, unsigned long long disproof) { return (proof << PROOF_SHIFT) + disproof; } /** range check ã‚’ã—ãªã„ private ãƒãƒ¼ã‚¸ãƒ§ãƒ³ */ ProofDisproof(unsigned long long value) : pdp(value) { } static const ProofDisproof make(unsigned int proof, unsigned int disproof) { return ProofDisproof(compose(proof, disproof)); } public: ProofDisproof() : pdp(compose(1, 1)) { } ProofDisproof(unsigned int proof, unsigned int disproof) : pdp(compose(proof,disproof)) { assert(proof < PROOF_MAX); assert(disproof < DISPROOF_MAX); assert(proof || disproof); assert((proof == 0) ^ (disproof < DISPROOF_LIMIT)); assert((disproof == 0) ^ (proof < PROOF_LIMIT)); } static const ProofDisproof makeDirect(unsigned long long value) { return ProofDisproof(value); } // constants static const ProofDisproof NoEscape() { return ProofDisproof(0, NO_ESCAPE_DISPROOF); } static const ProofDisproof Checkmate() { return ProofDisproof(0, CHECK_MATE_DISPROOF); } static const ProofDisproof NoCheckmate() { return ProofDisproof(NO_CHECK_MATE_PROOF, 0); } static const ProofDisproof PawnCheckmate() { return ProofDisproof(PAWN_CHECK_MATE_PROOF, 0); } static const ProofDisproof LoopDetection() { return ProofDisproof(LOOP_DETECTION_PROOF, 0); } static const ProofDisproof AttackBack() { return ProofDisproof(ATTACK_BACK_PROOF, 0); } static const ProofDisproof Unknown () { return ProofDisproof(1, 1); } /** 攻方ã«ã‚‚å—æ–¹ã«ã‚‚ä¸éƒ½åˆãªä»®æƒ³çš„ãªæ•° */ static const ProofDisproof Bottom () { return make(PROOF_MAX, DISPROOF_MAX); } unsigned int proof() const { return pdp >> PROOF_SHIFT; } unsigned int disproof() const { return pdp & DISPROOF_MASK; } bool isCheckmateSuccess() const { return proof()==0; } bool isCheckmateFail() const { return disproof()==0; } bool isFinal() const { return isCheckmateSuccess() || isCheckmateFail(); } bool isUnknown() const { return !isFinal(); } /** 打歩詰ã‚ãªã‚‰çœŸ */ bool isPawnDropFoul(Move move) const { return (pdp == NoEscape().pdp) && move.isNormal() && move.isDrop() && (move.ptype()==PAWN); } bool isLoopDetection() const { return pdp == LoopDetection().pdp; } unsigned long long ulonglongValue() const { return pdp; } static const unsigned int BigProofNumber=PROOF_MAX; /** * this ㌠r より攻方ã«éƒ½åˆãŒè‰¯ã„時ã«çœŸ */ bool isBetterForAttack(const ProofDisproof& r) const { const unsigned int lp = proof(); const unsigned int rp = r.proof(); if (lp != rp) return lp < rp; return disproof() > r.disproof(); } /** * this ㌠r ã‚ˆã‚Šå—æ–¹ã«éƒ½åˆãŒè‰¯ã„時ã«çœŸ */ bool isBetterForDefense(const ProofDisproof& r) const { const unsigned int ld = disproof(); const unsigned int rd = r.disproof(); if (ld != rd) return ld < rd; return proof() > r.proof(); } /** * 攻方ã«éƒ½åˆãŒè‰¯ã„方を返㙠*/ const ProofDisproof& betterForAttack(const ProofDisproof& r) const { return (isBetterForAttack(r) ? *this : r); } /** * å—æ–¹ã«éƒ½åˆãŒè‰¯ã„方を返㙠*/ const ProofDisproof& betterForDefense(const ProofDisproof& r) const { return (isBetterForDefense(r) ? *this : r); } }; inline bool operator==(const ProofDisproof& l, const ProofDisproof& r) { return l.ulonglongValue() == r.ulonglongValue(); } inline bool operator!=(const ProofDisproof& l, const ProofDisproof& r) { return ! (l == r); } inline bool operator<(const ProofDisproof& l, const ProofDisproof& r) { return l.ulonglongValue() < r.ulonglongValue(); } std::ostream& operator<<(std::ostream& os, const ProofDisproof& proofDisproof); } // namespace checkmate using checkmate::ProofDisproof; } // namespace osl #endif // _PROOF_DISPROOF_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/fixedDepthSearcher.h0000644000000000000000000001010312316770314022022 0ustar rootroot/* fixedDepthSearcher.h */ #ifndef OSL_CHECKMATE_FIXED_DEPTH_SERCHER_H #define OSL_CHECKMATE_FIXED_DEPTH_SERCHER_H #include "osl/checkmate/proofDisproof.h" #include "osl/numEffectState.h" #include "osl/bits/king8Info.h" #include "osl/bits/pieceStand.h" namespace osl { namespace checkmate { struct NoProofPieces { static void setAttackLeaf(Move /*best_move*/, PieceStand& /*proof_pieces*/) { } static void attack(Move /*best_move*/, PieceStand, PieceStand& /*proof_pieces*/) { } static void setLeaf(const NumEffectState&, Player, PieceStand, PieceStand&) { } static void clear(PieceStand& /*proof_pieces*/) { } static void updateMax(PieceStand /*child*/, PieceStand& /*proof_pieces*/) { } static void addMonopolizedPieces(const NumEffectState&, Player, PieceStand, PieceStand&) { } static ProofDisproof attackEstimation(const NumEffectState&, Player, King8Info) { return ProofDisproof(); } }; /** * æ·±ã•固定ã§ï¼Œãã®æ·±ã•ã¾ã§ depth first searchã§èª­ã‚€è©°å°†æ£‹. * æ·±ã•0ã§è©°ã¿çŠ¶æ…‹ã‹ã©ã†ã‹(æ”»ã‚æ‰‹ã®æ‰‹ç•ªã®å ´åˆ),王手をã‹ã‘る手ãŒãªã„ã‹ã‚’判定å¯èƒ½ * æ·±ã•1ã§é€šå¸¸ã®ä¸€æ‰‹è©°ã¿ã‚’判定(æ”»ã‚æ‰‹ã®æ‰‹ç•ªã®å ´åˆ) * 使ã†ã®ã¯æ·±ã•3ä½ã¾ã§? * NumEffectState専用 */ class FixedDepthSearcher { protected: NumEffectState *state; int count; public: FixedDepthSearcher() : state(0), count(0) { } explicit FixedDepthSearcher(NumEffectState& s) : state(&s), count(0) { } void setState(NumEffectState& s) { state = &s; } private: void addCount() { count++; } public: int getCount() const { return count; } const PieceStand stand(Player P) const { return PieceStand(P, *state); } public: // private: Note: helper ã®éƒ½åˆ template const ProofDisproof attack(int depth, Move& best_move, PieceStand& proof_pieces); template const ProofDisproof attackMayUnsafe(int depth, Move& best_move, PieceStand& proof_pieces); template const ProofDisproof defense(Move last_move,int depth, PieceStand& proof_pieces); private: /** * move を作らãšã« ProofDisproof ã®äºˆæ¸¬ã‚’計算ã™ã‚‹ */ template const ProofDisproof defenseEstimation(Move last_move, PieceStand& proof_pieces, Piece attacker_piece, Square target_position) const; public: template const ProofDisproof hasCheckmateMove(int depth,Move& best_move) { PieceStand proof_pieces; return attack(depth, best_move, proof_pieces); } template const ProofDisproof hasCheckmateMove(int depth) { Move checkmate_move; return hasCheckmateMove

(depth, checkmate_move); } template const ProofDisproof hasEscapeMove(Move last_move,int depth) { PieceStand proof_pieces; return defense(last_move, depth, proof_pieces); } template const ProofDisproof hasEscapeByMove(Move next_move, int depth); const ProofDisproof hasCheckmateMoveOfTurn(int depth,Move& best_move); const ProofDisproof hasEscapeMoveOfTurn(Move last_move,int depth); const ProofDisproof hasEscapeByMoveOfTurn(Move next_move, int depth); /** * ç„¡é§„åˆã‚’ãªã‚‹ã¹ã生æˆã—ãªã„,åˆé§’ç”Ÿæˆ */ template void generateBlockingWhenLiberty0(Piece defense_king, Square attack_from, CheckMoveVector& moves) const; template int blockEstimation(Square attack_from, Square defense_king) const; }; } // namespace checkmate } // namespace osl #endif /* OSL_CHECKMATE_FIXED_DEPTH_SERCHER_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/checkmate/immediateCheckmate.tcc0000644000000000000000000003613312316770314022361 0ustar rootroot/* immediateCheckmate.tcc */ #ifndef OSL_CHECKMATE_IMMEDIATE_CHECKMATE_TCC #define OSL_CHECKMATE_IMMEDIATE_CHECKMATE_TCC #include "osl/checkmate/immediateCheckmate.h" #include "osl/checkmate/immediateCheckmateTable.h" #include "osl/move_classifier/kingOpenMove.h" #include "osl/bits/directionTraits.h" #include "osl/bits/pieceTable.h" #include "osl/bits/mask.h" namespace osl { namespace checkmate { namespace detail { using osl::misc::BitOp; template bool blockingVerticalAttack(NumEffectState const& state,Square pos) { PieceMask effect=state.effectSetAt(pos)& state.effectSetAt(pos+DirectionPlayerTraits::offset()); mask_t mask=effect.getMask(1); // longã¯å¸¸ã«1 mask&=(state.piecesOnBoard(P).getMask(1)<<8); if((mask&mask_t::makeDirect(PtypeFuns::indexMask<<8)).none()){ mask&=mask_t::makeDirect(PtypeFuns::indexMask<<8); while(mask.any()){ int num=mask.takeOneBit()+NumBitmapEffect::longToNumOffset; Square from=state.pieceOf(num).square(); assert(from.isOnBoard()); if(from.isU

(pos)) goto found; } return false; found:; } const Offset offset=DirectionPlayerTraits::offset(); pos+=offset; const Player altP=alt(P); for(int i=0;i<3;i++,pos+=offset){ Piece p=state.pieceAt(pos); if(p.canMoveOn()){ // 自分ã®é§’ã‹ç©ºç™½ if(state.countEffect(P,pos)==1) return true; if(!p.isEmpty()) return false; } else return false; } return false; } template bool #ifdef __GNUC__ __attribute__ ((pure)) #endif blockingDiagonalAttack(NumEffectState const& state,Square pos,Square target, King8Info canMoveMask) { const Player altP=alt(P); Square to=target-DirectionPlayerTraits::offset(); // Uã«ç›¸æ‰‹ã®é§’ãŒã‚ã‚‹ if((canMoveMask.uint64Value()&(0x10000<::indexMask<<8); while(mask.any()){ int num=mask.takeOneBit()+NumBitmapEffect::longToNumOffset; Square from=state.pieceOf(num).square(); assert(from.isOnBoard()); Offset offset=Board_Table.getShort8OffsetUnsafe(to,from); if(to+offset != pos) continue; if(state.countEffect(P,to)==1) return true; // UãŒspaceã ã¨çµ¡ã‚“ã§ãã‚‹ if(!state.pieceAt(to).isEmpty()) return false; Square pos1=to-offset; // BISHOPã®åˆ©ã一ã¤ã§æ­¢ã‚ã¦ã„㟠Piece p=state.pieceAt(pos1); if(p.canMoveOn() && state.countEffect(P,pos1)==1){ return true; } } return false; } template bool hasKnightCheckmate(NumEffectState const& state, Square target, Square pos, King8Info canMoveMask, Move& bestMove, mask_t mask1) { if(!pos.isOnBoard()) return false; const Player altP=alt(P); Piece p=state.pieceAt(pos); if(p.canMoveOn

() && !state.hasEffectByNotPinned(altP,pos) ){ mask_t mask=state.effectSetAt(pos).getMask()&mask1; if(mask.any()){ if(blockingVerticalAttack

(state,pos) || blockingDiagonalAttack

(state,pos,target,canMoveMask)) return false; if(setBestMove){ int num=mask.takeOneBit()+(PtypeFuns::indexNum<<5); Piece p1=state.pieceOf(num); Square from=p1.square(); bestMove=Move(from,pos,KNIGHT,p.ptype(),false,P); } return true; } else if(canDrop && p.isEmpty()){ if(blockingVerticalAttack

(state,pos) || blockingDiagonalAttack

(state,pos,target,canMoveMask)) return false; if(setBestMove) bestMove=Move(pos,KNIGHT,P); return true; } } return false; } // KNIGHT // KNIGHTã®dropã¯åˆ©ãã‚’é®ã‚‹ã“ã¨ã¯ãªã„ template bool hasCheckmateMoveKnight(NumEffectState const& state, Square target, King8Info canMoveMask,Move& bestMove) { // 8è¿‘å‚ã«ç§»å‹•ã§ãã‚‹æ™‚ã¯æ¡‚馬ã®ä¸€æ‰‹è©°ã‚ã¯ãªã„ if((canMoveMask.uint64Value()&0xff00)!=0) return false; mask_t mask=mask_t::makeDirect(PtypeFuns::indexMask); mask&=state.piecesOnBoard(P).getMask(); mask&= ~state.promotedPieces().getMask(); mask&= ~state.pinOrOpen(P).getMask(); if(state.hasPieceOnStand(P)){ Square pos=target-DirectionPlayerTraits::offset(); if(hasKnightCheckmate(state,target,pos,canMoveMask,bestMove,mask)) return true; pos=target-DirectionPlayerTraits::offset(); return hasKnightCheckmate(state,target,pos,canMoveMask,bestMove,mask); } else{ Square pos=target-DirectionPlayerTraits::offset(); if(hasKnightCheckmate(state,target,pos,canMoveMask,bestMove,mask)) return true; pos=target-DirectionPlayerTraits::offset(); return hasKnightCheckmate(state,target,pos,canMoveMask,bestMove,mask); } return false; } template bool slowCheckDrop(NumEffectState const& state,Square target, Ptype ptype,King8Info canMoveMask,Move& bestMove) { unsigned int dropMask=(canMoveMask.uint64Value()&0xff) &Immediate_Checkmate_Table.ptypeDropMask(ptype,canMoveMask); // dropMaskãŒ0ãªã‚‰ã“ã“ã«æ¥ãªã„ assert(dropMask!=0); while(dropMask!=0){ int i=BitOp::takeOneBit(dropMask); Direction d=static_cast(i); unsigned int blockingMask=Immediate_Checkmate_Table.blockingMask(ptype,d) & (canMoveMask.uint64Value()>>16); Square drop=target-Board_Table.getOffset

(d); if(blockingMask!=0){ NumBitmapEffect effect=state.effectSetAt(drop); mask_t longEffect=effect.getMask(1)&NumBitmapEffect::longEffectMask(); longEffect&=(state.piecesOnBoard(P).getMask(1)<<8); if(longEffect.any()){ do{ int j=BitOp::takeOneBit(blockingMask); Direction d1=static_cast(j); Square pos=target-Board_Table.getOffset

(d1); NumBitmapEffect effect1=state.effectSetAt(pos); if(effect1.countEffect(P)>1) continue; mask_t longEffect1=effect1.getMask(1)&longEffect; if(!longEffect1.any()) continue; // int num=longEffect1.takeOneBit()+NumBitmapEffect::longToNumOffset; if(Board_Table.isBetween(drop,state.pieceOf(num).square(),pos)) goto tryNext; }while(blockingMask!=0); } } // blockingMaskã®ç‚¹ãŒã™ã¹ã¦OKãªã‚‰OK if(setBestMove) bestMove=Move(drop,ptype,P); return true; tryNext:; } return false; } } // detail } // checkmate } // osl // not KNIGHT template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateDrop(NumEffectState const& state, Square target, King8Info canMoveMask,Move& bestMove) { typedef misc::GeneralMask mask_t; mask_t dropPtypeMask=mask_t::makeDirect(Immediate_Checkmate_Table.dropPtypeMask(canMoveMask)); while(dropPtypeMask.any()){ Ptype ptype=static_cast(dropPtypeMask.takeOneBit()+PTYPE_BASIC_MIN); if(state.hasPieceOnStand(P,ptype) && detail::slowCheckDrop(state,target,ptype,canMoveMask, bestMove)) return true; } return false; } template bool osl::checkmate::ImmediateCheckmate:: slowHasCheckmateMoveDirPiece(NumEffectState const& state, Square target, King8Info canMoveMask,Direction d,Square pos,Piece p,Ptype ptype,Move& bestMove){ const Player altP=alt(P); // ptypeãŒPROOKã®æ™‚ã¯ï¼Œæ›´ãªã‚‹ãƒã‚§ãƒƒã‚¯ãŒå¿…è¦ if(ptype==PROOK){ int dx=target.x()-pos.x(); int dy=target.y()-pos.y(); if(abs(dx)==1 && abs(dy)==1){ { Square pos1=pos+Offset(dx,0); Piece p1=state.pieceAt(pos1); if(!p1.isEmpty()){ { // * -OU * // (A)(B)(D) // * (C) * // (E) * * // +RY (C) -> (A), (E) -> (A) // -?? - (B) // (D) - 竜以外ã®åˆ©ããªã— Square pos2=pos+Offset(2*dx,0); if(state.pieceAt(pos2).template canMoveOn()){ NumBitmapEffect effect2=state.effectSetAt(pos2); if(effect2.countEffect(P)==0 || (effect2.countEffect(P)==1 && effect2.test(p.number()))) return false; } } { // * -OU * // (A)(B) * // * (C) * // +RY (C) -> (A) // -?? - (B)竜ã§pinã•れã¦ã„ã‚‹ãŒå®Ÿã¯Aã¸ã®åˆ©ãæŒã¤ if(p.square()==target-Offset(0,2*dy) && state.hasEffectByPiece(p1,pos)) return false; } } } { Square pos1=pos+Offset(0,dy); Piece p1=state.pieceAt(pos1); if(!p1.isEmpty()){ Square pos2=pos+Offset(0,2*dy); { if(state.pieceAt(pos2).template canMoveOn()){ NumBitmapEffect effect2=state.effectSetAt(pos2); if(effect2.countEffect(P)==0 || (effect2.countEffect(P)==1 && effect2.test(p.number()))) return false; } { // (C)(B)-OU // * (A) * // +RY (C) -> (A) // -?? - (B)竜ã§pinã•れã¦ã„ã‚‹ãŒå®Ÿã¯Aã¸ã®åˆ©ãæŒã¤ if(p.square()==target-Offset(2*dx,0) && state.hasEffectByPiece(p1,pos)) return false; } } } } } } // 元々2ã¤ã®åˆ©ããŒã‚ã£ãŸãƒžã‚¹ãŒï¼Œ // block & 自分ã®åˆ©ãã®é™¤åŽ»ã§åˆ©ããŒãªããªã‚‹ã“ã¨ã¯ã‚ã‚‹ã‹? // -> ã‚る. // +KA * * // * (A) +KI // * -OU (B) // * * * // ã§é‡‘ãŒAã«ç§»å‹•ã—ã¦çŽ‹æ‰‹ã‚’ã‹ã‘ã‚‹ã¨ï¼ŒBã®åˆ©ããŒ2ã‹ã‚‰0ã«ãªã‚‹ï¼Ž mask_t mask=mask_t::makeDirect((canMoveMask.uint64Value()>>16)&Immediate_Checkmate_Table.noEffectMask(ptype,d)); if(mask.any()){ int num=p.number(); NumBitmapEffect effect2=state.effectSetAt(pos); effect2.reset(num+8); mask_t longEffect2=effect2.getMask(1)&NumBitmapEffect::longEffectMask(); longEffect2&=(state.piecesOnBoard(P).getMask(1)<<8); do { Direction d1=static_cast(mask.takeOneBit()); Square pos1=target-Board_Table.getOffset

(d1); NumBitmapEffect effect1=state.effectSetAt(pos1); int count=effect1.countEffect(P); // 自分ã®åˆ©ãã®é™¤åŽ» if(effect1.test(num)) count--; if(count==0) return false; // blockã—ã¦ã„る利ãã®é™¤åŽ» mask_t longEffect1=effect1.getMask(1)&longEffect2; while(longEffect1.any()){ int num1=longEffect1.takeOneBit()+NumBitmapEffect::longToNumOffset; if(Board_Table.isBetween(pos,state.pieceOf(num1).square(),pos1)) count--; if(count==0) return false; } } while (mask.any()); } // 自殺手ã§ãªã„ã“ã¨ã®ãƒã‚§ãƒƒã‚¯ã‚’入れる if(move_classifier::KingOpenMove

::isMember(state,ptype,p.square(),pos)) return false; if(setBestMove){ bestMove=Move(p.square(),pos,ptype, state.pieceAt(pos).ptype(), ptype!=p.ptype(),P); } return true; } template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMoveDirPiece(NumEffectState const& state, Square target, King8Info canMoveMask,Direction d,Square pos,Piece p,Move& bestMove){ Square from=p.square(); Ptype ptype=p.ptype(); // 相手ã®åˆ©ããŒä¼¸ã³ã¦ã—ã¾ã£ã¦ç§»å‹•後も利ããŒã¤ã„ã¦ãã‚‹å¯èƒ½æ€§ { const Player altP=alt(P); Direction d1=Board_Table.getShort8Unsafe

(from,pos); if(d1!=DIRECTION_INVALID_VALUE){ // not knight move int num=state.longEffectNumTable()[p.number()][P==BLACK ? d1 : inverse(d1)]; if(num != EMPTY_NUM && state.pieceOf(num).isOnBoardByOwner()) return false; } } if(canPromote(ptype) && (from.canPromote

() || pos.canPromote

())){ Ptype pptype=promote(ptype); if((((canMoveMask.uint64Value()>>8)|0x100)& Immediate_Checkmate_Table.noEffectMask(pptype,d))==0){ if(slowHasCheckmateMoveDirPiece(state,target,canMoveMask,d,pos,p,pptype,bestMove)) return true; } if (ptype==PAWN || /*basic because canpromote*/isMajorBasic(ptype)) return false; } if((((canMoveMask.uint64Value()>>8)|0x100)& Immediate_Checkmate_Table.noEffectMask(ptype,d))==0){ if(slowHasCheckmateMoveDirPiece(state,target,canMoveMask,d,pos,p,ptype,bestMove)) return true; } return false; } template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMoveDir(NumEffectState const& state, Square target, King8Info canMoveMask,Direction d,Move& bestMove){ Square pos=target-Board_Table.getOffset

(d); if(state.countEffect(P,pos)<2 && !effect_util::AdditionalEffect::hasEffect(state,pos,P)) return false; PieceMask pieceMask=state.piecesOnBoard(P)&state.effectSetAt(pos); assert(pos.isOnBoard()); // 玉ã§çŽ‹æ‰‹ã‚’ã‹ã‘ãªã„ pieceMask.reset(KingTraits

::index); for(int i=0;i<=PieceMask::numToIndex(40);i++){ mask_t mask=pieceMask.getMask(i); while (mask.any()){ const int num=mask.takeOneBit()+i*32; if(hasCheckmateMoveDirPiece(state,target,canMoveMask,d,pos,state.pieceOf(num),bestMove)) return true; } } return false; } // not KNIGHT template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const& state, Square target, King8Info canMoveMask,Move& bestMove) { assert(! state.inCheck()); typedef misc::GeneralMask mask_t; mask_t mask2=mask_t::makeDirect((canMoveMask.uint64Value()>>24)&0xff); while(mask2.any()){ Direction d=static_cast(mask2.takeOneBit()); if(hasCheckmateMoveDir(state,target,canMoveMask,d,bestMove)) return true; } return false; } template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const& state, King8Info canMoveMask) { const Player altP=alt(P); const Square target=state.kingSquare(altP); assert(target.isOnBoard()); // 相手ã‹ã‚‰ã®çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ãªã„ Move dummy; if(hasCheckmateMove(state,target,canMoveMask,dummy)) return true; if(detail::hasCheckmateMoveKnight(state,target,canMoveMask,dummy)) return true; return hasCheckmateDrop(state,target,canMoveMask,dummy); } template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const& state) { const Player altP=alt(P); #ifndef NDEBUG const Square target=state.kingSquare(altP); #endif assert(target.isOnBoard()); King8Info canMoveMask(state.Iking8Info(altP)); return hasCheckmateMove

(state, canMoveMask); } template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const& state, King8Info canMoveMask, Square target, Move& bestMove) { assert(! state.inCheck()); assert(target.isOnBoard()); if(hasCheckmateMove(state,target,canMoveMask,bestMove)) return true; if(detail::hasCheckmateMoveKnight(state,target,canMoveMask,bestMove)) return true; return hasCheckmateDrop(state,target,canMoveMask,bestMove); } template bool osl::checkmate::ImmediateCheckmate:: hasCheckmateMove(NumEffectState const& state,Move& bestMove) { const Player altP=alt(P); const Square target=state.kingSquare(altP); King8Info canMoveMask(state.Iking8Info(altP)); return hasCheckmateMove

(state, canMoveMask, target, bestMove); } #endif /* OSL_CHECKMATE_IMMEDIATE_CHECKMATE_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/numEffectState.tcc0000644000000000000000000001175212316770314017607 0ustar rootroot/* numEffectState.tcc */ #ifndef OSL_NUM_EFFECT_STATE_TCC #define OSL_NUM_EFFECT_STATE_TCC #include "osl/numEffectState.h" #include "osl/move_classifier/kingOpenMove.h" #include "osl/bits/numSimpleEffect.tcc" template bool osl::NumEffectState:: hasEffectByWithRemove(Square target,Square removed) const { const Piece piece = pieceAt(removed); if (! piece.isPiece()) return hasEffectAt

(target); if (piece.owner() == P) { if (hasEffectNotBy(P, piece, target)) return true; } else { if (hasEffectAt(P, target)) return true; } if (! longEffectAt(removed, P).any()) return false; const Direction d = Board_Table.getLongDirection(Offset32(target,removed)); if (!isLong(d)) return false; const int num=longEffectNumTable()[piece.number()][longToShort(d)]; return (! Piece::isEmptyNum(num) && pieceOf(num).owner()==P); } namespace osl { template struct TestEffectOfMove { template static void testShort(const State& s, int mask, Square from, Function& f) { static_assert(! DirectionTraits

::isLong, "Dir"); if (! (mask & DirectionTraits::mask)) return; const Offset offset = DirectionPlayerTraits::offset(); const Square target = from+offset; const Piece piece = s.pieceAt(target); if (piece.isEdge()) return; if (InterestEmpty || (! piece.isEmpty())) f(target); } template static void testLong(const State& s, int mask, Square from, Function& f) { static_assert(DirectionTraits::isLong, "Dir"); if (! (mask & DirectionTraits::mask)) return; const Offset offset = DirectionPlayerTraits::offset(); Square target = from+offset; Piece piece = s.pieceAt(target); while (piece.isEmpty()) { if (InterestEmpty) f(target); target = target+offset; piece = s.pieceAt(target); } if (piece.isPiece()) { f(target); } } }; struct SafeCapture { public: const NumEffectState& state; Piece safe_one; SafeCapture(const NumEffectState& s) : state(s), safe_one(Piece::EMPTY()) { } template void doAction(Piece effect_piece, Square target) { if (move_classifier::KingOpenMove

::isMember (state, effect_piece.ptype(), effect_piece.square(), target)) return; safe_one = effect_piece; } }; } // namespace osl template void osl::NumEffectState:: forEachEffectOfPtypeO(Square from, Ptype ptype, Function& f) const { const int mask = Ptype_Table.getMoveMask(ptype); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testShort(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); TestEffectOfMove::testLong(*this, mask, from, f); } template void osl::NumEffectState:: forEachEffectOfPtypeO(Square from, PtypeO ptypeo, Function& f) const { const Player P = getOwner(ptypeo); if (P == BLACK) this->template forEachEffectOfPtypeO (from, getPtype(ptypeo), f); else this->template forEachEffectOfPtypeO (from, getPtype(ptypeo), f); } template osl::Piece osl::NumEffectState::safeCaptureNotByKing(Square target, Piece king) const { assert(king.owner() == P); assert(king.ptype() == KING); PieceMask ignore = pin(P); ignore.set(king.number()); const Piece piece = findAttackNotBy(P, target, ignore); if (piece.isPiece()) return piece; SafeCapture safe_captures(*this); this->template forEachEffectNotBy

(target, king, safe_captures); return safe_captures.safe_one; } #endif /* OSL_NUM_EFFECT_STATE_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/basic_type.cc0000644000000000000000000002050412316770314016623 0ustar rootroot#include "osl/basic_type.h" #include "osl/bits/boardTable.h" #include "osl/bits/ptypeTable.h" #include "osl/simpleState.h" #include "osl/bits/squareCompressor.h" // #include "move-phash.c" #include bool osl::isValid(Player player) { return player==BLACK || player==WHITE; } std::ostream& osl::operator<<(std::ostream& os,Player player) { if(player==BLACK) return os << "+"; else return os << "-"; } bool osl::isValid(Ptype ptype) { return static_cast(ptype)>=PTYPE_MIN && static_cast(ptype)<=PTYPE_MAX; } bool osl::isValidPtypeO(int ptypeO) { return (ptypeO >= PTYPEO_MIN) && (ptypeO <= PTYPEO_MAX); } std::istream& osl::operator>>(std::istream& is, osl::Ptype& ptype) { std::string s; is >> s; if (s == "PTYPE_EMPTY") ptype = PTYPE_EMPTY; else if (s == "PTYPE_EDGE") ptype = PTYPE_EDGE; else if (s == "PPAWN") ptype = PPAWN; else if (s == "PLANCE") ptype = PLANCE; else if (s == "PKNIGHT") ptype = PKNIGHT; else if (s == "PSILVER") ptype = PSILVER; else if (s == "PBISHOP") ptype = PBISHOP; else if (s == "PROOK") ptype = PROOK; else if (s == "KING") ptype = KING; else if (s == "GOLD") ptype = GOLD; else if (s == "PAWN") ptype = PAWN; else if (s == "LANCE") ptype = LANCE; else if (s == "KNIGHT") ptype = KNIGHT; else if (s == "SILVER") ptype = SILVER; else if (s == "BISHOP") ptype = BISHOP; else if (s == "ROOK") ptype = ROOK; else{ std::cerr << "Incorrect input : " << s << std::endl; ptype = PTYPE_EMPTY; } return is; } std::ostream& osl::operator<<(std::ostream& os,const osl::Ptype ptype) { return os << Ptype_Table.getName(ptype); } std::ostream& osl::operator<<(std::ostream& os,const osl::PtypeO ptypeO) { if (isPiece(ptypeO)) return os << "PtypeO(" << getOwner(ptypeO) << "," << getPtype(ptypeO) << ")"; return os << "PtypeO(" << (int)ptypeO << "," << getPtype(ptypeO) << ")"; } bool osl::isValid(Direction d){ return DIRECTION_MIN<=d && d<=DIRECTION_MAX; } std::ostream& osl::operator<<(std::ostream& os,const Direction d){ static const char* names[]={ "UL","U","UR","L", "R","DL","D","DR", "UUL","UUR","LONG_UL", "LONG_U","LONG_UR","LONG_L", "LONG_R","LONG_DL","LONG_D","LONG_DR" }; return os << names[static_cast(d)]; } #define OFFSET_INDEX(dx,dy) ((dx*BOARD_HEIGHT + dy) - OFFSET_MIN) osl::Offset::Offset(Player player, Direction direction) { *this = Board_Table.getOffset(player, direction); } /** * Offsetã‹ã‚‰ä¸€èˆ¬ã« dxã¯æ±‚ã¾ã‚‰ãªã„ã®ã§, * ã“ã“ã§ã®å…¥åŠ›ã¯12è¿‘å‚ã®ã¿ã¨ã™ã‚‹ */ int osl::Offset::dx() const { switch (index()) { case OFFSET_INDEX(-1,-2): return -1; case OFFSET_INDEX(1,-2): return 1; case OFFSET_INDEX(-1,-1): return -1; case OFFSET_INDEX(0,-1): return 0; case OFFSET_INDEX(1,-1): return 1; case OFFSET_INDEX(-1,0): return -1; case OFFSET_INDEX(1,0): return 1; case OFFSET_INDEX(-1,1): return -1; case OFFSET_INDEX(0,1): return 0; case OFFSET_INDEX(1,1): return 1; case OFFSET_INDEX(-1,2): return -1; case OFFSET_INDEX(1,2): return 1; default: std::cerr << index() << " " << ZERO().index() << "\n"; assert(0); } return 0; } /** * Offsetã‹ã‚‰ä¸€èˆ¬ã« dyã¯æ±‚ã¾ã‚‰ãªã„ã®ã§, * ã“ã“ã§ã®å…¥åŠ›ã¯12è¿‘å‚ã®ã¿ã¨ã™ã‚‹ */ int osl::Offset::dy() const { switch (index()) { case OFFSET_INDEX(-1,-2): return -2; case OFFSET_INDEX(1,-2): return -2; case OFFSET_INDEX(-1,-1): return -1; case OFFSET_INDEX(0,-1): return -1; case OFFSET_INDEX(1,-1): return -1; case OFFSET_INDEX(-1,0): return 0; case OFFSET_INDEX(1,0): return 0; case OFFSET_INDEX(-1,1): return 1; case OFFSET_INDEX(0,1): return 1; case OFFSET_INDEX(1,1): return 1; case OFFSET_INDEX(-1,2): return 2; case OFFSET_INDEX(1,2): return 2; default: assert(0); } return 0; } #ifndef MINIMAL std::ostream& osl::operator<<(std::ostream& os, Offset offset) { return os << "offset(" << offset.intValue() << ')'; } #endif static_assert(sizeof(osl::Square) == 4, "square size"); bool osl::Square::isOnBoardSlow() const { return (1<=x() && x() <=9 && 1<=y() && y() <=9); } bool osl::Square::isValid() const { return isPieceStand() || isOnBoard(); } const osl::Square osl:: Square::neighbor(Player P, Direction D) const { return Board_Table.nextSquare(P, *this, D); } const osl::Square osl:: Square::back(Player P, Direction D) const { return Board_Table.nextSquare(alt(P), *this, D); } bool osl::Square::isNeighboring8(Square to) const { return (*this != to) && (to == *this+Board_Table.getShortOffsetNotKnight(Offset32(to,*this))); } std::ostream& osl::operator<<(std::ostream& os, Square square) { if (square.isPieceStand()) return os << "OFF"; return os << "Square(" << square.x() << square.y() << ")"; } static_assert(sizeof(osl::Piece) == 4, "piece size"); std::ostream& osl::operator<<(std::ostream& os,const Piece piece) { if (piece.isPiece()) os << "Piece(" << piece.owner() << "," << piece.ptype() << ",num=" << piece.number() << "," << piece.square() << ')'; else if (piece == Piece::EMPTY()) os << "PIECE_EMPTY"; else if (piece == Piece::EDGE()) os << "PIECE_EDGE"; else os << "unkown piece?!"; return os; } const osl::Piece osl::Piece::makeKing(Player owner, Square position) { const int number = ((owner == BLACK) ? (int)KingTraits::index : (int)KingTraits::index); return Piece(owner, KING, number, position); } namespace osl { static_assert(sizeof(Move) == 4, "move size"); } //namespace osl bool osl::Move::isValid() const { if (! isNormal()) return false; const Square from = this->from(); if (! from.isValid()) return false; const Square to = this->to(); if (! to.isOnBoard()) return false; return osl::isValid(ptype()) && osl::isValid(capturePtype()) && capturePtype()!=KING && osl::isValid(player()); } const osl::Move osl::Move::rotate180() const { if (isPass()) return Move::PASS(alt(player())); if (! isNormal()) return *this; return Move(from().rotate180Safe(), to().rotate180(), ptype(), capturePtype(), isPromotion(), alt(player())); } std::ostream& osl::operator<<(std::ostream& os,const Move move) { if (move == Move::DeclareWin()) return os << "MOVE_DECLARE_WIN"; if (move.isInvalid()) return os << "MOVE_INVALID"; if (move.isPass()) return os << "MOVE_PASS"; const Player turn = move.player(); if (move.isValid()) { if (move.from().isPieceStand()) { os << "Drop(" << turn << "," << move.ptype() << "," << move.to() << ")"; } else { const Ptype capture_ptype=move.capturePtype(); os << "Move(" << turn << "," << move.ptype() << "," << move.from() << "->" << move.to() ; if (move.promoteMask()) os << ",promote"; if (capture_ptype != PTYPE_EMPTY) os << ",capture=" << capture_ptype; os << ")"; } } else { os << "InvalidMove " << move.from() << " " << move.to() << " " << move.ptypeO() << " " << move.oldPtypeO() << " " << move.promoteMask() << " " << move.capturePtype() << "\n"; } return os; } unsigned int osl::Move::hash() const { assert(capturePtype() == PTYPE_EMPTY); // return move_phash(intValue()); return intValue(); } const osl::Move osl::Move:: fromMove16(Move16 move16, const SimpleState& state) { if (move16==MOVE16_NONE) return Move(); Player turn=state.turn(); Square to=SquareCompressor::melt((move16>>8)&0x7f); if((move16&0x80)!=0){ Ptype ptype=(Ptype)(move16-0x80); return Move(to,ptype,turn); } Square from=SquareCompressor::melt(move16&0x7f); Ptype ptype=state[from].ptype(); Ptype capture_ptype=state[to].ptype(); bool is_promote=(move16&0x8000)!=0; if(is_promote) return Move(from,to,::osl::promote(ptype),capture_ptype,true,turn); else return Move(from,to,ptype,capture_ptype,false,turn); } osl::Move16 osl::Move::toMove16() const { if (isInvalid()) return MOVE16_NONE; if (isDrop()) return Move16(0x80+(uint16_t)ptype()+((SquareCompressor::compress(to()))<<8)); if (isPromotion()) return Move16(SquareCompressor::compress(from())+(SquareCompressor::compress(to())<<8)+0x8000); return Move16(SquareCompressor::compress(from())+(SquareCompressor::compress(to())<<8)); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/numEffectState.cc0000644000000000000000000011607412317712235017425 0ustar rootroot/* numEffectState.cc */ #include "osl/numEffectState.h" #include "osl/numEffectState.tcc" #include "osl/simpleState.tcc" #include "osl/bits/numSimpleEffect.tcc" #include "osl/move_classifier/moveAdaptor.h" #include "osl/move_classifier/check_.h" #include "osl/move_classifier/safeMove.h" #include "osl/move_classifier/pawnDropCheckmate.h" #include "osl/move_generator/allMoves.h" #include "osl/move_generator/escape_.h" #include "osl/move_generator/move_action.h" #include "osl/move_generator/effect_action.h" #include #if (defined(__i386__) || defined(__x86_64__)) && !defined(OSL_NO_SSE) #include typedef __v2di v2di; #endif bool osl::operator==(const NumEffectState& st1, const NumEffectState& st2) { assert(st1.isConsistent(true)); assert(st2.isConsistent(true)); if (!(st1.effects == st2.effects)) return false; if (!(st1.pieces_onboard == st2.pieces_onboard)) return false; if (!(st1.promoted == st2.promoted)) return false; if (!(st1.pin_or_open == st2.pin_or_open)) return false; if (!(st1.king_mobility == st2.king_mobility)) return false; if (!(st1.king8infos == st2.king8infos)) return false; return (static_cast(st1) == static_cast(st2)); } const osl::checkmate::King8Info osl:: NumEffectState::king8Info(Player king) const { return King8Info(Iking8Info(king)); } template void osl::NumEffectState::makeKing8Info() { const Player altP=alt(P); #ifdef ALLOW_KING_ABSENCE if (kingSquare

().isPieceStand()) return; #endif king8infos[P]=King8Info::make(*this,kingSquare

()).uint64Value(); } osl:: NumEffectState::NumEffectState(const SimpleState& st) : SimpleState(st),effects(st) { pieces_onboard[0].resetAll(); pieces_onboard[1].resetAll(); promoted.resetAll(); effects.effected_mask[0].resetAll(); effects.effected_mask[1].resetAll(); effects.effected_changed_mask[0].resetAll(); effects.effected_changed_mask[1].resetAll(); for(int num=0;num<40;num++){ Piece p=pieceOf(num); if (p.isOnBoard()){ pieces_onboard[p.owner()].set(num); if (p.isPromoted()) promoted.set(num); for(int i=0;i<2;i++){ Player pl=indexToPlayer(i); if(hasEffectAt(pl,p.square())) { effects.effected_mask[i].set(num); effects.effected_changed_mask[i].set(num); } } } } makePinOpen(BLACK); makePinOpen(WHITE); if(kingSquare().isOnBoard()) makeKing8Info(); if(kingSquare().isOnBoard()) makeKing8Info(); } osl:: NumEffectState::~NumEffectState() { } const osl::Piece osl:: NumEffectState::selectCheapPiece(PieceMask effect) const { if (! effect.any()) return Piece::EMPTY(); mask_t pieces = effect.selectBit(), ppieces; if (pieces.any()) { ppieces = pieces & promoted.getMask(); pieces &= ~ppieces; if (pieces.any()) return pieceOf(pieces.bsf()+PtypeFuns::indexNum*32); return pieceOf(ppieces.bsf()+PtypeFuns::indexNum*32); } pieces = effect.selectBit(); if (pieces.any()) { ppieces = pieces & promoted.getMask(); pieces &= ~ppieces; if (pieces.any()) return pieceOf(pieces.bsf()+PtypeFuns::indexNum*32); return pieceOf(ppieces.bsf()+PtypeFuns::indexNum*32); } mask_t king = effect.selectBit(); effect.clearBit(); if (effect.none()) return pieceOf(king.bsf()+PtypeFuns::indexNum*32); // depends on current piece numbers: , KE 18, GI 22, KI 26, , , KA 36, HI 38, const int index = 0; ppieces = effect.getMask(index) & promoted.getMask(index); pieces = effect.getMask(index) & ~ppieces; if (pieces.none() || ppieces.none()) return pieceOf(pieces.any() ? pieces.bsf() : ppieces.bsf()); const int num = pieces.bsf(), nump = ppieces.bsf(); if (Piece_Table.getPtypeOf(num) == Piece_Table.getPtypeOf(nump)) return pieceOf(num); return pieceOf(std::min(num, nump)); } const osl::Piece osl:: NumEffectState::findThreatenedPiece(Player P) const { assert(! inCheck(P)); PieceMask pieces = piecesOnBoard(P) & effectedMask(alt(P)); PieceMask nolance = pieces; nolance.clearBit(); int pp=-1, npp=-1, ret=-1; const int lance_index = PtypeFuns::indexNum; // 64bit: 0, 32bit: 1 for (int i=lance_index; i>=0; --i) { mask_t all = nolance.getMask(i); mask_t promoted = all & promotedPieces().getMask(i); mask_t notpromoted = all & ~promoted; if (promoted.any()) { pp = promoted.bsr() + i*32; notpromoted &= ~Ptype_Table.getMaskLow(Piece_Table.getPtypeOf(pp)); } if (notpromoted.any()) npp = notpromoted.bsr() + i*32; ret = std::max(pp, npp); if (ret >= PtypeTraits::indexMin) return pieceOf(ret); } mask_t lance = pieces.selectBit(); if (lance.any()) { mask_t plance = lance & promotedPieces().getMask(lance_index); if (plance.any()) return pieceOf(plance.bsr()+lance_index*32); return pieceOf(lance.bsr()+lance_index*32); } if (ret >= 0) { assert(Piece_Table.getPtypeOf(ret) == PAWN); return pieceOf(ret); } return Piece::EMPTY(); } bool osl:: NumEffectState::wasCheckEvasion(Move last_move) const { if (! last_move.isNormal()) return false; const Square from = last_move.from(), to = last_move.to(); if (last_move.ptype() == KING) { if (last_move.isCapture() && hasEffectIf(last_move.capturePtypeO(), to, from)) return true; return hasEffectAt(turn(), from); } if (last_move.isCapture()) return hasEffectIf(last_move.capturePtypeO(), to, kingSquare(alt(turn()))) && !Board_Table.isBetweenSafe(from, to, kingSquare(alt(turn()))); const Piece piece = pieceOnBoard(to); if (! pin(alt(turn())).test(piece.number())) return false; if (last_move.isDrop() || last_move.oldPtype() == KNIGHT) return true; const Direction d=pinnedDir(piece); return primDir(d) !=primDirUnsafe(Board_Table.getShort8Unsafe(piece.owner(), from,to)); } void osl::NumEffectState::makeMove(Move move) { assert(turn() == move.player()); if (move.isPass()) { makeMovePass(); return; } assert(isAlmostValidMove(move)); const Square from=move.from(); const Square to=move.to(); if (from.isPieceStand()) { doDropMove(to,move.ptype()); } else { const Piece captured = pieceOnBoard(to); if (captured != Piece::EMPTY()) { doCaptureMove(from,to,captured,move.promoteMask()); } else { doSimpleMove(from,to,move.promoteMask()); } } changeTurn(); } void osl::NumEffectState:: doSimpleMove(Square from, Square to, int promoteMask) { Piece oldPiece; int num; PtypeO oldPtypeO, newPtypeO; CArray pin_or_open_backup; KingMobility king_mobility_backup; PieceMask promoted_backup; CArray effected_mask_backup; CArray effected_changed_mask_backup; CArray king8infos_backup; mobility::MobilityTable mobilityTable; if (turn()==BLACK){ prologueSimple(Player2Type(), from, to, promoteMask, oldPiece, num, oldPtypeO, newPtypeO, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup,king8infos_backup,mobilityTable); } else{ prologueSimple(Player2Type(), from, to, promoteMask, oldPiece, num, oldPtypeO, newPtypeO, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup,king8infos_backup,mobilityTable); } if (promoteMask!=0 && num < PtypeTraits::indexLimit) clearPawn(turn(),from); } void osl::NumEffectState:: doCaptureMove(Square from, Square to, Piece target, int promoteMask) { Piece oldPiece; PtypeO oldPtypeO, capturePtypeO, newPtypeO; int num0, num1, num1Index; mask_t num1Mask; CArray pin_or_open_backup; KingMobility king_mobility_backup; PieceMask promoted_backup; CArray effected_mask_backup; CArray effected_changed_mask_backup; CArray king8infos_backup; mobility::MobilityTable mobilityTable; if(turn()==BLACK){ prologueCapture(Player2Type(), from, to, target, promoteMask, oldPiece, oldPtypeO, capturePtypeO, newPtypeO, num0, num1, num1Index,num1Mask, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup,king8infos_backup,mobilityTable); } else{ prologueCapture(Player2Type(), from, to, target, promoteMask, oldPiece, oldPtypeO, capturePtypeO, newPtypeO, num0, num1, num1Index,num1Mask, pin_or_open_backup, king_mobility_backup, promoted_backup, effected_mask_backup, effected_changed_mask_backup,king8infos_backup,mobilityTable); } const Ptype capturePtype=target.ptype(); if (capturePtype==PAWN) clearPawn(alt(turn()),to); if (promoteMask!=0 && num0::indexLimit) clearPawn(turn(),from); } void osl::NumEffectState:: doDropMove(Square to,Ptype ptype) { Piece oldPiece; PtypeO ptypeO; int num, numIndex; mask_t numMask; CArray pin_or_open_backup; KingMobility king_mobility_backup; CArray effected_mask_backup; CArray effected_changed_mask_backup; CArray king8infos_backup; mobility::MobilityTable mobilityTable; if(turn()==BLACK){ prologueDrop(Player2Type(), to, ptype, oldPiece, num, ptypeO, numIndex, numMask, pin_or_open_backup, king_mobility_backup, effected_mask_backup, effected_changed_mask_backup,king8infos_backup,mobilityTable); } else{ prologueDrop(Player2Type(), to, ptype, oldPiece, num, ptypeO, numIndex, numMask, pin_or_open_backup, king_mobility_backup, effected_mask_backup, effected_changed_mask_backup,king8infos_backup,mobilityTable); } if (ptype==PAWN) setPawn(turn(),to); } template void osl::NumEffectState:: prologueSimple(Player2Type

, Square from, Square to, int promoteMask, Piece& oldPiece, int& num, PtypeO& oldPtypeO, PtypeO& new_ptypeo, CArray& pin_or_open_backup, KingMobility& king_mobility_backup, PieceMask& promoted_backup, CArray& effected_mask_backup, CArray& effected_changed_mask_backup, CArray& king8infos_backup, MobilityTable &mobility_backup) { mobility_backup = effects.mobilityTable; pin_or_open_backup = pin_or_open; king_mobility_backup = king_mobility; effected_mask_backup = effects.effected_mask; effected_changed_mask_backup = effects.effected_changed_mask; king8infos_backup=king8infos; oldPiece=pieceAt(from); Piece newPiece=oldPiece.promoteWithMask(promoteMask); newPiece+=(to-from); num=oldPiece.number(); oldPtypeO=oldPiece.ptypeO(); new_ptypeo=newPiece.ptypeO(); // 自分自身ã®åйãを外㙠setPieceOf(num,newPiece); effects.clearChangedEffects(); effects.clearEffectedChanged(); effects.template doEffect(*this,oldPtypeO,from,num); // 自分自身ãŒãƒ–ロックã—ã¦ã„ãŸpromote?ã®å»¶é•· // ã‚ã‚‹ã„ã¯è‡ªåˆ†è‡ªèº«ã®ãƒ–ロック effects.effectedNumTable[num].clear(); setBoard(to,newPiece); effects.template doBlockAt(*this,to,num); setBoard(from,Piece::EMPTY()); effects.template doBlockAt(*this,from,num); effects.template doEffect(*this,new_ptypeo,to,num); if (oldPtypeO == newPtypeO(P,KING)) makePinOpen(P); else { Direction lastD=UL; pin_or_open[P].reset(num); recalcPinOpen(from,lastD,P); recalcPinOpen(to,lastD,P); } { Direction lastD=UL; pin_or_open[alt(P)].reset(num); recalcPinOpen(from,lastD,alt(P)); recalcPinOpen(to,lastD,alt(P)); } promoted_backup = promoted; if (promoteMask) promoted.set(num); if(hasEffectAt(BLACK,to)) effects.effected_mask[BLACK].set(num); else effects.effected_mask[BLACK].reset(num); if(hasEffectAt(WHITE,to)) effects.effected_mask[WHITE].set(num); else effects.effected_mask[WHITE].reset(num); effects.effected_changed_mask[BLACK].set(num); effects.effected_changed_mask[WHITE].set(num); { BoardMask changed=changedEffects(BLACK)|changedEffects(WHITE); changed.set(from); changed.set(to); if(changed.anyInRange(Board_Mask_Table3x3.mask(kingSquare())) || pin_or_open[BLACK]!=pin_or_open_backup[BLACK]) makeKing8Info(); if(changed.anyInRange(Board_Mask_Table3x3.mask(kingSquare())) || pin_or_open[WHITE]!=pin_or_open_backup[WHITE]) makeKing8Info(); } } void osl::NumEffectState:: epilogueSimple(Square from, Square to, Piece oldPiece, int num, PtypeO oldPtypeO, PtypeO newPtypeO, const CArray& pin_or_open_backup, const KingMobility& king_mobility_backup, const PieceMask& promoted_backup, const CArray& effected_mask_backup, const CArray& effected_changed_mask_backup, const CArray& king8infos_backup, const MobilityTable & mobility_backup) { setPieceOf(num,oldPiece); effects.doEffect(*this,newPtypeO,to,num); setBoard(from,oldPiece); effects.effectedNumTable[num].clear(); effects.doBlockAt(*this,from,num); setBoard(to,Piece::EMPTY()); effects.doBlockAt(*this,to,num); effects.doEffect(*this,oldPtypeO,from,num); effects.invalidateChangedEffects(); pin_or_open = pin_or_open_backup; king_mobility = king_mobility_backup; promoted = promoted_backup; effects.effected_mask = effected_mask_backup; effects.effected_changed_mask = effected_changed_mask_backup; effects.mobilityTable = mobility_backup; king8infos = king8infos_backup; } template void osl::NumEffectState:: prologueDrop(Player2Type

, Square to, Ptype ptype, Piece& oldPiece, int& num, PtypeO& ptypeO, int& numIndex, mask_t& numMask, CArray& pin_or_open_backup, KingMobility& king_mobility_backup, CArray& effected_mask_backup, CArray& effected_changed_mask_backup, CArray& king8infos_backup, MobilityTable &mobility_backup) { king8infos_backup = king8infos; mobility_backup = effects.mobilityTable; pin_or_open_backup = pin_or_open; king_mobility_backup = king_mobility; effected_mask_backup = effects.effected_mask; effected_changed_mask_backup = effects.effected_changed_mask; #if OSL_WORDSIZE == 64 numIndex=0; #elif OSL_WORDSIZE == 32 numIndex=Ptype_Table.getIndex(ptype); #endif const mask_t ownMochigoma= standMask(P).getMask(numIndex) & Ptype_Table.getMaskLow(ptype); assert(ownMochigoma.any()); numMask=ownMochigoma.lowestBit(); int numLow = ownMochigoma.bsf(); num = numLow|(numIndex<<5); oldPiece=pieceOf(num); Piece newPiece=oldPiece; newPiece+=to-Square::STAND(); ptypeO=newPiece.ptypeO(); setPieceOf(num,newPiece); effects.clearChangedEffects(); effects.clearEffectedChanged(); effects.template doBlockAt(*this,to,num); effects.template doEffect(*this,ptypeO,to,num); setBoard(to,newPiece); standMask(P).xorMask(numIndex,numMask); stand_count[P][ptype-PTYPE_BASIC_MIN]--; pieces_onboard[P].xorMask(numIndex,numMask); { Direction lastD=UL; recalcPinOpen(to,lastD,P); } { Direction lastD=UL; recalcPinOpen(to,lastD,alt(P)); } if(hasEffectAt(BLACK,to)) effects.effected_mask[BLACK].set(num); else effects.effected_mask[BLACK].reset(num); if (hasEffectAt(WHITE,to)) effects.effected_mask[WHITE].set(num); else effects.effected_mask[WHITE].reset(num); effects.effected_changed_mask[BLACK].set(num); effects.effected_changed_mask[WHITE].set(num); { BoardMask changed=changedEffects(BLACK)|changedEffects(WHITE); changed.set(to); if(changed.anyInRange(Board_Mask_Table3x3.mask(kingSquare())) || pin_or_open[BLACK]!=pin_or_open_backup[BLACK]) makeKing8Info(); if(changed.anyInRange(Board_Mask_Table3x3.mask(kingSquare())) || pin_or_open[WHITE]!=pin_or_open_backup[WHITE]) makeKing8Info(); } } template void osl::NumEffectState:: epilogueDrop(Player2Type

, Square to, Ptype ptype, Piece oldPiece, int num, PtypeO ptypeO, int numIndex, mask_t numMask, const CArray& pin_or_open_backup, const KingMobility& king_mobility_backup, const CArray& effected_mask_backup, const CArray& effected_changed_mask_backup, const CArray& king8infos_backup, const MobilityTable& mobility_backup) { standMask(P).xorMask(numIndex,numMask); stand_count[P][ptype-PTYPE_BASIC_MIN]++; pieces_onboard[P].xorMask(numIndex,numMask); setBoard(to,Piece::EMPTY()); effects.template doEffect(*this,ptypeO,to,num); effects.template doBlockAt(*this,to,num); setPieceOf(num,oldPiece); effects.effectedNumTable[num].clear(); effects.invalidateChangedEffects(); pin_or_open = pin_or_open_backup; king_mobility = king_mobility_backup; effects.effected_mask = effected_mask_backup; effects.effected_changed_mask = effected_changed_mask_backup; effects.mobilityTable = mobility_backup; king8infos = king8infos_backup; } template void osl::NumEffectState:: prologueCapture(Player2Type

, Square from, Square to, Piece target, int promoteMask, Piece& oldPiece, PtypeO& oldPtypeO, PtypeO& capturePtypeO, PtypeO& new_ptypeo, int& num0, int& num1, int& num1Index, mask_t& num1Mask, CArray& pin_or_open_backup, KingMobility& king_mobility_backup, PieceMask& promoted_backup, CArray& effected_mask_backup, CArray& effected_changed_mask_backup, CArray& king8infos_backup, MobilityTable &mobility_backup) { mobility_backup = effects.mobilityTable; pin_or_open_backup = pin_or_open; king_mobility_backup = king_mobility; effected_mask_backup = effects.effected_mask; effected_changed_mask_backup = effects.effected_changed_mask; king8infos_backup = king8infos; num1=target.number(); num1Index=PieceMask::numToIndex(num1); num1Mask=PieceMask::numToMask(num1); pieces_onboard[alt(P)].xorMask(num1Index,num1Mask); standMask(P).xorMask(num1Index,num1Mask); oldPiece=pieceAt(from); Piece newPiece=oldPiece.promoteWithMask(promoteMask); newPiece+=(to-from); num0=oldPiece.number(); setPieceOf(num0,newPiece); setPieceOf(num1,target.captured()); oldPtypeO=oldPiece.ptypeO(); new_ptypeo=newPiece.ptypeO(); capturePtypeO=target.ptypeO(); stand_count[P][unpromote(getPtype(capturePtypeO))-PTYPE_BASIC_MIN]++; effects.clearChangedEffects(); effects.clearEffectedChanged(); effects.setChangedPieces(effectSetAt(to)); effects.template doEffect(*this,capturePtypeO,to,num1); effects.template doEffect(*this,oldPtypeO,from,num0); setBoard(from,Piece::EMPTY()); effects.template doBlockAt(*this,from,num0); effects.effectedNumTable[num0]=effects.effectedNumTable[num1]; effects.effectedNumTable[num1].clear(); setBoard(to,newPiece); effects.template doEffect(*this,new_ptypeo,to,num0); if (oldPtypeO == newPtypeO(P,KING)) makePinOpen(P); else { Direction lastD=UL; pin_or_open[P].reset(num0); pin_or_open[P].reset(num1); // captured is not pin recalcPinOpen(from,lastD,P); recalcPinOpen(to,lastD,P); } { Direction lastD=UL; pin_or_open[alt(P)].reset(num0); pin_or_open[alt(P)].reset(num1); // captured is not pin recalcPinOpen(from,lastD,alt(P)); recalcPinOpen(to,lastD,alt(P)); } promoted_backup = promoted; promoted.reset(num1); effects.effected_mask[BLACK].reset(num1); effects.effected_mask[WHITE].reset(num1); if (promoteMask) promoted.set(num0); if(hasEffectAt(BLACK,to)) effects.effected_mask[BLACK].set(num0); else effects.effected_mask[BLACK].reset(num0); if(hasEffectAt(WHITE,to)) effects.effected_mask[WHITE].set(num0); else effects.effected_mask[WHITE].reset(num0); effects.effected_changed_mask[BLACK].set(num0); effects.effected_changed_mask[WHITE].set(num0); { BoardMask changed=changedEffects(BLACK)|changedEffects(WHITE); changed.set(from); changed.set(to); if(changed.anyInRange(Board_Mask_Table3x3.mask(kingSquare())) || pin_or_open[BLACK]!=pin_or_open_backup[BLACK]) makeKing8Info(); if(changed.anyInRange(Board_Mask_Table3x3.mask(kingSquare())) || pin_or_open[WHITE]!=pin_or_open_backup[WHITE]) makeKing8Info(); } } template void osl::NumEffectState:: epilogueCapture(Player2Type

, Square from, Square to, Piece target, Piece oldPiece, PtypeO oldPtypeO, PtypeO capturePtypeO, PtypeO newPtypeO, int num0, int num1, int num1Index, mask_t num1Mask, const CArray& pin_or_open_backup, const KingMobility& king_mobility_backup, const PieceMask& promoted_backup, const CArray& effected_mask_backup, const CArray& effected_changed_mask_backup, const CArray& king8infos_backup, const MobilityTable &mobility_backup) { standMask(P).xorMask(num1Index,num1Mask); stand_count[P][unpromote(getPtype(capturePtypeO))-PTYPE_BASIC_MIN]--; pieces_onboard[alt(P)].xorMask(num1Index,num1Mask); effects.effectedNumTable[num1]=effects.effectedNumTable[num0]; effects.effectedNumTable[num0].clear(); setPieceOf(num0,oldPiece); setPieceOf(num1,target); effects.template doEffect(*this,newPtypeO,to,num0); setBoard(from,oldPiece); setBoard(to,target); effects.template doBlockAt(*this,from,num0); effects.template doEffect(*this,capturePtypeO,to,num1); effects.template doEffect(*this,oldPtypeO,from,num0); effects.invalidateChangedEffects(); pin_or_open = pin_or_open_backup; king_mobility = king_mobility_backup; promoted = promoted_backup; effects.effected_mask = effected_mask_backup; effects.effected_changed_mask = effected_changed_mask_backup; effects.mobilityTable = mobility_backup; king8infos = king8infos_backup; } #ifndef MINIMAL bool osl::NumEffectState::isConsistent(bool showError) const { if (!SimpleState::isConsistent(showError)) { if (showError) std::cerr << "error before effect\n"; return false; } effect::NumSimpleEffectTable effects1(*this); if (!(effects1==effects)) { if (showError) { std::cerr << "Effect error 1" << std::endl; std::cerr << *this; for(int y=1;y<=9;y++) for(int x=9;x>0;x--) { Square pos(x,y); if (!(effects1.effectSetAt(pos)==effects.effectSetAt(pos))) { std::cerr << pos << ",real=" << effects.effectSetAt(pos) << ",ideal=" << effects1.effectSetAt(pos) << std::endl; } } for(int num=0;num<=39;num++){ for(int i=0;i<8;i++){ Direction d=static_cast(i); if(effects.effectedNumTable[num][d]!=effects1.effectedNumTable[num][d]){ std::cerr << "piece=" << pieceOf(num) << ",num=" << num << ",d=" << d << ",v1=" << effects.effectedNumTable[num][d] << ",v2=" << effects1.effectedNumTable[num][d] << std::endl; } } } std::cerr << effects.effectedNumTable << std::endl; } return false; } for (int z=0; z<2; ++z) { const Player p = indexToPlayer(z); #ifdef ALLOW_KING_ABSENCE if (kingSquare(p).isPieceStand()) continue; #endif #if 0 const PieceMask pin2 = effect_util::Pin::make(*this, p); if (pin(p) != pin2) { if (showError) std::cerr << "pin for " << p << " differs " << pin(p) << " " << pin2 << "\n"; return false; } #endif King8Info king8info2 = King8Info::make(alt(p), *this); if (King8Info(Iking8Info(p)).uint64Value() != king8info2.uint64Value()) { if (showError) std::cerr << "king8info for " << p << " differs \n" << King8Info(Iking8Info(p)) << "\n" << king8info2 << "\n"; return false; } } for (int i=0; i changed_squares = {{ changedEffects(BLACK), changedEffects(WHITE) }}; const BoardMask changed_all = changed_squares[BLACK] | changed_squares[WHITE]; CArray each_effect, prev_effect; for (int i=0; i bool #if (defined __GNUC__) && (! defined GPSONE) && (! defined GPSUSIONE) __attribute__ ((used,noinline)) #endif osl::NumEffectState::isAlmostValidMove(Move move) const{ assert(move.isValid()); assert(move.isNormal()); assert(this->turn() == move.player()); assert(isValidMoveByRule(move, true)); const Square from=move.from(); if (from.isPieceStand()) // æ‰“ã¤æ‰‹ return isAlmostValidDrop(move); const Square to=move.to(); const Piece from_piece = this->pieceAt(from); if (! testValidityOtherThanEffect(move)) return false; if(!hasEffectByPiece(from_piece,to)){ if (show_error) { std::cerr << " No such move2 : " << move << std::endl; } return false; } return true; } bool osl::NumEffectState:: isAlmostValidMove(Move move,bool show_error) const{ #ifdef MINIMAL show_error=false; #endif if(show_error) return isAlmostValidMove(move); else return isAlmostValidMove(move); } #ifndef MINIMAL void osl::NumEffectState::showEffect(std::ostream& os) const { os<< static_cast(*this); for(int y=1;y<=9;y++){ os << 'P' << y; for(int x=9;x>0;x--){ Square pos(x,y); os << csa::show(pieceAt(pos)) << effectSetAt(pos); } os << std::endl; } // æŒã¡é§’ã®è¡¨ç¤º for(int num=0;num(target,pins,mask,defense); makePinOpenDir(target,pins,mask,defense); makePinOpenDir(target,pins,mask,defense); makePinOpenDir(target,pins,mask,defense); makePinOpenDir(target,pins,mask,defense); makePinOpenDir

(target,pins,mask,defense); makePinOpenDir(target,pins,mask,defense); makePinOpenDir(target,pins,mask,defense); return pins; } void osl::NumEffectState:: makePinOpen(osl::Player defense) { pin_or_open[defense]=makePinOpen(kingSquare(defense),defense); } const osl::mask_t osl::NumEffectState:: allEffectAt(Player attack, Ptype ptype, Square target) const { switch (ptype) { case PAWN: case PPAWN: return allEffectAt(attack, target); case LANCE: case PLANCE: return allEffectAt(attack, target); case KNIGHT: case PKNIGHT: return allEffectAt(attack, target); case SILVER: case PSILVER: return allEffectAt(attack, target); case GOLD: return allEffectAt(attack, target); case BISHOP: case PBISHOP: return allEffectAt(attack, target); case ROOK: case PROOK: return allEffectAt(attack, target); case KING: return allEffectAt(attack, target); default: assert(0); } return mask_t(); } void osl::NumEffectState::copyFrom(const NumEffectState& src) { #ifndef MINIMAL (*this).used_mask=src.used_mask; #endif (*this).stand_mask=src.stand_mask; #if (defined(__i386__) || defined(__x86_64__)) && !defined(OSL_NO_SSE) { v2di b16=*((v2di*)&src.board[16]); v2di b20=*((v2di*)&src.board[20]); v2di b24=*((v2di*)&src.board[24]); v2di b32=*((v2di*)&src.board[32]); v2di b36=*((v2di*)&src.board[36]); v2di b40=*((v2di*)&src.board[40]); v2di b48=*((v2di*)&src.board[48]); v2di b52=*((v2di*)&src.board[52]); v2di b56=*((v2di*)&src.board[56]); *((v2di*)&(*this).board[16])=b16; *((v2di*)&(*this).board[20])=b20; *((v2di*)&(*this).board[24])=b24; *((v2di*)&(*this).board[32])=b32; *((v2di*)&(*this).board[36])=b36; *((v2di*)&(*this).board[40])=b40; *((v2di*)&(*this).board[48])=b48; *((v2di*)&(*this).board[52])=b52; *((v2di*)&(*this).board[56])=b56; v2di b64=*((v2di*)&src.board[64]); v2di b68=*((v2di*)&src.board[68]); v2di b72=*((v2di*)&src.board[72]); v2di b80=*((v2di*)&src.board[80]); v2di b84=*((v2di*)&src.board[84]); v2di b88=*((v2di*)&src.board[88]); v2di b96=*((v2di*)&src.board[96]); v2di b100=*((v2di*)&src.board[100]); v2di b104=*((v2di*)&src.board[104]); *((v2di*)&(*this).board[64])=b64; *((v2di*)&(*this).board[68])=b68; *((v2di*)&(*this).board[72])=b72; *((v2di*)&(*this).board[80])=b80; *((v2di*)&(*this).board[84])=b84; *((v2di*)&(*this).board[88])=b88; *((v2di*)&(*this).board[96])=b96; *((v2di*)&(*this).board[100])=b100; *((v2di*)&(*this).board[104])=b104; v2di b112=*((v2di*)&src.board[112]); v2di b116=*((v2di*)&src.board[116]); v2di b120=*((v2di*)&src.board[120]); v2di b128=*((v2di*)&src.board[128]); v2di b132=*((v2di*)&src.board[132]); v2di b136=*((v2di*)&src.board[136]); v2di b144=*((v2di*)&src.board[144]); v2di b148=*((v2di*)&src.board[148]); v2di b152=*((v2di*)&src.board[152]); *((v2di*)&(*this).board[112])=b112; *((v2di*)&(*this).board[116])=b116; *((v2di*)&(*this).board[120])=b120; *((v2di*)&(*this).board[128])=b128; *((v2di*)&(*this).board[132])=b132; *((v2di*)&(*this).board[136])=b136; *((v2di*)&(*this).board[144])=b144; *((v2di*)&(*this).board[148])=b148; *((v2di*)&(*this).board[152])=b152; v2di p0=*((v2di*)&src.pieces[0]); v2di p4=*((v2di*)&src.pieces[4]); v2di p8=*((v2di*)&src.pieces[8]); v2di p12=*((v2di*)&src.pieces[12]); v2di p16=*((v2di*)&src.pieces[16]); v2di p20=*((v2di*)&src.pieces[20]); v2di p24=*((v2di*)&src.pieces[24]); v2di p28=*((v2di*)&src.pieces[28]); v2di p32=*((v2di*)&src.pieces[32]); v2di p36=*((v2di*)&src.pieces[36]); *((v2di*)&(*this).pieces[0])=p0; *((v2di*)&(*this).pieces[4])=p4; *((v2di*)&(*this).pieces[8])=p8; *((v2di*)&(*this).pieces[12])=p12; *((v2di*)&(*this).pieces[16])=p16; *((v2di*)&(*this).pieces[20])=p20; *((v2di*)&(*this).pieces[24])=p24; *((v2di*)&(*this).pieces[28])=p28; *((v2di*)&(*this).pieces[32])=p32; *((v2di*)&(*this).pieces[36])=p36; } #else for(int x=1;x<=9;x++) for(int y=1;y<=9;y++) (*this).board[Square(x,y).index()]=src.board[Square(x,y).index()]; (*this).pieces=src.pieces; #endif (*this).pawnMask=src.pawnMask; this->stand_count = src.stand_count; this->player_to_move=src.player_to_move; effects.copyFrom(src.effects); this->pieces_onboard=src.pieces_onboard; (*this).promoted=src.promoted; (*this).pin_or_open=src.pin_or_open; (*this).king_mobility=src.king_mobility; (*this).king8infos=src.king8infos; } void osl::NumEffectState::copyFrom(const SimpleState& src) { copyFrom(NumEffectState(src)); } bool osl::NumEffectState::isSafeMove(Move move) const { using namespace move_classifier; return ConditionAdaptor::isMember(*this, move); } bool osl::NumEffectState::isCheck(Move move) const { using namespace move_classifier; return PlayerMoveAdaptor::isMember(*this, move); } bool osl::NumEffectState::isPawnDropCheckmate(Move move) const { using namespace move_classifier; return PlayerMoveAdaptor::isMember(*this, move); } bool osl::NumEffectState::isDirectCheck(Move move) const { using namespace move_classifier; return PlayerMoveAdaptor::isMember(*this, move); } bool osl::NumEffectState::isOpenCheck(Move move) const { using namespace move_classifier; return ConditionAdaptor::isMember(*this, move); } #ifndef MINIMAL void osl::NumEffectState::generateAllUnsafe(MoveVector& out) const { move_action::Store store(out); move_generator::AllMoves::generate(turn(), *this, store); } void osl::NumEffectState::generateLegal(MoveVector& moves) const { if (inCheck()) { // 王手ãŒã‹ã‹ã£ã¦ã„る時ã¯é˜²ã手ã®ã¿ã‚’生æˆ, 王手回é¿ã¯ä¸æˆã‚‚ç”Ÿæˆ GenerateEscapeKing::generate(*this, moves); } else { // ãã†ã§ãªã‘れã°å…¨ã¦ã®æ‰‹ã‚’ç”Ÿæˆ MoveVector all_moves; GenerateAllMoves::generate(turn(), *this, all_moves); // ã“ã®æŒ‡æ‰‹ã¯ï¼Œçމã®ç´ æŠœããŒã‚ã£ãŸã‚Šï¼Œæ‰“æ­©è©°ã®å¯èƒ½æ€§ãŒã‚ã‚‹ã®ã§ // 確èªãŒå¿…è¦ std::copy_if(all_moves.begin(), all_moves.end(), std::back_inserter(moves), [&](Move m){ return this->isSafeMove(m) && ! this->isPawnDropCheckmate(m); }); } } void osl::NumEffectState::generateWithFullUnpromotions(MoveVector& moves) const { generateLegal(moves); if (inCheck()) return; for (int i=0, iend=moves.size(); i(Square, Square) const; template bool NumEffectState:: hasEffectByWithRemove(Square, Square) const; template void NumEffectState::makeKing8Info(); template void NumEffectState::makeKing8Info(); template void NumEffectState:: prologueSimple(Player2Type, Square, Square, int, Piece&, int&, PtypeO&, PtypeO&, CArray&, KingMobility&, PieceMask&, CArray&, CArray&, CArray&, MobilityTable&); template void NumEffectState:: prologueSimple(Player2Type, Square, Square, int, Piece&, int&, PtypeO&, PtypeO&, CArray&, KingMobility&, PieceMask&, CArray&, CArray&, CArray&, MobilityTable&); template void NumEffectState:: prologueCapture(Player2Type, Square, Square, Piece, int, Piece&, PtypeO&, PtypeO&, PtypeO&, int&, int&, int&, mask_t&, CArray&, KingMobility&, PieceMask&, CArray&, CArray&, CArray&, MobilityTable&); template void NumEffectState:: prologueCapture(Player2Type, Square, Square, Piece, int, Piece&, PtypeO&, PtypeO&, PtypeO&, int&, int&, int&, mask_t&, CArray&, KingMobility&, PieceMask&, CArray&, CArray&, CArray&, MobilityTable&); template void NumEffectState:: prologueDrop(Player2Type, Square, Ptype, Piece&, int&, PtypeO&, int&, mask_t&, CArray&, KingMobility&, CArray&, CArray&, CArray&, MobilityTable&); template void NumEffectState:: prologueDrop(Player2Type, Square, Ptype, Piece&, int&, PtypeO&, int&, mask_t&, CArray&, KingMobility&, CArray&, CArray&, CArray&, MobilityTable&); template void NumEffectState:: epilogueCapture(Player2Type, Square, Square, Piece, Piece, PtypeO, PtypeO, PtypeO, int, int, int, mask_t, const CArray&, const KingMobility&, const PieceMask&, const CArray&, const CArray&, const CArray&, const MobilityTable&); template void NumEffectState:: epilogueCapture(Player2Type, Square, Square, Piece, Piece, PtypeO, PtypeO, PtypeO, int, int, int, mask_t, const CArray&, const KingMobility&, const PieceMask&, const CArray&, const CArray&, const CArray&, const MobilityTable&); template void NumEffectState:: epilogueDrop(Player2Type, Square, Ptype, Piece, int, PtypeO, int, mask_t, const CArray&, const KingMobility&, const CArray&, const CArray&, const CArray&, const MobilityTable&); template void NumEffectState:: epilogueDrop(Player2Type, Square, Ptype, Piece, int, PtypeO, int, mask_t, const CArray&, const KingMobility&, const CArray&, const CArray&, const CArray&, const MobilityTable&); #ifndef DFPNSTATONE template Piece NumEffectState::safeCaptureNotByKing(Square, Piece) const; template Piece NumEffectState::safeCaptureNotByKing(Square, Piece) const; #endif } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/container.cc0000644000000000000000000000366312316770314016472 0ustar rootroot#include "osl/container.h" #include "osl/eval/ptypeEval.h" #include std::ostream& osl::operator<<(std::ostream& os,MoveVector const& mv) { os<< "MoveVector" << std::endl; for (Move m: mv) { os << m << std::endl; } return os< abs(eval::Ptype_Eval_Table.captureValue(ptypeo1))); } }; } // namespace osl void osl::PieceVector::sortByBasic() { std::sort(begin(),end(),PieceBasicLessThan()); } void osl::PieceVector::sortByPtype() { std::sort(begin(),end(),PiecePtypeMoreThan()); } #ifndef MINIMAL std::ostream& osl::operator<<(std::ostream& os,PieceVector const& pv) { os << "PieceVector"; for (Piece p: pv) { os << " " << p; } return os << std::endl; } #endif struct osl::PtypeOSquareVector::PtypeOSquareLessThan { bool operator()(const std::pair& l, const std::pair& r) { const int vall = abs(eval::Ptype_Eval_Table.captureValue(l.first)); const int valr = abs(eval::Ptype_Eval_Table.captureValue(r.first)); if (vall != valr) return vall < valr; return l.second.uintValue() < r.second.uintValue(); } }; void osl::PtypeOSquareVector::sort() { std::sort(begin(),end(),PtypeOSquareLessThan()); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/progress.h0000644000000000000000000002460612316770314016216 0ustar rootroot/* newProgress.h */ #ifndef PROGRESS_EXPERIMENTAL_NEW_PROGRESS_H #define PROGRESS_EXPERIMENTAL_NEW_PROGRESS_H #include "osl/numEffectState.h" #include "osl/eval/midgame.h" #include "osl/container.h" #include namespace osl { namespace progress { template class ProgressN { int progress; public: explicit ProgressN(int value=0) : progress(value) { assert(isValid()); } int value() const { return progress; } bool isValid() const { return (progress >= 0) && (progress < N); } }; template inline bool operator==(ProgressN l, ProgressN r) { return l.value() == r.value(); } template inline bool operator!=(ProgressN l, ProgressN r) { return ! (l == r); } template inline bool operator<(ProgressN l, ProgressN r) { return l.value() < r.value(); } typedef ProgressN<16> Progress16; typedef ProgressN<32> Progress32; namespace ml { struct NewProgressDebugInfo { enum Feature { ATTACK_5X3, DEFENSE_5X3, ATTACK5X5, STAND, EFFECT5X5, KING_RELATIVE_ATTACK, KING_RELATIVE_DEFENSE, NON_PAWN_ATTACKED_PAIR, FEATURE_LIMIT }; CArray black_values; CArray white_values; }; struct NewProgressData { CArray non_pawn_ptype_attacked_pair_eval; MultiInt promotion37_eval; CArray progresses, attack5x5_progresses, stand_progresses, effect_progresses, defenses; CArray rook, bishop, gold, silver, promoted, king_relative_attack, king_relative_defense, non_pawn_ptype_attacked_pair; int pawn_facing, promotion37, piecestand7; }; class NewProgress : private NewProgressData { public: enum { ProgressScale = 2 }; private: static bool initialized_flag; static CArray stand_weight; static CArray attack5x5_weight; static CArray attack5x5_x_weight; static CArray attack5x5_y_weight; static CArray effectstate_weight; static CArray attack_relative; static CArray defense_relative; static CArray king_relative_weight; static CArray attacked_ptype_pair_weight; static CArray pawn_facing_weight; static CArray promotion37_weight; static CArray piecestand7_weight; static int max_progress; void updatePieceKingRelativeBonus(const NumEffectState &state); void updateNonPawnAttackedPtypePair(const NumEffectState& state); template void updateNonPawnAttackedPtypePairOne(const NumEffectState& state); void updatePawnFacing(const NumEffectState& state); template void promotion37One(const NumEffectState& state, int rank); void updatePromotion37(const NumEffectState& state); void updatePieceStand7(const NumEffectState& state); template static void progressOne(const NumEffectState &state, int &attack, int &defense); template void updateAttack5x5PiecesAndState(const NumEffectState &state); template void updateAttack5x5Pieces(PieceMask, const NumEffectState&); template int attack5x5Value(const NumEffectState &state) const; template static int index(Square king, Square target) { const int x_diff = std::abs(king.x() - target.x()); // [0, 4] const int y_diff = (P == BLACK ? king.y() - target.y() : target.y() - king.y()) + 2; // [-2, 2] + 2 return x_diff * 5 + y_diff; } template static int indexX(Square king, Square target) { int target_x = (king.x() > 5 ? 10 - king.x() : king.x()); // [1, 5] int x_diff = king.x() - target.x(); // [-4, 4] if (P == BLACK && king.x() >= 6) { x_diff = -x_diff; } else if (P == WHITE && king.x() >= 5) { x_diff = -x_diff; } const int y_diff = (P == BLACK ? king.y() - target.y() : target.y() - king.y()) + 2; // [-2, 2] + 2 return ((x_diff + 4) * 5 + y_diff) * 5 + target_x - 1; } template static int indexY(Square king, Square target) { const int x_diff = std::abs(king.x() - target.x()); // [0, 4] const int y_diff = (P == BLACK ? king.y() - target.y() : target.y() - king.y()) + 2; // [-2, 2] + 2 const int king_y = (P == BLACK ? king.y() : 10 - king.y()); // [1, 9] return (x_diff * 5 + y_diff) * 9 + king_y - 1; } static int index5x5(int rook, int bishop, int gold, int silver, int promoted) { assert(0 <= promoted && promoted <= 4); return promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook))); } static int index5x5x(int rook, int bishop, int gold, int silver, int promoted, int king_x) { assert(0 <= promoted && promoted <= 4); return king_x - 1 + 5 * (promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook)))); } static int index5x5y(int rook, int bishop, int gold, int silver, int promoted, int king_y) { assert(0 <= promoted && promoted <= 4); return king_y - 1 + 9 * (promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook)))); } template static int indexPerEffect(Square king, Square target, int count) { const int x_diff = std::abs(king.x() - target.x()); // [0, 4] const int y_diff = (P == BLACK ? king.y() - target.y() : target.y() - king.y()) + 2; // [-2, 2] + 2 return x_diff * 5 + y_diff + std::min(8, count) * 25; } template static int indexPerEffectY(Square king, Square target, int count) { const int king_y = (P == BLACK ? king.y() : 10 - king.y()); const int x_diff = std::abs(king.x() - target.x()); // [0, 4] const int y_diff = (P == BLACK ? king.y() - target.y() : target.y() - king.y()) + 2; // [-2, 2] + 2 return king_y - 1 + 9 * (x_diff * 5 + y_diff + std::min(8, count) * 25); } template static int indexPerEffectX(Square king, Square target, int count) { const int king_x = (king.x() > 5 ? 10 - king.x() : king.x()); int x_diff = king.x() - target.x(); // [-4, 4] if ((P == BLACK && (king.x() > 5)) || (P == WHITE && (king.x() >= 5))) x_diff = -x_diff; const int y_diff = (P == BLACK ? king.y() - target.y() : target.y() - king.y()) + 2; // [-2, 2] + 2 return king_x - 1 + 5 * (x_diff + 4 + 9 * (y_diff + 5 * std::min(8, count))); } template static int indexRelative(const Square king, const Ptype ptype, const Square pos) { const int x = std::abs(pos.x() - king.x()); const int y = (king.y() - pos.y()) * (P == osl::BLACK ? 1 : -1) + 8; return (ptype - osl::PTYPE_PIECE_MIN) * 17 * 9 + (x * 17 + y); } static int indexRelative(const Player player, const Square king, const Piece piece) { if (player == BLACK) { return indexRelative(king, piece.ptype(), piece.square()); } else { return indexRelative(king, piece.ptype(), piece.square()); } } public: NewProgress(const NumEffectState &state); int progress() const { return std::max(std::min(progresses[0] + progresses[1] + attack5x5_progresses[0] + attack5x5_progresses[1] + stand_progresses[0] + stand_progresses[1] + effect_progresses[0] + effect_progresses[1] + defenses[0] + defenses[1] + king_relative_attack[0] + king_relative_attack[1] + king_relative_defense[0] + king_relative_defense[1] + non_pawn_ptype_attacked_pair[0] + non_pawn_ptype_attacked_pair[1] + pawn_facing + promotion37 + piecestand7, max_progress-ProgressScale), 0) / ProgressScale; } static int maxProgress() { return max_progress / ProgressScale; } template void updateSub(const NumEffectState &new_state, Move last_move); void update(const NumEffectState &new_state, Move last_move){ if(new_state.turn()==BLACK) updateSub(new_state,last_move); else updateSub(new_state,last_move); } NewProgressDebugInfo debugInfo() const; private: template void updateMain(const NumEffectState &new_state, Move last_move); public: const Progress16 progress16() const { return Progress16(16 * progress() / maxProgress()); } const Progress16 progress16(Player p) const { assert(maxProgress() > 0); return Progress16( 16 * std::max( std::min(progresses[playerToIndex(alt(p))] + attack5x5_progresses[playerToIndex(alt(p))] + stand_progresses[playerToIndex(alt(p))] + effect_progresses[playerToIndex(alt(p))] + defenses[playerToIndex(alt(p))] + king_relative_attack[playerToIndex(alt(p))] + king_relative_defense[playerToIndex(p)] + non_pawn_ptype_attacked_pair[p], max_progress-ProgressScale), 0) / ProgressScale / maxProgress()); } // p == attack player, alt(p) == king owner const Progress16 progressAttack(Player p) const { assert(maxProgress() > 0); return Progress16( 8 * std::max( std::min(progresses[alt(p)] + attack5x5_progresses[alt(p)] + stand_progresses[alt(p)] + effect_progresses[alt(p)] + king_relative_attack[alt(p)], max_progress-ProgressScale), -max_progress+ProgressScale) / ProgressScale / maxProgress() + 8); } // p == king owner (defense player) const Progress16 progressDefense(Player p) const { assert(maxProgress() > 0); return Progress16( 8 * std::max( std::min(defenses[alt(p)] + king_relative_defense[p] + non_pawn_ptype_attacked_pair[p], max_progress-ProgressScale), -max_progress + ProgressScale) / ProgressScale / maxProgress() + 8); } static bool initialized() { return initialized_flag; } static bool setUp(const char *filename); static bool setUp(); static std::string defaultFilename(); const NewProgressData rawData() const { return *this; } }; bool operator==(const NewProgressData& l, const NewProgressData& r); inline bool operator==(const NewProgress& l, const NewProgress& r) { return l.rawData() == r.rawData(); } } using ml::NewProgress; } using progress::Progress16; using progress::Progress32; using progress::NewProgress; } #endif // PROGRESS_EXPERIMENTAL_NEW_PROGRESS_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/0000755000000000000000000000000012316770314015132 5ustar rootrootlibosl-0.8.0.orig/core/osl/bits/pieceStand.cc0000644000000000000000000000500212316770314017515 0ustar rootroot/* pieceStand.cc */ #include "osl/bits/pieceStand.h" #include "osl/bits/ptypeTable.h" #include "osl/simpleState.h" #include namespace osl { static_assert(sizeof(unsigned int)*/*CHARBITS*/8>=32, "PieceStand"); const CArray PieceStand::order = {{ ROOK, BISHOP, GOLD, SILVER, KNIGHT, LANCE, PAWN, }}; const CArray PieceStand::shift = {{ 0,0,0,0,0,0,0,0, 28, 24, 18, 14, 10, 6, 3, 0, }}; const CArray PieceStand::mask = {{ 0,0,0,0,0,0,0,0, (1<<2)-1, (1<<3)-1, (1<<5)-1, (1<<3)-1, (1<<3)-1, (1<<3)-1, (1<<2)-1, (1<<2)-1 }}; const unsigned int PieceStand::carryMask; } osl::PieceStand:: PieceStand(Player pl, const SimpleState& state) : flags(0) { for (Ptype ptype: PieceStand::order) add(ptype, state.countPiecesOnStand(pl, ptype)); } bool osl::PieceStand::canAdd(Ptype type) const { const int max = Ptype_Table.getIndexLimit(type) - Ptype_Table.getIndexMin(type); assert(max >= 0); return (static_cast(get(type)) != max); } void osl::PieceStand::tryAdd(Ptype type) { if (canAdd(type)) add(type); } bool osl::PieceStand::atMostOneKind() const { return misc::BitOp::countBit(getFlags()) <= 1; } #ifndef MINIMAL bool osl::PieceStand:: carryUnchangedAfterAdd(const PieceStand& original, const PieceStand& other) const { if (original.testCarries() == testCarries()) return true; std::cerr << original << " + " << other << " = " << *this << "\n"; return false; } bool osl::PieceStand:: carryUnchangedAfterSub(const PieceStand& original, const PieceStand& other) const { if (original.testCarries() == testCarries()) return true; std::cerr << original << " - " << other << " = " << *this << "\n"; return false; } std::ostream& osl::operator<<(std::ostream& os, osl::PieceStand stand) { os << "(stand"; for (Ptype ptype: PieceStand::order) { os << ' ' << stand.get(ptype); } return os << ")"; } #endif std::ostream& osl:: PieceStandIO::writeNumbers(std::ostream& os, const PieceStand& stand) { for (Ptype ptype: PieceStand::order) { os << stand.get(ptype) << " "; } return os; } std::istream& osl:: PieceStandIO::readNumbers(std::istream& is, PieceStand& stand) { stand = PieceStand(); for (Ptype ptype: PieceStand::order) { int val; if (is >> val) stand.add(ptype, val); } return is; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/boardMask.h0000644000000000000000000001031312316770314017204 0ustar rootroot/* boardMask.h */ #ifndef OSL_BOARDMASK_H #define OSL_BOARDMASK_H #include "osl/basic_type.h" #include "osl/bits/directionTraits.h" #include "osl/bits/mask.h" #include "osl/container.h" #include namespace osl { namespace container { class BoardMask; bool operator==(const BoardMask&, const BoardMask&); std::ostream& operator<<(std::ostream&, const BoardMask&); /** 11 x 12 */ class BoardMask { /** the third one is only for edge */ CArray contents; public: BoardMask() { invalidate(); } BoardMask(const BoardMask& src) { contents[0] = src.contents[0]; contents[1] = src.contents[1]; } BoardMask& operator=(const BoardMask& src) { if (this != &src) { contents[0] = src.contents[0]; contents[1] = src.contents[1]; } return *this; } void clear() { contents[0]=contents[1]=0; } void invalidate() { contents[0] = static_cast(-1); } bool isInvalid() const { return contents[0] == static_cast(-1); } void set(unsigned int i) { int j=(i>>6); contents[j]|=(1ull<<(i&63)); } void set(Square pos) { set(index(pos)); } void reset(unsigned int i) { int j=(i>>6); contents[j] &= ~(1ull<<(i&63)); } void reset(Square pos) { reset(index(pos)); } bool test(unsigned int i) const { int j=(i>>6); return (contents[j]&(1ull<<(i&63)))!=0; } bool test(Square pos) const { return test(index(pos)); } bool anyInRange(const BoardMask& mask) const { return (contents[0] & mask.contents[0]) || (contents[1] & mask.contents[1]); } BoardMask& operator|=(const BoardMask& mask) { contents[0] |= mask.contents[0]; contents[1] |= mask.contents[1]; return *this; } bool any() const { assert(! isInvalid()); return contents[0] || contents[1]; } Square takeOneBit() { assert(! isInvalid() && any()); if (contents[0]) return toSquare(BitOp::takeOneBit(contents[0])); return toSquare(BitOp::takeOneBit(contents[1])+64); } static int index(int x,int y){ return x*12+y+1; } static int index(Square pos) { int v=pos.index(); return v-((v>>2)&0x3c); } template static int getIndexOffset() { int blackDx=DirectionTraitsGen::blackDx; int blackDy=DirectionTraitsGen::blackDy; int val=blackDx*12+blackDy; if(P==BLACK) return val; else return -val; } static Square toSquare(int n) { return Square::makeDirect(n+(((n*21)>>8)<<2)); } friend bool operator==(const BoardMask&, const BoardMask&); }; inline const BoardMask operator|(const BoardMask& l, const BoardMask& r) { BoardMask result = l; result |= r; return result; } inline bool operator==(const BoardMask& l, const BoardMask& r) { return l.contents[0] == r.contents[0] && l.contents[1] == r.contents[1]; } class BoardMaskTable5x5 { CArray data; public: BoardMaskTable5x5(); /** p中心ã®5x5 ã®ç¯„囲ã®bitã‚’ç«‹ã¦ãŸã‚‚ã®, centeringãªã—*/ const BoardMask& mask(Square p) const { return data[p.index()]; } }; extern const BoardMaskTable5x5 Board_Mask_Table5x5; class BoardMaskTable3x3 { CArray data; public: BoardMaskTable3x3(); /** p中心ã®3x3 ã®ç¯„囲ã®bitã‚’ç«‹ã¦ãŸã‚‚ã®, centeringãªã—*/ const BoardMask& mask(Square p) const { return data[p.index()]; } }; extern const BoardMaskTable3x3 Board_Mask_Table3x3; class BoardMaskTable5x3Center { CArray data; public: BoardMaskTable5x3Center(); /** p中心ã®5x3 ã®ç¯„囲ã®bitã‚’ç«‹ã¦ãŸã‚‚ã®, centering*/ const BoardMask& mask(Square p) const { return data[p.index()]; } }; extern const BoardMaskTable5x3Center Board_Mask_Table5x3_Center; } // namespace container using container::BoardMask; using container::Board_Mask_Table5x5; using container::Board_Mask_Table5x3_Center; using container::Board_Mask_Table3x3; } // namespace osl #endif /* OSL_BOARDMASK_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/additionalOrShadow.h0000644000000000000000000000215712316770314021067 0ustar rootroot/* additionalOrShadow.h */ #ifndef OSL_ADDITIONALORSHADOW_H #define OSL_ADDITIONALORSHADOW_H #include "osl/numEffectState.h" #include "osl/bits/boardTable.h" namespace osl { namespace effect_util { struct AdditionalOrShadow { template static int count(const PieceVector& direct_pieces, const NumEffectState& state, Square target, Player attack) { int result=0; for (Piece p: direct_pieces) { const Square from = p.square(); int num = p.number(); const Direction long_d=Board_Table.getLongDirection(Offset32(target,from)); if(!isLong(long_d)) continue; // unpromoted Knightを除ã„ã¦ãŠãã®ã¨ã©ã¡ã‚‰ãŒå¾—ã‹? Direction d=longToShort(long_d); for(;;){ num=state.longEffectNumTable()[num][d]; if(Piece::isEmptyNum(num) || state.pieceOf(num).owner()!=attack) break; if (++result >= count_max) return result; } } return result; } }; } } // namespace osl #endif /* OSL_ADDITIONALORSHADOW_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/core/osl/bits/boardTable.cc0000644000000000000000000000374312316770314017507 0ustar rootroot/* directionTable.cc */ #include "osl/bits/boardTable.h" #include "osl/bits/directionTraits.h" template void osl::BoardTable::setDirections(){ const int blackDx=DirectionTraits::blackDx; const int blackDy=DirectionTraits::blackDy; Offset offset=Offset(blackDx,blackDy); #ifndef MINIMAL space_counts[Offset32Wide(0,0).index()]=0; #endif for(int i=1;i<=8;i++){ int dx=i*blackDx; int dy=i*blackDy; Offset32 offset32(dx,dy); directions[offset32.index()]=Dir; short_offsets[offset32.index()]=offset; short_offsets_not_knight[offset32.index()]=offset; short8Dir[Offset(dx,dy).intValue()-Offset::ONBOARD_OFFSET_MIN]= longToShort(Dir); short8Offset[Offset(dx,dy).intValue()-Offset::ONBOARD_OFFSET_MIN]= offset.intValue(); } #ifndef MINIMAL for(int i=1;i<=10;i++){ int dx=i*blackDx; int dy=i*blackDy; Offset32Wide offset32w(dx,dy); space_counts[offset32w.index()]=i-1; } #endif } template void osl::BoardTable::setKnightDirections(){ int dx=DirectionTraits::blackDx; int dy=DirectionTraits::blackDy; Offset32 offset32=Offset32(dx,dy); Offset offset=Offset(dx,dy); short_offsets[offset32.index()]=offset; short_offsets[(-offset32).index()]= -offset; } void osl::BoardTable::init(){ short8Dir.fill(DIRECTION_INVALID_VALUE); short8Offset.fill(); directions.fill(); short_offsets_not_knight.fill(); #ifndef MINIMAL space_counts.fill(-1); #endif setDirections(); setDirections(); setDirections(); setDirections(); setDirections(); setDirections(); setDirections(); setDirections(); setKnightDirections(); setKnightDirections(); } osl::BoardTable::BoardTable(){ init(); assert(! getOffset(BLACK, UL).zero()); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/hash.txt0000644000000000000000000122472012316770314016626 0ustar rootroot// 0 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 0u, 0ull, 0u, 268435456u, 0ull, 0u, 16777216u, 0ull, 0u, 262144u, 0ull, 0u, 16384u, 0ull, 0u, 1024u, 0ull, 0u, 64u, 0ull, 0u, 8u, 0ull, 0u, 1u, // 1 17239567440292618612ull, 3673615093u, 0u, 6172303736550128412ull, 543498702u, 0u, 3695749114345028314ull, 2509728321u, 0u, 16054863083577142412ull, 2092436302u, 0u, 13737865900613252398ull, 2303621713u, 0u, 2639318566429542706ull, 2409601987u, 0u, 1102434879247150842ull, 19582927u, 0u, 5943934691290543224ull, 3509647142u, 0u, 265590134573815656ull, 1248844238u, 0u, 3555002998745190910ull, 2296765403u, 0u, 11430007700404899314ull, 4199176742u, 0u, 9130860564849885760ull, 1390263464u, 0u, 11445287930697219650ull, 1716764885u, 0u, 11826436868819985094ull, 3338076164u, 0u, 10660797215547322848ull, 2500930858u, 0u, 871599561670188856ull, 4064169421u, 0u, 273990103553889314ull, 3909173397u, 0u, 12944415969698165312ull, 2931154438u, 0u, 14715726140648860468ull, 3429108716u, 0u, 11311252768836468422ull, 3961118761u, 0u, 2781134358365850228ull, 449238368u, 0u, 11844055209151137720ull, 2002061157u, 0u, 14010015055109698026ull, 3955523258u, 0u, 6074826391974374560ull, 2844905775u, 0u, 14828145374014075846ull, 4282164687u, 0u, 15872436949052473202ull, 3037006502u, 0u, 12197023444969257338ull, 589254866u, 0u, 1865069062159697056ull, 2667299887u, 0u, 613506751323979332ull, 730197379u, 0u, 12538049933276203878ull, 112286008u, 0u, 10729675427979747164ull, 2205032700u, 0u, 16972443111633143858ull, 79447842u, 0u, // 2 3032794187041872708ull, 2760799218u, 0u, 8350059039688129276ull, 597695775u, 0u, 3577088221659634956ull, 2322574714u, 0u, 13928521248747522438ull, 3313517568u, 0u, 17985267644801246478ull, 4054073899u, 0u, 10380388548192556722ull, 757047651u, 0u, 1414850733162967846ull, 2159037595u, 0u, 3373544649629573650ull, 1914753136u, 0u, 8277286307519112748ull, 4260388042u, 0u, 4577846079346366500ull, 1302630637u, 0u, 4776899588751504566ull, 4156005721u, 0u, 11827814812522501546ull, 2037263681u, 0u, 6003034160819748084ull, 3116474176u, 0u, 9495630359399744244ull, 1918874379u, 0u, 4905899699224347488ull, 3862552229u, 0u, 10024194535228474026ull, 1038321979u, 0u, 4014705929102294006ull, 3667187272u, 0u, 15487920018442585726ull, 1875739108u, 0u, 6525765092430354572ull, 2603808548u, 0u, 1650312615542881078ull, 144261698u, 0u, 5515121407813894638ull, 357477742u, 0u, 14183314892860083426ull, 1202768801u, 0u, 15748203616341118552ull, 2369409403u, 0u, 10763463666566843136ull, 2261897444u, 0u, 17279501944501331954ull, 3235993257u, 0u, 1297802477461754036ull, 1828569974u, 0u, 3802899323050475094ull, 1788287907u, 0u, 11180715175939494170ull, 3355410906u, 0u, 12767582390836110878ull, 14474256u, 0u, 14357966938202614396ull, 513389479u, 0u, 3363296483462733050ull, 151991685u, 0u, 11957323156130117678ull, 1164323211u, 0u, // 3 17579269092545851998ull, 152152106u, 0u, 14315690717537191804ull, 1142524326u, 0u, 16438430137614336508ull, 2902662702u, 0u, 4709051073570750040ull, 2450801864u, 0u, 18003891138411783356ull, 1627769428u, 0u, 6816847511785003646ull, 2110764767u, 0u, 14797651336065093550ull, 1397670918u, 0u, 10752211910474090592ull, 972737961u, 0u, 11078192692837949892ull, 3637544823u, 0u, 13141417600963774268ull, 938371281u, 0u, 9783156285621690568ull, 144279013u, 0u, 14005342896734479848ull, 2142346512u, 0u, 3687965627901620732ull, 3908568430u, 0u, 17244331111938843868ull, 1301221032u, 0u, 13667228479000068932ull, 109748204u, 0u, 3009762990800772926ull, 1831073315u, 0u, 16092243155692937446ull, 1915838964u, 0u, 8353208703767973838ull, 2940194588u, 0u, 5663208635080727718ull, 1492323395u, 0u, 8524385725031673172ull, 2783585197u, 0u, 3228693015160687050ull, 749498799u, 0u, 13087376489284951310ull, 266490400u, 0u, 15036932280402077372ull, 2568492051u, 0u, 2715166158742630600ull, 1901048665u, 0u, 2145788446321373006ull, 171265131u, 0u, 1614581823989886218ull, 1185966112u, 0u, 2537115218957627678ull, 1889925543u, 0u, 13394591859263581010ull, 3492611389u, 0u, 6097550674843005540ull, 845331621u, 0u, 2040735274435878228ull, 675177022u, 0u, 11672248940287188610ull, 2886510889u, 0u, 10699592466748743578ull, 4038369009u, 0u, // 4 14042969659257451214ull, 1767355953u, 0u, 8840899498611518140ull, 811677792u, 0u, 7271517295949193276ull, 2848504537u, 0u, 15378201330520028658ull, 971604845u, 0u, 10021644380152967352ull, 2021465591u, 0u, 2461698134891992494ull, 3600724245u, 0u, 16511935859405909864ull, 2071278241u, 0u, 9196998657994964346ull, 4269638525u, 0u, 13836308518268452942ull, 2986764007u, 0u, 16972626029171712614ull, 4249049648u, 0u, 3698765437112088902ull, 57274986u, 0u, 3321563692710176924ull, 3171588434u, 0u, 12663450430432841666ull, 1740044449u, 0u, 6345163853918156126ull, 2342220022u, 0u, 1800432073919749528ull, 2113925454u, 0u, 17146506344418715524ull, 2501635281u, 0u, 1478643949321010302ull, 3746260534u, 0u, 4094351269895681916ull, 1633536145u, 0u, 6201148338003493718ull, 2219033651u, 0u, 8630791509094940266ull, 739093178u, 0u, 9522279912698885842ull, 2566977882u, 0u, 14649365179849284028ull, 2123120134u, 0u, 18226926095297701178ull, 141189145u, 0u, 9793003894850152776ull, 1400142411u, 0u, 7395593039958476214ull, 1786561109u, 0u, 3651372715156790992ull, 2324975691u, 0u, 4324656153839031688ull, 2529422626u, 0u, 17095796148875422564ull, 1713108847u, 0u, 9527136668589449330ull, 2449772581u, 0u, 16674879443937761870ull, 4037215381u, 0u, 7773164039780879890ull, 242630248u, 0u, 11056549593218857962ull, 3309114384u, 0u, // 5 12341768520818754704ull, 1505857812u, 0u, 15808412615131634556ull, 3097138637u, 0u, 6179203591253592418ull, 633698892u, 0u, 14141345560936135966ull, 2952367516u, 0u, 3959918188775589210ull, 4273592656u, 0u, 10306353570728321334ull, 1925707682u, 0u, 15976403452807267614ull, 2418034758u, 0u, 2993699912240515318ull, 1211008316u, 0u, 7471120822719013600ull, 2467783862u, 0u, 10799731292620294448ull, 2013280255u, 0u, 12995317652897169596ull, 2883362033u, 0u, 7096830149831123196ull, 599167397u, 0u, 1055401658655169572ull, 1164539646u, 0u, 17962874022754666140ull, 2636514424u, 0u, 11032925049660345480ull, 4275436579u, 0u, 6133030434502006132ull, 437731726u, 0u, 8036360430448443404ull, 3851560140u, 0u, 11972910011268725418ull, 565531679u, 0u, 2251252505241493306ull, 2804523888u, 0u, 3103033088950145296ull, 2645435476u, 0u, 7132249429611413352ull, 3702610682u, 0u, 12179240979970739448ull, 132744612u, 0u, 5140767907855731376ull, 2918605755u, 0u, 3239532096474594426ull, 3648646032u, 0u, 2719881443161834382ull, 2880619250u, 0u, 14917929589428419698ull, 3644481494u, 0u, 10207332459694987242ull, 4266466467u, 0u, 1515644208303976666ull, 3548931283u, 0u, 6651462125755749712ull, 1096972967u, 0u, 6780584733362622916ull, 2744346363u, 0u, 4150154082129577658ull, 2247893466u, 0u, 14349990248900632902ull, 1831390083u, 0u, // 6 8978543013012172298ull, 3762465068u, 0u, 76605619401716100ull, 832795818u, 0u, 10580314489324673854ull, 1181237638u, 0u, 18281555813568650134ull, 4144013907u, 0u, 17459950282045829370ull, 2644773275u, 0u, 9124468109086322674ull, 293642063u, 0u, 6555496309297419906ull, 1216120264u, 0u, 2173126788454071526ull, 2744509062u, 0u, 5236392095710651078ull, 1822315554u, 0u, 18158931472337486970ull, 2092483445u, 0u, 12792845906443772748ull, 689582612u, 0u, 4443173736031372040ull, 2955283069u, 0u, 15050383842843008622ull, 2059107088u, 0u, 16706009343129124224ull, 3649905813u, 0u, 12095544638922503406ull, 274444442u, 0u, 13549765613507326196ull, 922174879u, 0u, 3221923107423747440ull, 392055411u, 0u, 8344386536256907398ull, 3356555798u, 0u, 1312724344656056348ull, 3377881587u, 0u, 2552866962737052112ull, 2447922353u, 0u, 613176525441549878ull, 3972432012u, 0u, 1751598122958512120ull, 2811562441u, 0u, 16979490323368933226ull, 1480567079u, 0u, 11024835220999220530ull, 42128127u, 0u, 16788566450531817630ull, 599704537u, 0u, 9689088562717434110ull, 567909419u, 0u, 13468695573300240638ull, 819581179u, 0u, 3725564311399188336ull, 2976900853u, 0u, 7622377965352580870ull, 154133293u, 0u, 3026531933200124542ull, 3085276301u, 0u, 9587687770419940042ull, 3923556585u, 0u, 16838151634816426138ull, 2241805973u, 0u, // 7 1231154985112822550ull, 3712266508u, 0u, 7010538165772684482ull, 1789205857u, 0u, 16271983599427271994ull, 1763905188u, 0u, 16439599986375146738ull, 2764214568u, 0u, 15566169850354027326ull, 4251413316u, 0u, 904258246945266466ull, 3222526256u, 0u, 7529631115798765172ull, 2308574266u, 0u, 16658011020461251362ull, 2937391815u, 0u, 3344697020358009580ull, 2500735212u, 0u, 380192539904680584ull, 2782348678u, 0u, 6534282238872984340ull, 771809115u, 0u, 3012366714609250530ull, 609739507u, 0u, 5207575729598125658ull, 415714904u, 0u, 3170205313048367454ull, 453599075u, 0u, 14887309338192058662ull, 1233680046u, 0u, 11881800610155608680ull, 3457250525u, 0u, 4152203392747821692ull, 2238757608u, 0u, 5443570042088666080ull, 1375290067u, 0u, 13906863747753690228ull, 1326761027u, 0u, 7178082825272308398ull, 1525494023u, 0u, 4692432530025908502ull, 1086605806u, 0u, 2914544991774448218ull, 1344808666u, 0u, 14860262391500513922ull, 1819331332u, 0u, 2681547512651295830ull, 2348893105u, 0u, 11567920588650313936ull, 2056862333u, 0u, 15281270368835284144ull, 469424720u, 0u, 248687291750450116ull, 153610763u, 0u, 16695641689088997490ull, 3002463613u, 0u, 13760402279086142098ull, 158102751u, 0u, 10598525450522460854ull, 1940336194u, 0u, 14239595814678579396ull, 555559250u, 0u, 6667867701370780170ull, 3378528965u, 0u, // 8 3741553193029674112ull, 1696887850u, 0u, 7137880701372418174ull, 3656977613u, 0u, 14059879408985400900ull, 3689898285u, 0u, 14454741299219578284ull, 900865791u, 0u, 4497512647547665924ull, 3432079008u, 0u, 7411531732125901384ull, 478883661u, 0u, 13968257523017977638ull, 4240767670u, 0u, 14275829960556773648ull, 2751352370u, 0u, 11719418845663091442ull, 3146402815u, 0u, 3652679149620009448ull, 196642899u, 0u, 17009129859402990186ull, 2882895159u, 0u, 15108597901047804950ull, 1336414079u, 0u, 2053979716530286532ull, 2128608355u, 0u, 8528133070020475876ull, 2659430741u, 0u, 1455977722632961986ull, 2506028586u, 0u, 18088417076315387654ull, 1898961654u, 0u, 7333631691783514476ull, 4184831654u, 0u, 13366140034927068740ull, 2927551233u, 0u, 11950911348024702214ull, 456933484u, 0u, 2054396330365241346ull, 2582898469u, 0u, 15771650351147994528ull, 18967857u, 0u, 9982208964840239344ull, 86962375u, 0u, 17739595669268474770ull, 4083624506u, 0u, 7616247150284970070ull, 2021945577u, 0u, 15587114100950882058ull, 2213258386u, 0u, 17904264901547019686ull, 3747479298u, 0u, 9350239212448821412ull, 1238829359u, 0u, 139664627120950076ull, 1742766233u, 0u, 899237081604257050ull, 4122152824u, 0u, 548140228188934688ull, 3604680334u, 0u, 15519218101637273132ull, 1884948854u, 0u, 16286354102305035226ull, 3377481183u, 0u, // 9 6477518569478548604ull, 3501076860u, 0u, 3240579293663718710ull, 840500343u, 0u, 14799656111350317388ull, 1401936388u, 0u, 10039081176065523054ull, 2714313584u, 0u, 1359579687094350210ull, 956063603u, 0u, 12284128015539986046ull, 2765983849u, 0u, 15694643579860730284ull, 76926899u, 0u, 81486894768439140ull, 3046491525u, 0u, 11765300564826682128ull, 2549656733u, 0u, 4934561616876935722ull, 229172642u, 0u, 7876822784367387818ull, 361325044u, 0u, 18104526378432687238ull, 2414029588u, 0u, 7728685578137070268ull, 4103319904u, 0u, 4513548291803997878ull, 955030925u, 0u, 5430562539407465850ull, 4017255687u, 0u, 17119158037827935152ull, 3795108573u, 0u, 16700349360454600576ull, 3613758581u, 0u, 1300601245383995738ull, 3617796590u, 0u, 1429002038926696596ull, 3914736557u, 0u, 12826171222074257600ull, 544431344u, 0u, 1237663247975961246ull, 2029869319u, 0u, 13858297019827062682ull, 2355011104u, 0u, 6254055841254502904ull, 3234073102u, 0u, 15293093447612708818ull, 1342059910u, 0u, 17077316305026452148ull, 3502530389u, 0u, 8579778056794596128ull, 1121929665u, 0u, 374885502278084590ull, 3695457004u, 0u, 5213523618028614506ull, 4167649732u, 0u, 9990727678559150928ull, 2362113518u, 0u, 10549583512679816400ull, 1589974225u, 0u, 3954283432497900012ull, 2957354499u, 0u, 11497451838371579420ull, 467382814u, 0u, // 10 13050979173856005878ull, 4242047436u, 0u, 5624400292692568638ull, 1470186780u, 0u, 8234728369116382606ull, 216806251u, 0u, 15861033957165508980ull, 285289734u, 0u, 5758273448135016066ull, 3925259794u, 0u, 3261128070881804430ull, 3337870397u, 0u, 3069853575445117656ull, 2314709586u, 0u, 14953349396144827696ull, 3255062345u, 0u, 17750292412691811128ull, 3288210804u, 0u, 5101170942570959844ull, 2230400383u, 0u, 2425524120577637840ull, 960878721u, 0u, 16399585111078364742ull, 3754419394u, 0u, 11727838380585690468ull, 1305759723u, 0u, 6041241575389649572ull, 2820113543u, 0u, 4904898741371325786ull, 3894933726u, 0u, 2256759864264036322ull, 731200357u, 0u, 14261673470786411374ull, 4148181500u, 0u, 1161608724638115812ull, 4077175471u, 0u, 10195743674551067312ull, 3108599795u, 0u, 16752631325815670936ull, 4078200780u, 0u, 394370120066688628ull, 3456188515u, 0u, 16930768258913103866ull, 3390472427u, 0u, 7809525730400597444ull, 2767733782u, 0u, 16234091413786853646ull, 876955100u, 0u, 6453751780496927720ull, 173750187u, 0u, 15299808860621673554ull, 717511842u, 0u, 13520334892609644860ull, 2078052339u, 0u, 17940020920880329450ull, 469978307u, 0u, 8221769171911458206ull, 4274208200u, 0u, 2059732763388754192ull, 1002527827u, 0u, 4451419859393490820ull, 1952894312u, 0u, 980656398630287906ull, 3938895958u, 0u, // 11 3717219314138275730ull, 3141911432u, 0u, 4735178003478396370ull, 3437788423u, 0u, 10706035553791140482ull, 3252199876u, 0u, 16812235613375822382ull, 3803342145u, 0u, 968029530139944190ull, 261917155u, 0u, 730166411782894680ull, 2080557040u, 0u, 16981110908366618714ull, 4028101375u, 0u, 17477632519859425970ull, 757902515u, 0u, 13714509341633472302ull, 3546600842u, 0u, 17908020979265945192ull, 3550671090u, 0u, 9206540343057843040ull, 43156109u, 0u, 15330254873844596286ull, 785834317u, 0u, 3861526987593153188ull, 1565863048u, 0u, 834175749767738302ull, 1874826054u, 0u, 5846464818915058842ull, 3045624954u, 0u, 7929422966508311806ull, 2960985690u, 0u, 11187169530377166248ull, 1140314448u, 0u, 15772472147515860664ull, 3264507527u, 0u, 3105652759028554274ull, 2088776904u, 0u, 12969364062799707980ull, 3575253266u, 0u, 9432262814911486ull, 3423538087u, 0u, 9083427487060846486ull, 4886928u, 0u, 10168200624962434382ull, 1534770597u, 0u, 15549252078104721740ull, 1786737175u, 0u, 2627003312704674038ull, 3963358648u, 0u, 4314435333119537538ull, 1315171575u, 0u, 6574611404615184686ull, 3561091070u, 0u, 18237446105047042258ull, 2005777943u, 0u, 2876876582553623956ull, 1877513280u, 0u, 1687237933758707170ull, 682887281u, 0u, 9948450858820052320ull, 1189856836u, 0u, 12464772715151579506ull, 2576537957u, 0u, // 12 7511976219660880686ull, 3137804189u, 0u, 257554171794987102ull, 3937359609u, 0u, 12529160678480134706ull, 163640668u, 0u, 18073413560104657812ull, 3524315292u, 0u, 2723680081016337418ull, 2397110160u, 0u, 2962325830150122598ull, 1428525514u, 0u, 17606907925663595582ull, 974777521u, 0u, 3482164628490601188ull, 3120547060u, 0u, 15430832835576471572ull, 3360333088u, 0u, 11275411387431822458ull, 58947553u, 0u, 12814147392325614958ull, 3181043690u, 0u, 13816281346367588330ull, 3179678129u, 0u, 1956068704662492248ull, 3227824939u, 0u, 719839109536714544ull, 3492222355u, 0u, 14256017447321845162ull, 256839706u, 0u, 18232317739341796934ull, 389084553u, 0u, 15606474963194826996ull, 4139702800u, 0u, 825442804041686854ull, 112652677u, 0u, 5623643482027114354ull, 2520674794u, 0u, 15449230818315717042ull, 3542829229u, 0u, 5752603700929728112ull, 1450317664u, 0u, 5404855745462509190ull, 4087716016u, 0u, 6743896916278050738ull, 2794042346u, 0u, 2039867442968929360ull, 1409781123u, 0u, 9722315855888063358ull, 2698692977u, 0u, 9925800388791337668ull, 702573889u, 0u, 14101725418084104286ull, 3460000706u, 0u, 15739536563168584042ull, 871773558u, 0u, 9506433001501470308ull, 166935459u, 0u, 11584716370411874654ull, 893589344u, 0u, 8417711040616749358ull, 2740281126u, 0u, 15983435410147347238ull, 2385054262u, 0u, // 13 9000416142859092722ull, 974582944u, 0u, 1625785264349965498ull, 674172664u, 0u, 4247848008518819604ull, 46152656u, 0u, 4501580772946888038ull, 1861027589u, 0u, 3681009591398527432ull, 3073856497u, 0u, 253532525209169824ull, 3616126839u, 0u, 7750234677353170796ull, 3626277452u, 0u, 16006975549168629984ull, 1381351604u, 0u, 5174020038699907970ull, 2381972059u, 0u, 2306502804797640276ull, 1330859781u, 0u, 6499164434730165898ull, 3099394245u, 0u, 16355442325210130358ull, 1211401938u, 0u, 16152683456040253258ull, 2165600630u, 0u, 6749429859573807640ull, 4112188148u, 0u, 14532081964367476086ull, 1933607171u, 0u, 5612444477481659574ull, 2719583244u, 0u, 10029846300017208642ull, 2171861989u, 0u, 6102704965022526084ull, 1416414204u, 0u, 14646038397774002446ull, 1536469947u, 0u, 5169336270476250066ull, 1637339936u, 0u, 14592876886057065912ull, 1743322952u, 0u, 17195522393654326884ull, 241627118u, 0u, 12138610337061889830ull, 675482165u, 0u, 11772075942421087250ull, 167033096u, 0u, 11040518254846798200ull, 1200101380u, 0u, 10981158608291325112ull, 3992296874u, 0u, 2944472978422133284ull, 1793849699u, 0u, 10427234505736842008ull, 3453318930u, 0u, 14352122957201831370ull, 3478082517u, 0u, 6651588083152089350ull, 2807158113u, 0u, 7240432503519883526ull, 3271912979u, 0u, 12818811519366759554ull, 3810628651u, 0u, // 14 2335412871195754486ull, 2769443511u, 0u, 7753387356796559474ull, 3248074104u, 0u, 2001793428647008956ull, 3238513706u, 0u, 8047660270603125974ull, 3700872505u, 0u, 12595715310876566756ull, 1906697366u, 0u, 2349363333633304828ull, 661503098u, 0u, 2705469547117472050ull, 2606455996u, 0u, 9021979948200579424ull, 2805146949u, 0u, 9314103070778066836ull, 1010871307u, 0u, 12986293623810130938ull, 1881273185u, 0u, 15315654636593335558ull, 467684017u, 0u, 2363477066297949016ull, 3856833797u, 0u, 7823143024618933286ull, 2751243395u, 0u, 14242233709844325556ull, 2007325155u, 0u, 15998062491379953054ull, 644318923u, 0u, 8814770317538585316ull, 987936930u, 0u, 2406438636380090870ull, 4104898421u, 0u, 11948137282079189772ull, 823407727u, 0u, 12272485781407596114ull, 3791410778u, 0u, 14962269631262342620ull, 669461439u, 0u, 7811518445222699976ull, 323204909u, 0u, 5068385392208620910ull, 2148902510u, 0u, 4142368816666127702ull, 2256579213u, 0u, 1132244147390549750ull, 1781663057u, 0u, 15796206987671407296ull, 3981285545u, 0u, 12863721722097538768ull, 341083521u, 0u, 9375696185883079512ull, 3348638825u, 0u, 2872428510248456408ull, 877140658u, 0u, 9243017477794317988ull, 297038824u, 0u, 10833792788914037936ull, 3984429041u, 0u, 11131007379254139064ull, 3739707957u, 0u, 12779135768883500498ull, 2769304050u, 0u, // 15 7556150776771609920ull, 1878400442u, 0u, 6502714883610648698ull, 3369256848u, 0u, 11025564350255501670ull, 2561304659u, 0u, 7552165240416525758ull, 839794353u, 0u, 8709108839193943660ull, 1918553759u, 0u, 4347228851784666560ull, 361434776u, 0u, 15788348426705999950ull, 599475174u, 0u, 16443943969207403012ull, 3419880460u, 0u, 8809004374371582604ull, 982759441u, 0u, 5253251670228929682ull, 452224108u, 0u, 4006852042577460790ull, 351436194u, 0u, 5100572163662882848ull, 2413437197u, 0u, 16999318182003656152ull, 2691468720u, 0u, 6400669045523202594ull, 1652095856u, 0u, 3103677301493239590ull, 3059439990u, 0u, 10740628467034457480ull, 1286920416u, 0u, 3444444105386693724ull, 3892650026u, 0u, 17862176883491534848ull, 585787902u, 0u, 7126307482137855214ull, 3620323454u, 0u, 12995611236919319270ull, 1939116780u, 0u, 8915254165202255686ull, 3454467934u, 0u, 11872069388182235062ull, 2065769976u, 0u, 11676168222414537296ull, 4158572345u, 0u, 12683290501789343984ull, 3379846319u, 0u, 7389166030224143192ull, 1515735788u, 0u, 9104517348910902038ull, 1510085996u, 0u, 4766995359808384368ull, 3272137368u, 0u, 11499752989977653430ull, 1674952655u, 0u, 10542397232795475548ull, 324954969u, 0u, 7436923113445808986ull, 1982505633u, 0u, 12293058474088517506ull, 3493728844u, 0u, 11388638129619759676ull, 421601825u, 0u, // 16 1226336866655080532ull, 330946728u, 0u, 15888672213077842730ull, 3756600339u, 0u, 3997238088647645176ull, 1243980769u, 0u, 15151404859783944252ull, 4276195096u, 0u, 3221882492268674498ull, 4242637621u, 0u, 5234354841152676250ull, 2819753429u, 0u, 8600471304917689030ull, 2390738075u, 0u, 12195027049952873340ull, 588704526u, 0u, 7005648944714646696ull, 2307447769u, 0u, 17927171532985037914ull, 3586412727u, 0u, 6084355877849714632ull, 491768371u, 0u, 1869741396057839938ull, 2946575642u, 0u, 8344278506321554176ull, 1951515334u, 0u, 7712374301529562900ull, 3092820263u, 0u, 13701118165281375094ull, 1109265985u, 0u, 2686028363986634620ull, 2453505828u, 0u, 52265292333687310ull, 3208354194u, 0u, 11566405482705576964ull, 3330848171u, 0u, 18264943452905581088ull, 1620876692u, 0u, 13397308121139952760ull, 2138785836u, 0u, 16803880244749177432ull, 2130829917u, 0u, 4180485005726458164ull, 805615356u, 0u, 1204649165932953530ull, 1945976135u, 0u, 15926323432522993088ull, 2683199436u, 0u, 15644119620808279610ull, 4148460515u, 0u, 4288157317063557472ull, 2393590665u, 0u, 17018344483476080626ull, 1481506852u, 0u, 8257871387217904864ull, 3341677658u, 0u, 11332643490544145242ull, 1821553770u, 0u, 4930017455939864064ull, 197817309u, 0u, 1108630346948989168ull, 3070132599u, 0u, 9269884808156505270ull, 4081947958u, 0u, // 17 9723145412559291050ull, 2622186067u, 0u, 355676787233225342ull, 3135903036u, 0u, 7180959379442315514ull, 2465277889u, 0u, 488886130496313266ull, 1117118496u, 0u, 474487512172990336ull, 936777456u, 0u, 10272840251362746192ull, 3364056818u, 0u, 3930636653764617360ull, 539902750u, 0u, 11561403661066755420ull, 2044976295u, 0u, 14557177390518088854ull, 415868005u, 0u, 11903384576098244004ull, 2040188722u, 0u, 5135027178782655548ull, 2971746562u, 0u, 16078749885029910672ull, 3048494469u, 0u, 7548582960315328636ull, 2144881170u, 0u, 1783790684200892656ull, 1091293779u, 0u, 13205711688593749844ull, 1185799494u, 0u, 2045093053484903374ull, 627097443u, 0u, 4727875995438998450ull, 2632077144u, 0u, 1368061701475992260ull, 3804159804u, 0u, 11580482155797117398ull, 444315134u, 0u, 14398479715348976692ull, 3584492666u, 0u, 7711020556719714298ull, 3528405376u, 0u, 17041851054829208614ull, 3624067774u, 0u, 860544172388425206ull, 4191169386u, 0u, 301410666383624930ull, 1577304913u, 0u, 17533622075907864664ull, 671774552u, 0u, 17435327862258924876ull, 2573016524u, 0u, 15783157156809984348ull, 1944028563u, 0u, 6751116169612773408ull, 2033646768u, 0u, 13248241672441795294ull, 808542641u, 0u, 2953443371372577920ull, 2867890779u, 0u, 16476522915646824234ull, 574628821u, 0u, 13937378439107331018ull, 2757252150u, 0u, // 18 6473288710058706998ull, 4283269676u, 0u, 12241658687226171540ull, 860527340u, 0u, 15661651611288525410ull, 14164204u, 0u, 15207391945617214320ull, 3372543768u, 0u, 4222711236889745654ull, 2614037039u, 0u, 4885021977981901594ull, 1251837673u, 0u, 18002510085041321194ull, 3442784473u, 0u, 9334491596103419290ull, 1866124443u, 0u, 6326943388679567440ull, 209622274u, 0u, 15473899733088810324ull, 33551286u, 0u, 7796062802952291896ull, 2426000020u, 0u, 18054435655626493202ull, 1916494724u, 0u, 18207752440679976988ull, 260298792u, 0u, 16726022148819433442ull, 1246611922u, 0u, 13413894327326824066ull, 2653633698u, 0u, 8597341975284643202ull, 3328409231u, 0u, 6103004899328059840ull, 3207000270u, 0u, 8703430158628940694ull, 3680577862u, 0u, 6903299206823924628ull, 1002744837u, 0u, 5263358280486298248ull, 2816195710u, 0u, 3856715630321608554ull, 4277340961u, 0u, 13056713872440971706ull, 3698679523u, 0u, 5686543778567708134ull, 3444800764u, 0u, 9049032980190384796ull, 324978988u, 0u, 17153732471782576002ull, 2371095167u, 0u, 9776371083877689344ull, 650356730u, 0u, 12746146747369213564ull, 153657411u, 0u, 18042783539674391978ull, 176163665u, 0u, 340596841647518736ull, 3237015717u, 0u, 15459404812950898778ull, 2156520457u, 0u, 12735897758112686126ull, 2979735375u, 0u, 10122405494494767082ull, 733584912u, 0u, // 19 3331068622841373408ull, 512332583u, 0u, 9726090010613158404ull, 760276559u, 0u, 10453493604062876048ull, 66031581u, 0u, 9575102740252518246ull, 3995190842u, 0u, 4718707051118086016ull, 612928460u, 0u, 6194581647604914182ull, 2906220228u, 0u, 16168558733109276076ull, 3701123564u, 0u, 9865215780347010526ull, 1911534039u, 0u, 12977060163694368228ull, 1754210890u, 0u, 13810044678894615136ull, 636505738u, 0u, 8538494414439099050ull, 4289407371u, 0u, 4171456021649700764ull, 1963381901u, 0u, 1228517851970138918ull, 1392606085u, 0u, 16362045771816049014ull, 1395517685u, 0u, 13668827339488864978ull, 1758893585u, 0u, 5329016000540091888ull, 3670116895u, 0u, 4608464105118797414ull, 124392095u, 0u, 11437620547430828612ull, 1999781475u, 0u, 2613993186164626460ull, 4057415009u, 0u, 16129452164955766704ull, 2889617469u, 0u, 14278606318959830862ull, 2748021865u, 0u, 14103972968559097054ull, 799016936u, 0u, 1677088807910678188ull, 807274930u, 0u, 1216863720934473192ull, 2320902158u, 0u, 12387049035474358864ull, 3099964347u, 0u, 13504284528711433814ull, 3436298049u, 0u, 10307477698011028308ull, 2612560999u, 0u, 1386870485442384206ull, 3360564794u, 0u, 274877196365450098ull, 2670317676u, 0u, 3437695867947622934ull, 1829763329u, 0u, 10356900833292286982ull, 3373539894u, 0u, 9995810363998455324ull, 1377168953u, 0u, // 20 3255636281218690514ull, 4148261178u, 0u, 8645914641470746758ull, 2183886571u, 0u, 13043817400546709492ull, 2737287698u, 0u, 99897261352802776ull, 2779128868u, 0u, 10194522296531925944ull, 3189632732u, 0u, 13487305582241675724ull, 2295519795u, 0u, 3847523054777571930ull, 1619367548u, 0u, 16492928385728211342ull, 1838213122u, 0u, 2074358921539907324ull, 3606971138u, 0u, 15125652370223058284ull, 1543923573u, 0u, 9821672049786275572ull, 2096629347u, 0u, 14973458357561587652ull, 1248368641u, 0u, 7107897975920427962ull, 2676069607u, 0u, 3767562552388184992ull, 754516793u, 0u, 8734151111171854870ull, 2118340217u, 0u, 13561175959115615030ull, 3100387465u, 0u, 3659474611797855992ull, 4026845055u, 0u, 16658484712701441806ull, 1734898774u, 0u, 8553593133491270526ull, 1023614655u, 0u, 12852419282668439206ull, 1251938429u, 0u, 1730362283624951774ull, 290327217u, 0u, 15493090114215505966ull, 1575801896u, 0u, 1276517826958102762ull, 3448925972u, 0u, 10687830058120718364ull, 1254569991u, 0u, 4216313400614606640ull, 3272942780u, 0u, 13598275677092161784ull, 2662653974u, 0u, 10892944776314018680ull, 2132952495u, 0u, 8801547943669610212ull, 573086311u, 0u, 2243540328569380700ull, 208646666u, 0u, 5233081596639738884ull, 1471639163u, 0u, 13852471664974076196ull, 3431911313u, 0u, 3590625010445092408ull, 4135765045u, 0u, // 21 15455091601960370642ull, 558620746u, 0u, 6987863428272019248ull, 4231404385u, 0u, 637910504714863886ull, 3602833012u, 0u, 7960877103458863282ull, 3774777966u, 0u, 16224887287656203084ull, 2111092812u, 0u, 1458376834835237656ull, 3542890186u, 0u, 12319190943539545116ull, 2528885207u, 0u, 2186200747917234758ull, 1898529592u, 0u, 6755351809630606010ull, 146466289u, 0u, 5442262443231635868ull, 2895649216u, 0u, 4925332259610965650ull, 3229034263u, 0u, 6889878832626829268ull, 858872442u, 0u, 12689017942524460968ull, 302374320u, 0u, 12958193842009168760ull, 427508570u, 0u, 17824279820062230948ull, 2995391845u, 0u, 11919475416905839510ull, 1562129874u, 0u, 6890231669097768086ull, 1011688744u, 0u, 6573628233463048330ull, 1952042634u, 0u, 16533837633450235042ull, 3299111575u, 0u, 872255119724476990ull, 1083401536u, 0u, 9727832922229934616ull, 3302929966u, 0u, 7853903668348676968ull, 646169896u, 0u, 7091758450932371302ull, 719790627u, 0u, 9535751618662681040ull, 1496155187u, 0u, 2607253843039817340ull, 3992361690u, 0u, 2693394613239879664ull, 2907824871u, 0u, 7630656481539346478ull, 2997737429u, 0u, 13427397377291039832ull, 3208678660u, 0u, 16271912337897044840ull, 696789509u, 0u, 3065064418858246464ull, 3301053851u, 0u, 3263458659375311374ull, 4016129330u, 0u, 14394075600526789844ull, 2759290311u, 0u, // 22 16740637847453222644ull, 447109326u, 0u, 2192623177250178802ull, 4043645658u, 0u, 14026925012764890906ull, 188825583u, 0u, 12286153729271899238ull, 4285537965u, 0u, 17939877465543994148ull, 2870427829u, 0u, 14135528752593323190ull, 3576910620u, 0u, 12714519281386732030ull, 1536008194u, 0u, 14170183831524558764ull, 1481978059u, 0u, 677707250024782762ull, 128800109u, 0u, 2927342431896201300ull, 928180u, 0u, 12237773940626864318ull, 1691831738u, 0u, 14295270752191726350ull, 2881481629u, 0u, 1981866277905323410ull, 3001329512u, 0u, 7797002643932324294ull, 3810138453u, 0u, 15719927159701912956ull, 2746638615u, 0u, 13891908793973272016ull, 2124514492u, 0u, 18217068621709855618ull, 342212590u, 0u, 2668854698876153422ull, 1161210491u, 0u, 9719536344341384050ull, 4065132530u, 0u, 13931361171024720870ull, 2901881934u, 0u, 1035447991625988104ull, 3918003623u, 0u, 5139296015520989572ull, 86636279u, 0u, 15150718952281253128ull, 3909377141u, 0u, 13599684272517316164ull, 2598560567u, 0u, 16816391744490445236ull, 984339342u, 0u, 14351008695723564906ull, 4279230062u, 0u, 17331308761258748356ull, 2720452282u, 0u, 4346613035457321948ull, 2556035727u, 0u, 11749240641743837152ull, 3289260601u, 0u, 8207823638824172028ull, 2703556553u, 0u, 18229441170718255938ull, 1096550595u, 0u, 12758470948559105882ull, 3059083488u, 0u, // 23 5792368527898649414ull, 3144509988u, 0u, 16780997414425627066ull, 3966135162u, 0u, 4395960862472957386ull, 4177909644u, 0u, 1807645191411955820ull, 3742257077u, 0u, 7345919023143444092ull, 3279229165u, 0u, 11283573207635790572ull, 2609583630u, 0u, 16492279114038243268ull, 1802550214u, 0u, 14176673653721614626ull, 1251897733u, 0u, 14082626005128297774ull, 2191230342u, 0u, 6196233433023355204ull, 45203656u, 0u, 2956614671820181882ull, 4198033368u, 0u, 5817177642466412874ull, 1757781859u, 0u, 12283596752752966550ull, 2399052274u, 0u, 8334598572229729020ull, 2483295663u, 0u, 705261990578088376ull, 689995848u, 0u, 11094455090180686012ull, 3563564838u, 0u, 13007327166363187314ull, 2150169641u, 0u, 9003719222105605590ull, 3739291142u, 0u, 9812401011663412322ull, 1948887895u, 0u, 1098224210439461100ull, 1559784153u, 0u, 6386241077663059584ull, 1007373127u, 0u, 18109800211208248126ull, 1406681282u, 0u, 4565140262245296784ull, 138511690u, 0u, 7159222801733170006ull, 2675337403u, 0u, 9362756596397566796ull, 3581215049u, 0u, 3295756828210409808ull, 1318791265u, 0u, 566909008427806970ull, 2060483768u, 0u, 12472130801715010852ull, 2253915243u, 0u, 7603459318138289448ull, 2136073277u, 0u, 16939945942499434864ull, 3303821899u, 0u, 124992818645042332ull, 3422000097u, 0u, 6405557609145311360ull, 1830043107u, 0u, // 24 1883466727136943558ull, 1467407841u, 0u, 12339985022479450058ull, 3726975786u, 0u, 1766217974745030104ull, 1534708500u, 0u, 6530521698488504044ull, 1686978915u, 0u, 5709708304551066352ull, 2119669573u, 0u, 4517234933534847788ull, 1844770778u, 0u, 6860016798124349314ull, 2526652963u, 0u, 10194145479015722618ull, 2358338103u, 0u, 1869189254655835334ull, 2045708486u, 0u, 9438796530909802806ull, 4217637176u, 0u, 16674450281998918302ull, 3027979110u, 0u, 214604186601457552ull, 2234833871u, 0u, 5151406860178194876ull, 4289461065u, 0u, 17019170404171086664ull, 4130891553u, 0u, 12147416227583924360ull, 3443199052u, 0u, 10729464199225383216ull, 3807745158u, 0u, 18295539217359500800ull, 2307366727u, 0u, 6033157574942687496ull, 1544807848u, 0u, 6890444823578152222ull, 1188071112u, 0u, 7045301074780232890ull, 651373289u, 0u, 825166737772667158ull, 3790419278u, 0u, 7204260869292615160ull, 1027056282u, 0u, 6967303343677136972ull, 1758190559u, 0u, 14752067805862675442ull, 2182627204u, 0u, 6599257596403157054ull, 193173086u, 0u, 18211108157563230536ull, 536324334u, 0u, 15519798463400305328ull, 1968618668u, 0u, 3441300981995083108ull, 2549074358u, 0u, 17905258493938821890ull, 3261440693u, 0u, 11478161687916426872ull, 60487526u, 0u, 11373177960252528866ull, 2542689346u, 0u, 2156086235950305086ull, 2377103105u, 0u, // 25 9837113133735204342ull, 3695713635u, 0u, 2018226225470538784ull, 611445506u, 0u, 1663574569026291020ull, 632036832u, 0u, 2729666507723338890ull, 2758470890u, 0u, 3071284731117069604ull, 2843792576u, 0u, 12580685974784066118ull, 2849204776u, 0u, 190423866755750130ull, 2060304401u, 0u, 15462878607674478614ull, 2351313456u, 0u, 16397363537129655430ull, 2918414780u, 0u, 2982642246129085550ull, 1246322412u, 0u, 9309252265752062688ull, 3099243773u, 0u, 17437897884266648410ull, 63175313u, 0u, 6470489589625642270ull, 622857033u, 0u, 12720753668988461404ull, 2462353098u, 0u, 5672989701370065214ull, 3156296093u, 0u, 16768552786219305692ull, 271342924u, 0u, 18211443897807220406ull, 3505234245u, 0u, 6815315267976099010ull, 1086018795u, 0u, 6802921642397272644ull, 3015334674u, 0u, 4231194396551816826ull, 918005093u, 0u, 13870187563289135604ull, 2571569896u, 0u, 3376538221658585432ull, 794169928u, 0u, 5803990111770754522ull, 4030425977u, 0u, 6689642437801411894ull, 2264328983u, 0u, 9403830665681153318ull, 1649606984u, 0u, 17877207146929807112ull, 2252753965u, 0u, 11412647483505278060ull, 4075289696u, 0u, 8528653614977707276ull, 2527755162u, 0u, 1369029204968302352ull, 2474393338u, 0u, 16192681280805161752ull, 3769610065u, 0u, 8353422318904680084ull, 791247442u, 0u, 5944750173431901844ull, 505026929u, 0u, // 26 1164806767832652738ull, 1263847532u, 0u, 1019185455857287636ull, 3857758540u, 0u, 13353829325750792302ull, 2114577966u, 0u, 7622531947304891736ull, 3359966288u, 0u, 12548514257924489970ull, 853517987u, 0u, 1698780325711761244ull, 3059744398u, 0u, 3714067678154678218ull, 137742431u, 0u, 17015348039141565738ull, 3085850273u, 0u, 781866169030517722ull, 1830324458u, 0u, 1689397634174181608ull, 3849780110u, 0u, 15510322727930418056ull, 348053075u, 0u, 11587650577411066444ull, 568456223u, 0u, 4340947793075610504ull, 3048314133u, 0u, 1057981969502028702ull, 3789276431u, 0u, 6789412994388566754ull, 95407523u, 0u, 10662450130641601224ull, 2432937414u, 0u, 5977168749872599906ull, 1699033191u, 0u, 4846924196167783508ull, 145108149u, 0u, 16679297916607791502ull, 1790900830u, 0u, 16724074919492857382ull, 776874222u, 0u, 1949986226507527994ull, 2874492502u, 0u, 15897278629831456106ull, 4183362755u, 0u, 16115126115129283024ull, 3004751292u, 0u, 7951993229904855216ull, 2759273541u, 0u, 7807670582603805250ull, 1255894394u, 0u, 10290866159330724942ull, 3610214627u, 0u, 2093000441318498366ull, 1566520733u, 0u, 4750287424706819106ull, 3095810998u, 0u, 7778582121676852838ull, 940746316u, 0u, 9658478455170783394ull, 2175914721u, 0u, 7004518753217432138ull, 1665459929u, 0u, 5569867453078048454ull, 331636229u, 0u, // 27 13322909769981885494ull, 2699788518u, 0u, 13618798743101680382ull, 3868963077u, 0u, 16161967764243094328ull, 3796615898u, 0u, 18040822275841048408ull, 641532488u, 0u, 12199455207323394134ull, 2671605071u, 0u, 12830670024334272522ull, 111241808u, 0u, 2538157427997459292ull, 3557073259u, 0u, 9029256124116100654ull, 1004036219u, 0u, 15914764170246386560ull, 1564251368u, 0u, 1502063028031816044ull, 179708300u, 0u, 6061210916981802836ull, 3559939173u, 0u, 6998632035067445128ull, 2477459518u, 0u, 4079631305063863222ull, 1197218324u, 0u, 10728317113680516470ull, 2601019865u, 0u, 11784917693592894544ull, 521276571u, 0u, 2094768905858818630ull, 3485400735u, 0u, 1510553187185923444ull, 1517541222u, 0u, 7420686821182108892ull, 480472915u, 0u, 14633877310735750802ull, 2120324379u, 0u, 16173386324532336060ull, 1917251925u, 0u, 12981156054635731596ull, 2882946087u, 0u, 6786925314637102224ull, 3453996476u, 0u, 13178313484655936550ull, 459310463u, 0u, 5107888727967355368ull, 2329962892u, 0u, 5497297660697119902ull, 2009187844u, 0u, 15528833016847426332ull, 2816418948u, 0u, 9498258344464636940ull, 2181915441u, 0u, 7716793031879017714ull, 964631905u, 0u, 2559718903541419776ull, 206550686u, 0u, 3170963551250436556ull, 3505374448u, 0u, 10116681877984813526ull, 1344861022u, 0u, 9246420438961917848ull, 2339028088u, 0u, // 28 8816203155784613944ull, 1809206689u, 0u, 12441799362809121804ull, 3856782278u, 0u, 4813390971776730974ull, 4102861637u, 0u, 7542582915338808896ull, 1179825908u, 0u, 12892803315310569414ull, 849533525u, 0u, 7428111958224106542ull, 1314147094u, 0u, 837131834438010050ull, 2825376486u, 0u, 10983651874375296328ull, 3938346472u, 0u, 6513098130121869960ull, 2190471985u, 0u, 11420041564268210454ull, 1694043070u, 0u, 18229025918433165622ull, 2536097u, 0u, 11325581697315451890ull, 3675189181u, 0u, 2917589365744811682ull, 2979441768u, 0u, 16084122104053303998ull, 3503530879u, 0u, 14427792491031081958ull, 4063291071u, 0u, 3869759780338916648ull, 180221815u, 0u, 17094074690942273582ull, 1062830182u, 0u, 14739259628552809402ull, 2331496305u, 0u, 8991535758590965770ull, 3729661113u, 0u, 13822702747704379200ull, 836011996u, 0u, 17468484890554970044ull, 3889631406u, 0u, 11865943461047322718ull, 4128965900u, 0u, 8775333877725653208ull, 3569943439u, 0u, 12299593649115873962ull, 127612256u, 0u, 18294313297827993016ull, 3684828551u, 0u, 1852796692774916096ull, 489824349u, 0u, 1600437962915299026ull, 4111715237u, 0u, 7901527101114232926ull, 3892859933u, 0u, 8441225796269264174ull, 1732209887u, 0u, 13025412354059436198ull, 4123987393u, 0u, 5473579560448782706ull, 3838049221u, 0u, 3474881891238945504ull, 3547942541u, 0u, // 29 13501729105815408240ull, 1582472495u, 0u, 17217474699967623948ull, 2825178187u, 0u, 9786008848618627528ull, 3130259565u, 0u, 231958284176545332ull, 1602566522u, 0u, 5160972330843885838ull, 2910994105u, 0u, 16976649469935133122ull, 177126920u, 0u, 12936052700435677166ull, 3077611439u, 0u, 11934830033436668844ull, 2068758200u, 0u, 15150417127769966310ull, 3347799407u, 0u, 17879639726411868660ull, 994579916u, 0u, 12241574716747533130ull, 2362500435u, 0u, 17090448566717655342ull, 514946402u, 0u, 12892907504373068110ull, 1443775365u, 0u, 10207160879100147500ull, 2546451103u, 0u, 9500299493799342946ull, 1419548683u, 0u, 3587070791055080396ull, 2084685896u, 0u, 17807371377374873002ull, 752229249u, 0u, 16604220742875495764ull, 4053900641u, 0u, 6924134647210446576ull, 1815965415u, 0u, 16990895758120257544ull, 3060458686u, 0u, 8059672678673118252ull, 1557288342u, 0u, 17776271490583908016ull, 3083331431u, 0u, 7291419720430327882ull, 792512640u, 0u, 267208636575392300ull, 1456028876u, 0u, 14634653683372267246ull, 2465555488u, 0u, 11812833048644280256ull, 3686910889u, 0u, 8656922775399054996ull, 1060241436u, 0u, 519070459451961426ull, 782546688u, 0u, 13764704520141916622ull, 680844520u, 0u, 14849526560463263250ull, 1560979150u, 0u, 3129470581396710076ull, 1507456125u, 0u, 6917085155221958138ull, 2119860468u, 0u, // 30 12791919956827961412ull, 1283502968u, 0u, 17278649762081698932ull, 966989998u, 0u, 3253045198764764150ull, 3409809982u, 0u, 4133918872810372430ull, 3867252468u, 0u, 14523977882491842200ull, 3581157877u, 0u, 8897499184593403642ull, 2338957051u, 0u, 13931650242967378088ull, 2795083416u, 0u, 10426340347287864266ull, 1744477241u, 0u, 2392565785122383968ull, 4227091227u, 0u, 6785170770148624392ull, 475115290u, 0u, 5590415390245034156ull, 1833647298u, 0u, 7803939811343783140ull, 1554269100u, 0u, 14261333142324922638ull, 3457336500u, 0u, 13717633781228549456ull, 1493525251u, 0u, 5772581583487262662ull, 3287647060u, 0u, 7167184607479776432ull, 1757566169u, 0u, 8505498035120001474ull, 3795324151u, 0u, 3655222040543585456ull, 1315170844u, 0u, 3688376398783855378ull, 715874132u, 0u, 9130811914047046608ull, 3492763940u, 0u, 9169634034032633556ull, 1046159262u, 0u, 14614458726232358964ull, 3614575520u, 0u, 12010757157856248518ull, 3176949292u, 0u, 978323344696009048ull, 2298122742u, 0u, 16447768286082463942ull, 3789741844u, 0u, 8617845926126754544ull, 458045729u, 0u, 12895771697753255152ull, 2743717066u, 0u, 17699789416443733192ull, 2447604898u, 0u, 15608329641830982524ull, 481026623u, 0u, 2846009955554270644ull, 2088739065u, 0u, 10375578923380511400ull, 2054311838u, 0u, 16587648878016940902ull, 2829027781u, 0u, // 31 41749991240686934ull, 3011396073u, 0u, 5665153980814259290ull, 4145906882u, 0u, 13449150586531049532ull, 3247315839u, 0u, 17430194915720502812ull, 3902625594u, 0u, 2055975487970369946ull, 3579324484u, 0u, 17229537866901735938ull, 1407039368u, 0u, 3891972813797825672ull, 1362638632u, 0u, 4673017619107233252ull, 2378866144u, 0u, 15275304040371893552ull, 821661956u, 0u, 11266244072038213906ull, 552620355u, 0u, 12707614128468530592ull, 2228309413u, 0u, 17913324112268499548ull, 3264511887u, 0u, 15556823803565948758ull, 3118279183u, 0u, 16244143336365838858ull, 2053813537u, 0u, 17388725147952715694ull, 2582269397u, 0u, 7458698349333549448ull, 4133072281u, 0u, 6714614240669455664ull, 2849197383u, 0u, 4681985369388886516ull, 2469758372u, 0u, 6403085231850788110ull, 3315793754u, 0u, 7785025580063284242ull, 2598952035u, 0u, 14789719978345234298ull, 3265189476u, 0u, 16630576879508705478ull, 3735118787u, 0u, 3565020129150253560ull, 1422921609u, 0u, 8136547063350165630ull, 1491022912u, 0u, 8786834418928023168ull, 1398244804u, 0u, 16164856989951486836ull, 2903012303u, 0u, 6897442619403102570ull, 2639910181u, 0u, 14357406690170195618ull, 3102682131u, 0u, 17036228454212198020ull, 2695429696u, 0u, 3261551207057252896ull, 3308317302u, 0u, 11774646586237898772ull, 4242685638u, 0u, 4549336532084611996ull, 2346825700u, 0u, // 32 16057032164495949962ull, 114725504u, 0u, 14343722260843472102ull, 2644902834u, 0u, 9184182959297105068ull, 3656311516u, 0u, 7036421047211650230ull, 3706905395u, 0u, 14148547339707470008ull, 646911379u, 0u, 13419100726080281582ull, 1118246411u, 0u, 4028300688247415726ull, 170883635u, 0u, 1247097384560023526ull, 285538761u, 0u, 3139587198555543914ull, 1685980191u, 0u, 9052783116320115594ull, 3985973924u, 0u, 18056927594014956626ull, 3398568337u, 0u, 938672089344242968ull, 2330142270u, 0u, 15741043571511489104ull, 2370724307u, 0u, 10761999142153759306ull, 386690335u, 0u, 12514443786761643376ull, 2439701525u, 0u, 12008063988197637630ull, 1216109148u, 0u, 12181909600873381326ull, 2173548972u, 0u, 1587460267139451600ull, 419094325u, 0u, 10097571099698962140ull, 3440898248u, 0u, 15525623517864249192ull, 1759117419u, 0u, 13418509741536276730ull, 3595982769u, 0u, 7113545609518829400ull, 1526096516u, 0u, 17454507081080204828ull, 1251033676u, 0u, 1035219033598270458ull, 2525782788u, 0u, 18137845778764339278ull, 3478371247u, 0u, 11829543727212617080ull, 927116749u, 0u, 5618544676332009730ull, 311068712u, 0u, 804542719089728582ull, 3828745468u, 0u, 11281609685222804616ull, 1896288158u, 0u, 8211509878441176008ull, 3139160282u, 0u, 7472399816379108736ull, 4242558323u, 0u, 11315209809227460500ull, 2612408429u, 0u, // 33 4012015078030796692ull, 729309987u, 0u, 17334970658225865448ull, 1368591833u, 0u, 5094158866021253496ull, 3919967722u, 0u, 15668540647945692140ull, 4082479004u, 0u, 11884309648770103116ull, 3842505469u, 0u, 14797928853238338978ull, 4091387548u, 0u, 10127565076953134696ull, 1051391156u, 0u, 17058699195981838232ull, 2529084624u, 0u, 12368694457590606988ull, 3676430640u, 0u, 10649979510745387502ull, 1460238688u, 0u, 10972617473864090944ull, 1778634005u, 0u, 18147881568450239374ull, 2350383950u, 0u, 16344016674981813804ull, 1661866882u, 0u, 3784089302550949080ull, 1030093996u, 0u, 7006738394599417580ull, 2063675151u, 0u, 8274518471034184110ull, 2407878010u, 0u, 2669388537287003392ull, 3996662416u, 0u, 6134157455600825280ull, 1162085648u, 0u, 10685450584732418518ull, 1876074608u, 0u, 15280256575939663040ull, 3132490342u, 0u, 3242079498910532292ull, 3930812458u, 0u, 11533078726148441488ull, 3421487587u, 0u, 7356657690897249584ull, 825549556u, 0u, 17290738822680467790ull, 827239909u, 0u, 13465983847598484014ull, 1232290699u, 0u, 7347862063356533688ull, 3228063588u, 0u, 3354282945800878812ull, 4268817865u, 0u, 2046822507811952844ull, 3173964598u, 0u, 11584944750649864772ull, 4053532804u, 0u, 11491592875126222044ull, 1297847955u, 0u, 12755074667111554244ull, 2744802153u, 0u, 1223241045832816840ull, 1548154948u, 0u, // 34 15911283873478952838ull, 3166615088u, 0u, 12885730058732622354ull, 1373032024u, 0u, 7759365751591137806ull, 4116637227u, 0u, 12916719812039567822ull, 1214353169u, 0u, 13550902169083145404ull, 3347372591u, 0u, 11263918305323757008ull, 540957581u, 0u, 16636687652882489170ull, 627870450u, 0u, 518370039648374376ull, 4689426u, 0u, 905927897238771634ull, 1651508748u, 0u, 14344471875774292928ull, 1267734809u, 0u, 5727543101143537828ull, 3985333287u, 0u, 14872198315692171766ull, 3896647689u, 0u, 4405541666683202122ull, 4156529783u, 0u, 1778678630087881824ull, 133890467u, 0u, 15214805496833739040ull, 748661899u, 0u, 8383771817952929118ull, 2269534288u, 0u, 3946129402934558294ull, 2744248464u, 0u, 7421628730936348198ull, 3475488744u, 0u, 3800008321808601462ull, 1222680869u, 0u, 1116526291167500180ull, 2127979069u, 0u, 4756961181276618958ull, 1193769563u, 0u, 17434919069622463818ull, 2216172743u, 0u, 16168257605987480210ull, 48890575u, 0u, 13075917892847842666ull, 1992492230u, 0u, 11900807164318537732ull, 2793454172u, 0u, 11111320540649273776ull, 123306976u, 0u, 5141579627152500860ull, 3685059209u, 0u, 12021728109670808668ull, 77367370u, 0u, 3908476319063788286ull, 3123319982u, 0u, 18434142967515620902ull, 1638979572u, 0u, 3469093176629202308ull, 136163625u, 0u, 17890009464632407562ull, 2914713502u, 0u, // 35 3650405349904104354ull, 1629798251u, 0u, 4881877976135097426ull, 983365093u, 0u, 17268668481239472124ull, 108348946u, 0u, 8441204468207995118ull, 1586902042u, 0u, 3187127463103707074ull, 1630867702u, 0u, 17055640067675175348ull, 185944676u, 0u, 8409589617400879208ull, 2022358770u, 0u, 13423443069996151738ull, 3093622943u, 0u, 17172809650906440610ull, 2651184333u, 0u, 3550718471922299766ull, 1671853523u, 0u, 17147358748280189296ull, 2500220570u, 0u, 2582299464161486994ull, 52446314u, 0u, 7798879675426609642ull, 3519827518u, 0u, 10521377883924693568ull, 3507935970u, 0u, 13355222162699141216ull, 3452252931u, 0u, 4310688604740395624ull, 592123526u, 0u, 18227588398602890492ull, 2174117535u, 0u, 5398215438648937198ull, 1144427457u, 0u, 1436080709129499368ull, 1218921188u, 0u, 7037654367733292084ull, 2194860819u, 0u, 6463045950433755592ull, 3714974730u, 0u, 1875994108130971562ull, 4093542651u, 0u, 1363279660235365290ull, 3158832608u, 0u, 2986919147284909152ull, 3137096058u, 0u, 4966117536057767472ull, 3489134029u, 0u, 4168390715194936350ull, 4161365743u, 0u, 1329321652354083806ull, 2452769709u, 0u, 2316433616319719750ull, 1142806681u, 0u, 10046834514726548630ull, 66015203u, 0u, 1534539254734954346ull, 692816625u, 0u, 5818673887554373306ull, 1611245159u, 0u, 15310212873509989588ull, 3649550810u, 0u, // 36 6116868064540439660ull, 2987558120u, 0u, 5280405820814569296ull, 4066504782u, 0u, 1000884124462215430ull, 3260868148u, 0u, 18192008890924907976ull, 2252409222u, 0u, 3172961190889372510ull, 3272467027u, 0u, 16779693700083763076ull, 2921812874u, 0u, 3133600811854725964ull, 218428979u, 0u, 18423122736963026106ull, 2962927145u, 0u, 9518914058838283068ull, 4058404165u, 0u, 15393092747924650272ull, 248483665u, 0u, 11534208160219247872ull, 2254209144u, 0u, 6771162914079423222ull, 1120310041u, 0u, 725598279600070924ull, 3022646211u, 0u, 7014502400623825852ull, 2642433106u, 0u, 7324641812451656712ull, 3748918008u, 0u, 6616688367071614772ull, 2206237259u, 0u, 4544073194722355400ull, 2240394165u, 0u, 3065281386881409566ull, 1089128100u, 0u, 2161866718759893526ull, 1844680118u, 0u, 15684604102193709138ull, 3652966963u, 0u, 4563042637055949810ull, 506833876u, 0u, 9309866579946068078ull, 1217184750u, 0u, 4377120144700341626ull, 3681960716u, 0u, 436811434050124172ull, 2000897035u, 0u, 1152771302696414526ull, 2544138118u, 0u, 3865614330427917018ull, 2972394045u, 0u, 16471439604108846920ull, 2474332511u, 0u, 17897786626727725514ull, 2211431856u, 0u, 11682612180284692444ull, 1618375038u, 0u, 3849537447619733254ull, 343425809u, 0u, 14456909988999252528ull, 1547569546u, 0u, 10990625574467117444ull, 102806521u, 0u, // 37 8864695364135738406ull, 523171828u, 0u, 2010007768711053112ull, 2313435487u, 0u, 2121403242749830800ull, 768787532u, 0u, 3154751035612779954ull, 1135930878u, 0u, 17932809455020236196ull, 3286616384u, 0u, 6075620969056442186ull, 1838410122u, 0u, 5422494247504656542ull, 617981763u, 0u, 7392859601042840724ull, 3511610753u, 0u, 16145587716110026444ull, 40244704u, 0u, 499178538047295630ull, 3126372941u, 0u, 9203941754035006118ull, 2007098637u, 0u, 6279091491819077870ull, 3528274000u, 0u, 54799531857499708ull, 3885175471u, 0u, 16042681793139352060ull, 1473052117u, 0u, 15796398577277602246ull, 115617081u, 0u, 18336482154915194716ull, 275272006u, 0u, 5445645212808551826ull, 192100219u, 0u, 9043373799629881382ull, 748726823u, 0u, 6877776004379640ull, 156225416u, 0u, 8685961573871176222ull, 4268406709u, 0u, 2959952279003291952ull, 815755721u, 0u, 4254303499848240494ull, 1170968246u, 0u, 4149487152036858918ull, 707778579u, 0u, 15572880518308242770ull, 3838867921u, 0u, 10221482195360631602ull, 352858904u, 0u, 16601873526734832984ull, 486221643u, 0u, 3059094051395918906ull, 1645784220u, 0u, 13881411442393108122ull, 2758906481u, 0u, 15005007915350580320ull, 4276772561u, 0u, 3311086225613380082ull, 3890178235u, 0u, 16877233185832301474ull, 3528241734u, 0u, 1428178539039161644ull, 1297075442u, 0u, // 38 10708586820508153170ull, 303474060u, 0u, 16653774834341641734ull, 4078292426u, 0u, 17473619298764482372ull, 3648815939u, 0u, 7514088033635931790ull, 387232503u, 0u, 16233307967062206940ull, 227299161u, 0u, 10844171817854790592ull, 1420018770u, 0u, 10238077758142550362ull, 3003488752u, 0u, 16456133491498076380ull, 4070130930u, 0u, 1093863537336569106ull, 1552105464u, 0u, 14682043646876655958ull, 3994306711u, 0u, 2732458795399190028ull, 2924673545u, 0u, 5251052013471088630ull, 1496085709u, 0u, 8870960331027640558ull, 3639263247u, 0u, 14221818388840921822ull, 3584776678u, 0u, 5786427112132936506ull, 747271575u, 0u, 3983481324631203762ull, 1078917687u, 0u, 7924274965913777784ull, 2368288219u, 0u, 926347983845771140ull, 1910600441u, 0u, 6881560240432175254ull, 2754650485u, 0u, 10517879743116298894ull, 428793813u, 0u, 5870156025405456564ull, 3237375132u, 0u, 1914409869083110766ull, 998085906u, 0u, 3061833487532636462ull, 1527071630u, 0u, 1372229181986917210ull, 3436773975u, 0u, 10699115477798620214ull, 2238655087u, 0u, 10284381491902755828ull, 180667708u, 0u, 4730643501861367656ull, 1692289673u, 0u, 13802944211700404690ull, 2020884247u, 0u, 15034859854130015096ull, 3648933197u, 0u, 10003736974920402134ull, 3814987308u, 0u, 11610405285830759792ull, 3630087373u, 0u, 10063459873840386172ull, 819545510u, 0u, // 39 13643957583614553180ull, 1922454442u, 0u, 12599685383809399452ull, 2827034660u, 0u, 10954396302199192254ull, 2623248591u, 0u, 7984134586533216952ull, 3679633666u, 0u, 15323201535567866504ull, 1947812073u, 0u, 12958149956774147884ull, 166353594u, 0u, 4606892927352955308ull, 3937658543u, 0u, 11564814400170753226ull, 1648389840u, 0u, 11495560801964330346ull, 1397190766u, 0u, 13150190473733551272ull, 2313195767u, 0u, 7272893666093436772ull, 832327448u, 0u, 17236896731463846192ull, 1811886115u, 0u, 10723246409621684058ull, 1881721288u, 0u, 9725483453933778764ull, 1883154412u, 0u, 12674773964023123528ull, 3497295491u, 0u, 14349702906676215394ull, 350559106u, 0u, 17313834167980711972ull, 3452867577u, 0u, 3392808724350161796ull, 364099012u, 0u, 17029785956333469178ull, 2435473825u, 0u, 15186065383181687120ull, 1385789726u, 0u, 9868341268961479018ull, 2398403493u, 0u, 9732063679350063636ull, 759742546u, 0u, 11563378204894526838ull, 2025188289u, 0u, 5673507279758926726ull, 3338816533u, 0u, 8755509021473465192ull, 976468787u, 0u, 7040052652582842832ull, 3588800719u, 0u, 12466338869317616694ull, 2586862911u, 0u, 13440938877050395772ull, 1389286509u, 0u, 5533595056350079076ull, 3218603471u, 0u, 10913189343833470314ull, 1064445589u, 0u, 9678628599764095908ull, 3952176973u, 0u, 11308672256178275998ull, 3507475680u, 0u, // 40 1235480579866073754ull, 1676970169u, 0u, 9060803285350532412ull, 1620461402u, 0u, 14239314629872173048ull, 1330568528u, 0u, 2327938548911854542ull, 1277522842u, 0u, 17707327125288182928ull, 887913832u, 0u, 17949388597490999364ull, 956318767u, 0u, 16124798788059171790ull, 2406378363u, 0u, 18309333433486656238ull, 1933178880u, 0u, 10216855581188925834ull, 566417749u, 0u, 13536789665917951734ull, 1918505709u, 0u, 9789843422887594308ull, 2759429793u, 0u, 10336268030276134748ull, 3539140208u, 0u, 365481394138964776ull, 2021460502u, 0u, 7591663402918028206ull, 2943548481u, 0u, 15889499274007189214ull, 3511829470u, 0u, 5601495869509594634ull, 623295878u, 0u, 1876136715991756406ull, 368238206u, 0u, 14717096535609789602ull, 3878479262u, 0u, 15682761487794323182ull, 4140675038u, 0u, 14446691422838890178ull, 1647685883u, 0u, 9192860727503393724ull, 4282500063u, 0u, 13184894740123089174ull, 259609118u, 0u, 11996102333304491976ull, 147017935u, 0u, 1120056939149148362ull, 1853197412u, 0u, 13374103249548365856ull, 644699543u, 0u, 17815368770852531244ull, 2200059043u, 0u, 2852782209660243716ull, 2084587267u, 0u, 16550751596884818806ull, 1495121446u, 0u, 14717528490679840184ull, 3714732652u, 0u, 17721943529335211338ull, 1153838435u, 0u, 7116441386235941946ull, 136868273u, 0u, 417114602863436530ull, 96399398u, 0u, // 41 4460170072051390506ull, 3710221543u, 0u, 1213133275059906506ull, 1026984660u, 0u, 14099166046949603252ull, 1866562476u, 0u, 16786062733949840928ull, 3146282533u, 0u, 11019197177955944496ull, 3869839410u, 0u, 15228206386688237078ull, 3500286099u, 0u, 13040794651046133190ull, 1807289237u, 0u, 5794139952643783752ull, 1632042073u, 0u, 13864434993119403608ull, 632113960u, 0u, 5287233158838606704ull, 3493692891u, 0u, 15245919108578935172ull, 745659230u, 0u, 6538681323346368574ull, 2247198794u, 0u, 8263795176467329898ull, 2186994764u, 0u, 12476832399070130068ull, 2243308483u, 0u, 7675451431614712136ull, 1407889651u, 0u, 2220022636935327256ull, 1199512503u, 0u, 7437283072939787662ull, 2206956157u, 0u, 8778673006290015220ull, 3817783467u, 0u, 14753637262123007412ull, 1736221035u, 0u, 14958631899183016530ull, 187855668u, 0u, 3664056123308712402ull, 3535300475u, 0u, 6351103979859234436ull, 2405702318u, 0u, 10226783996190301212ull, 4114948999u, 0u, 9080230101084770364ull, 2192870455u, 0u, 31883567136599550ull, 1803155966u, 0u, 18333306208529847746ull, 4051638719u, 0u, 10935688670231781002ull, 3243626947u, 0u, 9262963619126572804ull, 1473540345u, 0u, 8900504603265633268ull, 1811836452u, 0u, 9501706072835990878ull, 3753628245u, 0u, 468578483960022586ull, 35161036u, 0u, 5032659617794726212ull, 319470408u, 0u, // 42 16676503750146117928ull, 333506104u, 0u, 15308730797193603766ull, 2091449263u, 0u, 5412150670320731670ull, 816241037u, 0u, 16556449125568662510ull, 135825583u, 0u, 16687214019284097104ull, 1374049829u, 0u, 17515789203280150452ull, 1742844415u, 0u, 1064126235701680450ull, 1378327251u, 0u, 2821357017801281614ull, 3766605813u, 0u, 10939554110922049142ull, 1741674227u, 0u, 1488333065389620360ull, 2089606976u, 0u, 5685065731153603880ull, 2868073321u, 0u, 17554572579913069178ull, 448524617u, 0u, 7094035211849381236ull, 1964809419u, 0u, 707672475543604698ull, 4113351235u, 0u, 7982495457091050298ull, 1182471967u, 0u, 17596427952764714396ull, 1552767705u, 0u, 9741634565229515122ull, 4068772164u, 0u, 15206084016631571542ull, 1166633457u, 0u, 1456590058595393710ull, 235479525u, 0u, 17474218057950992328ull, 1627515926u, 0u, 5348100820135507648ull, 3056009084u, 0u, 16498794848448929762ull, 3320987944u, 0u, 2609592111657270520ull, 1705948216u, 0u, 8124044135979046702ull, 1095295665u, 0u, 3294893865987529800ull, 4259726520u, 0u, 10100870435073304690ull, 1800130199u, 0u, 15213968055048501322ull, 2640924926u, 0u, 17141094761624969156ull, 4197184739u, 0u, 17794876400812144426ull, 2317223763u, 0u, 16299775715227997176ull, 1318684368u, 0u, 7205712445318770772ull, 1714209129u, 0u, 8159590718744400242ull, 601714287u, 0u, // 43 14021521613446120726ull, 1446487457u, 0u, 9987944940146279210ull, 3494158138u, 0u, 4216585634983490942ull, 1228639294u, 0u, 16555675362396599220ull, 101515954u, 0u, 2976077705807993044ull, 1920995254u, 0u, 9647962551720451986ull, 88257550u, 0u, 8710933390187154680ull, 3726836450u, 0u, 17361517110539035180ull, 63679820u, 0u, 6675871995630099274ull, 2543754081u, 0u, 13414695284105478170ull, 2518351142u, 0u, 12416180851361684118ull, 2140484648u, 0u, 16581793164939210106ull, 3388041170u, 0u, 2387342548268387310ull, 1049309485u, 0u, 2389483849304064340ull, 1781672539u, 0u, 7492557237185868002ull, 2830727227u, 0u, 6422251193319331166ull, 3156607872u, 0u, 18241791474070758366ull, 333253852u, 0u, 2563741347892662958ull, 1069706279u, 0u, 1749492416648996780ull, 1049879931u, 0u, 7852335401878801642ull, 1980915167u, 0u, 14636177194797892068ull, 644626146u, 0u, 3804998346075223794ull, 1660865097u, 0u, 1144655181691163624ull, 308422839u, 0u, 6486960240660537352ull, 2982269092u, 0u, 9987720262531143158ull, 3308882143u, 0u, 294290683595966954ull, 1538378451u, 0u, 9494302225798709048ull, 3218999785u, 0u, 6687649078695157804ull, 1566401262u, 0u, 2502104430480902576ull, 4051578363u, 0u, 1526142709847218806ull, 4163810341u, 0u, 5374487042050017800ull, 3093654977u, 0u, 1770317389802521844ull, 414997156u, 0u, // 44 10646454591751687874ull, 1709663318u, 0u, 16292652942858139568ull, 73702025u, 0u, 8638447268768537228ull, 2032065026u, 0u, 12949002525954384904ull, 497794369u, 0u, 13983411287237371600ull, 2667073742u, 0u, 12949966868474578440ull, 3603925938u, 0u, 12005562404661236226ull, 4148599564u, 0u, 3727805260635936252ull, 280581513u, 0u, 15102480886478498698ull, 766208473u, 0u, 9515139132841503456ull, 947646875u, 0u, 5170540042980594946ull, 2270383169u, 0u, 4324047062565941002ull, 2398627196u, 0u, 2909417250584064614ull, 159348665u, 0u, 17959761934546621620ull, 2196456995u, 0u, 8505160107447015092ull, 3122772427u, 0u, 9492731612915089436ull, 4011426726u, 0u, 3128370901006269686ull, 2573687570u, 0u, 12037819780690519234ull, 595635057u, 0u, 17999606533933587224ull, 2480075196u, 0u, 12046609644240087130ull, 388689281u, 0u, 2766130069563156040ull, 4158203953u, 0u, 16345781319487112404ull, 2973688992u, 0u, 6562478516339240368ull, 3600662117u, 0u, 11209869962605752314ull, 1111455122u, 0u, 5093329307632622984ull, 3258625533u, 0u, 10910156907810470308ull, 827281792u, 0u, 17894411210227136344ull, 3629670195u, 0u, 5663090254586299764ull, 1519184550u, 0u, 5876761823513515326ull, 17123728u, 0u, 7687780657285686324ull, 1086266961u, 0u, 9070973296756604632ull, 1410292899u, 0u, 13790680804521061362ull, 2755409234u, 0u, // 45 9027892721748815708ull, 1959559041u, 0u, 2903775098696260388ull, 907413103u, 0u, 7029699153693357746ull, 2067338082u, 0u, 16719957813922243082ull, 223073105u, 0u, 7415819035850164064ull, 3441256802u, 0u, 7976756893196631748ull, 983108754u, 0u, 5542248881986456028ull, 2520030306u, 0u, 578395644807279380ull, 3567281931u, 0u, 7423837137059289220ull, 632024022u, 0u, 9828992707246502206ull, 130146148u, 0u, 11645889221068702442ull, 2797956242u, 0u, 6622176271008939662ull, 2067895216u, 0u, 2593155756954337806ull, 1589815869u, 0u, 14101712315110431382ull, 3729582783u, 0u, 2726103527307394842ull, 39431150u, 0u, 10232351185114946722ull, 2559640187u, 0u, 3667129350387348432ull, 2428159981u, 0u, 18417190693936959240ull, 3550642121u, 0u, 15125728988891208318ull, 2558482321u, 0u, 2260173427281367658ull, 2889908187u, 0u, 9222440352173842918ull, 2276224085u, 0u, 1094025083203811876ull, 2916861589u, 0u, 995816821390333984ull, 2051082173u, 0u, 10391837912152845408ull, 3083060390u, 0u, 5665202186307842054ull, 2761204665u, 0u, 4545549160299730576ull, 3926596616u, 0u, 14915863120850304692ull, 758234379u, 0u, 7246357743588342284ull, 233441464u, 0u, 13176272149909997798ull, 2785714845u, 0u, 16811307279982735012ull, 3470550852u, 0u, 15243413727274119468ull, 3275330715u, 0u, 994159841857664344ull, 2718529103u, 0u, // 46 15325902772626437522ull, 2536563455u, 0u, 10503795405258504082ull, 3792347841u, 0u, 14755301200311694002ull, 127692558u, 0u, 8528659320764304772ull, 3012966496u, 0u, 12038263862591638326ull, 460857156u, 0u, 14929709800821696568ull, 2139765433u, 0u, 16253998545822392576ull, 3300812515u, 0u, 15960362029567018616ull, 1307603899u, 0u, 17345241183907074876ull, 2368286181u, 0u, 13001831469750811418ull, 501912241u, 0u, 9515252352365058682ull, 2772719426u, 0u, 5690431029826708782ull, 1208676634u, 0u, 18398939879931663784ull, 1565490176u, 0u, 4726513240313847094ull, 3466611667u, 0u, 1345917514735600398ull, 2452563290u, 0u, 2923100782726834680ull, 3740536487u, 0u, 12679299808006011170ull, 226093545u, 0u, 18147853457793280552ull, 2216025427u, 0u, 3208537306054340824ull, 869527397u, 0u, 1797256735528240438ull, 223083195u, 0u, 14642132518295853734ull, 3023078731u, 0u, 3480997003072181704ull, 818388653u, 0u, 1701511219399512834ull, 871608244u, 0u, 8385008290505384152ull, 1365917180u, 0u, 14772959421324973550ull, 3688284775u, 0u, 1337628985698724974ull, 2739920881u, 0u, 15745110459314715770ull, 3107044441u, 0u, 9632984213198267670ull, 189687072u, 0u, 16311155952801828194ull, 2662810013u, 0u, 13539881143133213754ull, 1660006010u, 0u, 3688363105762350884ull, 1032991131u, 0u, 164012469014191350ull, 1778123412u, 0u, // 47 8391933122548476984ull, 185048364u, 0u, 9372120988188654784ull, 1983643359u, 0u, 9146587265144999072ull, 3351507821u, 0u, 9233667786262749018ull, 3999834869u, 0u, 9575791850986991864ull, 3451228352u, 0u, 12972064553887978522ull, 2089030682u, 0u, 6383339060605099092ull, 1193309256u, 0u, 6305062529914752766ull, 1627823706u, 0u, 17530465537930489674ull, 3586071600u, 0u, 9373315283529754708ull, 4102137699u, 0u, 15302795174277283666ull, 3352995372u, 0u, 3417180670021175724ull, 2712430066u, 0u, 12227761756907601096ull, 2761474865u, 0u, 45863474831059182ull, 1833045184u, 0u, 16442292483766365462ull, 1696333767u, 0u, 15989624383553104752ull, 930186214u, 0u, 14056969264149612830ull, 3565700886u, 0u, 7352589618820683496ull, 3166287087u, 0u, 2886320643376631508ull, 951689596u, 0u, 5396030403380799190ull, 2179307630u, 0u, 17949795490282756470ull, 2749208716u, 0u, 12280412538905920298ull, 1429790900u, 0u, 16358026388626034018ull, 380035648u, 0u, 12749302653831990260ull, 3338858415u, 0u, 12654734065495452198ull, 2166050567u, 0u, 557778707733664966ull, 2151908778u, 0u, 11639922016134789892ull, 2896592175u, 0u, 16105636176175346306ull, 3104892940u, 0u, 11966033272529932288ull, 3173152934u, 0u, 611350375823755372ull, 3849187082u, 0u, 15500317087035736458ull, 228505562u, 0u, 11088540552360544562ull, 3805835047u, 0u, // 48 2590962560669003480ull, 3110651850u, 0u, 9441807280454724310ull, 3387386414u, 0u, 10056085483581694442ull, 3286152073u, 0u, 91709293636586814ull, 3942571637u, 0u, 1131915595645169922ull, 3198639132u, 0u, 5772091722581730672ull, 3526747117u, 0u, 11059883577827821752ull, 4046172963u, 0u, 10261830168974819654ull, 4037754059u, 0u, 9665990199941537076ull, 279002712u, 0u, 16105870599334513770ull, 3816781933u, 0u, 5555118288835563936ull, 1507780112u, 0u, 14937004286742075458ull, 3626666210u, 0u, 17755656915997822038ull, 1221486309u, 0u, 15366934969154719628ull, 2248490553u, 0u, 4908113143070094940ull, 4234399373u, 0u, 7117570662070133300ull, 2892307710u, 0u, 16611541415804779224ull, 1551555785u, 0u, 13288733281020681854ull, 1445629801u, 0u, 15696984398610477224ull, 2419964710u, 0u, 13772555391012932810ull, 2908882702u, 0u, 18377975852314051708ull, 810070358u, 0u, 12208432217797013482ull, 1726449579u, 0u, 3454936714229500668ull, 1594910469u, 0u, 10008587063621563052ull, 3402210980u, 0u, 9972918361029448754ull, 937777114u, 0u, 11928733203107224270ull, 1707233425u, 0u, 16134702319665524858ull, 1499002042u, 0u, 2206130070692577656ull, 2524260469u, 0u, 17653491622925305622ull, 3036067465u, 0u, 10783141189363285740ull, 3314230427u, 0u, 10233454333172085104ull, 1112359549u, 0u, 9350088750470912038ull, 937115546u, 0u, // 49 17247478811382590290ull, 1716980607u, 0u, 7299435941908355640ull, 2404107547u, 0u, 9294280196822537298ull, 591938172u, 0u, 15441977090689436814ull, 1261876536u, 0u, 453501337216287696ull, 3461651649u, 0u, 6590938893682818634ull, 102984735u, 0u, 15055881112820553194ull, 807737854u, 0u, 9011883682656381294ull, 814889307u, 0u, 14649307228694017636ull, 4223612962u, 0u, 6927663793915218832ull, 469060256u, 0u, 4638285019623294510ull, 243609595u, 0u, 15291239209347259632ull, 3324275230u, 0u, 3489006421940089140ull, 318781861u, 0u, 2429504978109627694ull, 3133153672u, 0u, 10606731750681691776ull, 811696633u, 0u, 17125878361055010900ull, 1089423753u, 0u, 7165954107149567916ull, 945576678u, 0u, 10273536461960360706ull, 4272738637u, 0u, 10527344697849508814ull, 2386353732u, 0u, 7329809894993998948ull, 3853744788u, 0u, 10312998887440972586ull, 885597889u, 0u, 9484946690433803078ull, 3425102133u, 0u, 17396015156619924046ull, 3735846125u, 0u, 7550592714488342550ull, 3128910344u, 0u, 13926899895409830620ull, 1651781158u, 0u, 8069779886321042938ull, 329553039u, 0u, 8510398570489742244ull, 640617305u, 0u, 5248913315920130584ull, 4179541319u, 0u, 6539115538248965856ull, 1656583656u, 0u, 12871770679153592306ull, 2885939141u, 0u, 12892170063680572530ull, 261482326u, 0u, 3326930359983688130ull, 2217720054u, 0u, // 50 6466758931854716274ull, 532125633u, 0u, 6852291260163655680ull, 1466269496u, 0u, 15509045199709125202ull, 1323831135u, 0u, 7639244427197945320ull, 2213577029u, 0u, 13375399695369331264ull, 3406573555u, 0u, 13689800587692488938ull, 3920027666u, 0u, 16926755750398245656ull, 562125058u, 0u, 12570622287137349344ull, 3236321271u, 0u, 4159564338958363470ull, 759966807u, 0u, 1170073417696729272ull, 740480501u, 0u, 8667761264084632470ull, 651428239u, 0u, 14266757303262270042ull, 1012751424u, 0u, 3322262815386002284ull, 2883882365u, 0u, 8718181631044706450ull, 3726305215u, 0u, 16761938131993461260ull, 2228169802u, 0u, 6176736781557680294ull, 581966893u, 0u, 2905821336398002394ull, 2268686658u, 0u, 13887479655184040018ull, 3929819009u, 0u, 9923198982867480326ull, 500650318u, 0u, 12905773880744818624ull, 2362819828u, 0u, 13827192104887174928ull, 2544523053u, 0u, 1094813685572631402ull, 3327387383u, 0u, 10645628687444479642ull, 1035391125u, 0u, 7750990358692310164ull, 336092661u, 0u, 14352042469941455376ull, 987185441u, 0u, 14334875084099676260ull, 1982107650u, 0u, 14743944546911007674ull, 86442868u, 0u, 16443790641350369298ull, 567324811u, 0u, 16249608663256824280ull, 3739263231u, 0u, 11600893350028684558ull, 1490090800u, 0u, 12159513907041029776ull, 1088256174u, 0u, 13429891745298097126ull, 4112261186u, 0u, // 51 10380644349906387840ull, 2567947292u, 0u, 5477023261663898426ull, 2601426884u, 0u, 8773177396446209632ull, 1848544058u, 0u, 12609100773900268100ull, 3384043842u, 0u, 3356873843933544844ull, 588446115u, 0u, 11811023752344025066ull, 3886706138u, 0u, 7384274986049624754ull, 2630397164u, 0u, 8418845685711589426ull, 1458787642u, 0u, 4291566038584956506ull, 977560762u, 0u, 3150080542279238918ull, 4283950334u, 0u, 163940733924544940ull, 574156303u, 0u, 10535397652784543402ull, 962337081u, 0u, 4896667664670627344ull, 606321092u, 0u, 4361099159797758228ull, 2126702850u, 0u, 18161159761385460242ull, 654383782u, 0u, 17461726891688469952ull, 1886296391u, 0u, 9523424042225295066ull, 472760731u, 0u, 3777226099327257920ull, 942695263u, 0u, 15635834860764038344ull, 866435133u, 0u, 15015155746305828130ull, 134770964u, 0u, 7456386074525906900ull, 458552679u, 0u, 2506547561982403984ull, 4171802132u, 0u, 13457647074374349328ull, 1350333669u, 0u, 641143950531009946ull, 369960243u, 0u, 176183462486338580ull, 750279214u, 0u, 11744494434842610130ull, 527727836u, 0u, 12977060426252142534ull, 167084722u, 0u, 15091706736095167112ull, 2594287680u, 0u, 17179195916780696232ull, 2902938152u, 0u, 12469647706241086436ull, 3919015356u, 0u, 670529047279093898ull, 3443141683u, 0u, 5885617461957645500ull, 3696631827u, 0u, // 52 13487846854204721760ull, 943648447u, 0u, 15185679010215598640ull, 2769192301u, 0u, 9470236163708491658ull, 3043614246u, 0u, 1381728556280939610ull, 276547606u, 0u, 1169715728000533714ull, 3784428659u, 0u, 8069813546499677722ull, 2027416833u, 0u, 12653288228163853704ull, 3206238448u, 0u, 657866859679770128ull, 1292649750u, 0u, 15557111501755059500ull, 173144414u, 0u, 13164985413977734502ull, 2765645068u, 0u, 5037247294164595796ull, 1668698918u, 0u, 5700864854401346210ull, 1704283243u, 0u, 14849349887549914666ull, 2361479932u, 0u, 9188012548281373084ull, 1729550993u, 0u, 11180531183681823972ull, 3441014721u, 0u, 11278921076851071948ull, 786606198u, 0u, 12597398835504485128ull, 3865006058u, 0u, 12729216933180947938ull, 299455271u, 0u, 3739014500030532630ull, 3279308754u, 0u, 13465480809876296660ull, 3563323486u, 0u, 10149325764129925902ull, 1939492444u, 0u, 8513877280975605540ull, 1498584821u, 0u, 15291312472160083390ull, 1957449251u, 0u, 5523230730298318932ull, 1785907067u, 0u, 2773661606465711098ull, 3895380541u, 0u, 16612569984316958300ull, 3032869195u, 0u, 13365992555536464912ull, 194834147u, 0u, 3553916305717609162ull, 3537517073u, 0u, 10623804852698143304ull, 1810053267u, 0u, 3039350794111475798ull, 1667028407u, 0u, 1031821512357363034ull, 2411922429u, 0u, 5984369063485559726ull, 856577977u, 0u, // 53 13770550272569626380ull, 1723911248u, 0u, 14518177639596457918ull, 2431896322u, 0u, 14299764641767941586ull, 2706272138u, 0u, 11280313978807722610ull, 243796630u, 0u, 13140782678257775728ull, 3433239174u, 0u, 1101133445111377178ull, 4260259449u, 0u, 3874242240705715062ull, 366909492u, 0u, 11202435861146844906ull, 3504249728u, 0u, 15382243714032249668ull, 342853820u, 0u, 14923505611042253086ull, 1999425318u, 0u, 6171882173042716820ull, 354768634u, 0u, 12404542130857574304ull, 3331824596u, 0u, 14466453821429730178ull, 167420136u, 0u, 5100023731179052674ull, 3975932906u, 0u, 7657002557538412368ull, 3723503631u, 0u, 14527491556614136574ull, 1674464712u, 0u, 5130891539490022714ull, 2322857577u, 0u, 518272396730997872ull, 4158378201u, 0u, 4000332720023198786ull, 3536470858u, 0u, 18400370647923125468ull, 2252922584u, 0u, 13717782750181491014ull, 2083474744u, 0u, 4649480566314459374ull, 3390125404u, 0u, 2558710523976756106ull, 1481776839u, 0u, 150682266339599438ull, 1358971978u, 0u, 16485876371965982348ull, 1492828687u, 0u, 10940458925490022706ull, 443717483u, 0u, 14355078320312624558ull, 620973903u, 0u, 867963284873921340ull, 2271083318u, 0u, 10319608737873476604ull, 294290485u, 0u, 10127375191254656038ull, 1364981278u, 0u, 16556771882799812790ull, 1508689297u, 0u, 5319756877057345852ull, 173452017u, 0u, // 54 4242917885421731228ull, 2386459067u, 0u, 8843588707630596276ull, 2887609329u, 0u, 53073321509093742ull, 2786677660u, 0u, 17015806889335461844ull, 3035736876u, 0u, 6145031937314794848ull, 2081175864u, 0u, 2069866414981381388ull, 4280971154u, 0u, 8438896021119612022ull, 1800953592u, 0u, 16921979011496577512ull, 658675639u, 0u, 11496267555940589178ull, 3855957392u, 0u, 15806294239341234042ull, 1809712553u, 0u, 11607152468003323784ull, 3733331077u, 0u, 4642267483908657732ull, 3384155026u, 0u, 15074463210256856684ull, 3472310040u, 0u, 14687115864593576878ull, 963329847u, 0u, 4887174395574774842ull, 2400179899u, 0u, 9634297508088005246ull, 3485117266u, 0u, 3126463545639530330ull, 1033446971u, 0u, 12366426979828151056ull, 168165790u, 0u, 5153010864998290506ull, 4012671081u, 0u, 13920659754031136996ull, 2398901277u, 0u, 7974042619077109114ull, 1758242956u, 0u, 4710804971645159252ull, 1847960712u, 0u, 12110885293725950924ull, 2294734828u, 0u, 11094089711377649564ull, 2528922031u, 0u, 13000532684028363666ull, 2947717603u, 0u, 15236124201534252096ull, 2910528749u, 0u, 3685456355522430532ull, 1572380107u, 0u, 3550538229742121898ull, 36976454u, 0u, 8260014315906753014ull, 473752600u, 0u, 168487436365059220ull, 3346224102u, 0u, 4431470284845953282ull, 2704651634u, 0u, 6785257937622181032ull, 1847725912u, 0u, // 55 17245325468260454234ull, 1708485863u, 0u, 10138999105174128344ull, 4285738742u, 0u, 12724309592364047112ull, 3725587055u, 0u, 7898643048177438516ull, 151490684u, 0u, 11768629668647664072ull, 3454345700u, 0u, 16082387183617459336ull, 4260891844u, 0u, 2329106116155243746ull, 1030964258u, 0u, 1501470001532386694ull, 886962331u, 0u, 4156061136342347944ull, 1256915787u, 0u, 1276346842971222540ull, 3639187749u, 0u, 2392804398760129070ull, 3043971011u, 0u, 3134232505903854206ull, 3253402670u, 0u, 17821836438422012678ull, 2057365082u, 0u, 10492034804915076242ull, 3938906756u, 0u, 10209690410716443796ull, 1641447009u, 0u, 5930389529976739500ull, 2379172293u, 0u, 654889837247045154ull, 1988028734u, 0u, 7875058084657549538ull, 1219685067u, 0u, 2403053907309419218ull, 4179487378u, 0u, 6755573447484205910ull, 3043479899u, 0u, 10482976424459270758ull, 1900495985u, 0u, 8474430599771747302ull, 424969640u, 0u, 17395877967232465104ull, 1974952576u, 0u, 10136214039775094170ull, 356670686u, 0u, 7798806950349100764ull, 3262963337u, 0u, 15014507884536081344ull, 709180477u, 0u, 17933300946306073578ull, 4170377637u, 0u, 4758170916635319268ull, 3118068638u, 0u, 2788334335841802414ull, 4142386838u, 0u, 5212116515533117826ull, 3977103252u, 0u, 12873949866068124830ull, 2835359781u, 0u, 17648562562324436636ull, 1587487511u, 0u, // 56 11231068057135771138ull, 3321287114u, 0u, 16449144501539445784ull, 2396566215u, 0u, 16280037404219604542ull, 2435164335u, 0u, 10658046471722122570ull, 3568577379u, 0u, 10967432250578016186ull, 3347639040u, 0u, 6210654597384564556ull, 852754525u, 0u, 13634079389091432470ull, 3341351365u, 0u, 12085954918847782998ull, 2558765332u, 0u, 12623383515922074260ull, 1953061708u, 0u, 10883206886164721892ull, 1265504548u, 0u, 7202907406785969668ull, 2228755039u, 0u, 13302707024516662816ull, 750356789u, 0u, 2957747755460630100ull, 229940152u, 0u, 7822271371718587904ull, 461782584u, 0u, 13231728414311710904ull, 3318262504u, 0u, 4844219377375360986ull, 2937783142u, 0u, 5644807729512766944ull, 2145897341u, 0u, 7464285457996730486ull, 1236433461u, 0u, 8655682434127179436ull, 1009085730u, 0u, 2109885729142244612ull, 798239437u, 0u, 14182024739892392668ull, 76029770u, 0u, 6963694985083554054ull, 3339292403u, 0u, 16022458810116281550ull, 1986853567u, 0u, 3411789459659624584ull, 61333396u, 0u, 12688200327639244362ull, 3017247533u, 0u, 16392356224387856650ull, 3512607709u, 0u, 6483626857740378056ull, 1608511979u, 0u, 16631431989522654674ull, 100502077u, 0u, 16624920273760752534ull, 876798486u, 0u, 6122037842958409860ull, 3724651751u, 0u, 11887681706727885410ull, 3346644525u, 0u, 13562885093549671494ull, 1061605977u, 0u, // 57 14758423903044415350ull, 559045689u, 0u, 15235704893853150714ull, 3022436226u, 0u, 8507157681861038898ull, 4116858643u, 0u, 18381227285934271602ull, 1755243551u, 0u, 14025000358932617640ull, 1876131469u, 0u, 3636581392534070928ull, 4056459826u, 0u, 16745265925472493244ull, 1897506625u, 0u, 10735259890405437228ull, 3365902502u, 0u, 12570128741723749744ull, 209002046u, 0u, 6817880118068147078ull, 804441720u, 0u, 17744949523596016906ull, 878637834u, 0u, 15183595210725476878ull, 78197893u, 0u, 6408646185613237884ull, 2677381712u, 0u, 11218625014377832912ull, 2028282563u, 0u, 11759779611769785902ull, 3238220390u, 0u, 17965019790928358610ull, 3548581170u, 0u, 11642192428071450908ull, 3948135075u, 0u, 2269330017328112470ull, 3738739062u, 0u, 13813286618329113122ull, 2816614932u, 0u, 14003772890799156356ull, 2753605451u, 0u, 2732035077131683622ull, 2792403887u, 0u, 11627597009536409204ull, 329240526u, 0u, 14323569243718324048ull, 2187331515u, 0u, 3417594133918513134ull, 612615675u, 0u, 11053007278162623258ull, 2353927678u, 0u, 11305238352661559106ull, 2089548560u, 0u, 2045652782439264464ull, 1884514647u, 0u, 4106953334758831470ull, 118316923u, 0u, 12612793702962931622ull, 4126944917u, 0u, 10007526842133355328ull, 1183629575u, 0u, 18149957274119513618ull, 952318371u, 0u, 14212612525055450478ull, 1790000274u, 0u, // 58 2351613372866432132ull, 3258917607u, 0u, 545554476033272526ull, 2340993111u, 0u, 33915551252792358ull, 3247475400u, 0u, 15744935795733827288ull, 4067139897u, 0u, 6678877218376864198ull, 4059999640u, 0u, 16903959589975066266ull, 1149080644u, 0u, 12790763427809344198ull, 104775122u, 0u, 4768248108250738622ull, 1117151989u, 0u, 17872897163181007078ull, 2094939267u, 0u, 3365827684457519778ull, 1098134947u, 0u, 639883554939831452ull, 1833023761u, 0u, 12754931624469790484ull, 3658602673u, 0u, 8799225796760556304ull, 1760092339u, 0u, 14303296962596169938ull, 3435375304u, 0u, 9532873424280329418ull, 3628040106u, 0u, 17772878823787321386ull, 2796784434u, 0u, 11259676695554535126ull, 3763629365u, 0u, 13244289317475610758ull, 1827024228u, 0u, 11393860277939912100ull, 201335673u, 0u, 16179164477992486460ull, 3117238363u, 0u, 2556516525571132222ull, 3289557661u, 0u, 7983169072615135984ull, 1980457088u, 0u, 2102910341700149556ull, 1194320891u, 0u, 6837090525886666448ull, 3625547874u, 0u, 5040313497241398232ull, 869120868u, 0u, 13145518759838617498ull, 500024337u, 0u, 4276361418517265268ull, 8527292u, 0u, 9206139022361636904ull, 2449715313u, 0u, 1515680529992754298ull, 4289237661u, 0u, 13372120088090195880ull, 1216662282u, 0u, 2581004103541230956ull, 2394608880u, 0u, 12580473766877031044ull, 1378446688u, 0u, // 59 5380755143285970002ull, 896121709u, 0u, 8218749919893096822ull, 706071103u, 0u, 16133740703412631762ull, 3730186370u, 0u, 5040516570931992216ull, 4199724622u, 0u, 9573735755748060456ull, 2396448817u, 0u, 1510154071194528018ull, 3511336974u, 0u, 1156894572769825126ull, 1211342122u, 0u, 15926166175014095516ull, 894700832u, 0u, 9412065885272456624ull, 518956235u, 0u, 12805428403014483772ull, 1191289118u, 0u, 12415896077753207504ull, 1928979847u, 0u, 14467202919808091018ull, 730616941u, 0u, 11916990479122417964ull, 1675833886u, 0u, 16591540516665083144ull, 1208333004u, 0u, 11771761302778773284ull, 1224462519u, 0u, 11108405374593391386ull, 865992154u, 0u, 2624510587655615114ull, 2203609080u, 0u, 12111823560589903980ull, 3630019431u, 0u, 6801039657214806848ull, 2325781903u, 0u, 14311114433732763288ull, 2914424236u, 0u, 12618641298862950440ull, 1875060794u, 0u, 3993210037353737176ull, 1888428721u, 0u, 15717683733593726294ull, 2176368184u, 0u, 8610847638697798672ull, 326689121u, 0u, 14822341343403999340ull, 3420047780u, 0u, 12487234499650499180ull, 126781637u, 0u, 5455195186950126748ull, 3743044281u, 0u, 11208623924747981388ull, 1381349499u, 0u, 10867021337253278286ull, 1974667363u, 0u, 5563215225325087386ull, 4197404490u, 0u, 11545345214814612712ull, 1053207852u, 0u, 6866018813256968190ull, 2596492800u, 0u, // 60 15792010337835212670ull, 390199585u, 0u, 14681649682987638178ull, 176147878u, 0u, 1252103058258826816ull, 2209143462u, 0u, 11503679361519699390ull, 972500525u, 0u, 11706574767983205548ull, 1664122539u, 0u, 12992793695081031998ull, 537544255u, 0u, 8478400458657159042ull, 1516070625u, 0u, 10828424465406934602ull, 3858087594u, 0u, 5176550822010640368ull, 4277323776u, 0u, 8182479561265919138ull, 2003270474u, 0u, 15162390236073061604ull, 4054299899u, 0u, 14618100838460093986ull, 442554540u, 0u, 3606544643185393774ull, 2523616244u, 0u, 9876568215958813416ull, 1748192903u, 0u, 14548553733169424506ull, 167820845u, 0u, 17900424188602247232ull, 1240389828u, 0u, 13536147296809374622ull, 1072375507u, 0u, 8363067275869961400ull, 2699960785u, 0u, 12083729121811056466ull, 1003636347u, 0u, 1197351476885746396ull, 3122555193u, 0u, 2291476941026807458ull, 1343051055u, 0u, 15474084071354714384ull, 2148340016u, 0u, 15015574935510510872ull, 743478345u, 0u, 11804629675954105342ull, 2029667101u, 0u, 14383765008428081058ull, 3431619598u, 0u, 3399716915372176214ull, 1416340099u, 0u, 14538307109740082214ull, 1809586187u, 0u, 5417074574530205776ull, 3266079874u, 0u, 10463212524837548636ull, 510740171u, 0u, 17718860699569616080ull, 938076525u, 0u, 1587115566960667334ull, 3038841983u, 0u, 6571678656852714210ull, 1494067974u, 0u, // 61 900598032613544644ull, 904046550u, 0u, 4081377670018224982ull, 2196214428u, 0u, 10785754534398303832ull, 140452730u, 0u, 14568564839414732310ull, 2065607172u, 0u, 11349982631494158630ull, 2034291736u, 0u, 1207749082685459766ull, 3323891621u, 0u, 17523755696165385348ull, 2142590637u, 0u, 12918625931719416492ull, 2237866467u, 0u, 12195606313105722142ull, 1558911702u, 0u, 7939176374926796166ull, 3833434354u, 0u, 10479610628527013318ull, 3860195694u, 0u, 13820363579758879258ull, 474144059u, 0u, 7524443084704045692ull, 981393721u, 0u, 9627282265226594080ull, 3327507721u, 0u, 732073116060643736ull, 550182046u, 0u, 1119473299598547330ull, 302892361u, 0u, 14082849734820869280ull, 3439053921u, 0u, 11392489621573931388ull, 825321118u, 0u, 156020985231784998ull, 3691578598u, 0u, 6855118154121394178ull, 3755967658u, 0u, 2243126044886145000ull, 963272550u, 0u, 11782038418544895178ull, 4245573490u, 0u, 997232719303637504ull, 1716769153u, 0u, 1297907083976202180ull, 1076028361u, 0u, 5544240797876582662ull, 3459632648u, 0u, 13294274772306120906ull, 4062839828u, 0u, 8183374958017997866ull, 874156011u, 0u, 15814060191770065550ull, 2910752632u, 0u, 17629907599108628440ull, 3319105766u, 0u, 7587817442753612910ull, 2596989842u, 0u, 17265294758171819630ull, 1207548427u, 0u, 11626126885244476324ull, 4288344793u, 0u, // 62 162138662940201618ull, 3342126758u, 0u, 3375696654950594282ull, 2363733887u, 0u, 3335191529155775544ull, 3728155912u, 0u, 10845090029549761396ull, 1984614578u, 0u, 2265733224851806366ull, 2501003724u, 0u, 15986684949983056660ull, 3341199064u, 0u, 8269697421440028372ull, 4125820261u, 0u, 11975539790564571956ull, 1720678558u, 0u, 5110795179268202236ull, 4120167830u, 0u, 15683695951229971956ull, 116126823u, 0u, 1446104344923397606ull, 3794302960u, 0u, 10231529532563343724ull, 2997767134u, 0u, 378249796538180848ull, 2158791351u, 0u, 1360271137916194112ull, 3677116279u, 0u, 705798013089059344ull, 2557701581u, 0u, 13953848825311211442ull, 2005531834u, 0u, 3883957232078526688ull, 869755336u, 0u, 3274031559638086964ull, 1314849786u, 0u, 13979457701922133516ull, 3681803079u, 0u, 2271703978147888852ull, 150128083u, 0u, 1847426183286176884ull, 195653046u, 0u, 2155361614393891506ull, 667776864u, 0u, 7286387337334197720ull, 2939582075u, 0u, 64031402466070148ull, 1092306699u, 0u, 9422356278716816750ull, 1466484060u, 0u, 14648311698010231828ull, 399672055u, 0u, 10004227510757914188ull, 3944992937u, 0u, 13544091364944716694ull, 1094396865u, 0u, 7987511443205771600ull, 3291356753u, 0u, 6124633461474066508ull, 1767121502u, 0u, 9251904455973229234ull, 475367629u, 0u, 14061782492899205392ull, 1842301217u, 0u, // 63 7057839891249420730ull, 236079662u, 0u, 15962260753620259810ull, 3727701859u, 0u, 11315412001869019236ull, 2658976430u, 0u, 18273227217132809668ull, 1038975136u, 0u, 15842597280528822310ull, 721025968u, 0u, 2202968999042926442ull, 4137091957u, 0u, 11022383045943806242ull, 705800118u, 0u, 13820859770476670136ull, 4130881452u, 0u, 15826667728690401344ull, 1317142572u, 0u, 9465391219225134816ull, 1723074495u, 0u, 10963396248526676778ull, 1719515029u, 0u, 11076998949577373126ull, 2090924513u, 0u, 4353150936588036520ull, 2390279756u, 0u, 7080708009529899526ull, 2466665773u, 0u, 7075717390044608050ull, 1696231294u, 0u, 3963276213256672048ull, 1905360459u, 0u, 2278571654235228840ull, 3766132068u, 0u, 10634064674185581818ull, 1687909725u, 0u, 10265999377185310746ull, 379015941u, 0u, 9423477494252337222ull, 242729567u, 0u, 14567951335339160714ull, 2693906655u, 0u, 2671494187050819236ull, 3365178539u, 0u, 414426065362087848ull, 1823464135u, 0u, 6794327168967239366ull, 827284249u, 0u, 13357869214786457876ull, 3687829623u, 0u, 15416150903859046478ull, 4163014933u, 0u, 13059671935542313014ull, 3339020646u, 0u, 2618984869486369258ull, 4108491808u, 0u, 17748072998909916168ull, 2823514394u, 0u, 4151060110501554542ull, 2077423176u, 0u, 1588122049879120486ull, 1049126157u, 0u, 15251968894787218754ull, 2445235844u, 0u, // 64 5631436048714425848ull, 1722257791u, 0u, 6481825033166395546ull, 773125759u, 0u, 8137349518820431330ull, 1609844534u, 0u, 13238019759761167414ull, 2217659325u, 0u, 4715214702897483526ull, 2269655019u, 0u, 12386693249275947014ull, 620899885u, 0u, 8027028949196983516ull, 2606858046u, 0u, 5114578247533026730ull, 3923680581u, 0u, 8715569880796321666ull, 736622278u, 0u, 9157880710673907304ull, 217827604u, 0u, 6129369563994579268ull, 1824218674u, 0u, 11883569881256171856ull, 2509266416u, 0u, 2130962727274392934ull, 1863248941u, 0u, 13200286475976138958ull, 3750618346u, 0u, 17238937532841097436ull, 47573605u, 0u, 7064101022752972684ull, 2893840777u, 0u, 8491609225622520004ull, 1037015591u, 0u, 7628369016647621184ull, 1474295189u, 0u, 2008481615342162044ull, 2843901309u, 0u, 11047813055342798276ull, 997558478u, 0u, 8901584207912338840ull, 3728602799u, 0u, 6694316485037813548ull, 631117066u, 0u, 6226559632756809788ull, 2948829790u, 0u, 9000355528483394888ull, 3637634564u, 0u, 8799840555577917610ull, 2975540821u, 0u, 9010728339949969186ull, 2274417164u, 0u, 1276809141156936644ull, 2968538543u, 0u, 2887366668300876956ull, 2424258714u, 0u, 2064085126143924492ull, 2441848602u, 0u, 740523155507351066ull, 2369969948u, 0u, 4233231696523368848ull, 2334289953u, 0u, 1599436899447592332ull, 1145759566u, 0u, // 65 293907851474078234ull, 1449506337u, 0u, 7037893313186945448ull, 1070527137u, 0u, 1796571960428986340ull, 3225170747u, 0u, 3273658610715947736ull, 587267725u, 0u, 12606277749813050068ull, 319154146u, 0u, 2287219277176366340ull, 3345218932u, 0u, 11842753773569782424ull, 2880420844u, 0u, 4105163843816945746ull, 2654577637u, 0u, 10604459635544653064ull, 3742241480u, 0u, 4099633956279597820ull, 4143871710u, 0u, 12032237553180763418ull, 3704367406u, 0u, 13069564994444147790ull, 1951313515u, 0u, 9437693105708438096ull, 2165128374u, 0u, 9729765797669868052ull, 3129672135u, 0u, 15361804035361376530ull, 889957126u, 0u, 16488940412648714874ull, 1715914665u, 0u, 7084473161727034800ull, 2564109025u, 0u, 6744805170483949552ull, 2777746506u, 0u, 9957410978923251456ull, 2639410696u, 0u, 9208614207871312778ull, 864464024u, 0u, 11498923541494107494ull, 502966522u, 0u, 3027989148233542630ull, 1336557831u, 0u, 3567021380347425266ull, 25436983u, 0u, 12164566434084146654ull, 4008587511u, 0u, 15845503739930560706ull, 1569663395u, 0u, 18263308155153486744ull, 991529227u, 0u, 17956466239287533866ull, 2107887571u, 0u, 491844422519503750ull, 3023244355u, 0u, 15694350546348450898ull, 3415005784u, 0u, 1048686268552200114ull, 421252235u, 0u, 16579305359203617484ull, 2487886154u, 0u, 13626486696653508400ull, 4003575713u, 0u, // 66 6177260692328161376ull, 2347093442u, 0u, 8582157319006196302ull, 617309917u, 0u, 11678002344290426578ull, 2121174377u, 0u, 8091334210279201922ull, 1692064054u, 0u, 14107198389203548202ull, 1915866267u, 0u, 18405421837171171936ull, 2294598183u, 0u, 5252820582451347722ull, 2163198988u, 0u, 15798770506014452644ull, 159263746u, 0u, 2680413937210315834ull, 4087821048u, 0u, 12224228895495878904ull, 342499824u, 0u, 15415982860865924686ull, 3398430314u, 0u, 16473872213141762622ull, 4185732617u, 0u, 17319310316222793438ull, 3715240248u, 0u, 16485444329529429414ull, 2575088818u, 0u, 11737417553694078992ull, 3967232925u, 0u, 15811522773121584778ull, 49644660u, 0u, 15866076396485952462ull, 140587355u, 0u, 13448652555588694820ull, 3485990214u, 0u, 5455326516274850124ull, 735353683u, 0u, 4893472852452510280ull, 1221855928u, 0u, 1405195767512439802ull, 1849062037u, 0u, 18155987804707090094ull, 4074340515u, 0u, 14964303780608253486ull, 713797772u, 0u, 7114732015704610104ull, 2961225352u, 0u, 3283412634626493570ull, 976243316u, 0u, 16403265095551961898ull, 95514789u, 0u, 648661768696515746ull, 4011545345u, 0u, 10350594075649269488ull, 2241207611u, 0u, 1726932788523041396ull, 4262812341u, 0u, 11266514891868011198ull, 1865352396u, 0u, 11545972090207883736ull, 2247197302u, 0u, 7143576915258542164ull, 3117787605u, 0u, // 67 9160753873695717862ull, 3896140267u, 0u, 13277640215213746786ull, 3917258214u, 0u, 9841153856370812112ull, 4160453132u, 0u, 14420786867623643694ull, 3591074611u, 0u, 9446907792600540270ull, 2489118323u, 0u, 9007921462732599576ull, 2745989908u, 0u, 8698364561076344028ull, 1723756343u, 0u, 14900279265297104292ull, 3629441709u, 0u, 16979968098407413632ull, 3899641344u, 0u, 9321618178030666574ull, 1861404430u, 0u, 10895628838947094276ull, 3940239555u, 0u, 18045970583821533112ull, 2961516974u, 0u, 7459776763741899150ull, 3849168975u, 0u, 13648718507551861686ull, 1439894593u, 0u, 9632839375135434394ull, 3699607547u, 0u, 5423772757247606788ull, 1401481605u, 0u, 8431541506651286742ull, 1059537133u, 0u, 12693020709898029080ull, 2281996066u, 0u, 11149517074012640654ull, 3069947226u, 0u, 12568039881286398638ull, 3622111382u, 0u, 13092515951506622466ull, 1482529876u, 0u, 10748314390168530272ull, 3444186899u, 0u, 1643338424132708662ull, 689527499u, 0u, 8056413785403697988ull, 1773868844u, 0u, 16138314911521948748ull, 3948611354u, 0u, 5502038682237530024ull, 3166763311u, 0u, 14766142570252135770ull, 1339265976u, 0u, 13853933042563108052ull, 1595318478u, 0u, 13894528121925978512ull, 3375977459u, 0u, 2396291964831729670ull, 1364687067u, 0u, 3917208242435765516ull, 2156515944u, 0u, 4495887088967251324ull, 1936580190u, 0u, // 68 3651456075134897418ull, 2460048867u, 0u, 1975593183798302286ull, 1049130294u, 0u, 15269162760315032242ull, 1760895674u, 0u, 1801481954248595854ull, 1176682991u, 0u, 2049662768885486056ull, 3239112900u, 0u, 3023104680422818358ull, 3228381512u, 0u, 15469287865058514462ull, 1529377871u, 0u, 4708537067004768464ull, 1538299549u, 0u, 956639522293149044ull, 2768739303u, 0u, 13274149609031852150ull, 1940766035u, 0u, 16846326685983389118ull, 1719392005u, 0u, 2861157297020441430ull, 272107540u, 0u, 15528427720597575788ull, 3701271307u, 0u, 639354401102630888ull, 2169385401u, 0u, 1103960233510993026ull, 1242450748u, 0u, 16404969907416658924ull, 2232499362u, 0u, 500077687999235946ull, 459694103u, 0u, 13805238844403563730ull, 1896935454u, 0u, 4025956886729660048ull, 3246942097u, 0u, 11923971216987972574ull, 3620256293u, 0u, 16154993540007470900ull, 3657511435u, 0u, 7498679565200537530ull, 2246163023u, 0u, 16928807379316704598ull, 4183061306u, 0u, 1607733513599096982ull, 3380779979u, 0u, 1835450603686099974ull, 4235544143u, 0u, 18327521969475429808ull, 3413038852u, 0u, 16392477060189495944ull, 2380421834u, 0u, 7226067077882482590ull, 1068011723u, 0u, 14686549804826319242ull, 847294313u, 0u, 16677946529111466700ull, 3673056168u, 0u, 7636651028846550204ull, 4215767269u, 0u, 11354336281769822318ull, 2522746419u, 0u, // 69 4095960389202116426ull, 2479339406u, 0u, 16127458101393172302ull, 770419856u, 0u, 17358535808606114842ull, 3514321876u, 0u, 3581140944579470108ull, 1239320521u, 0u, 16150769927750619694ull, 1995053202u, 0u, 15995639684406863358ull, 1779091638u, 0u, 8832209414798008854ull, 293863527u, 0u, 1451700053933572740ull, 3121707232u, 0u, 10952065016232071674ull, 1041338328u, 0u, 2174648180104368116ull, 1696572845u, 0u, 6165284386586782436ull, 4200111028u, 0u, 86217138752224008ull, 597177716u, 0u, 16690598755468298238ull, 1656077240u, 0u, 2907098189573309344ull, 417893167u, 0u, 17747246848085892464ull, 2533731827u, 0u, 16168641531526515494ull, 303329172u, 0u, 14009967565870681134ull, 1392781962u, 0u, 686559399329777512ull, 1970118786u, 0u, 2662681914647542350ull, 1864696070u, 0u, 17481985067211388962ull, 785839534u, 0u, 34625070830419030ull, 3425415135u, 0u, 15078952966410821140ull, 1844832110u, 0u, 17276193231569675174ull, 748463588u, 0u, 6514247872365641012ull, 237423985u, 0u, 13622678965325461528ull, 4066292742u, 0u, 3707455187522170046ull, 1917347187u, 0u, 17181954834933635152ull, 1945022125u, 0u, 1973906365578926500ull, 170991403u, 0u, 3809944538266422882ull, 3844383807u, 0u, 6170944453131538794ull, 1750073578u, 0u, 14680616781897021884ull, 2876518534u, 0u, 10788498211685809858ull, 3970724485u, 0u, // 70 5950755120796339768ull, 170151251u, 0u, 9793396980406638802ull, 3964823094u, 0u, 13431170978794537664ull, 123476577u, 0u, 11543271805919806758ull, 603042535u, 0u, 2377167322282865288ull, 3790240896u, 0u, 11412781194399842340ull, 3467219701u, 0u, 5564934476492238886ull, 3475336554u, 0u, 4059616328971225960ull, 3802047418u, 0u, 11418450866181966942ull, 2857854181u, 0u, 16656539639202144062ull, 2879671944u, 0u, 16073909273359862442ull, 2891915545u, 0u, 9677469475165511216ull, 238054390u, 0u, 16252907014491127454ull, 3438021630u, 0u, 16612502235595116798ull, 875117469u, 0u, 15989097435263635410ull, 3074531905u, 0u, 1438880709723991010ull, 913384866u, 0u, 1405932736400703296ull, 783856799u, 0u, 11330202147985472772ull, 912264496u, 0u, 15791368464038245696ull, 142971804u, 0u, 1587494689128034414ull, 1020293732u, 0u, 7077233052361478704ull, 170012407u, 0u, 14759520845383109044ull, 3102550070u, 0u, 17988404228419856270ull, 2656794148u, 0u, 14188726367183400692ull, 74653444u, 0u, 2083710815057477294ull, 2373177306u, 0u, 12939780985304749750ull, 901674290u, 0u, 15069757803076594966ull, 2342183422u, 0u, 10550333043227999042ull, 149887832u, 0u, 4464422790797132904ull, 95831549u, 0u, 234234406633067156ull, 1712490249u, 0u, 5146588706688628506ull, 766398597u, 0u, 5490382984833148170ull, 1316329189u, 0u, // 71 6558328047154266266ull, 3507096713u, 0u, 1118405926946418ull, 1755016244u, 0u, 3826771772278124646ull, 423514907u, 0u, 3239864496610119568ull, 1854117930u, 0u, 13715003826219049948ull, 1439892134u, 0u, 7697218915896045590ull, 4248897559u, 0u, 14653055466193685446ull, 3786347618u, 0u, 1751003993784594606ull, 72167409u, 0u, 9040258359105293348ull, 168416461u, 0u, 946296112912696762ull, 4173106202u, 0u, 1574218884769647622ull, 4253344919u, 0u, 12095815962666910794ull, 4185207334u, 0u, 3697049713429550848ull, 3625782924u, 0u, 15987055330203633832ull, 2884546828u, 0u, 12769949550891175436ull, 1944444971u, 0u, 16352004097545570148ull, 735056293u, 0u, 832113875308726256ull, 3560243228u, 0u, 16746069767638172990ull, 2821330739u, 0u, 3217859186188622482ull, 3934134126u, 0u, 13122101622954638720ull, 655563416u, 0u, 15033794285272195514ull, 48833948u, 0u, 4320163697942675830ull, 3927524839u, 0u, 3980620610089100180ull, 4169676780u, 0u, 9785727534402089748ull, 3747239645u, 0u, 11917724611867588628ull, 1221949405u, 0u, 6981361445740438940ull, 1700845155u, 0u, 5262459019990388940ull, 1151985028u, 0u, 5825435418231614626ull, 3856544947u, 0u, 11005165089232174554ull, 1480454264u, 0u, 3476309718899278746ull, 165351235u, 0u, 6800778757538600054ull, 3312666688u, 0u, 17264448179632765634ull, 146667897u, 0u, // 72 14972498245584082292ull, 1745241268u, 0u, 10488452361074258318ull, 4104560422u, 0u, 14194804341008042114ull, 3397022185u, 0u, 909364345183850054ull, 2356307462u, 0u, 492747457387043836ull, 2002593273u, 0u, 16962214689191212304ull, 2039927790u, 0u, 801139423826129342ull, 1625656006u, 0u, 8562174927732886644ull, 1698223163u, 0u, 3038393004111696586ull, 233421200u, 0u, 6848107819741455800ull, 1172815587u, 0u, 7145318177078972036ull, 2645437393u, 0u, 15517904145457406308ull, 1573391670u, 0u, 9663011854588417592ull, 1466009892u, 0u, 9171593545190943712ull, 1800445677u, 0u, 13107256742634540630ull, 3176067825u, 0u, 11585938397696424666ull, 1807689297u, 0u, 5487894830860677268ull, 942598788u, 0u, 14535281092019089062ull, 453708846u, 0u, 7544778432441274820ull, 2874997181u, 0u, 7003079583659704562ull, 292762654u, 0u, 233986120776333072ull, 3946738837u, 0u, 15280167804595511694ull, 1548101303u, 0u, 15287211973339771592ull, 74161913u, 0u, 1347137394095655718ull, 3485724544u, 0u, 2254170415289915058ull, 3581548969u, 0u, 2716060140539786894ull, 386451387u, 0u, 13825376798779760484ull, 2679710933u, 0u, 11418384284457169402ull, 1941338441u, 0u, 18342474751087042100ull, 837165872u, 0u, 17457970824392151784ull, 2118174967u, 0u, 5459237203170205466ull, 3547044255u, 0u, 5074111644795458590ull, 3149409492u, 0u, // 73 9283928844073119464ull, 4262728411u, 0u, 14794445909572290044ull, 3218169738u, 0u, 7716215285861751702ull, 1968436399u, 0u, 11883494247769502916ull, 2461278999u, 0u, 10136059496454160018ull, 1763042096u, 0u, 6500371738081531882ull, 3598334821u, 0u, 16814620109271009154ull, 2918851751u, 0u, 5601168060347988672ull, 1917974059u, 0u, 6766082993293195882ull, 3509733051u, 0u, 13150388099107072922ull, 1502482396u, 0u, 5791342428914814652ull, 3919491037u, 0u, 15835418810390927194ull, 1588842938u, 0u, 8951078406742435106ull, 1390110898u, 0u, 13856732993074051882ull, 720231486u, 0u, 2495271033284686184ull, 1903611692u, 0u, 1116160143237664616ull, 1049646537u, 0u, 11304876181995856094ull, 2137733692u, 0u, 12716463377322987154ull, 1210387254u, 0u, 750693023245411608ull, 2521673946u, 0u, 14512973860284867172ull, 3497012194u, 0u, 9670768551055654588ull, 2958185358u, 0u, 3762658772782496214ull, 2010829828u, 0u, 8575386111105543932ull, 2961159888u, 0u, 6271153529200281612ull, 2544254603u, 0u, 13183944000033613600ull, 3354057785u, 0u, 431225679306647800ull, 1486427929u, 0u, 17309088545267624744ull, 3213120291u, 0u, 7719128599641975296ull, 261401182u, 0u, 14759879759051918862ull, 3885721910u, 0u, 17973367313911851516ull, 619884062u, 0u, 16859507293025037588ull, 312279037u, 0u, 1763538177478240006ull, 1891112851u, 0u, // 74 10325180278491918574ull, 2737061675u, 0u, 232858442815129284ull, 4193231390u, 0u, 5086922622255170910ull, 1641436404u, 0u, 9704266834157624160ull, 2311967400u, 0u, 16208593271514927786ull, 2092665604u, 0u, 4809246753777571972ull, 4041831328u, 0u, 12855495246185879452ull, 1848149543u, 0u, 11417745231389783762ull, 1623714105u, 0u, 7950555781523554164ull, 401841129u, 0u, 14291498296271532934ull, 2714553246u, 0u, 16964625331771698218ull, 1641513641u, 0u, 7307268890252759716ull, 2475093803u, 0u, 13359986128699016682ull, 2520068600u, 0u, 7632069459589766288ull, 1344019076u, 0u, 18098378268849179060ull, 95994233u, 0u, 17673121901936409326ull, 1279712002u, 0u, 5268234627104304182ull, 255739737u, 0u, 18022896715160091084ull, 3417568933u, 0u, 16325916509176232130ull, 2205859829u, 0u, 7936132179079798810ull, 265406890u, 0u, 9672340727369181090ull, 846282974u, 0u, 6962379709833358442ull, 100700563u, 0u, 9813989966794196736ull, 1826468926u, 0u, 10563519583441313988ull, 907702418u, 0u, 6432685273500878620ull, 610456238u, 0u, 6983897353082399902ull, 3216291400u, 0u, 12298241830733401416ull, 2664021437u, 0u, 8117459262144997596ull, 3500076632u, 0u, 17577601869420411442ull, 1506424153u, 0u, 15615511901777574090ull, 468470631u, 0u, 18357674751777423382ull, 485574625u, 0u, 10379544244194866956ull, 960165934u, 0u, // 75 2978759685318182882ull, 898632892u, 0u, 12509208826196360830ull, 361498440u, 0u, 17475743896757129396ull, 778495826u, 0u, 1146380962204695776ull, 4036310060u, 0u, 390500437871177392ull, 2157387580u, 0u, 9743443981622115222ull, 270684119u, 0u, 12355346384123695388ull, 1554524083u, 0u, 828650905756861658ull, 3939978516u, 0u, 10807702883993292914ull, 4263623544u, 0u, 8113739349669127734ull, 400845643u, 0u, 6400967429453488226ull, 3578076774u, 0u, 14598836146062408016ull, 2791470392u, 0u, 1352887982630849794ull, 779134959u, 0u, 12733617819594930318ull, 3983160974u, 0u, 15527285776040570002ull, 399216985u, 0u, 11780363491432439472ull, 1685028255u, 0u, 16359787335871868ull, 2941086249u, 0u, 13812126487153923850ull, 2313027961u, 0u, 12102468992219666312ull, 704178408u, 0u, 4744994427347555654ull, 3843564850u, 0u, 17178413001848451398ull, 4253228815u, 0u, 10869617876938358358ull, 1827799001u, 0u, 10239624482976991828ull, 2334387832u, 0u, 8563741039814274420ull, 671878313u, 0u, 12996086349133734122ull, 1928120080u, 0u, 15598734181287150844ull, 922634486u, 0u, 13038049130020156060ull, 960840552u, 0u, 14411684906471661782ull, 493214832u, 0u, 17266311551783234962ull, 1717873471u, 0u, 14898465457926690090ull, 497864426u, 0u, 16032699129175883282ull, 3263854355u, 0u, 11542819439079214984ull, 2733609088u, 0u, // 76 16219439966560261538ull, 466295512u, 0u, 9095483364586281566ull, 1612674761u, 0u, 14077618129616149540ull, 1172349962u, 0u, 7519885284686575098ull, 2611030293u, 0u, 4811868059522936226ull, 1705132678u, 0u, 9156092762632306418ull, 4293661557u, 0u, 5914458989187553842ull, 1065908638u, 0u, 11255652313167876766ull, 2811711283u, 0u, 3622088586537350034ull, 4194438008u, 0u, 14456256219938843762ull, 412942420u, 0u, 3278542824762197890ull, 149350720u, 0u, 5124208741658338370ull, 3136133419u, 0u, 7272939679272129954ull, 391542710u, 0u, 8297794022897813130ull, 2882615124u, 0u, 111951947427499748ull, 1881375230u, 0u, 15845226847852598416ull, 4281364939u, 0u, 45345814833618584ull, 3297516944u, 0u, 5482054389213548164ull, 3047434008u, 0u, 13986465681040871910ull, 2661159003u, 0u, 6553018536820163124ull, 197783630u, 0u, 10838141773502534082ull, 1118807583u, 0u, 15473536465326204192ull, 2781688365u, 0u, 16938498357365554250ull, 1385491629u, 0u, 12446612918385293382ull, 3323776756u, 0u, 4337571578088199422ull, 2022914978u, 0u, 9599273704592598886ull, 2621969569u, 0u, 8600517324484978580ull, 4183375628u, 0u, 5222858768660786818ull, 3691462544u, 0u, 5685098239016800932ull, 2218760459u, 0u, 15516443814100561946ull, 3942383147u, 0u, 18008558847000337550ull, 835282296u, 0u, 17297970801247684716ull, 1366822507u, 0u, // 77 13272887750779424750ull, 2283217307u, 0u, 677111034480055742ull, 2112505714u, 0u, 2773413067333201430ull, 2518768222u, 0u, 12180229068883509102ull, 791880571u, 0u, 15376226088342309130ull, 2599338483u, 0u, 11207433970597098762ull, 3974276056u, 0u, 13024728747539131810ull, 4116674836u, 0u, 4268145106350858200ull, 2759083507u, 0u, 20010663463583558ull, 1805373483u, 0u, 12510732445941237514ull, 3266711223u, 0u, 17137527436209671634ull, 4162794804u, 0u, 14259242479713777960ull, 1079628994u, 0u, 5597439993416006638ull, 2255544156u, 0u, 1343111491047690256ull, 3211412541u, 0u, 12527804298094985444ull, 378367575u, 0u, 16824745143814464830ull, 1080513315u, 0u, 3792416392177500750ull, 2889300393u, 0u, 2564578844806831908ull, 1357189760u, 0u, 11573369339073137740ull, 3943364372u, 0u, 14728977266581866342ull, 847244879u, 0u, 10250219746693143212ull, 2308992056u, 0u, 3089728778078473970ull, 384878256u, 0u, 6397948476450228274ull, 780511435u, 0u, 6433412433209688912ull, 3628031108u, 0u, 8710831494649135416ull, 2605528729u, 0u, 7821696797056293032ull, 1134696877u, 0u, 468625682449843562ull, 1089647229u, 0u, 1015065107487814686ull, 3270204349u, 0u, 1481839581206835492ull, 4076422042u, 0u, 135294450755538684ull, 4033337743u, 0u, 2963492217156611906ull, 483865214u, 0u, 1457683287513335350ull, 1128573682u, 0u, // 78 7248209563676014384ull, 1750549164u, 0u, 9811337978210930352ull, 4185439632u, 0u, 869644458912166408ull, 2818449635u, 0u, 18021672195435847150ull, 2801206794u, 0u, 13700430135113926476ull, 817950353u, 0u, 6594134414330249298ull, 2417965537u, 0u, 7047261968510408946ull, 3737006207u, 0u, 14928473997105329738ull, 1807397848u, 0u, 16675167742107624600ull, 2697001932u, 0u, 15814660742535647502ull, 2886854721u, 0u, 11373892163615215002ull, 1963858540u, 0u, 9873168195741415892ull, 1472496606u, 0u, 13518627524984288592ull, 2827880587u, 0u, 5700022581251940868ull, 796897868u, 0u, 15462013827769347642ull, 1039378156u, 0u, 12895974985485090450ull, 660891136u, 0u, 10603784889764193172ull, 3981317329u, 0u, 18227847837388499654ull, 579443791u, 0u, 3783115626760525878ull, 1173821963u, 0u, 11284803747989208616ull, 545844587u, 0u, 14732094288972515560ull, 2779947758u, 0u, 2133124916459169014ull, 713598770u, 0u, 13400620591730550814ull, 1690313784u, 0u, 16721440689221851106ull, 1875523571u, 0u, 8744983010157167800ull, 1230130376u, 0u, 17994500967106125820ull, 1050329024u, 0u, 15652654512209847482ull, 2091473253u, 0u, 8273518155151308928ull, 4008490898u, 0u, 14745619736728562864ull, 275108715u, 0u, 9002086646249263468ull, 567952860u, 0u, 14355067594044732860ull, 3984424664u, 0u, 3994869402295339912ull, 4062977496u, 0u, // 79 2294691042981193478ull, 4231337955u, 0u, 5722392946325023210ull, 1471259041u, 0u, 16665872327640066462ull, 1718132544u, 0u, 17256876713656484290ull, 316864060u, 0u, 14584719174473957636ull, 3024521604u, 0u, 16467425425091783302ull, 755346865u, 0u, 16365099423473459794ull, 3130271130u, 0u, 5995075213965330228ull, 735608799u, 0u, 4186842012561054432ull, 3827601125u, 0u, 4357592338886332776ull, 1916261010u, 0u, 14899949053866927892ull, 1730949660u, 0u, 18327374586367027144ull, 1526949075u, 0u, 290529537142333608ull, 4177271039u, 0u, 9434882603440544484ull, 3450415568u, 0u, 9726809718647893724ull, 3379943877u, 0u, 6336065320806434170ull, 2220964708u, 0u, 793273171225791796ull, 408212791u, 0u, 10513623483725964490ull, 1153519419u, 0u, 13024592584210098290ull, 2904076781u, 0u, 17851667436244238084ull, 4227940853u, 0u, 4306820035850361006ull, 2058076981u, 0u, 3238706636199638578ull, 2804113004u, 0u, 13491171336084708634ull, 3043507143u, 0u, 5025633158598851482ull, 3319065643u, 0u, 868277000246546508ull, 859569585u, 0u, 1061662958644414866ull, 3440869967u, 0u, 12654208895929580628ull, 3068675432u, 0u, 8072121672919949378ull, 1793173365u, 0u, 1266260585252911956ull, 794118729u, 0u, 15244744827195174834ull, 4141818954u, 0u, 7950067513222704178ull, 2544487725u, 0u, 18352621704499099208ull, 1844778645u, 0u, // 80 14643607963218810172ull, 2200759631u, 0u, 11433023538727672324ull, 223631760u, 0u, 4877516387377521022ull, 1461332358u, 0u, 4157605234522989400ull, 3536916037u, 0u, 7896615221377864302ull, 3963360739u, 0u, 9000086022537235764ull, 3858287384u, 0u, 12201802823698380088ull, 3158924494u, 0u, 6596882981364016650ull, 2480651820u, 0u, 7673238252371559986ull, 3804607702u, 0u, 13249042693780667086ull, 1123876262u, 0u, 15821189265408263664ull, 1629053702u, 0u, 688397098036776470ull, 4112447514u, 0u, 8484366595604826912ull, 3443268342u, 0u, 5911940522154064172ull, 3520178600u, 0u, 1075279069532888450ull, 1317067251u, 0u, 7469640648482198816ull, 1427855808u, 0u, 15558423935936172924ull, 2375188967u, 0u, 16272122969345141340ull, 2264277365u, 0u, 13751627485083017876ull, 1516045573u, 0u, 6216671299669323660ull, 3767837239u, 0u, 8670657541039998230ull, 1607509437u, 0u, 13008646130559979660ull, 595656176u, 0u, 11922328945328040096ull, 3497297473u, 0u, 8852050698208757368ull, 2315694666u, 0u, 17241565394214266434ull, 3321512493u, 0u, 2442772055139931806ull, 136976402u, 0u, 14442522664517593436ull, 600408227u, 0u, 9838362171671033402ull, 3608018329u, 0u, 10132038939555153972ull, 953741820u, 0u, 6422872487592168290ull, 3197179629u, 0u, 9393104274801295528ull, 1807682920u, 0u, 15549809582074088738ull, 419032610u, 0u, // 81 10794772325613711644ull, 2043933885u, 0u, 15272518176447970226ull, 3392763228u, 0u, 3140893480716340072ull, 3855620288u, 0u, 15485491542617061958ull, 4234336557u, 0u, 11796275138586209328ull, 125377002u, 0u, 17932297817412488720ull, 3484493620u, 0u, 4231517607165462832ull, 719050857u, 0u, 7125558052286745334ull, 2443441780u, 0u, 16736826847143399432ull, 3155917068u, 0u, 5570296025395256536ull, 4061641669u, 0u, 7853334499927848528ull, 2237631545u, 0u, 4355127242053802656ull, 1367336155u, 0u, 4795562640146566658ull, 2606148971u, 0u, 16290921583010326588ull, 61350316u, 0u, 10362032524920010498ull, 3417789500u, 0u, 12116433316496807318ull, 2578247153u, 0u, 9981521764087613210ull, 1741570104u, 0u, 11444388437738221056ull, 415259444u, 0u, 10419874777207955944ull, 2149611466u, 0u, 14628387863384836810ull, 2744892251u, 0u, 8445819134543721350ull, 270662589u, 0u, 2940127090676459462ull, 3731995665u, 0u, 8074228341216879264ull, 1894816903u, 0u, 11215337266692385866ull, 1275824992u, 0u, 7471382319043469872ull, 14221081u, 0u, 11027446244344190108ull, 1164090030u, 0u, 4441048902526455170ull, 3611443977u, 0u, 12175232004035089644ull, 834989211u, 0u, 8900960155452771348ull, 2341623483u, 0u, 15419472591310163306ull, 2448439476u, 0u, 17717719340925996828ull, 3964640312u, 0u, 13898260569314708710ull, 3663064392u, 0u, // 82 13032503277176112212ull, 3968119808u, 0u, 17648964602477733238ull, 2255549881u, 0u, 9507501987411662246ull, 1413617463u, 0u, 2706881236731684172ull, 342374987u, 0u, 12542469988774610932ull, 3130041156u, 0u, 2576856777751677084ull, 1402344577u, 0u, 8167205734770163582ull, 4096128346u, 0u, 9500470523192084082ull, 337556561u, 0u, 12359603558264672210ull, 3596165652u, 0u, 8470264025066985360ull, 1278209651u, 0u, 8968053268486942828ull, 3089880535u, 0u, 5491927752651655516ull, 3957502181u, 0u, 6856238413661086326ull, 85507045u, 0u, 4564759840305367778ull, 370001618u, 0u, 7131701971958308070ull, 2476174918u, 0u, 1582744522043275248ull, 4086146140u, 0u, 13679057835046288328ull, 674150920u, 0u, 2167169424751749556ull, 4225114417u, 0u, 3862578594514359320ull, 2552881773u, 0u, 6467304600689441664ull, 937645256u, 0u, 11716366617424424484ull, 2062848608u, 0u, 16664739097594652052ull, 4147367234u, 0u, 15230794804665445650ull, 4098080278u, 0u, 10613871829581137236ull, 1794159226u, 0u, 17454669392971167106ull, 2487913021u, 0u, 13244530298479883196ull, 2733916310u, 0u, 12897125420908048134ull, 3766724685u, 0u, 11984608636425255532ull, 405291776u, 0u, 14847601039661503780ull, 1897531998u, 0u, 13586052868825205304ull, 2859044078u, 0u, 3629820175302887734ull, 2849073920u, 0u, 13450977586639780300ull, 2766868230u, 0u, // 83 11335992523420531812ull, 3876929565u, 0u, 12128743183045788830ull, 2303016356u, 0u, 14497889461547219718ull, 498399313u, 0u, 77972347155118810ull, 2495395517u, 0u, 15170311125395866546ull, 3768292912u, 0u, 12601451665059144714ull, 1803044066u, 0u, 16799055877490795330ull, 2498609071u, 0u, 16023575488530395364ull, 1175862007u, 0u, 12117718998688531486ull, 5373235u, 0u, 10016515418027960154ull, 187684267u, 0u, 6513090182685713492ull, 2763821893u, 0u, 1006332514583203922ull, 2890862422u, 0u, 6211508205808614718ull, 2133075957u, 0u, 3826855993539968790ull, 2596553888u, 0u, 10121728435083424678ull, 1285023626u, 0u, 14282772913431777202ull, 1909003635u, 0u, 18101947150382496722ull, 565086014u, 0u, 15926897088513714410ull, 421039228u, 0u, 9784422334904909680ull, 2947939240u, 0u, 1396794026615719562ull, 119899695u, 0u, 14183289941876679044ull, 1612070039u, 0u, 6971292509456563718ull, 1105839221u, 0u, 14153250552198502706ull, 3352805707u, 0u, 15416612152379284146ull, 2273505535u, 0u, 9779384440942192510ull, 891485915u, 0u, 4166301851877468952ull, 704750206u, 0u, 5355621874329097164ull, 2305338429u, 0u, 11375539192159449514ull, 3445215462u, 0u, 17038865941492645526ull, 3857745929u, 0u, 1632474545929456642ull, 1568522475u, 0u, 8117694950274924298ull, 3994284201u, 0u, 5709581177654623822ull, 3679430455u, 0u, // 84 9462060888252527530ull, 501885645u, 0u, 2520736743039476420ull, 1321609451u, 0u, 14436021799503911368ull, 307462578u, 0u, 18245230741664230414ull, 53343878u, 0u, 7215957417271809086ull, 3206214413u, 0u, 6243806431642643388ull, 887193140u, 0u, 8479387163972047180ull, 2182659190u, 0u, 14414551778296790116ull, 587184604u, 0u, 18380362148012473422ull, 1514230446u, 0u, 1408810225746725672ull, 3319419706u, 0u, 17367154460194745912ull, 3707030508u, 0u, 4481453330426854552ull, 2041527608u, 0u, 13925864135806775950ull, 548845991u, 0u, 8753089739470296460ull, 1862864809u, 0u, 13782135816337162746ull, 88039448u, 0u, 9180461242135753004ull, 2092429437u, 0u, 12470718905474889226ull, 940639272u, 0u, 13057918169138263856ull, 2000438428u, 0u, 7997274267728367972ull, 3166919532u, 0u, 15277479370448506914ull, 2719437410u, 0u, 10202737043451956264ull, 3664718261u, 0u, 12869996320082131960ull, 737670196u, 0u, 3167434619942949492ull, 108121133u, 0u, 909983600591562852ull, 2549441556u, 0u, 14355196481759205914ull, 1251186557u, 0u, 14853049047273315170ull, 1243118469u, 0u, 17943156004556904526ull, 1032218387u, 0u, 8260229219953487128ull, 314689510u, 0u, 12871340851144686902ull, 1666588963u, 0u, 822629277765747322ull, 49147796u, 0u, 10881166322470579244ull, 1907857988u, 0u, 2816208367402197902ull, 2842480673u, 0u, // 85 15977631850765957818ull, 1959356511u, 0u, 7385424485855765972ull, 3112886235u, 0u, 13021143038353813688ull, 2515731502u, 0u, 12757471850292990106ull, 2313745968u, 0u, 8765016635269887296ull, 1721104862u, 0u, 8365894414860426630ull, 3293161852u, 0u, 1221759167082752820ull, 1921927529u, 0u, 10281304175565372604ull, 3497568862u, 0u, 11631255666628597108ull, 3449549336u, 0u, 8332682274596118648ull, 4118622478u, 0u, 7850428911145277540ull, 776635712u, 0u, 1591839933846164592ull, 2028484041u, 0u, 3733936435128942004ull, 3502097037u, 0u, 7833605354683640020ull, 2497336147u, 0u, 8772532298349841942ull, 1193823112u, 0u, 13497452564324583000ull, 1053456867u, 0u, 8951382898734113456ull, 1371229449u, 0u, 3662059956645126196ull, 3868917822u, 0u, 16978753012455168520ull, 1199969158u, 0u, 720663106516063180ull, 1647022416u, 0u, 5219765154230018956ull, 3488023894u, 0u, 4780872097222660124ull, 2127342712u, 0u, 6529243473860107484ull, 2579732711u, 0u, 2868587811409769650ull, 1343476267u, 0u, 9046526468267595762ull, 1892280099u, 0u, 5277824581090281700ull, 2935173344u, 0u, 14610822632135873862ull, 2324531310u, 0u, 335111494877680120ull, 3024839885u, 0u, 17519343574882604830ull, 128993695u, 0u, 10544554171124926536ull, 3535996113u, 0u, 5862154368887384440ull, 1634286598u, 0u, 2291468792817370696ull, 4103634281u, 0u, // 86 10639425584264754652ull, 3746500549u, 0u, 8619292184306953046ull, 1643751511u, 0u, 14076459754225369844ull, 818431682u, 0u, 12831524508548493150ull, 1088566671u, 0u, 5573346325292953932ull, 247018710u, 0u, 9718627671496664346ull, 3092672000u, 0u, 7574001456960447204ull, 989737486u, 0u, 2375511134337416422ull, 2321580745u, 0u, 2762025807373167576ull, 787100795u, 0u, 11143926384075508432ull, 2258828225u, 0u, 15541667894779560572ull, 566489931u, 0u, 1014323302680459790ull, 4076940946u, 0u, 16712397310125763864ull, 3255077554u, 0u, 261726382806744088ull, 2327005171u, 0u, 12276632437199797272ull, 2066363452u, 0u, 1255007030079859138ull, 2994107623u, 0u, 13969057430984859322ull, 3646606010u, 0u, 7952352608052188608ull, 398580044u, 0u, 2054313559087703322ull, 877424135u, 0u, 16473083046552348586ull, 2012578423u, 0u, 18167343506907688484ull, 1413609664u, 0u, 3210870907636613368ull, 1656730295u, 0u, 13952466661297812570ull, 1040598488u, 0u, 3577544595414567322ull, 72533498u, 0u, 15910258084146824290ull, 2700983517u, 0u, 3859271871424896522ull, 2359531254u, 0u, 7273923226755110100ull, 3865294650u, 0u, 16430816878311809340ull, 812071742u, 0u, 2840423651234286194ull, 2409012412u, 0u, 3165653931088554748ull, 979911757u, 0u, 17188159911820292660ull, 2613785731u, 0u, 10549050855209994568ull, 1752126180u, 0u, // 87 18188371607168318266ull, 379076305u, 0u, 2796058944354278282ull, 3010540011u, 0u, 16473691901037918474ull, 2814632502u, 0u, 17061003901861772766ull, 1016995121u, 0u, 4359760680640025266ull, 3441242477u, 0u, 6683774588382224104ull, 612822963u, 0u, 13326600300328702960ull, 2980383810u, 0u, 9666124929668893914ull, 2987857258u, 0u, 466503295879796626ull, 3371266264u, 0u, 8166330211029153276ull, 4294579241u, 0u, 12070445444541775620ull, 3278103082u, 0u, 7341575381945266746ull, 3895666319u, 0u, 6579620896904989598ull, 1939382334u, 0u, 4072247369318450554ull, 2016566230u, 0u, 838782589495201956ull, 3299805369u, 0u, 699203445093562438ull, 3603391982u, 0u, 5950377878764258816ull, 3279595374u, 0u, 12588289070761397736ull, 3266259433u, 0u, 18115688515722885958ull, 524550389u, 0u, 14403217402385337022ull, 2892803923u, 0u, 16668070545688709018ull, 4178238041u, 0u, 1601686082900105972ull, 4155306413u, 0u, 12995358954829266366ull, 3759933181u, 0u, 4148261917819520852ull, 3273678634u, 0u, 643254975860819422ull, 2366942875u, 0u, 6919617568071723112ull, 3612049237u, 0u, 5029067121767525842ull, 3901616100u, 0u, 16342229597934863222ull, 1163664351u, 0u, 2985909731715416390ull, 2323484831u, 0u, 552644865515120996ull, 2297759742u, 0u, 15418254661010422190ull, 3639158611u, 0u, 11527274307601376198ull, 4236380963u, 0u, // 88 4733780207155200046ull, 3377913511u, 0u, 11399815682196412320ull, 1690947279u, 0u, 9988727793251964750ull, 109094877u, 0u, 10952606170047372314ull, 574804752u, 0u, 11044248824961174878ull, 4228811376u, 0u, 7348420310468343436ull, 2413695293u, 0u, 16283846335733034298ull, 3533007271u, 0u, 6302009155144227290ull, 2354100111u, 0u, 12780900158052342000ull, 3962014620u, 0u, 7090943401949381712ull, 933141474u, 0u, 4522587583091326608ull, 1231443534u, 0u, 10197626691090130648ull, 2558895630u, 0u, 10090352062642009252ull, 1187149840u, 0u, 15795679539531240068ull, 1795189426u, 0u, 2465143343505942788ull, 4141372569u, 0u, 4586259167169073794ull, 3437752774u, 0u, 8689937569055672738ull, 3697780777u, 0u, 14150726152851581592ull, 2713705650u, 0u, 8621356738761071798ull, 2283712760u, 0u, 12349284875897559432ull, 2907520105u, 0u, 16051027856195815356ull, 116784503u, 0u, 8529803813907000262ull, 3888417200u, 0u, 12221653989150388652ull, 2805785702u, 0u, 15817035674485903586ull, 3115052802u, 0u, 11820676697839361152ull, 2091447218u, 0u, 4629154167509431666ull, 3075583823u, 0u, 870567251762904954ull, 844983835u, 0u, 6747174654021114536ull, 1595787007u, 0u, 4519967569290960350ull, 2632386595u, 0u, 13528574636827803264ull, 4101390347u, 0u, 14340154297494723674ull, 3519800210u, 0u, 2222626944316940652ull, 533043838u, 0u, // 89 18325243872118846588ull, 2646458495u, 0u, 9888465316924713414ull, 194584651u, 0u, 609716784457420026ull, 3021282501u, 0u, 1900957722996204052ull, 49017060u, 0u, 10669727811978451102ull, 1966433075u, 0u, 17791918159748551752ull, 2064261983u, 0u, 7417826427640926816ull, 783599832u, 0u, 11263206573629418566ull, 793572832u, 0u, 17044270709248520812ull, 3864233963u, 0u, 4673838502822036516ull, 3241670156u, 0u, 14877491340527928892ull, 1282103595u, 0u, 876893020251087656ull, 2380057771u, 0u, 12637934379226248578ull, 3404697443u, 0u, 26464141463381568ull, 3329653057u, 0u, 12740186778622371506ull, 2024030858u, 0u, 7199665080738835534ull, 520140849u, 0u, 6668484505671075056ull, 2164045525u, 0u, 9794404249112147090ull, 369764750u, 0u, 12022350060302613566ull, 3362667249u, 0u, 9576240908160295674ull, 3641994553u, 0u, 8020120085292007616ull, 3447046091u, 0u, 1034984997487272062ull, 3448067196u, 0u, 10200456459793486428ull, 4098876889u, 0u, 14943696690376916548ull, 2857010076u, 0u, 9879018153288444090ull, 74242715u, 0u, 12492928899096712326ull, 1313938621u, 0u, 7087342225995102166ull, 3203696849u, 0u, 4249693827854711640ull, 1292289526u, 0u, 13783442285698289712ull, 2524252707u, 0u, 14373488214443652670ull, 3991964901u, 0u, 16045169478827173034ull, 1904650575u, 0u, 6082291363471511318ull, 596059024u, 0u, // 90 2608403505412256ull, 2336718444u, 0u, 12661190749550959762ull, 793690867u, 0u, 4775406775355411974ull, 3610868247u, 0u, 5725364914927672236ull, 994697006u, 0u, 3026517030782659652ull, 4001553065u, 0u, 17088609114306166376ull, 28721445u, 0u, 10261551408410322630ull, 4271596563u, 0u, 7980068282736375276ull, 933825198u, 0u, 6542900983727892254ull, 4187278097u, 0u, 7938824816751845346ull, 375937305u, 0u, 11484832577740831254ull, 206526493u, 0u, 6493036661985329470ull, 3759379219u, 0u, 12845002641974178428ull, 2890578235u, 0u, 14577589397389077418ull, 3611930876u, 0u, 8621824121968365988ull, 3495005239u, 0u, 8858427717892025072ull, 2045346850u, 0u, 1968113826898442220ull, 401849861u, 0u, 839205159449488830ull, 532573359u, 0u, 5827739345262974688ull, 595047365u, 0u, 7029851277319082390ull, 4094118630u, 0u, 17845975138965286138ull, 1440159419u, 0u, 15628529438265202118ull, 1169982365u, 0u, 12754964935059349830ull, 4082287771u, 0u, 7433317562941687638ull, 2496310609u, 0u, 9535246497762748490ull, 358595103u, 0u, 11423352788179250118ull, 508891436u, 0u, 16240765378728294200ull, 1030039866u, 0u, 6692618470266646776ull, 1698387246u, 0u, 11120980132752948750ull, 2873780209u, 0u, 520223072585949074ull, 134631756u, 0u, 5903124867443019138ull, 768235836u, 0u, 4250119235436250222ull, 2174121064u, 0u, // 91 12619506756327376134ull, 3552737353u, 0u, 9227139471852245268ull, 428151278u, 0u, 8445713870944942330ull, 2874664669u, 0u, 4949292027002297928ull, 1971314641u, 0u, 15681412416083163338ull, 1877746475u, 0u, 2321151734253581686ull, 4291273577u, 0u, 7679843808923965820ull, 238802388u, 0u, 14171828728067911232ull, 676502665u, 0u, 7053651010785595410ull, 2023150379u, 0u, 1578370425093809824ull, 205741265u, 0u, 1414100079565324392ull, 1438134241u, 0u, 2351605421136469238ull, 3283522428u, 0u, 654871939011934344ull, 435431629u, 0u, 11685382036684482638ull, 229244224u, 0u, 1176903907450305822ull, 3712175961u, 0u, 8757176494915640232ull, 3725625841u, 0u, 3345212360604948942ull, 1612765364u, 0u, 13249131585563726752ull, 2168032685u, 0u, 18220056806404316202ull, 1535627370u, 0u, 8483507374757072710ull, 1869557880u, 0u, 13027480111678682190ull, 1652522165u, 0u, 10179964550237359528ull, 3217191500u, 0u, 9389173686425015838ull, 176209839u, 0u, 15664477013750985306ull, 1572240138u, 0u, 13504073967352532378ull, 2008745547u, 0u, 600332578391990990ull, 1014110782u, 0u, 7235786555941714774ull, 488924330u, 0u, 12222123090007543532ull, 1621016876u, 0u, 12261673475310270276ull, 4061869767u, 0u, 6281595495306733948ull, 1115736032u, 0u, 379657633838297886ull, 932664241u, 0u, 15934186850154115762ull, 800360129u, 0u, // 92 16167785724481457674ull, 475514876u, 0u, 236460462477900550ull, 305810273u, 0u, 9804843729898201280ull, 2386056282u, 0u, 11475476460188807266ull, 1937930793u, 0u, 14492841261172746930ull, 253179301u, 0u, 18033475033951998700ull, 117810291u, 0u, 6501182623663972338ull, 3719798466u, 0u, 17903930251040661782ull, 3766446400u, 0u, 16483824802205248482ull, 59838056u, 0u, 9086555105933992210ull, 1061279941u, 0u, 11306052424418103504ull, 1208502732u, 0u, 11900545433779898612ull, 2024567537u, 0u, 4713390417675552382ull, 3149471025u, 0u, 214466610538321902ull, 1967302964u, 0u, 3926225298806368778ull, 293045513u, 0u, 2193038130640170218ull, 1225856619u, 0u, 16081570426521471966ull, 933207768u, 0u, 10933058275463997066ull, 618312428u, 0u, 11316160128362432286ull, 551903834u, 0u, 18047423468021549528ull, 4285107695u, 0u, 15251658513179627360ull, 1333728928u, 0u, 15281355086793438024ull, 2900753423u, 0u, 1208593646367216618ull, 1248934299u, 0u, 17029773260768748120ull, 3561686457u, 0u, 9271818939616798490ull, 2353631386u, 0u, 15043122667454539982ull, 2911246712u, 0u, 8270365138300263722ull, 1579564515u, 0u, 14961008756223151276ull, 910215948u, 0u, 1266073924340920666ull, 110789191u, 0u, 5074294923599782882ull, 1674983862u, 0u, 5820499592377477778ull, 316536147u, 0u, 4130515350492041424ull, 994293931u, 0u, // 93 6545413213715377098ull, 1887372156u, 0u, 16993480824772683804ull, 455411926u, 0u, 14168820521983153536ull, 3987324676u, 0u, 6664594148303590114ull, 702987514u, 0u, 17330744297095446096ull, 2991279266u, 0u, 3162550826718328116ull, 627996109u, 0u, 15893845618901950040ull, 3211062313u, 0u, 14503505212089832496ull, 2196392371u, 0u, 16146098633444438040ull, 144604045u, 0u, 995854146801618198ull, 2614879983u, 0u, 664744345078067004ull, 700593772u, 0u, 2943087646157502554ull, 588529450u, 0u, 1354426894751375492ull, 640356283u, 0u, 12961067536749458670ull, 2089287618u, 0u, 1891199666022854216ull, 3114947952u, 0u, 6474870302951618628ull, 2133217143u, 0u, 2106838859547634856ull, 1927148801u, 0u, 5479858565097299954ull, 221030011u, 0u, 5901748427882158118ull, 4164229555u, 0u, 4172682303472455482ull, 2135084965u, 0u, 8319167638508435580ull, 4084239037u, 0u, 18084912544568374750ull, 908641064u, 0u, 4090693122649064502ull, 3379445791u, 0u, 10278383165184033406ull, 1223218048u, 0u, 16650361935497147390ull, 2753711927u, 0u, 1454709076762464296ull, 214258046u, 0u, 15051195449959491898ull, 516141817u, 0u, 7353383127665632854ull, 2022590187u, 0u, 6887731579694651728ull, 1433770707u, 0u, 12823945646197756570ull, 3833142617u, 0u, 13928444960515383120ull, 94974285u, 0u, 6136350698512018422ull, 2543437377u, 0u, // 94 15683322696352810892ull, 1420700458u, 0u, 10363684517325092648ull, 477014372u, 0u, 16604533620381856600ull, 3268940445u, 0u, 14792691954859859480ull, 1442774461u, 0u, 16693873951264978658ull, 3367519525u, 0u, 2302644605497637998ull, 1021383310u, 0u, 14563276355819869386ull, 3809637423u, 0u, 7273062807749561868ull, 3506989892u, 0u, 4138017252092858950ull, 578307328u, 0u, 17191771347556523214ull, 3739815534u, 0u, 6754713801077095330ull, 100865596u, 0u, 15609979820310101250ull, 3628302304u, 0u, 3787554213743537996ull, 491219724u, 0u, 1461712721457195026ull, 2686965950u, 0u, 8728789160013142112ull, 170538326u, 0u, 3743319724594904640ull, 1507788995u, 0u, 6072796612565662078ull, 3340264920u, 0u, 17812892715069667374ull, 3243336083u, 0u, 9629826310421819728ull, 472606798u, 0u, 3280063377668205576ull, 4225961166u, 0u, 10502001162771614534ull, 3992596925u, 0u, 6492049555951003190ull, 1617484063u, 0u, 15058872496014193278ull, 127994801u, 0u, 6573320275892067082ull, 2679761067u, 0u, 14051925725014211164ull, 1742561248u, 0u, 8564348194361266244ull, 3940417074u, 0u, 11678709795610413588ull, 4209338653u, 0u, 5748750055859400696ull, 2873556367u, 0u, 323499068919278318ull, 939475901u, 0u, 7583299982546944052ull, 854203724u, 0u, 8244547731688608772ull, 67824707u, 0u, 13768960089907053848ull, 3720439153u, 0u, // 95 8647760582275536078ull, 3441643970u, 0u, 10569165821042394998ull, 2394706671u, 0u, 10508398243443421454ull, 536092018u, 0u, 12735177004517417398ull, 2017747306u, 0u, 2107266807532260864ull, 3986024496u, 0u, 10447665173105729570ull, 1449038237u, 0u, 16190508853388313322ull, 1558694505u, 0u, 12096209413022944930ull, 1396296193u, 0u, 18415610737704422434ull, 3999651644u, 0u, 7468499947443123444ull, 2361378421u, 0u, 2611618818954490692ull, 497101849u, 0u, 6071149680604731716ull, 1006762722u, 0u, 6252021014731709146ull, 454344678u, 0u, 9708314786381924212ull, 1025098542u, 0u, 10313397398672919698ull, 2071410972u, 0u, 11546512783198923598ull, 842755163u, 0u, 12452549544705224454ull, 963739418u, 0u, 12894540453208053926ull, 979213150u, 0u, 1506312731663212244ull, 210061329u, 0u, 4637447461358111706ull, 4287508984u, 0u, 13207261750616166250ull, 2450867420u, 0u, 13623033720950905278ull, 2064991015u, 0u, 10711737933798534786ull, 1837651283u, 0u, 13655015974906207768ull, 2722865974u, 0u, 5911741313320280550ull, 4149755660u, 0u, 4385362372591152962ull, 2471403175u, 0u, 342786377717863708ull, 4009936044u, 0u, 4497138458385217112ull, 592858835u, 0u, 10899952348802494492ull, 3775758281u, 0u, 3109565795667864536ull, 1582126755u, 0u, 573888680568979424ull, 3322905203u, 0u, 14522672036485637832ull, 1191084704u, 0u, // 96 5209511740835686564ull, 1760585503u, 0u, 9432118298257193916ull, 609099430u, 0u, 7689516870230126220ull, 1517744304u, 0u, 14904721118358049826ull, 2062571657u, 0u, 9748939706214424936ull, 2808413835u, 0u, 9440876412860365910ull, 550706180u, 0u, 2682513986132628378ull, 1977582916u, 0u, 15065293124479575994ull, 281864741u, 0u, 7918102675170705560ull, 320148465u, 0u, 11421995898217737142ull, 3607609677u, 0u, 6293785690370507452ull, 1058062536u, 0u, 3814427528571068510ull, 523599820u, 0u, 11015099983515507182ull, 3684209790u, 0u, 7637248910798932148ull, 1006879813u, 0u, 2942888256939633234ull, 3342064601u, 0u, 18301952215751967926ull, 3884866873u, 0u, 6043726743887286028ull, 2000913313u, 0u, 15387382483116310762ull, 4162576156u, 0u, 10585226265393400452ull, 2604810502u, 0u, 14705626200604982598ull, 2073120675u, 0u, 1499834749679549144ull, 490308818u, 0u, 668169935144192412ull, 1689755443u, 0u, 1561839343613680926ull, 2098163677u, 0u, 12654111384357627246ull, 532897093u, 0u, 2573510816353625342ull, 3224423896u, 0u, 8898115226339610874ull, 3376321311u, 0u, 2158119872284734112ull, 561949590u, 0u, 12404920934412941350ull, 959528633u, 0u, 6205264369396858662ull, 3676928338u, 0u, 18143807002062284714ull, 1641092013u, 0u, 10744010421443041972ull, 1179968991u, 0u, 16621114044177374060ull, 699583039u, 0u, // 97 12856504601766196104ull, 4252826126u, 0u, 7194830379583710166ull, 1272968505u, 0u, 14471342420020084466ull, 4247005451u, 0u, 16162220412074728982ull, 835643397u, 0u, 15396353841806716210ull, 383696845u, 0u, 15091394063777054876ull, 3648896129u, 0u, 519939473489089588ull, 1845938512u, 0u, 8759289383348732318ull, 1621862479u, 0u, 5151752280202192696ull, 971822378u, 0u, 9666267802975617952ull, 335817396u, 0u, 17831761478835631706ull, 3484241992u, 0u, 63514483425094060ull, 1866572759u, 0u, 12513124753160102802ull, 1152377508u, 0u, 17961746069571731646ull, 2842522278u, 0u, 63431983390525400ull, 2696530964u, 0u, 4006545701591163880ull, 3967075869u, 0u, 869749472099170962ull, 158702022u, 0u, 7000887020946858460ull, 349255611u, 0u, 4607579965607306544ull, 318376554u, 0u, 9579849869408980490ull, 732797544u, 0u, 8850459107967863734ull, 1229395573u, 0u, 10416076739099468168ull, 3668538519u, 0u, 16218455326179017382ull, 3428315756u, 0u, 11033571568455339116ull, 2807535680u, 0u, 13005215386509194232ull, 2238716532u, 0u, 16737030997203943850ull, 2442819940u, 0u, 8618345129149660254ull, 2535525134u, 0u, 8536418720797825124ull, 1412404741u, 0u, 13351668982154326162ull, 349029279u, 0u, 13519563359536482294ull, 1318261411u, 0u, 17125751621490881616ull, 1930345150u, 0u, 11549604981351651978ull, 2666300640u, 0u, // 98 4122532144824805230ull, 4270717330u, 0u, 17703930416667014330ull, 2224009573u, 0u, 6407235207217561974ull, 946633250u, 0u, 3434271778380115690ull, 2195685037u, 0u, 15504857752668562996ull, 2813436297u, 0u, 7924419269583335904ull, 2355814801u, 0u, 12795977315990618868ull, 2795926324u, 0u, 5517456145663598620ull, 1427335554u, 0u, 9929135400735604114ull, 2108665390u, 0u, 12549618686118948852ull, 4229266194u, 0u, 14377712757933099528ull, 1002227599u, 0u, 6006614259808061898ull, 3989832796u, 0u, 2361999719077431054ull, 2218525331u, 0u, 3075301767558828886ull, 3528344410u, 0u, 8057797954475657006ull, 1797993819u, 0u, 14460230243569824394ull, 134016552u, 0u, 402021942218491332ull, 78945934u, 0u, 15375245820704203948ull, 629758736u, 0u, 6940819960512913460ull, 1485470757u, 0u, 4701980352903505770ull, 3812463586u, 0u, 13243113578940689998ull, 1693607242u, 0u, 13365802837705896972ull, 3263991231u, 0u, 7489456397951419074ull, 3053234098u, 0u, 1187767212013207858ull, 3921802732u, 0u, 8672653556484818046ull, 2593892768u, 0u, 3719757809936506372ull, 1013831374u, 0u, 9208652462898570344ull, 791719949u, 0u, 3692627918721718418ull, 880407456u, 0u, 14482569987993900034ull, 444007830u, 0u, 8553385032483846308ull, 3400167172u, 0u, 8897486276400255970ull, 4086768584u, 0u, 9277031084619875044ull, 2990742536u, 0u, // 99 5239337045824247076ull, 1272723371u, 0u, 3898911764694512352ull, 3915733885u, 0u, 1978363149085925572ull, 3379952750u, 0u, 12616550627186889114ull, 2834738562u, 0u, 13650194261208628342ull, 2723064775u, 0u, 17724339636849080748ull, 946445140u, 0u, 45602405570698808ull, 2910397607u, 0u, 13757242372764281132ull, 3026460004u, 0u, 14684076799356766474ull, 1651627513u, 0u, 7356577747253224932ull, 3480210750u, 0u, 14378046675923053546ull, 4054618196u, 0u, 10878312565220385700ull, 3988049948u, 0u, 2477918220143801528ull, 534154372u, 0u, 1403727233570996322ull, 1704163432u, 0u, 767191550291905260ull, 3344743077u, 0u, 9051625714888953484ull, 293648257u, 0u, 15866740537749257732ull, 2519601147u, 0u, 8270918643665743446ull, 1369195546u, 0u, 11825276575045421364ull, 1018167939u, 0u, 13171578672679742136ull, 3308805007u, 0u, 4980455244833847690ull, 876236697u, 0u, 4974623585424231188ull, 1120130992u, 0u, 18060413578502373130ull, 3564315022u, 0u, 4529644943131819760ull, 4216035308u, 0u, 17517164253348262860ull, 4237274295u, 0u, 4334531989513441206ull, 2284127593u, 0u, 5088446344818230944ull, 2502584191u, 0u, 16383888434186888040ull, 2166818174u, 0u, 5841866930081549794ull, 2430292784u, 0u, 2370439386800289494ull, 858744813u, 0u, 15187614562256316876ull, 48134900u, 0u, 16550654516003156478ull, 3247831969u, 0u, // 100 4126813866025481910ull, 1280924956u, 0u, 11400330983297728284ull, 367442496u, 0u, 14830991364214041486ull, 62813496u, 0u, 7196783886588970200ull, 1108728922u, 0u, 4851701630057105768ull, 2690217274u, 0u, 15193966325956846488ull, 865054337u, 0u, 13142486650034570274ull, 2700092812u, 0u, 6320856641798726062ull, 2585238353u, 0u, 13298888833331177326ull, 216687756u, 0u, 6819242715182978036ull, 2183161993u, 0u, 3598293483174174054ull, 1031928386u, 0u, 14706229789052110506ull, 1118551582u, 0u, 9351516567549666952ull, 574896604u, 0u, 12788350080197002510ull, 3080648580u, 0u, 3680195489898655172ull, 1907030026u, 0u, 1506136072428507618ull, 3377346531u, 0u, 13693447888159062892ull, 4221978845u, 0u, 12952539027099552578ull, 3946257740u, 0u, 14373237407742481904ull, 2865030787u, 0u, 9085371560988695264ull, 999481385u, 0u, 3428447770455033004ull, 2443730112u, 0u, 11128245290663656894ull, 1001800716u, 0u, 2269100623843832376ull, 3401374272u, 0u, 9473109953217413738ull, 1384486655u, 0u, 7065471580196986426ull, 600329015u, 0u, 10953771200605388070ull, 4231724472u, 0u, 13965457353588255202ull, 2330931749u, 0u, 16407130067445372468ull, 564473015u, 0u, 2521676475581553364ull, 1790563525u, 0u, 13112190653136929406ull, 2154794543u, 0u, 10849855972828540098ull, 4038411834u, 0u, 9754732210476941748ull, 4096967813u, 0u, // 101 12889686097738721476ull, 209708180u, 0u, 14210446530829489362ull, 694261542u, 0u, 9431361080150996366ull, 3377092533u, 0u, 13019350667869706416ull, 3798459121u, 0u, 13548847250501244534ull, 2763858493u, 0u, 3314666590316679580ull, 144460036u, 0u, 14533602416280756566ull, 4118729407u, 0u, 5823988936545231964ull, 926458459u, 0u, 9708893442382297680ull, 1637940387u, 0u, 4618213274204313960ull, 4149195563u, 0u, 685637861562605376ull, 863016836u, 0u, 8505335378166423074ull, 3844259158u, 0u, 15239221912349826538ull, 1745050983u, 0u, 11210514769847937596ull, 1226931754u, 0u, 16324706120136473348ull, 3171468784u, 0u, 6157170251367823570ull, 1551658439u, 0u, 15160474379848096956ull, 519568176u, 0u, 1972159670933899282ull, 4131904510u, 0u, 4597655664722405092ull, 787935527u, 0u, 13268292719086064724ull, 3723626551u, 0u, 14021959559369263092ull, 4090418413u, 0u, 13331554803432426660ull, 3037522840u, 0u, 9547014451068463312ull, 3736806451u, 0u, 12325711862465548008ull, 1469025453u, 0u, 13234101271257575416ull, 2784841977u, 0u, 2750785235328523672ull, 626232587u, 0u, 6196859034794052454ull, 1053459929u, 0u, 4227328768361075744ull, 2929370081u, 0u, 8160558491800332432ull, 1854674533u, 0u, 2750731388849695964ull, 3058140888u, 0u, 15588851883674770736ull, 1965124815u, 0u, 9593492007394907776ull, 1825241969u, 0u, // 102 16340346865621012514ull, 184724117u, 0u, 7873808140223724392ull, 3245215371u, 0u, 289035124729086320ull, 800534182u, 0u, 3737733700549129266ull, 3984369898u, 0u, 3910196999100623920ull, 1175307466u, 0u, 4658859142598623496ull, 3757616589u, 0u, 18354206927132040810ull, 3745428422u, 0u, 1283458168089793370ull, 3463125530u, 0u, 8045570783426757948ull, 2206575341u, 0u, 11137387944025281806ull, 1282076039u, 0u, 4902133844912393112ull, 30710661u, 0u, 10037106343763623662ull, 2317349447u, 0u, 13110635057842480586ull, 243530236u, 0u, 10859281535924601688ull, 772166549u, 0u, 3261236611694792106ull, 835864066u, 0u, 2221404534139888478ull, 215187534u, 0u, 4765841448336436696ull, 2225171502u, 0u, 17192623422587950896ull, 3027969646u, 0u, 6063355585052143584ull, 2720488552u, 0u, 5569182593407089662ull, 3753282677u, 0u, 8615188467281218218ull, 2627375941u, 0u, 2937584319462997196ull, 3668381253u, 0u, 14053821151840756518ull, 1795697221u, 0u, 9355064259480680736ull, 646337946u, 0u, 1512219058522019742ull, 3215282992u, 0u, 18147882609691927222ull, 3724679340u, 0u, 3686006232909013898ull, 3718010210u, 0u, 790657724946669888ull, 766436371u, 0u, 3649477783768961962ull, 3007389902u, 0u, 4926701247359446496ull, 2868101231u, 0u, 1668978715518127614ull, 270661615u, 0u, 13290508374436259720ull, 1082842892u, 0u, // 103 4862571862465554798ull, 725117751u, 0u, 13340606220252832636ull, 2098336710u, 0u, 2270459030312483468ull, 1118921441u, 0u, 4083843240332828964ull, 3157183213u, 0u, 2367162255194749074ull, 3685792600u, 0u, 1018072153361834176ull, 793219026u, 0u, 2637972403545379038ull, 2035977565u, 0u, 17825519242868735194ull, 1322398185u, 0u, 14492323956715179656ull, 387390092u, 0u, 11739908320452318540ull, 2478756543u, 0u, 7545524881746866228ull, 1708006175u, 0u, 5245616435495708996ull, 1946819698u, 0u, 7523735317060869334ull, 727854973u, 0u, 1825103579034289746ull, 4186999994u, 0u, 9576921674630788366ull, 2682508075u, 0u, 60450233758335000ull, 40005617u, 0u, 10627234162669303136ull, 1214144777u, 0u, 6192832930576413628ull, 385984222u, 0u, 17895512008108756792ull, 4213263183u, 0u, 11926517785539789380ull, 1151865021u, 0u, 6640600726237698014ull, 1215007526u, 0u, 13581893355169266568ull, 4074451736u, 0u, 2807364568032508256ull, 2488217411u, 0u, 731681608500989922ull, 4181893941u, 0u, 16815608110047098348ull, 261560416u, 0u, 18091681490014901114ull, 1291702430u, 0u, 16479230259876986310ull, 3826838096u, 0u, 7692071863173028588ull, 129154914u, 0u, 4459722382923273820ull, 1240362768u, 0u, 12551958348201956430ull, 3810952501u, 0u, 14419791555160067754ull, 1145383952u, 0u, 793290654292963628ull, 816182026u, 0u, // 104 14225838380776954516ull, 1920576826u, 0u, 8943610017355024930ull, 2572666705u, 0u, 6798577287326123630ull, 2446169459u, 0u, 12783254912697886140ull, 964232423u, 0u, 456806552723373878ull, 1672631988u, 0u, 12231225806152006220ull, 3551922857u, 0u, 870945632921867096ull, 3160354397u, 0u, 10425825239251412066ull, 2189770399u, 0u, 12517186139792404556ull, 3404536237u, 0u, 9701760156808407082ull, 3128842469u, 0u, 5565297030139197856ull, 1468278525u, 0u, 12447221299143152908ull, 3962155914u, 0u, 8773711361745285868ull, 4068005420u, 0u, 13118279068636335518ull, 2795461889u, 0u, 5002544002941107944ull, 1443820673u, 0u, 16551357723856768414ull, 1167735081u, 0u, 912968203529439178ull, 2745657241u, 0u, 5378265664811869822ull, 3063237860u, 0u, 9789990319247228720ull, 1601191074u, 0u, 11257408494882271422ull, 2644059690u, 0u, 1035428385306727208ull, 839983481u, 0u, 4757164438081852986ull, 3881790970u, 0u, 16961512610384335494ull, 2473253994u, 0u, 2737551816586533332ull, 3337766895u, 0u, 5806169525334342760ull, 3626663683u, 0u, 14833346335583838876ull, 819915985u, 0u, 11685894800194623718ull, 263863867u, 0u, 14471998093085327984ull, 1729045683u, 0u, 8760934313218178432ull, 1150630925u, 0u, 11772560592696187982ull, 1453478533u, 0u, 2620776440383156808ull, 3211702613u, 0u, 374079388147906070ull, 4150941480u, 0u, // 105 4073973034797465478ull, 1614042162u, 0u, 14264558693407093544ull, 1522608677u, 0u, 11741186850214035464ull, 1218078885u, 0u, 9160390349284059972ull, 4219508423u, 0u, 6245635009944680848ull, 4139291881u, 0u, 13015781566358525752ull, 864424718u, 0u, 7849541908879535142ull, 552871168u, 0u, 10290439634366249986ull, 3583019836u, 0u, 13350691312550024066ull, 1402039281u, 0u, 6953859098748137504ull, 3059298652u, 0u, 13927244922219015250ull, 4026118759u, 0u, 14357899688579974370ull, 2897952741u, 0u, 1012609041580158208ull, 4177523845u, 0u, 12118391512454545242ull, 2854466420u, 0u, 15607796764562163648ull, 4087187064u, 0u, 285954295583105802ull, 3179107202u, 0u, 3772094688982657062ull, 542827779u, 0u, 17300154093819496314ull, 2190161869u, 0u, 7943157547115275002ull, 4037034997u, 0u, 2564148738518715754ull, 1848692691u, 0u, 1185327564352812502ull, 3542083577u, 0u, 1980695844411916686ull, 746612932u, 0u, 14164433770055928978ull, 3786572463u, 0u, 10323230196689781736ull, 3904756980u, 0u, 10573158708101849038ull, 1478750787u, 0u, 11898216606131783410ull, 3951462132u, 0u, 2702502346975031538ull, 388266253u, 0u, 1554816593942803368ull, 3201644240u, 0u, 7783390911542774344ull, 3477739963u, 0u, 10188178774731211254ull, 4135007663u, 0u, 15390831461396410136ull, 3504385259u, 0u, 14176977960595759644ull, 3205981489u, 0u, // 106 1958001312169460756ull, 4029716956u, 0u, 10537594405328560256ull, 3070931650u, 0u, 16538545727135296692ull, 369296188u, 0u, 16507821910815246040ull, 176909228u, 0u, 14117232260295529946ull, 472517363u, 0u, 7021467070482113022ull, 1920324786u, 0u, 3029791791617037878ull, 477151051u, 0u, 11559768281623993880ull, 1336395804u, 0u, 10394064170220669604ull, 1677436940u, 0u, 639967860362432150ull, 39642935u, 0u, 16146148183811993270ull, 2919076994u, 0u, 7655532344153761908ull, 1191995109u, 0u, 1377381799882979020ull, 3375880014u, 0u, 7456283049402864228ull, 1327248585u, 0u, 11393464913210713266ull, 3342771472u, 0u, 3639292354367837396ull, 2101994105u, 0u, 18438670795151141038ull, 225271967u, 0u, 6595913040289745582ull, 951311234u, 0u, 7388602909641603158ull, 1997488563u, 0u, 5738336343717103528ull, 696087863u, 0u, 12596894694854548130ull, 1791187548u, 0u, 14616876261134064466ull, 231210571u, 0u, 18224286469790902064ull, 4272877066u, 0u, 10276238281280701058ull, 2247731306u, 0u, 10747370987306012302ull, 2166401369u, 0u, 1448815383753944130ull, 1715332993u, 0u, 5631917352578196252ull, 3835769165u, 0u, 6252216042898829602ull, 3546241958u, 0u, 2273328059958388472ull, 4168113658u, 0u, 3200678171959396756ull, 2308570098u, 0u, 3072550043365805542ull, 2995497564u, 0u, 13361364783317328448ull, 3970160172u, 0u, // 107 18155342099938273648ull, 2952770333u, 0u, 16229322907694293170ull, 4147548533u, 0u, 5834407020923444834ull, 662563010u, 0u, 16060929865508476572ull, 2247074293u, 0u, 3875122293629093456ull, 3337917086u, 0u, 1130494918328338968ull, 3033294387u, 0u, 1487957588759672426ull, 2629003548u, 0u, 8748674419437421832ull, 613577475u, 0u, 503210774965482644ull, 1181927913u, 0u, 11483759744277879594ull, 3234677257u, 0u, 17127672243052292492ull, 3164170032u, 0u, 17652112749277719992ull, 2554545772u, 0u, 17829817996217217644ull, 1668503700u, 0u, 6750322657456417652ull, 530152899u, 0u, 1441418359342227362ull, 4245680078u, 0u, 8847172929526935448ull, 3243279384u, 0u, 14079360882109467816ull, 1117932684u, 0u, 4458730431407812000ull, 2800990334u, 0u, 14401418106907769704ull, 3121689189u, 0u, 12519529602864304490ull, 4252212040u, 0u, 12621705619072777484ull, 1300739614u, 0u, 4395900283412119136ull, 362240603u, 0u, 6262691553942748392ull, 4155200306u, 0u, 18431995711778808586ull, 337630107u, 0u, 15018876264680638504ull, 2364412092u, 0u, 9800510026919022584ull, 3872968727u, 0u, 12700550377112904428ull, 2862262272u, 0u, 7364895972653813130ull, 3643786469u, 0u, 10169559251131780364ull, 1058494028u, 0u, 14808064136205099748ull, 4289207662u, 0u, 16463888303251322216ull, 2861229254u, 0u, 3503071705322020718ull, 4166722462u, 0u, // 108 5546952969000042192ull, 1376316540u, 0u, 16302018226685468814ull, 3541244717u, 0u, 8764998801182337956ull, 4181960988u, 0u, 9806201699431397666ull, 2177913839u, 0u, 17310545642639876534ull, 9826084u, 0u, 8065036614472094354ull, 3263140193u, 0u, 15651946020651116462ull, 3625723582u, 0u, 10080911994697415510ull, 7478837u, 0u, 13084079539022984658ull, 2177717791u, 0u, 13800287963636731936ull, 130824821u, 0u, 12959076901192390012ull, 3303388789u, 0u, 9362019529980253890ull, 2885441687u, 0u, 7908680536959646734ull, 2218765466u, 0u, 5635390339395936604ull, 1572775332u, 0u, 14748974339679738280ull, 2089482171u, 0u, 7412286218100720390ull, 4112942471u, 0u, 5283485914581701864ull, 2044062721u, 0u, 7680599473699583014ull, 1650696598u, 0u, 5497080177445073908ull, 2518005754u, 0u, 3397733242234761990ull, 2560639508u, 0u, 16968789045772025254ull, 511679782u, 0u, 4361494822952441756ull, 2488039146u, 0u, 9440599301152617480ull, 1902875894u, 0u, 10610941512176200350ull, 1866239534u, 0u, 844191536994779756ull, 4143810072u, 0u, 8940873935216431858ull, 3764348470u, 0u, 16757606663814487524ull, 1307452107u, 0u, 16851118323325831832ull, 349534380u, 0u, 16762051481433791456ull, 3521731267u, 0u, 5597097148111513052ull, 1921401538u, 0u, 15698801960542156194ull, 2148807493u, 0u, 5006011604166355748ull, 3300362002u, 0u, // 109 3022356896661940648ull, 4198671799u, 0u, 838129277296418ull, 2522533707u, 0u, 1151830367392538920ull, 3748152053u, 0u, 18274055379830532322ull, 3708171759u, 0u, 3046395488596254318ull, 2907135278u, 0u, 15768368898503537856ull, 3024336040u, 0u, 11801561479982468366ull, 927136073u, 0u, 9794986380632639028ull, 2501876491u, 0u, 14759622468541778698ull, 2790967469u, 0u, 857295151382397154ull, 4242639635u, 0u, 12933760768867532356ull, 2636336289u, 0u, 8658518329668680762ull, 178385339u, 0u, 8947734089036824310ull, 2481437061u, 0u, 10601518809601959624ull, 2010124169u, 0u, 2483721343801462760ull, 3151380296u, 0u, 7392831662294655572ull, 1215647089u, 0u, 12678452125956258718ull, 2679874092u, 0u, 3957436108876738760ull, 2500844089u, 0u, 7455106978080324678ull, 4060114839u, 0u, 3472282078422205882ull, 1392329398u, 0u, 3433955510301659846ull, 2685386213u, 0u, 17354864872661021466ull, 3501398u, 0u, 8555779533775812840ull, 1600673637u, 0u, 3471135681520900134ull, 4194819612u, 0u, 4059987860025310536ull, 3489687899u, 0u, 9582391003081246610ull, 3918246623u, 0u, 36941562889845934ull, 4134035812u, 0u, 7234149153687000518ull, 2870709363u, 0u, 12674346312155069258ull, 648554577u, 0u, 7911542804688512990ull, 963258214u, 0u, 11909233512699477136ull, 2166412531u, 0u, 499629170671524224ull, 4032094526u, 0u, // 110 12854215280231878716ull, 1085113498u, 0u, 8756172119787597976ull, 1844920321u, 0u, 13547344122397319294ull, 1989154143u, 0u, 5432439572492682018ull, 4080467537u, 0u, 16162085147321422454ull, 1642460240u, 0u, 9510389790901088304ull, 3660156637u, 0u, 18434671423266149506ull, 4282159884u, 0u, 13936140377933191822ull, 2691426983u, 0u, 3301729920682365240ull, 1191818479u, 0u, 2287328919163662438ull, 1260573916u, 0u, 10861523254809012246ull, 3327622077u, 0u, 13174214501147017532ull, 4255240571u, 0u, 7923214858454644754ull, 2975693474u, 0u, 8698585009677673254ull, 3111978618u, 0u, 9956246696552400544ull, 2938486665u, 0u, 16342512130952435972ull, 3059685721u, 0u, 10940754841439207150ull, 3587069886u, 0u, 16622344834872206250ull, 3146115564u, 0u, 5076854101254074994ull, 201024462u, 0u, 5748590708581846042ull, 2736951407u, 0u, 2403336472536291934ull, 1151286175u, 0u, 14918005764425559646ull, 3570039602u, 0u, 4041258322198455262ull, 1513103535u, 0u, 18432742335729919220ull, 1318364287u, 0u, 7247875807486293576ull, 2748703424u, 0u, 18310993804265991874ull, 3676463858u, 0u, 6046900375304673998ull, 263450233u, 0u, 12368012320839114596ull, 2168134257u, 0u, 15537165258953404726ull, 3266234463u, 0u, 2033729818074689796ull, 3688264062u, 0u, 11478133963045052902ull, 2658197116u, 0u, 9103612085689871928ull, 1670298424u, 0u, // 111 6735376282308423628ull, 3966571u, 0u, 9326386830523122492ull, 3418880615u, 0u, 12343816098098876678ull, 2010193943u, 0u, 9066762270661672422ull, 2598526557u, 0u, 2067145066392825558ull, 2353582139u, 0u, 1452993262892797394ull, 2253653614u, 0u, 2988625226341298060ull, 2674586874u, 0u, 8389208161732570986ull, 964640073u, 0u, 13148623911076779548ull, 4098752583u, 0u, 9719505874572158906ull, 1525070231u, 0u, 8131847870079064150ull, 1875943198u, 0u, 15953718223571109380ull, 387255265u, 0u, 2019499596643272570ull, 2391137533u, 0u, 3435026651909693542ull, 3250596670u, 0u, 6772447584608052604ull, 3196694699u, 0u, 11020102339363928082ull, 1979606731u, 0u, 10788236486116489122ull, 388710082u, 0u, 12692253193450560830ull, 1300761207u, 0u, 1009664675152379374ull, 2578059176u, 0u, 10330984140906503812ull, 3025920248u, 0u, 13276837559656910010ull, 2544937048u, 0u, 10458467458017573676ull, 1035891845u, 0u, 16032172771214662222ull, 4214624394u, 0u, 2975821028865699898ull, 3440132182u, 0u, 18330677239985075828ull, 4267995934u, 0u, 17795444542210893936ull, 2989560351u, 0u, 3565181029631901256ull, 1606505394u, 0u, 6170367271612557342ull, 1461686085u, 0u, 18074610768063876652ull, 1877496846u, 0u, 30401405041054030ull, 618637476u, 0u, 4417507309842362044ull, 693055210u, 0u, 2460883211393754590ull, 3247158214u, 0u, // 112 6738224291580328778ull, 309880768u, 0u, 14002582950753915068ull, 1180479458u, 0u, 9416463270408570364ull, 1108815284u, 0u, 12362461275482703248ull, 2703506577u, 0u, 11882736988217205526ull, 1448168748u, 0u, 1231726157473799280ull, 291667414u, 0u, 355039058531339862ull, 3785275383u, 0u, 14400317716293209570ull, 1326288982u, 0u, 13339307844833438160ull, 1152898151u, 0u, 2478291309663860846ull, 1931532299u, 0u, 16814837972110729226ull, 3233459528u, 0u, 12252231218268750630ull, 1678627780u, 0u, 3658617749450288682ull, 1459604911u, 0u, 4840918189385324950ull, 1234725839u, 0u, 14692403447934483764ull, 3385320280u, 0u, 11531123433886780456ull, 4153229582u, 0u, 471733171231528328ull, 1693302121u, 0u, 12920696793029264306ull, 3288905476u, 0u, 9826098492654380932ull, 1940332167u, 0u, 8449565506644944356ull, 3065864085u, 0u, 14575398639720512630ull, 2884443283u, 0u, 7224245912851012416ull, 1604081788u, 0u, 3513655041174887204ull, 3609296311u, 0u, 17031219652329795624ull, 974587442u, 0u, 11472264346567112496ull, 1217529695u, 0u, 539292491897674548ull, 1190139379u, 0u, 6122646140009871744ull, 4210855798u, 0u, 848339233288590868ull, 1470964162u, 0u, 14867424173518427098ull, 3289580872u, 0u, 6170303593382474494ull, 3719902888u, 0u, 5193007795116211958ull, 2457782574u, 0u, 2536506687164307496ull, 815347289u, 0u, // 113 14498913615042136574ull, 2610990548u, 0u, 4534605278031916754ull, 709564833u, 0u, 7232478645191607638ull, 2751368097u, 0u, 5172030248582593070ull, 4192936432u, 0u, 4486477626152754636ull, 3851674190u, 0u, 9220750496090379542ull, 2738613939u, 0u, 18395252702154194798ull, 1660695044u, 0u, 6673889416465468472ull, 2881591961u, 0u, 3687714227756630180ull, 2050367610u, 0u, 5231460118372375784ull, 517388869u, 0u, 17867801165316365724ull, 1406759684u, 0u, 10041149199220694984ull, 3637947222u, 0u, 7391970443367873502ull, 3672438671u, 0u, 16963143692523920798ull, 2959722337u, 0u, 7786345377977943970ull, 1900078858u, 0u, 6374866941971683386ull, 4220872376u, 0u, 5527550203035643064ull, 2631161952u, 0u, 11420538764095577558ull, 3211924787u, 0u, 10945528357603503418ull, 1878126986u, 0u, 741644423085068550ull, 228920930u, 0u, 17129163335311179624ull, 3585621309u, 0u, 14548032901564500948ull, 374551047u, 0u, 8887340006772895162ull, 4008905513u, 0u, 454706539044424586ull, 3124064061u, 0u, 1472342781427363486ull, 815370996u, 0u, 8957963682184853042ull, 395635267u, 0u, 3089198995146136768ull, 1867942674u, 0u, 14610065741450603258ull, 1759218978u, 0u, 3643989699188792918ull, 614801780u, 0u, 2127739696631210046ull, 83346499u, 0u, 8956899926382773302ull, 3504881403u, 0u, 16540238674754030302ull, 3296351606u, 0u, // 114 14659136307541749840ull, 232393325u, 0u, 9511521692556461604ull, 1255053373u, 0u, 2284358428989969806ull, 131484620u, 0u, 5767170215218339176ull, 1744234349u, 0u, 14095284348080916620ull, 2816439432u, 0u, 11856137326638934502ull, 582722586u, 0u, 7276207298517888968ull, 1885643636u, 0u, 10892732608252143078ull, 322346717u, 0u, 5725141764361538314ull, 3941643621u, 0u, 13588608818168036590ull, 2933768576u, 0u, 247110623036578492ull, 540350600u, 0u, 3615347407519733626ull, 1700874714u, 0u, 6701972531178798350ull, 2047869851u, 0u, 7425550739064568750ull, 1588291689u, 0u, 10292478580495275000ull, 3828253108u, 0u, 10735299324375629078ull, 3716257516u, 0u, 1709430529782341176ull, 1320643945u, 0u, 10259031808783935814ull, 699598084u, 0u, 10686821492965442516ull, 2398199004u, 0u, 14517289957870257994ull, 826133995u, 0u, 7147648203568087506ull, 2879276249u, 0u, 9300303956865009050ull, 1038442392u, 0u, 16095931757233284474ull, 3489691443u, 0u, 13399969753387980576ull, 2350932598u, 0u, 13927564115387494102ull, 3654120821u, 0u, 6238108179653770172ull, 2860851570u, 0u, 13249841828546022790ull, 455861270u, 0u, 14093314131478286210ull, 1559135779u, 0u, 17394738566512030676ull, 3935848187u, 0u, 16111931206653217674ull, 4243751957u, 0u, 10824207677027695108ull, 2880139355u, 0u, 8398446021231012218ull, 2000089761u, 0u, // 115 11545664961852077698ull, 2305292348u, 0u, 2350040008013199916ull, 3853461263u, 0u, 7847749087802980278ull, 2405072257u, 0u, 14075847722915077140ull, 2086334060u, 0u, 17233764059158198554ull, 3625177335u, 0u, 10560091038587000338ull, 1891158816u, 0u, 10585822532268495612ull, 3544062821u, 0u, 5993766474653494218ull, 2468357069u, 0u, 8116378401277194098ull, 1417369641u, 0u, 4232065462428835104ull, 3983319094u, 0u, 15476887708254384908ull, 2813893879u, 0u, 14712943279740647186ull, 2978931645u, 0u, 3663575739474996046ull, 3796848865u, 0u, 11642065597988909180ull, 1915422368u, 0u, 18104010316705444210ull, 955713317u, 0u, 17174210106967978842ull, 3676973501u, 0u, 14196106534962292386ull, 4063451248u, 0u, 16327415183780192948ull, 3541018221u, 0u, 11555161110963004128ull, 3006335623u, 0u, 12206181608326547890ull, 2494676418u, 0u, 17176101005917829762ull, 2560695445u, 0u, 2421061607210519512ull, 82418071u, 0u, 4162505487737665120ull, 811048878u, 0u, 66413782670318738ull, 352889575u, 0u, 6015020775360451788ull, 2544673607u, 0u, 1955480653246420890ull, 4202015439u, 0u, 6389137030230420900ull, 4206235909u, 0u, 7139374315218558202ull, 3423029166u, 0u, 5356242571454716706ull, 402820385u, 0u, 121651504388219176ull, 4011214032u, 0u, 2786030078423205656ull, 3544460619u, 0u, 4937520934993487246ull, 423675111u, 0u, // 116 13393998155303037886ull, 200901490u, 0u, 17411138876024917880ull, 3781920070u, 0u, 5978452734922997306ull, 2570468773u, 0u, 10291906981656591468ull, 858581634u, 0u, 4926940841956481448ull, 2860115978u, 0u, 11999572954384267642ull, 3405676172u, 0u, 14275737030074089490ull, 389379800u, 0u, 15595853176846313950ull, 3922090034u, 0u, 308504417403883574ull, 2971214573u, 0u, 11315208111431837466ull, 799351325u, 0u, 7081354361030031644ull, 36447640u, 0u, 1428814841687307992ull, 1112344508u, 0u, 12280264308222746350ull, 2236711754u, 0u, 10007325127254589826ull, 3860922631u, 0u, 2356013134071330340ull, 1697193124u, 0u, 15776912950669922112ull, 1272332079u, 0u, 13893410068242335916ull, 1554735895u, 0u, 1288072831092828308ull, 3613700414u, 0u, 1587957909832432356ull, 3184696945u, 0u, 1939142370869527452ull, 2264148938u, 0u, 16649322742706358320ull, 1409234485u, 0u, 6885321215211114976ull, 2250383939u, 0u, 14896102135745141072ull, 2230451771u, 0u, 8486342483569349522ull, 1116801694u, 0u, 5358729089347515362ull, 1420812501u, 0u, 4896601559152044724ull, 330528695u, 0u, 13727493673077612928ull, 25396565u, 0u, 1210213414063926980ull, 2295630559u, 0u, 10876334468465122162ull, 2165115991u, 0u, 8069719214728616790ull, 3831349579u, 0u, 9056020826890820420ull, 2442616359u, 0u, 10863216781788088016ull, 4145673138u, 0u, // 117 17463978000768183220ull, 4007105318u, 0u, 1870418514760005166ull, 2852154281u, 0u, 16988138129822597964ull, 1384733917u, 0u, 16695683893570867874ull, 263243501u, 0u, 1707702307169096498ull, 266856688u, 0u, 15253647915017539820ull, 3965469820u, 0u, 10633747367456657810ull, 2140306976u, 0u, 16982583824420395958ull, 2925098472u, 0u, 9710534509734937600ull, 2653754452u, 0u, 4534129361145197184ull, 2709587509u, 0u, 522495400120337576ull, 4215624511u, 0u, 15386804356504770458ull, 6499240u, 0u, 7292966059055218866ull, 377668156u, 0u, 16829400175229294536ull, 1957021586u, 0u, 7935503808328328144ull, 93568600u, 0u, 13280056721320600366ull, 204068690u, 0u, 10945285827882737768ull, 3655314965u, 0u, 15613336090700977604ull, 1173574174u, 0u, 229046649972461958ull, 2213392059u, 0u, 8303310811240659588ull, 4029888656u, 0u, 16267804861002273730ull, 321900578u, 0u, 9161525582788990008ull, 3947203955u, 0u, 7798002036171571820ull, 464378724u, 0u, 15162495801005515470ull, 196104591u, 0u, 3503102747268577864ull, 780463057u, 0u, 7073783525093549200ull, 3386144369u, 0u, 14456572502551862230ull, 2714750077u, 0u, 10182310967025045680ull, 4213227915u, 0u, 527691581736155548ull, 667167606u, 0u, 1861411431540480774ull, 841611043u, 0u, 15266039710742295840ull, 2187756321u, 0u, 16104886125253215916ull, 3869205689u, 0u, // 118 15070020279182175700ull, 3990962373u, 0u, 8629442559150395834ull, 4087899344u, 0u, 14426273670385880846ull, 2143318981u, 0u, 7298001394662850030ull, 1321614255u, 0u, 18233782771338773892ull, 3890433745u, 0u, 11250372331578078838ull, 2842749611u, 0u, 9856737232108099722ull, 1613005306u, 0u, 16104542716723964404ull, 1318885641u, 0u, 3340366245846599908ull, 4028671572u, 0u, 6271671631375544782ull, 4248564483u, 0u, 2922437089655796564ull, 1980132169u, 0u, 12584529379244506466ull, 3607784260u, 0u, 17815498116228492094ull, 2596611582u, 0u, 9684442163056480896ull, 4063015897u, 0u, 5045209109174642936ull, 1996731532u, 0u, 7162657015086947942ull, 2242050366u, 0u, 7206815149836645802ull, 1021364283u, 0u, 7095374229156056256ull, 2368221782u, 0u, 7735340153072867052ull, 2557588653u, 0u, 10262482865799750192ull, 2365704430u, 0u, 145467729825996682ull, 396214246u, 0u, 2868406962271692842ull, 1975947564u, 0u, 12685354515232498676ull, 1459094209u, 0u, 15736107469162996164ull, 911432370u, 0u, 7135253112628776104ull, 302554245u, 0u, 9346089963417923902ull, 505941947u, 0u, 3986304648782573452ull, 897939135u, 0u, 4394509673422969308ull, 3378039924u, 0u, 9979010800570471422ull, 858787671u, 0u, 7810377600065834800ull, 3486571467u, 0u, 1033650019714878716ull, 2358342255u, 0u, 8563760083005182416ull, 2477076941u, 0u, // 119 17502432039634600102ull, 1967646926u, 0u, 3633496118898197680ull, 434879275u, 0u, 6075368162774830260ull, 182119718u, 0u, 674077513031857930ull, 3444490361u, 0u, 10824622715928333194ull, 2509651894u, 0u, 2033123996190412026ull, 2376620591u, 0u, 5078987621422580870ull, 960999216u, 0u, 9320669333846014740ull, 1839966859u, 0u, 400558228008685768ull, 476743751u, 0u, 5977379216050788646ull, 721662222u, 0u, 3356254602442737488ull, 2003685078u, 0u, 7857805741138585402ull, 3791655939u, 0u, 7260230019888293912ull, 991934197u, 0u, 8091281517694148198ull, 2438213473u, 0u, 6809478270794189510ull, 465398361u, 0u, 6608773088224679218ull, 178319300u, 0u, 15674743405843553768ull, 607497919u, 0u, 9371506334798898096ull, 4107720169u, 0u, 4245478098109952392ull, 4109153933u, 0u, 2269614104648863318ull, 1442328457u, 0u, 14036044086030287260ull, 3353470731u, 0u, 8609103573895133908ull, 463239461u, 0u, 17150390422368877762ull, 1768989871u, 0u, 147933760219310898ull, 3421029917u, 0u, 13872405043178445272ull, 1262875904u, 0u, 12809302565992660506ull, 864896725u, 0u, 12147682245142645910ull, 3629932923u, 0u, 6107905594932749580ull, 3652575814u, 0u, 8663324665333678934ull, 3506375698u, 0u, 3078102179633856204ull, 1759772643u, 0u, 1855306806634827012ull, 2398207631u, 0u, 4341655741626071262ull, 1049112174u, 0u, // 120 11160828817954991588ull, 417754218u, 0u, 3827619876153757716ull, 64898337u, 0u, 1747421785199306974ull, 294257511u, 0u, 4351402593528831508ull, 1789085152u, 0u, 14308476206375932624ull, 948093530u, 0u, 11150886330385202830ull, 1746573087u, 0u, 11007987693833128002ull, 4288279822u, 0u, 13019538238264299092ull, 991241303u, 0u, 12448250526559397246ull, 2132485116u, 0u, 15834031389169300000ull, 1290517172u, 0u, 5837299970619277220ull, 2984118983u, 0u, 1251365431305255290ull, 1546048967u, 0u, 18360364690748145754ull, 853456569u, 0u, 13747793255567492058ull, 1209349481u, 0u, 2887520024429088334ull, 3817788839u, 0u, 12226703947498151080ull, 3242527305u, 0u, 442803337802398434ull, 2411104498u, 0u, 6389404404242937290ull, 3538076621u, 0u, 13565049232173685836ull, 3046208940u, 0u, 5433833671834875850ull, 1670464708u, 0u, 4203699675655615816ull, 1222860412u, 0u, 9763806038748999716ull, 3606388285u, 0u, 3464055640833883372ull, 2889898099u, 0u, 5070019604923292794ull, 2333667518u, 0u, 2319622628867658226ull, 2137025957u, 0u, 9779098909174112608ull, 27902251u, 0u, 18132893720718321698ull, 2674837210u, 0u, 7891495972094148190ull, 1526616320u, 0u, 3192039878582821174ull, 2525122633u, 0u, 11033504495658408514ull, 2484688977u, 0u, 7080122053291917070ull, 1201271645u, 0u, 17935467686396985944ull, 2623729648u, 0u, // 121 15911831656089647458ull, 4216073208u, 0u, 8277710987629729572ull, 610745214u, 0u, 17272745117385598684ull, 1099336340u, 0u, 17680594612016069694ull, 624029947u, 0u, 5787234807301668424ull, 965923467u, 0u, 7437085902663251008ull, 2222095741u, 0u, 17884255253774367052ull, 3683609625u, 0u, 15635119208650769708ull, 1144035002u, 0u, 14634095998340926758ull, 3712472347u, 0u, 6708859290118945940ull, 1175957456u, 0u, 3051306374766679536ull, 2724433342u, 0u, 14443748801460229492ull, 1086807768u, 0u, 7823444654420081164ull, 1261074725u, 0u, 16114273059243938060ull, 936683666u, 0u, 16347785804232059660ull, 3090105812u, 0u, 18323703597290956878ull, 772294819u, 0u, 13638760260639852782ull, 2189095510u, 0u, 143433857112537264ull, 1867726988u, 0u, 14542045746069014528ull, 3826104053u, 0u, 4081206427587123788ull, 1511819232u, 0u, 16239019697314052082ull, 2672470174u, 0u, 8601840110757479698ull, 2334747521u, 0u, 15667392843227362152ull, 3655121666u, 0u, 7581702372913784414ull, 376268820u, 0u, 2940585895977631614ull, 3314504360u, 0u, 7823930076253903428ull, 1427984966u, 0u, 1973272758837940390ull, 557583092u, 0u, 12890778468059469716ull, 1647127316u, 0u, 2449697774843583514ull, 3299853054u, 0u, 16716905873138200466ull, 4021231424u, 0u, 3267857381804395332ull, 2654427882u, 0u, 1851149807587169716ull, 3056592481u, 0u, // 122 8701303240306580586ull, 733007476u, 0u, 7637331001634773368ull, 3656919009u, 0u, 15630295779505437450ull, 2955022184u, 0u, 10218125820826539560ull, 2532566153u, 0u, 12966726072526905258ull, 2998458247u, 0u, 15265977032383277154ull, 600712696u, 0u, 6071736125818321572ull, 4130941918u, 0u, 8885721284901020768ull, 2033250446u, 0u, 12876759701435670900ull, 4094080286u, 0u, 1630842067377189496ull, 3273628547u, 0u, 10437415086434772922ull, 2225156184u, 0u, 6901464913782451440ull, 386698923u, 0u, 16289750282814607806ull, 2117613955u, 0u, 7377842888628115300ull, 2876082617u, 0u, 6741318350388982198ull, 1083926044u, 0u, 5806673100122274330ull, 3044027103u, 0u, 16300828535508193038ull, 1625685461u, 0u, 15057841097465878318ull, 3944726154u, 0u, 5542986725259932738ull, 3226426189u, 0u, 999724468134459526ull, 4291584536u, 0u, 3632182639958937690ull, 1096516245u, 0u, 17008750299981618068ull, 2504881835u, 0u, 12605027551811413882ull, 1482850476u, 0u, 16799695178199558920ull, 3112761303u, 0u, 1133339784987395052ull, 397512490u, 0u, 12437956562888769514ull, 1396147188u, 0u, 8465611667770595550ull, 649530298u, 0u, 7262760812226493820ull, 869362229u, 0u, 3030287389664072064ull, 3354554250u, 0u, 16194317515161722146ull, 2635578301u, 0u, 8561819858439098974ull, 2842275065u, 0u, 10317530617112958808ull, 939208226u, 0u, // 123 2718035145920744172ull, 2609940434u, 0u, 10881345198838169292ull, 3937115092u, 0u, 12903716568089634596ull, 1875236003u, 0u, 3245419273815283384ull, 3796155582u, 0u, 5974924486481845304ull, 2925423251u, 0u, 4764526415002518770ull, 3145356954u, 0u, 199593520001105778ull, 1197965076u, 0u, 15561043688339900518ull, 1864750080u, 0u, 16138350471368485954ull, 61927185u, 0u, 9273327531016374262ull, 926314622u, 0u, 2810895372423188284ull, 3834152917u, 0u, 8358539092862036654ull, 216795744u, 0u, 3685005378973043472ull, 443342591u, 0u, 17802623785314224090ull, 3039548143u, 0u, 3741315064779898432ull, 2554616848u, 0u, 18034290028025362618ull, 1019320205u, 0u, 276909472275882688ull, 292883411u, 0u, 4613368751216343524ull, 3074752900u, 0u, 1090948175633342574ull, 301741091u, 0u, 10600151183713350036ull, 1916227690u, 0u, 11973376642147275458ull, 593712118u, 0u, 17186555067601890632ull, 2590560055u, 0u, 16311085077619412962ull, 3637032533u, 0u, 17586092402104986854ull, 4279698998u, 0u, 373551566242584172ull, 2310960404u, 0u, 2445143499630571020ull, 2927972060u, 0u, 2871583019322549866ull, 2670423373u, 0u, 7215085630139793988ull, 2152120471u, 0u, 15216599648718840478ull, 1098347558u, 0u, 3769933526222411690ull, 3636570918u, 0u, 1613785135029772164ull, 2777450150u, 0u, 14250904836650763132ull, 1426546676u, 0u, // 124 1148960923586711626ull, 2246828907u, 0u, 11139515706194254210ull, 3214026829u, 0u, 8729656334801734564ull, 3791528078u, 0u, 2555942358767178224ull, 4243761586u, 0u, 15615696426660276524ull, 2545869153u, 0u, 15490277310810376412ull, 2305686520u, 0u, 14005526003536429540ull, 2353313879u, 0u, 18122966439203706838ull, 4126568448u, 0u, 5141488340131428822ull, 1393866951u, 0u, 10687870775407131554ull, 1627594154u, 0u, 2589176439744133138ull, 2200476909u, 0u, 9170758798156064070ull, 3034995808u, 0u, 13279632420772133450ull, 518911808u, 0u, 9565788491671933600ull, 65248942u, 0u, 14751262644160015844ull, 1557100317u, 0u, 17221916814683332404ull, 2350514293u, 0u, 1796518804737569132ull, 271978005u, 0u, 9440755237744431894ull, 2425678249u, 0u, 15438018124862733946ull, 2528812455u, 0u, 17694660928485084488ull, 4217430156u, 0u, 6613105272044594794ull, 489373249u, 0u, 5834768496551966970ull, 4095445108u, 0u, 3299024941861480090ull, 204232555u, 0u, 13537806098884995674ull, 2282239251u, 0u, 16935863244276378788ull, 2933670553u, 0u, 9592219863306858410ull, 2085099986u, 0u, 6077187529124994734ull, 3874264564u, 0u, 7426994769239001816ull, 2011443244u, 0u, 12565507185603285226ull, 1286032438u, 0u, 14045327800877665988ull, 2147096299u, 0u, 15150936375195921562ull, 4185963178u, 0u, 4323689898177776694ull, 1714453671u, 0u, // 125 8897026775215205382ull, 3329644848u, 0u, 16073008546299594422ull, 739579831u, 0u, 1606389051392785560ull, 1418429943u, 0u, 4090335535604832184ull, 2509037011u, 0u, 13094412955365190302ull, 331725337u, 0u, 1296574227852163398ull, 3871089845u, 0u, 14312002096041221392ull, 1163805931u, 0u, 986972452413738432ull, 1409857744u, 0u, 7262024100768845554ull, 1272239791u, 0u, 5785890503317299152ull, 3137423148u, 0u, 11321945938772967690ull, 1591308236u, 0u, 6646690857091344022ull, 3612126468u, 0u, 16803521573955265290ull, 477067167u, 0u, 11824953059130702356ull, 1184152907u, 0u, 8537959008398415058ull, 3734890748u, 0u, 14718119216202983416ull, 1998918544u, 0u, 18165050943443646728ull, 1268815827u, 0u, 13730486241439733768ull, 3505505811u, 0u, 5407647415746329688ull, 1608011668u, 0u, 5449916790945462626ull, 986804857u, 0u, 16357403097170048912ull, 4128791928u, 0u, 18417468178950227776ull, 2587547707u, 0u, 13117576823967287072ull, 916126794u, 0u, 17401143904138435290ull, 2746985278u, 0u, 10207177179055500374ull, 699841070u, 0u, 15238053518189082284ull, 3194051231u, 0u, 1133599601922712296ull, 1216488998u, 0u, 11852594289170791592ull, 3933653412u, 0u, 7866594372905873532ull, 905108477u, 0u, 10047138465525320410ull, 414082439u, 0u, 11838883922936841320ull, 1685310561u, 0u, 8479487811988842110ull, 103417581u, 0u, // 126 8399827200540181644ull, 627017854u, 0u, 3681141842777903806ull, 3566018906u, 0u, 5777516546991257148ull, 2354247445u, 0u, 7833595692518028322ull, 830443592u, 0u, 10383652077070702686ull, 205188778u, 0u, 11944754898817422158ull, 2393485335u, 0u, 16161594101738291840ull, 87990130u, 0u, 12679804804211002756ull, 488335941u, 0u, 9130599428730102252ull, 2544378882u, 0u, 5053134919441898592ull, 1796416229u, 0u, 15236918512882623950ull, 3544452173u, 0u, 1201411178787092858ull, 1108807089u, 0u, 9124905981498087278ull, 3438923592u, 0u, 14612626677398423560ull, 2606998593u, 0u, 16560408865826232212ull, 4102750512u, 0u, 12261126950283414252ull, 502343880u, 0u, 17281211893582445698ull, 3871730395u, 0u, 16168886256569819244ull, 3330373860u, 0u, 3143771709649888638ull, 619763654u, 0u, 4662952415429956384ull, 698959090u, 0u, 595177636790642884ull, 1808456686u, 0u, 1045799697851578484ull, 698188603u, 0u, 18018026442957523706ull, 108735855u, 0u, 15217377375739926878ull, 2117742692u, 0u, 16636015753884087346ull, 2474915219u, 0u, 17838914632298750936ull, 3421120097u, 0u, 13053337460180366220ull, 765726068u, 0u, 5795898449614427114ull, 2802819291u, 0u, 4088800011457136744ull, 2608628396u, 0u, 8448554942535108648ull, 1370262735u, 0u, 7174605446218033950ull, 1178941949u, 0u, 4105347206457887438ull, 2239552839u, 0u, // 127 13448803607393653164ull, 3119584657u, 0u, 2680279041677838980ull, 1398837920u, 0u, 14050864442863258716ull, 568302776u, 0u, 15359185407938448750ull, 3152964800u, 0u, 15589532933077829762ull, 459759113u, 0u, 8140845460251414156ull, 2140184715u, 0u, 12790975067752565548ull, 1816139034u, 0u, 12852832271019063042ull, 3232021876u, 0u, 18128777820658428936ull, 1449110146u, 0u, 18185054802468365334ull, 2606502911u, 0u, 9723447994371396374ull, 532364373u, 0u, 12668260535022285698ull, 195542945u, 0u, 17956088761279365738ull, 714505718u, 0u, 11499463477151684436ull, 567611506u, 0u, 10494748930630543320ull, 1385442984u, 0u, 12327096980731054282ull, 1053137183u, 0u, 11473162844074316842ull, 394424663u, 0u, 2354413906930634858ull, 1279877520u, 0u, 1498242227404848900ull, 2483125114u, 0u, 8512486946865007216ull, 3362535871u, 0u, 8317733963882406296ull, 4193190744u, 0u, 9715813279819444236ull, 3115920572u, 0u, 16567779795330827640ull, 1704302722u, 0u, 3758711993966770500ull, 3143215792u, 0u, 17692370092163019064ull, 3463253280u, 0u, 410589635016403082ull, 4111164955u, 0u, 7122619031080485724ull, 1489337727u, 0u, 1667923188734605436ull, 631891852u, 0u, 2112677293827620282ull, 3872073263u, 0u, 769323163346737126ull, 2707601567u, 0u, 2143980936528167936ull, 1597653588u, 0u, 10103988742720486708ull, 1091026910u, 0u, // 128 9039536830012510722ull, 537296718u, 0u, 10418568447888865308ull, 2329184213u, 0u, 16511316811723571382ull, 1242181687u, 0u, 7323421039051065244ull, 2495167244u, 0u, 18111472368284553858ull, 5520895u, 0u, 8046602419629689890ull, 2606895378u, 0u, 6771784976495331170ull, 2622261739u, 0u, 18367697891209877722ull, 1217207376u, 0u, 18008436982715704120ull, 4210794899u, 0u, 13350313495803843084ull, 3798117956u, 0u, 13564194162991678248ull, 2639507588u, 0u, 11890520192870264430ull, 1441724361u, 0u, 10273077807899168774ull, 1116972056u, 0u, 17945672344481918642ull, 2977455535u, 0u, 16611047373584888820ull, 1762683093u, 0u, 11344690568941219840ull, 4040337429u, 0u, 17148575049363489394ull, 1212463274u, 0u, 16063332686464636438ull, 2638780494u, 0u, 15960463720483202340ull, 3655403755u, 0u, 5018550702732718920ull, 1642328886u, 0u, 4349277839859901490ull, 3881433321u, 0u, 6210828232641517958ull, 5615063u, 0u, 10421662111452660738ull, 1835564161u, 0u, 11441724107844351338ull, 3517262343u, 0u, 6384204838488086350ull, 4012777418u, 0u, 3453208512470241840ull, 2257149491u, 0u, 1111782618565505188ull, 1008229057u, 0u, 8050405294639234622ull, 1331026205u, 0u, 16337609453350907108ull, 2264847896u, 0u, 5641317841667102596ull, 903631758u, 0u, 12897370781727240862ull, 3951303476u, 0u, 2679020506492664366ull, 219875746u, 0u, // 129 1963278645461016614ull, 213112600u, 0u, 6505215029697612810ull, 4008229107u, 0u, 12598613654931184192ull, 2860827747u, 0u, 9897771476560839142ull, 1751424055u, 0u, 9029871995858227746ull, 3012687019u, 0u, 9786120815281876218ull, 2686875767u, 0u, 6394394788673707760ull, 963307538u, 0u, 6200716124481064506ull, 265414833u, 0u, 14036383086095695838ull, 1240161753u, 0u, 8834681094922574102ull, 4126767037u, 0u, 3253094683967179642ull, 2829327447u, 0u, 12469931243180113508ull, 3828550224u, 0u, 6809852205062932804ull, 1233917535u, 0u, 15827195519060830954ull, 3771915452u, 0u, 2166113435188421106ull, 2286358880u, 0u, 14257224320432836286ull, 292096495u, 0u, 14615473407842356028ull, 1101016557u, 0u, 13283371344572134278ull, 2995292938u, 0u, 6608548090722764138ull, 2531342634u, 0u, 18292254789521223082ull, 3515268414u, 0u, 12166110829136888852ull, 3365865485u, 0u, 2569643368031324808ull, 1060400481u, 0u, 3760477563813295036ull, 349230036u, 0u, 12468301935833915442ull, 3195056542u, 0u, 419884793505179456ull, 2492258096u, 0u, 9132483044306855738ull, 3279800225u, 0u, 15658957012312193056ull, 1864210412u, 0u, 16836135308061481052ull, 1316677387u, 0u, 1685478567882329352ull, 3837877203u, 0u, 16422663697191848200ull, 2787217494u, 0u, 8953982071212893164ull, 4093596014u, 0u, 6251126148388156466ull, 2531361267u, 0u, // 130 619315677762580512ull, 2186094413u, 0u, 14284859358630863828ull, 3056973099u, 0u, 16592335499208743396ull, 954386922u, 0u, 8047391394050460464ull, 4201387311u, 0u, 14813821320623781276ull, 2147576512u, 0u, 5894730337928573334ull, 1896313908u, 0u, 4287311281219145286ull, 4221331622u, 0u, 4885864034458923386ull, 3740548872u, 0u, 10961818821620754664ull, 3959703843u, 0u, 5921598507404610990ull, 2024778629u, 0u, 6107725158139432662ull, 1015218223u, 0u, 7976444262988058594ull, 116769287u, 0u, 15497862044751982916ull, 3155292339u, 0u, 2391369697985586904ull, 2645626035u, 0u, 6225020785210914428ull, 2760675634u, 0u, 7872442851816150098ull, 2212532068u, 0u, 6787666130504743016ull, 5376185u, 0u, 11166035573127657990ull, 3185600939u, 0u, 16987106967693672720ull, 3175302046u, 0u, 2064564314307528954ull, 2370169719u, 0u, 15029894902420101292ull, 2019345113u, 0u, 4075073720040284368ull, 1292573546u, 0u, 4442618397839339358ull, 3937505761u, 0u, 10876507202600569206ull, 1329088363u, 0u, 15464320807675430464ull, 3608794017u, 0u, 10667366588373631900ull, 269083461u, 0u, 6009947876284576138ull, 2562361670u, 0u, 4064234522751060748ull, 4027039244u, 0u, 6254114422812364270ull, 1927091989u, 0u, 1804585237140696970ull, 4091913652u, 0u, 6372845661425378146ull, 1020604882u, 0u, 16591122132969800968ull, 4041292312u, 0u, // 131 8711004812549123954ull, 1282128637u, 0u, 1909278649970394596ull, 3204021819u, 0u, 2899356864044645034ull, 3412819628u, 0u, 10117630710509875908ull, 2836589283u, 0u, 13353298629358386988ull, 1996784548u, 0u, 2990547695717465944ull, 3726046712u, 0u, 364304891474717838ull, 1469189708u, 0u, 6620027375399752512ull, 1114879014u, 0u, 15485875045859682ull, 3829057331u, 0u, 10135740976946219294ull, 1888614596u, 0u, 10738677042877455114ull, 2862866837u, 0u, 11281042176218424816ull, 433246613u, 0u, 17124131230138276084ull, 895869022u, 0u, 17824398477604695822ull, 3158358867u, 0u, 14634469555780270714ull, 1574687926u, 0u, 17945634429530795390ull, 223179302u, 0u, 13946072395334180214ull, 3829091255u, 0u, 2138645855999420628ull, 2182135747u, 0u, 13294259406293881284ull, 468438862u, 0u, 3252255004563481214ull, 3773773662u, 0u, 11853536142724257392ull, 3636452425u, 0u, 16151007072840447642ull, 1142443658u, 0u, 6362915919128661398ull, 4180801062u, 0u, 7369760547807795238ull, 3490357550u, 0u, 10736587807988877950ull, 104494302u, 0u, 18431994098329411048ull, 1921366113u, 0u, 9399214226535716726ull, 212529920u, 0u, 11638234022327951122ull, 211380373u, 0u, 3595827096950695654ull, 2618522912u, 0u, 1160652113159715646ull, 3540123680u, 0u, 1830646770975902720ull, 1246130471u, 0u, 17673883872911440902ull, 3738508774u, 0u, // 132 4841673108046683952ull, 4089746996u, 0u, 12933557324266148250ull, 466896994u, 0u, 13401373873781021552ull, 146981041u, 0u, 17195635636344099772ull, 622163878u, 0u, 9792951466133530422ull, 1142965856u, 0u, 3073671119019361076ull, 895529801u, 0u, 3568770743722790644ull, 1179270170u, 0u, 16722100405509923738ull, 4203865931u, 0u, 4937754092473165972ull, 666483135u, 0u, 2371270746343075328ull, 1271960030u, 0u, 7833463079622298108ull, 2503100633u, 0u, 5092039527841529996ull, 2623853407u, 0u, 17895788388154132276ull, 4091048879u, 0u, 5642789453567107830ull, 875476673u, 0u, 2225102117782842264ull, 2392364243u, 0u, 10244073129422269920ull, 3408388358u, 0u, 15120933928570132308ull, 1025375939u, 0u, 11341368434544258698ull, 3954476454u, 0u, 16756841012993662374ull, 3107804223u, 0u, 3395975572525450ull, 4100122630u, 0u, 7588846999223172430ull, 3327933532u, 0u, 4674171131648198248ull, 3224849101u, 0u, 1292837254406333606ull, 3988402971u, 0u, 7480384328386318140ull, 45825330u, 0u, 10527888337899454096ull, 1271430104u, 0u, 17014563845226484372ull, 4292432994u, 0u, 3688445250546789958ull, 410370748u, 0u, 14224714484182777496ull, 3914259265u, 0u, 7496442945526770330ull, 2278497296u, 0u, 9630537733093276840ull, 747844520u, 0u, 9621914380913612870ull, 2595811753u, 0u, 9919564823648763794ull, 401843891u, 0u, // 133 925685318274799068ull, 565488228u, 0u, 6384796078926352598ull, 7534957u, 0u, 8344041269446708024ull, 1744386924u, 0u, 18429919029485269434ull, 497763008u, 0u, 6198298413512305358ull, 1358511646u, 0u, 16847807809288083182ull, 1864748131u, 0u, 12585250098917871064ull, 400212075u, 0u, 11001789700089623356ull, 3147661913u, 0u, 11922452049837402910ull, 1567268754u, 0u, 5839326845218968068ull, 3099270434u, 0u, 17147150236299715436ull, 900085256u, 0u, 16813489620656041720ull, 3878613337u, 0u, 6473497000578614406ull, 4220287338u, 0u, 15125713138769678192ull, 3206783516u, 0u, 17425816294774404234ull, 3908478937u, 0u, 3243009955434246886ull, 3399504765u, 0u, 1304837423661538602ull, 3683951248u, 0u, 11770659570713201086ull, 337842268u, 0u, 15486390251061606270ull, 1477311913u, 0u, 11168489206296386432ull, 3230146071u, 0u, 13549162099515546734ull, 1408104229u, 0u, 10897283044692846108ull, 1027124743u, 0u, 2419985568603856406ull, 313808932u, 0u, 11419582866296713460ull, 3835647383u, 0u, 2866148629835821524ull, 2193061417u, 0u, 7419675732140132876ull, 118666849u, 0u, 11356184370237957950ull, 2704171846u, 0u, 14023183882512170856ull, 3296607460u, 0u, 5415460491547094994ull, 2146581883u, 0u, 1642887388176605586ull, 3959977255u, 0u, 17062257408238867504ull, 537212621u, 0u, 3271904746103642060ull, 2954439613u, 0u, // 134 12956854275439902036ull, 1101149418u, 0u, 15537428229543057848ull, 2408706713u, 0u, 3377702820696149148ull, 1372409350u, 0u, 14040355155384013612ull, 1683585461u, 0u, 1640336874735840054ull, 2847826212u, 0u, 9701038416943106104ull, 854837269u, 0u, 7335076045525874544ull, 1315184405u, 0u, 5805923006054944450ull, 1072163818u, 0u, 2751995742396151178ull, 2065235477u, 0u, 5357723359621355860ull, 2741070815u, 0u, 16908299496792749060ull, 19733017u, 0u, 14767332876439978018ull, 1671383566u, 0u, 3171879589722939872ull, 2821117029u, 0u, 5897323545362801826ull, 3532031015u, 0u, 14183167335020798046ull, 982870623u, 0u, 14820108970530107092ull, 1572178764u, 0u, 18360701434111721350ull, 2064932478u, 0u, 7700700285987010598ull, 1842892657u, 0u, 4122648316498204202ull, 3549660382u, 0u, 18146731146584744356ull, 2983888734u, 0u, 7449761708017357386ull, 3739037855u, 0u, 15452473698771856720ull, 3526289398u, 0u, 6368687703053832158ull, 3465429720u, 0u, 7086786968184332344ull, 2232309742u, 0u, 3574621925742899668ull, 3295890189u, 0u, 13661031969117738092ull, 2414189003u, 0u, 8359555195970777454ull, 1689651167u, 0u, 8866709735843737082ull, 2215671624u, 0u, 14112056004165322134ull, 2344805125u, 0u, 4931387129270930986ull, 4026339556u, 0u, 2923755262425375144ull, 210715284u, 0u, 8541316414446415454ull, 618700961u, 0u, // 135 5634343559011575900ull, 2388645913u, 0u, 10353658900105835212ull, 2015221083u, 0u, 11585825568994555900ull, 3539950824u, 0u, 4362476314559155506ull, 947829461u, 0u, 568416434657351852ull, 37677791u, 0u, 8025258035735125434ull, 4227343884u, 0u, 5362431344813091450ull, 2330276611u, 0u, 709008383255503158ull, 1131321575u, 0u, 6261123932044166504ull, 570092257u, 0u, 2858357511529420380ull, 3535169177u, 0u, 2470971998130209142ull, 3399919734u, 0u, 1108151265936872024ull, 1601169105u, 0u, 7402477026418834216ull, 2505498128u, 0u, 14671286458158259588ull, 3305539750u, 0u, 9175835307969559074ull, 1682971544u, 0u, 16863343793050909702ull, 934988775u, 0u, 17061101784282107034ull, 1753536563u, 0u, 5847011503868809338ull, 2129283819u, 0u, 5850109681760726852ull, 379345395u, 0u, 6150701550612291884ull, 260459518u, 0u, 11723402000754995944ull, 1217075474u, 0u, 3124223940506911728ull, 1632494978u, 0u, 7893014655280377780ull, 5806740u, 0u, 2173816246308052408ull, 1324756217u, 0u, 17952785606474119238ull, 2426870007u, 0u, 8898568655976812606ull, 1254579881u, 0u, 10487736494614704360ull, 2619785017u, 0u, 8829117890431968018ull, 951387365u, 0u, 4056494691275697828ull, 3377566086u, 0u, 9564198271753794626ull, 75716810u, 0u, 5634800378089491580ull, 1256235095u, 0u, 8916507266357556870ull, 303931609u, 0u, // 136 7346661416102445516ull, 3836618890u, 0u, 15272634876140863788ull, 702669346u, 0u, 3163947776764168238ull, 4172720107u, 0u, 3485667483246143220ull, 2489637381u, 0u, 3775758050080714160ull, 3306270028u, 0u, 10640229378678245622ull, 2215382065u, 0u, 6785559389642076700ull, 98895965u, 0u, 14451707069301137920ull, 4026019630u, 0u, 860496559700956610ull, 3054072716u, 0u, 15741113973386590608ull, 1113461142u, 0u, 11971132647684049574ull, 877702822u, 0u, 3719046066105514298ull, 661409899u, 0u, 1466938696365591010ull, 3256399669u, 0u, 198241847591200266ull, 2209420166u, 0u, 17495789912024542246ull, 1671379053u, 0u, 18012122846593789516ull, 1629737437u, 0u, 15375089777759231930ull, 3965348676u, 0u, 10196121474480879514ull, 3506498418u, 0u, 7675174754313116324ull, 1531887763u, 0u, 3448853042305968992ull, 2421244995u, 0u, 15791140355701655502ull, 884609789u, 0u, 4359237449619535952ull, 2582308750u, 0u, 8237726756426475138ull, 2357207219u, 0u, 18076954502321000896ull, 3645762404u, 0u, 9562663196655939700ull, 1512736866u, 0u, 6924731232495595910ull, 359109471u, 0u, 13956837297845193510ull, 958851290u, 0u, 652901972172286956ull, 50719620u, 0u, 10342973646710553784ull, 1654593091u, 0u, 9367586147142425306ull, 2129474515u, 0u, 583337072250289838ull, 1977224526u, 0u, 9255006856742354494ull, 3292194430u, 0u, // 137 5198342648135569978ull, 2336878968u, 0u, 5326937084184793738ull, 3950823108u, 0u, 4426315329978498752ull, 1576495328u, 0u, 6257153533628928024ull, 2508880211u, 0u, 10697504927964020796ull, 2809771648u, 0u, 7457266764108991056ull, 1285482047u, 0u, 9033135833543791668ull, 189852743u, 0u, 4763001207244268710ull, 609459582u, 0u, 4067469797337544420ull, 3781545766u, 0u, 3932063829173206640ull, 542476351u, 0u, 12413809935378917720ull, 14021373u, 0u, 1528095908904788568ull, 4196146532u, 0u, 16976315549644099298ull, 2795333122u, 0u, 17936277343096209472ull, 3735952570u, 0u, 12263365486789406806ull, 84612044u, 0u, 9681917094900622328ull, 3802074090u, 0u, 2188318899509125918ull, 3486536104u, 0u, 7045741019394519118ull, 3219767427u, 0u, 13406144618670521942ull, 732124116u, 0u, 16024491763416413932ull, 2313834346u, 0u, 12070648923406093108ull, 221659512u, 0u, 16375294848810789066ull, 3781280773u, 0u, 2868938240464210948ull, 1935502126u, 0u, 4644820610160364326ull, 695230870u, 0u, 5680912158342736502ull, 3904180178u, 0u, 11023781328997778562ull, 1178668917u, 0u, 15508249795495157742ull, 837193458u, 0u, 5196378614659162066ull, 3837382875u, 0u, 12204691768461763190ull, 162245042u, 0u, 6228910577502447148ull, 13389126u, 0u, 4523635823077359354ull, 783595588u, 0u, 16426301053898204904ull, 1754743656u, 0u, // 138 587355264594178962ull, 4237238068u, 0u, 11815369247850415818ull, 445929285u, 0u, 476326847657108796ull, 53843162u, 0u, 16147713090653149666ull, 3729202814u, 0u, 751589798731288290ull, 2444225475u, 0u, 11588870463339759148ull, 1491072845u, 0u, 17917854768043918244ull, 1725421102u, 0u, 16635478680137378418ull, 2161558037u, 0u, 1666318530987832096ull, 1193238244u, 0u, 3546537193254966680ull, 2411020958u, 0u, 406458331368927380ull, 3426343456u, 0u, 6155913189660407384ull, 3868786054u, 0u, 9548299803624691748ull, 1216907772u, 0u, 1928548986115489370ull, 4137590792u, 0u, 7976949446089058270ull, 1295711825u, 0u, 3778342862259385270ull, 2966356534u, 0u, 18382439396499546202ull, 351675691u, 0u, 2003541025505224860ull, 1413815859u, 0u, 15710823523951584124ull, 2854106477u, 0u, 17112196808269149532ull, 122654157u, 0u, 11119221828053080878ull, 272690600u, 0u, 11555844175691260978ull, 2447036904u, 0u, 8693674477911387582ull, 1977884290u, 0u, 9510297816878945562ull, 1189203188u, 0u, 3230601349649715656ull, 647417297u, 0u, 9241511513763428132ull, 2277081847u, 0u, 4371990710057505518ull, 2263843615u, 0u, 10568431966174346892ull, 1482616056u, 0u, 8913115803761258522ull, 568978266u, 0u, 5460290363207127798ull, 2141504456u, 0u, 974693594035470ull, 3371586798u, 0u, 1568320599843652316ull, 2587179801u, 0u, // 139 2998656200421943894ull, 2585341031u, 0u, 12650322163439086098ull, 847181355u, 0u, 1841825459382326490ull, 2159195430u, 0u, 17418630288014066120ull, 3960724470u, 0u, 14343329968369922182ull, 1683783444u, 0u, 10875032017919934782ull, 1201443790u, 0u, 10349669821878310104ull, 3952271839u, 0u, 2734056227566320948ull, 201770057u, 0u, 108214177234356004ull, 2565181826u, 0u, 13111668715994418616ull, 2594652313u, 0u, 2082371168151495650ull, 3547470891u, 0u, 14951693278024616194ull, 624430515u, 0u, 11615163721553086180ull, 541474856u, 0u, 9078924500227757422ull, 1922957050u, 0u, 7621482454599794022ull, 199353423u, 0u, 8699205570316733008ull, 309526207u, 0u, 8349326860412993554ull, 1574030886u, 0u, 14380958884377461142ull, 3101818357u, 0u, 13791477864907066222ull, 668353175u, 0u, 15860223028727802900ull, 4219971158u, 0u, 17149617343221137848ull, 2892597863u, 0u, 11837849758884668406ull, 1030265785u, 0u, 8049226722878150108ull, 2161893032u, 0u, 1203278077776386842ull, 2388801003u, 0u, 9073513551142310526ull, 1263621362u, 0u, 5578401077242402986ull, 34086702u, 0u, 15216039138837979892ull, 4232092587u, 0u, 17954747702991810322ull, 3386456117u, 0u, 12039558246604888024ull, 962706277u, 0u, 16779563934930360866ull, 393767597u, 0u, 9860811215280077548ull, 630880043u, 0u, 6995401029927020194ull, 2268799938u, 0u, // 140 17582067774123457590ull, 867270417u, 0u, 4837130344966330766ull, 3294785060u, 0u, 16561728449354095140ull, 2856025357u, 0u, 10473809543840044996ull, 3101623756u, 0u, 8298183909780437058ull, 1053232402u, 0u, 6480702549201742350ull, 3515415553u, 0u, 16763537827328985678ull, 2055226248u, 0u, 7703525094259179270ull, 2611916121u, 0u, 2408199466653813234ull, 3718704213u, 0u, 16793733760538054186ull, 2718413595u, 0u, 1693291771954179136ull, 290699059u, 0u, 17390466914683017500ull, 3583771747u, 0u, 12880091940199442154ull, 1787967118u, 0u, 13627187734148526340ull, 1495066620u, 0u, 4546743225284295414ull, 3152274127u, 0u, 17080573540859572820ull, 399671959u, 0u, 17692401879837513026ull, 417901100u, 0u, 8318961619419866558ull, 3227763120u, 0u, 18371128035085241040ull, 510697041u, 0u, 17470660186591948028ull, 2438901893u, 0u, 16305952216529694674ull, 346045929u, 0u, 15484896183877072858ull, 2784338001u, 0u, 13877265866326493272ull, 2026356336u, 0u, 8631520781095078330ull, 959211640u, 0u, 769814977677482116ull, 2127570235u, 0u, 13320725497439488688ull, 4037122717u, 0u, 14059314713979468226ull, 1973976432u, 0u, 16506784755108880342ull, 638748638u, 0u, 3854379295551050070ull, 2650032196u, 0u, 12717077552382827050ull, 3724908935u, 0u, 13320617945333920570ull, 2834055063u, 0u, 9089253629122040904ull, 3747087181u, 0u, // 141 3696179089781430716ull, 471676039u, 0u, 4581979409096982572ull, 3180391245u, 0u, 5210122849014020242ull, 1695890768u, 0u, 5361432833089460046ull, 4232579493u, 0u, 16923631166116114224ull, 2055862703u, 0u, 5971040962048186964ull, 1840056973u, 0u, 879712380960133306ull, 1468940550u, 0u, 11949507261675694192ull, 2295455459u, 0u, 16991443873738071460ull, 1436729020u, 0u, 1873246308885223636ull, 965669381u, 0u, 1970789643263155236ull, 1228950790u, 0u, 17630805127843461558ull, 2928847748u, 0u, 14871671940452831052ull, 3254844377u, 0u, 18178936883439329934ull, 1903229151u, 0u, 8801532411943397528ull, 1389060763u, 0u, 14301755491967337576ull, 81626737u, 0u, 16219780117012441312ull, 3847599440u, 0u, 2814183034289980920ull, 3806035679u, 0u, 572737308651732302ull, 1083161447u, 0u, 8769325709106324882ull, 3797158528u, 0u, 12954503071990027014ull, 3175374403u, 0u, 9827352799952962954ull, 903426128u, 0u, 9530715135426314408ull, 1257514030u, 0u, 3499282190510668632ull, 2749675009u, 0u, 10502376257249733294ull, 2475000175u, 0u, 6262474015193893294ull, 4121218142u, 0u, 15855282669698100334ull, 2326615036u, 0u, 2265534543956450374ull, 1936848578u, 0u, 15099089163117884364ull, 3020353850u, 0u, 8679179259424173306ull, 393537483u, 0u, 10192730399649564690ull, 3957341439u, 0u, 10625318590028786842ull, 2894621283u, 0u, // 142 3994105882215407594ull, 1019085328u, 0u, 9699264887694947248ull, 1945822941u, 0u, 2399260531809384734ull, 3930460575u, 0u, 7790929055575805940ull, 1138887837u, 0u, 2858219861170284286ull, 1566983849u, 0u, 5704429369088661460ull, 1961869138u, 0u, 3540569724712146462ull, 3546991938u, 0u, 4936859659588382630ull, 1147622689u, 0u, 14038451476419609064ull, 3102689073u, 0u, 12993312638984448238ull, 1988996284u, 0u, 14104554184295309662ull, 2469789196u, 0u, 5338390605849545126ull, 3625341384u, 0u, 13072548150977671440ull, 597295056u, 0u, 15375599802433940562ull, 3227448185u, 0u, 12682566487037875332ull, 32915665u, 0u, 14949953261724526408ull, 2235176297u, 0u, 13364747912655510604ull, 3840403365u, 0u, 6893695839681311822ull, 3131282200u, 0u, 14162348347812605646ull, 2845402083u, 0u, 10746661146397586144ull, 483522486u, 0u, 4435397708616444908ull, 2764020621u, 0u, 14793655976010207440ull, 3209523578u, 0u, 167286767561125534ull, 320230119u, 0u, 2879955631411304860ull, 351028776u, 0u, 10338442418453022630ull, 220118693u, 0u, 9914498582022222910ull, 3424984918u, 0u, 1405070643265758336ull, 1762890858u, 0u, 17698351299227872106ull, 1509084908u, 0u, 10732748290728725644ull, 1626062109u, 0u, 17425987143998801928ull, 119341372u, 0u, 15105308270508967544ull, 782683992u, 0u, 2760544925052573082ull, 2158179430u, 0u, // 143 6409125497551238132ull, 4291928181u, 0u, 16739071939552229006ull, 3567733651u, 0u, 8814138687966319288ull, 2247384110u, 0u, 5012393790283928630ull, 2949606872u, 0u, 9737704384559441094ull, 2747006367u, 0u, 7957169781632971480ull, 2780499523u, 0u, 9793479881929514482ull, 3635856719u, 0u, 14376343744212385990ull, 1278219133u, 0u, 1660942264780696188ull, 1577510078u, 0u, 18109801383599772518ull, 2384385575u, 0u, 16680210559213606466ull, 4256761401u, 0u, 8440220179674194758ull, 1280426743u, 0u, 16324285466641949612ull, 3537933129u, 0u, 1558958099521926784ull, 170842541u, 0u, 13705202443951567354ull, 4245008641u, 0u, 3785431380993743308ull, 1054197396u, 0u, 268057651692505326ull, 2056434592u, 0u, 16268309449327736918ull, 107483u, 0u, 3419318606455871450ull, 2938634649u, 0u, 17250922050048824194ull, 957436740u, 0u, 13452823098222446006ull, 456217516u, 0u, 8111593908442336270ull, 3230084460u, 0u, 12663591162524453150ull, 2239211824u, 0u, 994531564884402218ull, 1391861392u, 0u, 4597466118498396224ull, 1165123472u, 0u, 17215608093155633218ull, 3655320259u, 0u, 3310904227358624088ull, 3661113758u, 0u, 9370894020103922156ull, 812182181u, 0u, 17950029806401197744ull, 4029349817u, 0u, 17603326143422766456ull, 4162505169u, 0u, 1156012202268385704ull, 3653456715u, 0u, 6012426199536569122ull, 838329365u, 0u, // 144 14263921152759925444ull, 3198462516u, 0u, 14566791071718942250ull, 2068595467u, 0u, 890217499964653492ull, 3870102034u, 0u, 2546263557799992800ull, 699706607u, 0u, 11382391924181370608ull, 813743890u, 0u, 2421903016490579424ull, 2855484783u, 0u, 3033016508582151276ull, 3004551612u, 0u, 5547418250771820892ull, 2359450604u, 0u, 508740499078001244ull, 1838769952u, 0u, 1538419969959155752ull, 173792964u, 0u, 14640272894406556970ull, 2838959319u, 0u, 2109807099927780524ull, 788123717u, 0u, 10815415971180824742ull, 3525135542u, 0u, 13601526117179031746ull, 1545919526u, 0u, 9803061689443752262ull, 2722327892u, 0u, 10568218244586595456ull, 1939563199u, 0u, 31172593132608840ull, 1955836137u, 0u, 6669989905054508136ull, 1104611635u, 0u, 14257724372749639506ull, 2241765367u, 0u, 5990144166744013562ull, 3338053108u, 0u, 13034915736890144764ull, 550124129u, 0u, 2155102653335146098ull, 504431420u, 0u, 3260505600300581226ull, 2098832762u, 0u, 1233196752089994082ull, 3354441469u, 0u, 9856769293294183104ull, 1551411160u, 0u, 12921692072053182838ull, 4110558479u, 0u, 17831987437646432160ull, 543729816u, 0u, 15843533492320115150ull, 3063089219u, 0u, 5767972526903173560ull, 3346272917u, 0u, 13110381249899949422ull, 4183034050u, 0u, 2059475925956756750ull, 1477622839u, 0u, 11817034303675327956ull, 1043818670u, 0u, // 145 7149455010340630584ull, 4252138842u, 0u, 12108310342032855350ull, 926291592u, 0u, 17810261448920126716ull, 3544957206u, 0u, 489967756849823654ull, 3465729960u, 0u, 7357637206733482828ull, 3809984761u, 0u, 17299181074642680124ull, 3596880878u, 0u, 9166793136706387444ull, 1626068117u, 0u, 1355089935069334516ull, 2583541818u, 0u, 8363246247138719306ull, 260799924u, 0u, 17404111696379238164ull, 1875438085u, 0u, 2539774274838400582ull, 2663002214u, 0u, 2300536811832445668ull, 2807269210u, 0u, 1474776076594931894ull, 1939613332u, 0u, 7399960417863175648ull, 2719866886u, 0u, 498495523847159144ull, 1361723492u, 0u, 61074799309795476ull, 2690770111u, 0u, 17345751887489815062ull, 222383347u, 0u, 12711724878005774378ull, 2123135425u, 0u, 3143796855814963474ull, 55124424u, 0u, 13123038564672067074ull, 1331456530u, 0u, 7231639130103805968ull, 1525442731u, 0u, 17720598802604426576ull, 857321076u, 0u, 15752534023307598190ull, 900688487u, 0u, 5528394735034491242ull, 3166127017u, 0u, 8512009711042075938ull, 1474143070u, 0u, 18271426178097389798ull, 2962074547u, 0u, 12387163932949906588ull, 102719414u, 0u, 9683312957948991678ull, 1840636708u, 0u, 5753823439607607888ull, 1406517115u, 0u, 5346734974354607028ull, 2286347453u, 0u, 13639134384599263694ull, 2252337974u, 0u, 9421400269838883998ull, 1179424107u, 0u, // 146 10018589921787812148ull, 1625576185u, 0u, 13102754596341083628ull, 811209489u, 0u, 9743895168884452164ull, 2641238431u, 0u, 9882657358743564868ull, 1821940765u, 0u, 12959966221250885634ull, 918740125u, 0u, 6605975932744070184ull, 555678293u, 0u, 3415486311465742850ull, 21066613u, 0u, 5461495507104248402ull, 4269883016u, 0u, 15557879805450219646ull, 4009972220u, 0u, 11015628424514866834ull, 1131466890u, 0u, 12371849926627109270ull, 545544481u, 0u, 17186165479622776436ull, 3932201703u, 0u, 8451581370603967782ull, 2979330046u, 0u, 12619095650769830798ull, 1849472470u, 0u, 15341075469364267310ull, 3183371445u, 0u, 4870330734205837486ull, 1552950030u, 0u, 11208669981719376202ull, 1844184742u, 0u, 7790748375760350626ull, 2088283592u, 0u, 2801098916649322212ull, 4220779507u, 0u, 18024161372503446800ull, 753530834u, 0u, 15947067419090307006ull, 1611632547u, 0u, 12195617598447290068ull, 212226251u, 0u, 4827120443629313210ull, 3284439906u, 0u, 12364280395598943726ull, 1975601157u, 0u, 4480566754444386976ull, 4229093847u, 0u, 9600481940666303534ull, 3264867081u, 0u, 9370134459182444780ull, 3489521046u, 0u, 13207377975215868104ull, 3475107583u, 0u, 9905688791403092706ull, 887286538u, 0u, 14409484869160138482ull, 2615590651u, 0u, 11981636641115532870ull, 868959175u, 0u, 12038112174224842980ull, 2621468108u, 0u, // 147 7710216235340022516ull, 3439695902u, 0u, 9377010943261206288ull, 3558870969u, 0u, 12231542642299829106ull, 3993179059u, 0u, 848337503198540686ull, 1461243231u, 0u, 14810574864179785510ull, 446842360u, 0u, 6487135612161500322ull, 2829691929u, 0u, 5235245298925832902ull, 1250304701u, 0u, 15766124578683597100ull, 943840231u, 0u, 7419139883797683760ull, 700487969u, 0u, 9981771792589704476ull, 2864503631u, 0u, 5509585766393940066ull, 225137246u, 0u, 17114077890744043952ull, 4118441263u, 0u, 6759498513630900568ull, 2996217767u, 0u, 14295290019651695654ull, 2775403021u, 0u, 9748854971418608568ull, 4161764185u, 0u, 5506667148799737916ull, 4047734732u, 0u, 10939565145077366706ull, 1743956283u, 0u, 15976501175646507246ull, 536764803u, 0u, 1374007037092049814ull, 2794813747u, 0u, 12572976249296256650ull, 1918505687u, 0u, 16288615267348908030ull, 4175876174u, 0u, 17855339427529387836ull, 2630496375u, 0u, 16504157920381900934ull, 1306490126u, 0u, 2650527864027873238ull, 1466757491u, 0u, 5472868388180155628ull, 2546691076u, 0u, 5916925087438651138ull, 130338200u, 0u, 16439695976286888026ull, 1486866682u, 0u, 555818212085578568ull, 1780264976u, 0u, 1309875882013465042ull, 3180862364u, 0u, 5830745972405922848ull, 442482672u, 0u, 5744473957604116878ull, 1521037102u, 0u, 12150388938808996764ull, 3009923894u, 0u, // 148 1915756942759381640ull, 834206584u, 0u, 11421760469298313784ull, 419211955u, 0u, 616177970270585142ull, 3278877097u, 0u, 17297503468857513878ull, 2500714009u, 0u, 4801546146335460256ull, 4235318247u, 0u, 5457784346242259922ull, 1316097216u, 0u, 15143471726677187758ull, 3414181417u, 0u, 17801721238528813270ull, 1296890581u, 0u, 4131481980066958208ull, 1354541293u, 0u, 4556267048103053980ull, 522274134u, 0u, 7481216808461786620ull, 1549919800u, 0u, 10151108582289484500ull, 295553622u, 0u, 14960801784453195996ull, 1181333402u, 0u, 14355200678753986222ull, 2443775864u, 0u, 11537236735719135310ull, 1295484230u, 0u, 13341953711580093276ull, 3080766676u, 0u, 7783876087539789648ull, 2954462048u, 0u, 1763147297048178442ull, 1833663498u, 0u, 9716102611065803900ull, 2100356301u, 0u, 4450058350583090956ull, 2589933556u, 0u, 18428258408202889974ull, 2128418101u, 0u, 4251167991408710464ull, 347438254u, 0u, 17521351170127908148ull, 3108961524u, 0u, 7372736213641381336ull, 2517779696u, 0u, 18204439750705593322ull, 3518535265u, 0u, 10291261130978821700ull, 4146343713u, 0u, 13160095520549514406ull, 2856987572u, 0u, 44480903743767078ull, 2318607234u, 0u, 1029493808233931276ull, 3090831759u, 0u, 11176560906315460946ull, 1428748936u, 0u, 8409448956863660806ull, 3506241579u, 0u, 8669852338148257516ull, 3483604911u, 0u, // 149 1257471418108026728ull, 2185696636u, 0u, 14069033361770025682ull, 552624582u, 0u, 2664399226165629758ull, 747677637u, 0u, 6778086756927354648ull, 2002275869u, 0u, 2759334666594843108ull, 1898258608u, 0u, 5120464816349998066ull, 834759679u, 0u, 703567009088969580ull, 3946429655u, 0u, 9476132657309069688ull, 2128392439u, 0u, 15329768663443992546ull, 554783905u, 0u, 2407190970985285398ull, 565588412u, 0u, 2008927443759177126ull, 4037498534u, 0u, 1243654725062490486ull, 2126583147u, 0u, 13276332816071727820ull, 1436601129u, 0u, 13972888800599480160ull, 195289341u, 0u, 6393520335762856296ull, 3086612862u, 0u, 10749175949879636792ull, 853322333u, 0u, 5247519171477581218ull, 2329463224u, 0u, 17860798393461561040ull, 1381514301u, 0u, 9970704314073474734ull, 3830298166u, 0u, 12400479269481218930ull, 2694639798u, 0u, 181929188108581666ull, 3689744671u, 0u, 17319887844674012184ull, 296068319u, 0u, 4463199245511087244ull, 3526923146u, 0u, 10486111729839468434ull, 775217315u, 0u, 7243680233142804300ull, 3515959302u, 0u, 5846362340980111884ull, 1432395248u, 0u, 12935540334891694546ull, 643910631u, 0u, 8996587809106337650ull, 3364047163u, 0u, 7185882321290010618ull, 4024661045u, 0u, 1968807381523934102ull, 936174998u, 0u, 5426520443975708944ull, 2509780937u, 0u, 17518722408991689022ull, 3932434990u, 0u, // 150 13833915116255130690ull, 1060012232u, 0u, 16016834217892741594ull, 1060763294u, 0u, 37493982406302264ull, 3343257001u, 0u, 2180425014599052722ull, 3553436417u, 0u, 15024937190280179064ull, 3321888752u, 0u, 12663571519651915134ull, 119391174u, 0u, 11480288531157712380ull, 1904988132u, 0u, 426630591828003564ull, 2935535183u, 0u, 1203000009698153180ull, 1140986201u, 0u, 9323639212638344462ull, 1465233240u, 0u, 4078384683022206528ull, 2407187419u, 0u, 11731629498440701952ull, 3099040651u, 0u, 6643914256021639818ull, 2441341511u, 0u, 9504750599727055662ull, 2774901182u, 0u, 5602315854343925988ull, 3762189709u, 0u, 6550648564214399620ull, 483209934u, 0u, 7041822315651609352ull, 460740448u, 0u, 2512611119768049346ull, 2530464153u, 0u, 9505874825447840246ull, 401661021u, 0u, 3954293914121060752ull, 2949249742u, 0u, 14460334842418626756ull, 1938455922u, 0u, 239435286256759588ull, 75007478u, 0u, 7555268351185760856ull, 4228446634u, 0u, 17151612151788108202ull, 1483774161u, 0u, 16983819483990155844ull, 2735436322u, 0u, 7912369122339040330ull, 4278663335u, 0u, 18221002649333861566ull, 2051157362u, 0u, 2309655554278562966ull, 2108997007u, 0u, 4620250596464839984ull, 4046389910u, 0u, 3959556427970797590ull, 3229343243u, 0u, 10922428155387137120ull, 3628636732u, 0u, 2494421804813328728ull, 3299689026u, 0u, // 151 9684186734662751470ull, 2392578577u, 0u, 11757079192980909252ull, 2233604183u, 0u, 3003192373524060826ull, 3661164604u, 0u, 10232436260764900276ull, 1971590508u, 0u, 2070670242345541810ull, 2742063417u, 0u, 928029363719451902ull, 1114292979u, 0u, 1524943139253043030ull, 1378598943u, 0u, 14299406644758703294ull, 799165822u, 0u, 5265575463067868460ull, 30862829u, 0u, 15174556400274404530ull, 2796175546u, 0u, 17321541098200839410ull, 919262352u, 0u, 16095449059908072510ull, 3220307001u, 0u, 14357146868822300174ull, 3734955384u, 0u, 11204955548653607422ull, 126696006u, 0u, 18371666036479679596ull, 425179394u, 0u, 10919696438018802198ull, 3520112738u, 0u, 1456580288751298390ull, 1330046680u, 0u, 4764757027483760560ull, 3487765284u, 0u, 950543391324211624ull, 4069236691u, 0u, 11581153406458980418ull, 552268855u, 0u, 4675234710448655636ull, 2155608077u, 0u, 14425159580695489752ull, 876391690u, 0u, 9733161782016707496ull, 887126870u, 0u, 5508943981037769066ull, 4196048666u, 0u, 17867059904879312330ull, 4197169932u, 0u, 7627939860539441076ull, 336725473u, 0u, 2473967199778462140ull, 384859129u, 0u, 13425993975014284952ull, 2989821041u, 0u, 6624678694702213950ull, 1711755667u, 0u, 8108119363426008566ull, 85153537u, 0u, 139821767465789548ull, 3189353571u, 0u, 16533604488089711128ull, 978740205u, 0u, // 152 14548316699961044664ull, 57271989u, 0u, 12878330746179066104ull, 2619393551u, 0u, 13877046950225006872ull, 3521180802u, 0u, 10793784616637168746ull, 13471346u, 0u, 4640326476397662706ull, 739473296u, 0u, 2463354197362176466ull, 795129260u, 0u, 17907832290682587108ull, 984351873u, 0u, 7324121966858563342ull, 663176203u, 0u, 1355009691800210398ull, 3969174875u, 0u, 6514732929702733502ull, 3256977017u, 0u, 12248247595034144658ull, 3111979394u, 0u, 762155665398568716ull, 1953461516u, 0u, 14622318833823840540ull, 1660990786u, 0u, 6136612451474885520ull, 3067232150u, 0u, 14737121559162853008ull, 1179428565u, 0u, 2134387449520191276ull, 3481644076u, 0u, 8054572132117883136ull, 1428984455u, 0u, 15221110070636125744ull, 1785416576u, 0u, 11519542536581926430ull, 549004837u, 0u, 15224369791104688722ull, 1402578189u, 0u, 1812468770614150964ull, 650331405u, 0u, 10341594776929374026ull, 1329426510u, 0u, 10284794448013541800ull, 1704521597u, 0u, 12382164048179057864ull, 2282762934u, 0u, 15642514324184822338ull, 225007751u, 0u, 8844255598201060666ull, 2348907452u, 0u, 496315040374227034ull, 3807002481u, 0u, 4396296828409939872ull, 2284285905u, 0u, 1255603857700441880ull, 4073488272u, 0u, 13344712100785849280ull, 3043070000u, 0u, 2985216131033158976ull, 2308388649u, 0u, 11135458011215471202ull, 2449717537u, 0u, // 153 1744693466823866598ull, 4235291451u, 0u, 12811455755102488760ull, 1750269301u, 0u, 4873442453324540326ull, 2637034289u, 0u, 11325445789507713344ull, 2083095811u, 0u, 5690248958991237918ull, 1116995850u, 0u, 2401104148694953842ull, 3280526252u, 0u, 17743339012997266284ull, 441307855u, 0u, 13349632967742733280ull, 3974325302u, 0u, 6586471482173574142ull, 661206325u, 0u, 286152252603332890ull, 2252632290u, 0u, 4104022048784183044ull, 1026405546u, 0u, 12036018056625951820ull, 461847652u, 0u, 14150860249632522006ull, 2691996262u, 0u, 750207422035781972ull, 1710783198u, 0u, 17587753405930906914ull, 1379332849u, 0u, 4338074112967355446ull, 1407769576u, 0u, 16719353754906887748ull, 4015159002u, 0u, 5532309054643820942ull, 2369987920u, 0u, 10260499029523699836ull, 2808774036u, 0u, 8605275729837443710ull, 3068186649u, 0u, 14248813171031769616ull, 1169182299u, 0u, 2780725308871971144ull, 1438069468u, 0u, 14464720216610481168ull, 2603792512u, 0u, 14086391975480309120ull, 2316273873u, 0u, 14300885623830191188ull, 3605608723u, 0u, 6009696061069743128ull, 341007645u, 0u, 11251526458408190754ull, 3546516418u, 0u, 509595017565798328ull, 2490800683u, 0u, 10646108630545724434ull, 3825312861u, 0u, 11128578597150846368ull, 3339190352u, 0u, 16014560673719204326ull, 2125860623u, 0u, 3363127269220406594ull, 2505715377u, 0u, // 154 10486142851484220728ull, 2218371120u, 0u, 15546806174173678682ull, 654018748u, 0u, 8723288279569947584ull, 46814701u, 0u, 16489820528997974946ull, 2450685857u, 0u, 4651269732509531970ull, 3874733905u, 0u, 17497899402789255792ull, 4013289322u, 0u, 5454397563074226026ull, 176716085u, 0u, 15186078934568127204ull, 1433859326u, 0u, 13288415541234732142ull, 3319599025u, 0u, 8840469555817552398ull, 1090143480u, 0u, 2134669005379729918ull, 2508705880u, 0u, 16809998149808454248ull, 3024278825u, 0u, 6392809366932848566ull, 417550441u, 0u, 4893051244948773974ull, 2708122699u, 0u, 8528111969616734964ull, 403795655u, 0u, 7353636486207983882ull, 2910240145u, 0u, 9195898584766171394ull, 1643279617u, 0u, 4903089172150956626ull, 1748967793u, 0u, 2004251447249831330ull, 1443139695u, 0u, 4936425902093859778ull, 110267216u, 0u, 4162753897313411402ull, 1161160587u, 0u, 8564430962808086720ull, 2218947940u, 0u, 7818075723091701500ull, 89662292u, 0u, 7644252008607810824ull, 316975913u, 0u, 7360653502216404050ull, 3609170372u, 0u, 4038299049103174470ull, 2231168628u, 0u, 13864180286216508934ull, 2779671752u, 0u, 11755585591229767332ull, 3711981387u, 0u, 11432117590059163872ull, 1852157602u, 0u, 14839739993706739134ull, 3755612574u, 0u, 4324560020141908336ull, 726055392u, 0u, 10320153093604054912ull, 2417924792u, 0u, // 155 8175450369349272896ull, 2516458186u, 0u, 5965905389727622790ull, 2800992051u, 0u, 1789514254552681836ull, 79465285u, 0u, 4509546509824912834ull, 2520828280u, 0u, 15480347681918275924ull, 2785757983u, 0u, 5570297158601029512ull, 2083915893u, 0u, 15735520586213721098ull, 4111386393u, 0u, 7322914101521025380ull, 242025489u, 0u, 10386796764645387486ull, 1536037679u, 0u, 5892387087531629876ull, 2446743522u, 0u, 2882910811957998368ull, 3438343886u, 0u, 4677083580802190254ull, 1866328981u, 0u, 5452977328022054808ull, 2439470861u, 0u, 12931634967572402634ull, 716724961u, 0u, 14564179706477199082ull, 819002766u, 0u, 15586612325398053608ull, 760062656u, 0u, 5912249004031608266ull, 3818173922u, 0u, 5625939709336045404ull, 1402572285u, 0u, 406765588997032452ull, 2908631881u, 0u, 18406840363804145434ull, 975457505u, 0u, 6389884869368649618ull, 3017026575u, 0u, 4947336530062062588ull, 494249737u, 0u, 321006255344341110ull, 651744720u, 0u, 16998140730525566502ull, 2676866403u, 0u, 3425015292087784634ull, 3823079505u, 0u, 17172740884757282506ull, 1437413200u, 0u, 810394351247782208ull, 1952966144u, 0u, 17995283590553198748ull, 889931593u, 0u, 11318200542785855384ull, 1861494254u, 0u, 6339043584385458204ull, 1376835284u, 0u, 17806444614174083524ull, 1310603314u, 0u, 12283108587682373944ull, 12174619u, 0u, // 156 13105301211270826610ull, 887895685u, 0u, 16055440063902516954ull, 1321321975u, 0u, 17238462536478627632ull, 197093935u, 0u, 6771525754384222346ull, 3194739821u, 0u, 3523759140263468542ull, 3447937101u, 0u, 9236621161437589540ull, 3064129344u, 0u, 1550643987842109342ull, 216135377u, 0u, 2330413941625390714ull, 1672023118u, 0u, 1249595167849569376ull, 1113642937u, 0u, 16010563343895777874ull, 1299179485u, 0u, 2370992964365224844ull, 2764075277u, 0u, 899833615908035484ull, 2402204095u, 0u, 1332111380706395836ull, 2357712236u, 0u, 2136619082781052246ull, 2014288892u, 0u, 15772776606792526510ull, 692900038u, 0u, 5258698985973134744ull, 4218465315u, 0u, 13078264820326404342ull, 2993231388u, 0u, 13947392546983511226ull, 2953708036u, 0u, 15362809414565578390ull, 940242050u, 0u, 18181636823467792634ull, 3289758122u, 0u, 1838183019734587288ull, 1968667033u, 0u, 15170560086359396154ull, 445052028u, 0u, 13560217242680424214ull, 2197026606u, 0u, 15512325642627096906ull, 974561491u, 0u, 5500581134996856960ull, 3799895315u, 0u, 14100844447568679066ull, 3960686554u, 0u, 9379111068889460614ull, 228363743u, 0u, 10263281327434175192ull, 2887996820u, 0u, 16088224359381664800ull, 3299745053u, 0u, 5212403960642294794ull, 439655848u, 0u, 13597643206580037174ull, 1987311708u, 0u, 1253781925034015646ull, 3425469159u, 0u, // 157 15442551492814810640ull, 3173888123u, 0u, 17291951593816008056ull, 2563700076u, 0u, 17831444512602161318ull, 1766922827u, 0u, 4740605827275051872ull, 3583076500u, 0u, 4335668472947897642ull, 440918349u, 0u, 4988769598170536056ull, 1536947596u, 0u, 15925589066888965238ull, 2845255109u, 0u, 13365731606724729024ull, 2168813706u, 0u, 2626283224187239484ull, 2616167952u, 0u, 15763081655683377234ull, 1965650799u, 0u, 15209392356075019962ull, 2176889684u, 0u, 12028837677090080724ull, 4167820999u, 0u, 11854350697476400880ull, 3672560631u, 0u, 6426015915090932992ull, 3835111103u, 0u, 4398845724398849072ull, 2507061974u, 0u, 18259777876599291732ull, 2059551298u, 0u, 2065102153766032782ull, 510222277u, 0u, 6215379139839177070ull, 1300097355u, 0u, 14415177054004130056ull, 721258189u, 0u, 5705102734117935766ull, 437047214u, 0u, 16055658759357847224ull, 4101942014u, 0u, 7406200582770183566ull, 1520516514u, 0u, 10227226650879553424ull, 1167233645u, 0u, 4429779059576293236ull, 2130729192u, 0u, 196736358849741176ull, 2744792510u, 0u, 5173484536487243974ull, 259988408u, 0u, 2554351642985658846ull, 3619146621u, 0u, 16449627999976909606ull, 2700447219u, 0u, 3379358467126796592ull, 4270895558u, 0u, 10971999583181937652ull, 335803560u, 0u, 9744441990587909858ull, 2085307982u, 0u, 6409881721383000292ull, 3398818526u, 0u, // 158 17966213468664538420ull, 2413361340u, 0u, 14511121256500133976ull, 1126221543u, 0u, 2389084899275712920ull, 371441047u, 0u, 17307312093042107986ull, 3115696764u, 0u, 8313193978015364496ull, 3405946475u, 0u, 9825884922292116618ull, 2579604284u, 0u, 742879569932243044ull, 1825395593u, 0u, 15165502735282807924ull, 3622287335u, 0u, 7470986228227570178ull, 759490473u, 0u, 1862486524998312640ull, 3033267857u, 0u, 11188494497178109674ull, 2650317437u, 0u, 4101547163938047386ull, 1097417149u, 0u, 15480389357193659004ull, 3513469751u, 0u, 15632424944014505428ull, 2313848759u, 0u, 6782868742863200178ull, 2047005788u, 0u, 17563765188263663404ull, 3540255059u, 0u, 16200709492386965156ull, 2620872331u, 0u, 11332613212687615856ull, 3444603885u, 0u, 18144850918053228236ull, 261236674u, 0u, 13272893940669483328ull, 1450626947u, 0u, 4447496037073963894ull, 1823124138u, 0u, 12403221496124296116ull, 1357697419u, 0u, 12583215162777543910ull, 2494459011u, 0u, 5495627556074130348ull, 3864038121u, 0u, 11249227246695539878ull, 3913012291u, 0u, 9754063155643771394ull, 3358977739u, 0u, 16979059524192189446ull, 3709238263u, 0u, 14828112125396668690ull, 4217961139u, 0u, 11617703275338571038ull, 1940614274u, 0u, 16512584854502728494ull, 1610958922u, 0u, 5306413118704661378ull, 3269573990u, 0u, 1365188725500450916ull, 968670654u, 0u, // 159 759508072556499360ull, 3172108851u, 0u, 2175418185792277968ull, 1336752959u, 0u, 13606676021560938226ull, 1578089372u, 0u, 4127892629718726076ull, 4634996u, 0u, 11410505878480338644ull, 824479611u, 0u, 6627664519912679212ull, 1343356988u, 0u, 13110739923636815088ull, 3545673946u, 0u, 18275955512558724836ull, 3954120169u, 0u, 3035010526925510024ull, 4103467906u, 0u, 3155250959931516396ull, 3210571274u, 0u, 17400262760542065346ull, 1896394265u, 0u, 1714535339448144660ull, 1926976141u, 0u, 982394472635128854ull, 3137600580u, 0u, 15442639161678571664ull, 1806710263u, 0u, 7064070548482286610ull, 2421788963u, 0u, 3700959783432077984ull, 2972360701u, 0u, 2980650008523119080ull, 3667814116u, 0u, 5473292825000535990ull, 334308207u, 0u, 12113110403873289706ull, 694777769u, 0u, 2148791061972769032ull, 765507388u, 0u, 512083142081994516ull, 2472455687u, 0u, 12685446129386013066ull, 2585332406u, 0u, 15051575457505808038ull, 2323870177u, 0u, 8293776218235501664ull, 361632392u, 0u, 5306036256933225612ull, 457846120u, 0u, 6741231222863608428ull, 3953378212u, 0u, 1121013046571236044ull, 698744289u, 0u, 10233460877807667394ull, 1888652180u, 0u, 9771449631195430946ull, 3273045615u, 0u, 16083310300901929862ull, 3991511660u, 0u, 9271099386692157134ull, 4029123332u, 0u, 9192474945661013178ull, 3413516314u, 0u, // 160 13898535906747176246ull, 1956574497u, 0u, 10025877295033889288ull, 739999797u, 0u, 9933148839864077120ull, 2407695440u, 0u, 3222909290559620374ull, 3787253805u, 0u, 2332898791416759090ull, 2173811253u, 0u, 4293444173020000610ull, 3919361778u, 0u, 8133041191469657836ull, 368452928u, 0u, 14436737546007016758ull, 1637928879u, 0u, 3778110095299511264ull, 4199452733u, 0u, 3858916473085368346ull, 3418934453u, 0u, 5252005993458258282ull, 477408382u, 0u, 17793341853583283890ull, 667165503u, 0u, 10668611682185176408ull, 1634965016u, 0u, 2747173895028062370ull, 2294581198u, 0u, 2163431780701369720ull, 3852045845u, 0u, 15874257278819884458ull, 3076920604u, 0u, 17054962587988937990ull, 158249600u, 0u, 16772432290015663208ull, 2246725940u, 0u, 18121904089225903940ull, 2373986706u, 0u, 3824543062944304088ull, 1646641846u, 0u, 2847858460810079072ull, 2933778087u, 0u, 5511218853423722226ull, 4113002459u, 0u, 10568328238589276486ull, 913607092u, 0u, 8498677552816690388ull, 1317665300u, 0u, 6101119320012132330ull, 4067679296u, 0u, 6409981330745659596ull, 2546746912u, 0u, 13388832461254229898ull, 4259163868u, 0u, 17473855457824843800ull, 4249409076u, 0u, 5199802094256337450ull, 494096227u, 0u, 836723837551113544ull, 2445217543u, 0u, 8699281454860321580ull, 706274111u, 0u, 14362907491111783464ull, 2941739326u, 0u, // 161 15843878511934703224ull, 2054091212u, 0u, 16494407794340885368ull, 1051824126u, 0u, 3863480025558156832ull, 1042744277u, 0u, 7574749935364438904ull, 3008527666u, 0u, 18312249264252047750ull, 3233950271u, 0u, 6684229486598143924ull, 3198504530u, 0u, 5544076272968721252ull, 2449878129u, 0u, 10728494457653128784ull, 3255161480u, 0u, 8964459669440481814ull, 1308003242u, 0u, 17818869862192587396ull, 3624728176u, 0u, 4286770033311274154ull, 1351903445u, 0u, 16557115631413436260ull, 2741880953u, 0u, 15420180196523690254ull, 2535319182u, 0u, 8223436080079998490ull, 3074237334u, 0u, 16760014069412052860ull, 3418320768u, 0u, 4895797345064933568ull, 2344687545u, 0u, 6262602996143568398ull, 2484898427u, 0u, 2920623634399707658ull, 3882542382u, 0u, 18404524202011338666ull, 810666133u, 0u, 6808715766868636884ull, 1297694822u, 0u, 12237951360194755858ull, 3848148664u, 0u, 6939136234249030692ull, 2203873860u, 0u, 17090385850360349000ull, 1364852873u, 0u, 12793342688970071660ull, 3631944426u, 0u, 11325279119727154348ull, 1194855639u, 0u, 458574136661014726ull, 455173594u, 0u, 15174679718122765744ull, 2182235087u, 0u, 563697412959825280ull, 2186683958u, 0u, 5692669980944968198ull, 1317058366u, 0u, 3849335014378899012ull, 4200052376u, 0u, 3229488234413578872ull, 2388773965u, 0u, 15170226857528795234ull, 2330749243u, 0u, // 162 9105838622706901490ull, 3136666619u, 0u, 13801751797035926108ull, 3231244650u, 0u, 16230966738957072394ull, 375850780u, 0u, 17581853367700699504ull, 222840497u, 0u, 2277200385247985020ull, 3506684482u, 0u, 13693762985720169856ull, 2968366361u, 0u, 4364829524262585788ull, 3895864771u, 0u, 11945929031652230382ull, 1871735755u, 0u, 2097134281173132872ull, 120265591u, 0u, 4825673391016085116ull, 1110737743u, 0u, 15507556702297805528ull, 2888534904u, 0u, 14366701087504509086ull, 859895165u, 0u, 9528610018610821664ull, 3664666711u, 0u, 13396339796588203702ull, 317391376u, 0u, 9658153077727640842ull, 3025159581u, 0u, 4459315954365967828ull, 166643554u, 0u, 14710559191884376632ull, 1815350757u, 0u, 4367951107993040860ull, 210955664u, 0u, 8090997514289525114ull, 1326921792u, 0u, 9696816232357282160ull, 4036533297u, 0u, 2121156617720089042ull, 930396545u, 0u, 14986352909796285774ull, 1319503012u, 0u, 5947648637942633736ull, 882840443u, 0u, 9905263987667835028ull, 554130811u, 0u, 14181263697718567440ull, 1913215704u, 0u, 4754203186285587372ull, 3477098661u, 0u, 3343582950733828560ull, 3397047600u, 0u, 15782918347298836820ull, 2071859890u, 0u, 7296013679116610618ull, 2612866209u, 0u, 4274381110950869322ull, 251382748u, 0u, 15921292744845392870ull, 1046193615u, 0u, 2623203014224368802ull, 1478767369u, 0u, // 163 14151050426994549478ull, 2679633722u, 0u, 13208534506395948178ull, 2001343332u, 0u, 8067170538575086932ull, 3239718327u, 0u, 18054575113455711902ull, 3034588660u, 0u, 17778154108585931058ull, 1572555309u, 0u, 12161466598462059350ull, 3232587059u, 0u, 2577374618299369798ull, 2759062589u, 0u, 15353286864333667422ull, 846911108u, 0u, 13752152524020333928ull, 853733078u, 0u, 2261389914469498164ull, 1984833320u, 0u, 4046366926694648332ull, 2990412507u, 0u, 258251235414748104ull, 1812367751u, 0u, 11534581931428459234ull, 1299137175u, 0u, 13832260878987888724ull, 157512859u, 0u, 3767845098261258726ull, 2816083384u, 0u, 7050700481898956970ull, 3177854089u, 0u, 3381362532080685022ull, 3926962141u, 0u, 7966845441536611976ull, 3504394165u, 0u, 15510879937889625614ull, 3226381105u, 0u, 8524862978023443076ull, 3820722063u, 0u, 3876087515274926058ull, 491222925u, 0u, 4029943029092792482ull, 890744927u, 0u, 3419364574235706518ull, 52203724u, 0u, 8284843456598045100ull, 3398398459u, 0u, 1527441497504248112ull, 260843123u, 0u, 2671670039616692278ull, 66133261u, 0u, 7627572300945746490ull, 3659273625u, 0u, 13725985710051102390ull, 640220477u, 0u, 8934102132117971548ull, 3074789648u, 0u, 1680167649587891888ull, 3144507364u, 0u, 6816242592995426042ull, 2692684858u, 0u, 2551765449697832ull, 4077926792u, 0u, // 164 16219640241487158100ull, 3110985030u, 0u, 11939164328083024000ull, 514790549u, 0u, 12413268855055834924ull, 4288840445u, 0u, 4235030072984471002ull, 2365104696u, 0u, 6948255125784593208ull, 2967294361u, 0u, 12121904738114010196ull, 1517359988u, 0u, 9682674453520197758ull, 3124145431u, 0u, 11451417472886960904ull, 3274267948u, 0u, 14028787286169209758ull, 3586297796u, 0u, 977557047619322466ull, 2786073989u, 0u, 14011042905278713246ull, 2111075663u, 0u, 10143971669905197186ull, 4151676250u, 0u, 17064446181103669886ull, 3908568681u, 0u, 2181814986430600618ull, 1364139472u, 0u, 9015937795199573236ull, 775736605u, 0u, 14706960080080223616ull, 2365045990u, 0u, 17690108413625130532ull, 1927587105u, 0u, 9528136873685041142ull, 3318585999u, 0u, 8700831538900907512ull, 984266437u, 0u, 14019005523369262928ull, 3675463570u, 0u, 13064326635489124806ull, 2182355480u, 0u, 888990508724807576ull, 225922621u, 0u, 12900558159498330492ull, 3290947488u, 0u, 5384541664754947498ull, 3429422948u, 0u, 1860013608435498126ull, 1318974366u, 0u, 2657823204477316656ull, 3202101935u, 0u, 5569702481948863670ull, 3585994619u, 0u, 16740290541117289086ull, 2506183398u, 0u, 8085050368503579746ull, 1186438141u, 0u, 14207937930375805478ull, 1852738270u, 0u, 15151117873992917412ull, 3974357364u, 0u, 7800524224627360470ull, 625676559u, 0u, // 165 8008847040926088198ull, 1374319985u, 0u, 16651287052163897626ull, 3798296678u, 0u, 11793585257350482892ull, 136335071u, 0u, 8898557453755369938ull, 2261953071u, 0u, 8091395870367603198ull, 3232570398u, 0u, 8091426633777681736ull, 3248832116u, 0u, 5901015363936976372ull, 2733838982u, 0u, 13980672857494281714ull, 1837793808u, 0u, 11114032871960952170ull, 1150549576u, 0u, 13810515650391857722ull, 3838700710u, 0u, 18235544716326761376ull, 3249882734u, 0u, 17128496186061775714ull, 2048622186u, 0u, 17954272933447745372ull, 1163197285u, 0u, 6727782535517963676ull, 3689278365u, 0u, 14574253525838070478ull, 1154158175u, 0u, 1739924064914453916ull, 212749567u, 0u, 7521888722708935502ull, 1997033466u, 0u, 6233814922883352076ull, 2837661978u, 0u, 13897906279904315536ull, 509481146u, 0u, 11101821697003098138ull, 521719517u, 0u, 13792557121871637418ull, 3827960777u, 0u, 17142445734964491048ull, 2726735822u, 0u, 7431254818519725102ull, 3339859894u, 0u, 8948493501519489818ull, 3352200137u, 0u, 14078417515050232390ull, 3284124184u, 0u, 2263812622099213188ull, 346405965u, 0u, 18382381259865520778ull, 2527907843u, 0u, 12800189299415808792ull, 3966517950u, 0u, 1551210371059272650ull, 2697958765u, 0u, 9197090359055945438ull, 1776208623u, 0u, 13435132315266678088ull, 1452854620u, 0u, 18355157573321195456ull, 3030603766u, 0u, // 166 7648737697706928804ull, 1311812404u, 0u, 18206793784224067100ull, 708502827u, 0u, 14224007932440990138ull, 621338701u, 0u, 2970051784087012688ull, 2550004405u, 0u, 4776805784247665694ull, 4235394122u, 0u, 11688482168447163302ull, 4256226127u, 0u, 10131745900398326852ull, 2211017084u, 0u, 5840977681185512658ull, 4251430399u, 0u, 9437201556069185690ull, 2462099870u, 0u, 9085526096242529738ull, 3953617288u, 0u, 17715363938530915922ull, 1969958123u, 0u, 10086834920536075418ull, 1861069632u, 0u, 7904381642651551878ull, 2652399937u, 0u, 12065142481374173448ull, 1583725222u, 0u, 1409261379423220660ull, 4139175759u, 0u, 13904668636478882852ull, 2963085557u, 0u, 2455880688505909544ull, 1042643283u, 0u, 4164366743589802898ull, 2392375725u, 0u, 6636914788752339790ull, 1360675178u, 0u, 12240668800056775324ull, 2415287476u, 0u, 9383313111843263576ull, 568682484u, 0u, 16879954570724107850ull, 2957106120u, 0u, 1798781306705164494ull, 1954753877u, 0u, 13960758610371845910ull, 3906152056u, 0u, 9803975377824759974ull, 2584247781u, 0u, 13452723475689988292ull, 1795136985u, 0u, 6538905328841904318ull, 3001413828u, 0u, 17537943729831629746ull, 846039470u, 0u, 6384194329480129984ull, 750005640u, 0u, 13858254042024209316ull, 460916706u, 0u, 10307564937078463270ull, 3705323173u, 0u, 7213676348057224606ull, 3271111288u, 0u, // 167 5212931434458680900ull, 3556483841u, 0u, 8276003424890408992ull, 3263390551u, 0u, 1748248408453983802ull, 569482437u, 0u, 864744561053907792ull, 4152871953u, 0u, 15222479821184120158ull, 1501350730u, 0u, 4083433304576741018ull, 4282940825u, 0u, 1618043112647415326ull, 2527651062u, 0u, 4916378096973268482ull, 2391060324u, 0u, 8049144084202345086ull, 3992438484u, 0u, 4614600346249258556ull, 1517000209u, 0u, 3087702842227259414ull, 1126962880u, 0u, 5768530902175389642ull, 4138517246u, 0u, 14350705973830133470ull, 280734905u, 0u, 5393616527934072994ull, 3701065735u, 0u, 17906536650929956838ull, 793343654u, 0u, 11417416343980529248ull, 734987279u, 0u, 11921372552695341740ull, 546151280u, 0u, 8253601213374877062ull, 902530345u, 0u, 8060410760564567092ull, 1421867259u, 0u, 1576919209754296430ull, 2921200101u, 0u, 17132004788327969720ull, 4047361684u, 0u, 13083633529768016302ull, 4279832873u, 0u, 7187702092733335338ull, 1280154804u, 0u, 12783794570290462338ull, 3598158720u, 0u, 3825580964069827634ull, 945859971u, 0u, 755926545108994384ull, 183823437u, 0u, 15367369980819162258ull, 311160809u, 0u, 6161079329545436720ull, 4241179504u, 0u, 14542111695863670512ull, 835772946u, 0u, 1024331950231839102ull, 3952916223u, 0u, 14454550111271508620ull, 1322603804u, 0u, 2809656053209491302ull, 1446992868u, 0u, // 168 4974139893003628432ull, 3101070464u, 0u, 14705589033035649708ull, 3264755530u, 0u, 16616312924119933860ull, 900340069u, 0u, 17929104631112265366ull, 2195355109u, 0u, 2376918307488850544ull, 2755318991u, 0u, 6083166573162935034ull, 3045721252u, 0u, 14446112785676417296ull, 1179202190u, 0u, 17284905064566063828ull, 3330157476u, 0u, 9160300139421813332ull, 2420954048u, 0u, 4283357733645916984ull, 4105943579u, 0u, 14290772377462351458ull, 1189760577u, 0u, 4916159551367760276ull, 1589154206u, 0u, 2642403551644531228ull, 1145527348u, 0u, 10949340495712663728ull, 82429800u, 0u, 13624362262089903786ull, 1186894951u, 0u, 15124024910535360828ull, 2796392280u, 0u, 7945239662216768194ull, 2420419148u, 0u, 3867773368332452362ull, 1270042386u, 0u, 4111189504285889236ull, 4181407303u, 0u, 3108176322294886786ull, 1869451268u, 0u, 2795920957998207298ull, 1277390036u, 0u, 9417940335834257894ull, 3344829476u, 0u, 17258024935637514858ull, 695659234u, 0u, 16349107065627023056ull, 3795301537u, 0u, 8352359953219594254ull, 3597123089u, 0u, 11661253846095125418ull, 1605478666u, 0u, 14616389078833670528ull, 3743182922u, 0u, 10056234900978375214ull, 2303445662u, 0u, 9018101508443983818ull, 490471288u, 0u, 17541620961015753102ull, 2389663984u, 0u, 17229096661284691562ull, 1239509214u, 0u, 6209854321058535504ull, 55317335u, 0u, // 169 11848066880875135578ull, 1082856035u, 0u, 10790658483881078332ull, 4090719035u, 0u, 7719404776954252206ull, 1875557641u, 0u, 630914791687268568ull, 2109599692u, 0u, 13878026298265720618ull, 2192144372u, 0u, 1848936854492674174ull, 583628299u, 0u, 15497969009378533560ull, 4121445427u, 0u, 1445383330749616022ull, 2154263462u, 0u, 4244977844243235460ull, 1041590580u, 0u, 6308751760956105758ull, 2101917871u, 0u, 13132596371259975708ull, 81533920u, 0u, 18077567162241293880ull, 3447891187u, 0u, 12285887731241782186ull, 5408697u, 0u, 17937150878265571716ull, 3970921576u, 0u, 9518738967078448794ull, 1974356157u, 0u, 16482939466622533188ull, 2082823678u, 0u, 13158250325539152140ull, 1804217194u, 0u, 8322168745085335710ull, 3487610700u, 0u, 16704512703167736750ull, 3608066920u, 0u, 7054220530276190584ull, 3717036710u, 0u, 15174905932689735798ull, 1361479685u, 0u, 16947649989132162078ull, 3157070197u, 0u, 5179287303185863174ull, 2051980445u, 0u, 4680730882009255084ull, 3658834816u, 0u, 4766608578239531278ull, 2672528127u, 0u, 6536648327349214416ull, 674160809u, 0u, 13795018392668990518ull, 1181723344u, 0u, 18250929259092687442ull, 2660318938u, 0u, 18030029416641010916ull, 1724402387u, 0u, 12549045286486644646ull, 927518278u, 0u, 12463836320603779538ull, 172609981u, 0u, 5526159119417657206ull, 287598867u, 0u, // 170 15743483362867922810ull, 97113578u, 0u, 13725339823517873928ull, 2024001758u, 0u, 2276249938773047222ull, 1709358991u, 0u, 207155771102464780ull, 1334481294u, 0u, 2114715504499812670ull, 2363495673u, 0u, 9455109750924817166ull, 444893897u, 0u, 2381603862966160326ull, 1202598494u, 0u, 407662124041754470ull, 1233370756u, 0u, 3777726962881204554ull, 442455980u, 0u, 7896413270561968254ull, 1858739135u, 0u, 17495266030139441632ull, 1618014477u, 0u, 15801932524264837786ull, 1537827434u, 0u, 232304477867977252ull, 1802775363u, 0u, 7443041386347066972ull, 1110601109u, 0u, 9393513962647006090ull, 272952249u, 0u, 5832522998557241874ull, 2738403082u, 0u, 9809459330538057670ull, 2866263332u, 0u, 7062132307315973646ull, 1147894875u, 0u, 11089971591169008154ull, 666967840u, 0u, 4460806388933783602ull, 4216036084u, 0u, 10624796227257300298ull, 443480105u, 0u, 5760858099412233364ull, 1663139997u, 0u, 10912147585222040706ull, 2687124163u, 0u, 17979883022655587598ull, 2531222238u, 0u, 16569346227443941538ull, 784045604u, 0u, 12063524282013382882ull, 2312078884u, 0u, 2324240537945281872ull, 4148225081u, 0u, 1906473520723179828ull, 2526381738u, 0u, 13785658048813972050ull, 1469608568u, 0u, 2959890411835641666ull, 2957887033u, 0u, 14776021512942724308ull, 3607546392u, 0u, 157987900546301824ull, 2219315287u, 0u, // 171 8349529494465633548ull, 804714925u, 0u, 16583292145819518910ull, 591524728u, 0u, 10708065047678001208ull, 1191601289u, 0u, 9656827996797712446ull, 2994483745u, 0u, 6937446999881579144ull, 601285141u, 0u, 16894568325052462426ull, 3742538737u, 0u, 7813134080258992046ull, 1515564420u, 0u, 4397185688842599848ull, 2009763214u, 0u, 1549009065473400484ull, 426597402u, 0u, 7715056743086551676ull, 1596432318u, 0u, 7595688080680622384ull, 344261865u, 0u, 6146764108316029760ull, 3390352893u, 0u, 3770109925718622374ull, 2196782572u, 0u, 6156897796267567286ull, 3038960411u, 0u, 14981954511426133884ull, 503940749u, 0u, 922683703779180926ull, 3176432477u, 0u, 2263281262490568738ull, 2306561622u, 0u, 964927353514992112ull, 287291217u, 0u, 18280230535036090548ull, 3880071288u, 0u, 5478715232228410308ull, 1721660311u, 0u, 6267435062673256252ull, 1355583853u, 0u, 16494802084985604358ull, 2138178622u, 0u, 13980694401184630034ull, 2513845062u, 0u, 3866796547245789170ull, 403385685u, 0u, 7091065609417295404ull, 4027989003u, 0u, 13329134471660860866ull, 1079742250u, 0u, 2789397389757485296ull, 4064084545u, 0u, 10603283339290030132ull, 1058689797u, 0u, 4092463487779341176ull, 1695752728u, 0u, 16542875812066181632ull, 4088154582u, 0u, 1062340212402360094ull, 2689063472u, 0u, 13163887666658667034ull, 1100599632u, 0u, // 172 3098482016272432248ull, 2702413430u, 0u, 6207106034525980974ull, 1643854962u, 0u, 1061948707004497444ull, 2420722322u, 0u, 6838880900997796090ull, 3953287688u, 0u, 6671910901624386364ull, 1422570268u, 0u, 1311806254586645968ull, 2111346590u, 0u, 12003801144371303670ull, 2698118600u, 0u, 9532237581844628542ull, 3325048086u, 0u, 13532207209684452962ull, 2707188208u, 0u, 3258597560664358844ull, 3429989791u, 0u, 12984325498099376114ull, 1290038907u, 0u, 8951564023891997784ull, 1812124984u, 0u, 5233561881338659188ull, 2521214209u, 0u, 873804277374489022ull, 195098050u, 0u, 12897732891696275534ull, 3690622515u, 0u, 11499004410528803070ull, 3585663951u, 0u, 2881521800597125018ull, 137441423u, 0u, 2663589532655267322ull, 3291988445u, 0u, 10761951982971427202ull, 734226415u, 0u, 16823758808360653892ull, 1152078614u, 0u, 4888203182264640352ull, 2341854581u, 0u, 3296786863817050064ull, 2612638729u, 0u, 10291499751489328046ull, 2549383497u, 0u, 13258277185355155950ull, 3210654155u, 0u, 9631069537358736472ull, 4067978802u, 0u, 13495732891571907294ull, 4208870718u, 0u, 13127478913067829810ull, 1317260189u, 0u, 14988131384356885212ull, 3809369u, 0u, 17221888689490976884ull, 3007378764u, 0u, 9049425165949547092ull, 2574382899u, 0u, 15476449911626982424ull, 4103946144u, 0u, 4631387827632216300ull, 536663833u, 0u, // 173 10611820021912213684ull, 2697920510u, 0u, 3541991877079202390ull, 4140492264u, 0u, 6004472925763795188ull, 1827034574u, 0u, 2288988796952592272ull, 1054671879u, 0u, 17157611773422481648ull, 3332584756u, 0u, 10313273929982678696ull, 1895936963u, 0u, 10096696439414015972ull, 742618251u, 0u, 14621366005474617928ull, 3995047317u, 0u, 7020941539052531872ull, 3740356538u, 0u, 9141666340458202290ull, 2549603824u, 0u, 17221253832150995730ull, 1845583861u, 0u, 10465352137014066514ull, 2711458483u, 0u, 18147453888478953084ull, 3202383230u, 0u, 12694981711902781650ull, 3699440543u, 0u, 8600917740834755394ull, 140348093u, 0u, 6065675973008786494ull, 3485688249u, 0u, 7106145062631842620ull, 1590594821u, 0u, 9969280420049310350ull, 691168455u, 0u, 420211751044432146ull, 1695826937u, 0u, 14082100710910845688ull, 1356951496u, 0u, 15864910441272043956ull, 2644207973u, 0u, 2809807393549692322ull, 2175667457u, 0u, 276955219306923228ull, 1681256781u, 0u, 14014639931226934688ull, 3163679229u, 0u, 6450882383684741212ull, 1670268387u, 0u, 11209451435206886176ull, 424774124u, 0u, 17858400583065584928ull, 678674332u, 0u, 14215283312230795442ull, 1369594591u, 0u, 10627899480138971826ull, 129871515u, 0u, 5699874920364023716ull, 1262077662u, 0u, 17207324518762699020ull, 2017981820u, 0u, 7430784614094197380ull, 1659413931u, 0u, // 174 10092668668760697182ull, 3453777160u, 0u, 13356163586849332868ull, 2603591775u, 0u, 15537412075446592902ull, 3090768366u, 0u, 5109495130738313952ull, 341051497u, 0u, 5162451946961153182ull, 2850498240u, 0u, 7734822563285880234ull, 796606986u, 0u, 500769938825469690ull, 1767652409u, 0u, 13607204920708550620ull, 134374490u, 0u, 8102626949408879892ull, 3005735860u, 0u, 15896137904070368670ull, 1416234225u, 0u, 6275945029892652542ull, 1216539984u, 0u, 13030496933728712926ull, 2046094492u, 0u, 11345563561689972376ull, 654393450u, 0u, 17620801532727003286ull, 3860275373u, 0u, 17204370156243265590ull, 1426104260u, 0u, 4184252778942092258ull, 1543845119u, 0u, 2594537185473266988ull, 3239755012u, 0u, 3950770737299276844ull, 3323578398u, 0u, 17652438995760652338ull, 3672702462u, 0u, 13888476045644157362ull, 1484284646u, 0u, 15981519826149755724ull, 3241850654u, 0u, 15356008995570918574ull, 2654415791u, 0u, 12145784844098372656ull, 3539892718u, 0u, 10741462177471333378ull, 832798272u, 0u, 12365813441690761888ull, 344093072u, 0u, 8157187315194750366ull, 2160638314u, 0u, 2497233677023090284ull, 2254679266u, 0u, 4232213060278604932ull, 389404284u, 0u, 10123586121190200154ull, 1323740153u, 0u, 7336594331839796822ull, 4090224152u, 0u, 9606879354204243768ull, 4132414370u, 0u, 17311703474789392632ull, 408146281u, 0u, // 175 9283786001865631882ull, 2631639853u, 0u, 1270121225485574490ull, 2003729186u, 0u, 6466724401394528788ull, 3747048053u, 0u, 3024770132642913696ull, 132517971u, 0u, 10142525660374771442ull, 4042264028u, 0u, 5405002952274302800ull, 1771068370u, 0u, 7228601603786190988ull, 779081127u, 0u, 9169229730420051806ull, 1368875689u, 0u, 1409593575826062578ull, 3656693917u, 0u, 8384080688463345756ull, 3409003536u, 0u, 7414689876242375630ull, 667008198u, 0u, 9342347872337880888ull, 806245067u, 0u, 13920336889474453988ull, 4281874682u, 0u, 16530268544758980820ull, 3947771555u, 0u, 18029527031082259334ull, 1740359541u, 0u, 16985840055965335748ull, 3729546202u, 0u, 1353646727661718046ull, 431833843u, 0u, 8283549754394425084ull, 2241826882u, 0u, 16729294937655324146ull, 1229585102u, 0u, 992015582627879416ull, 3753604406u, 0u, 11459359852675334428ull, 715102990u, 0u, 15780295031220776676ull, 2849327479u, 0u, 15292882070254034754ull, 2661709892u, 0u, 2139065972611011500ull, 4013694686u, 0u, 3530163592614497828ull, 3162831094u, 0u, 3590868605047215866ull, 2920570167u, 0u, 17780809170585386292ull, 2082094119u, 0u, 16632346864747554850ull, 3995946939u, 0u, 9537943092702409664ull, 3926339991u, 0u, 16840129803449202896ull, 2149011355u, 0u, 10795023727480018324ull, 1742110979u, 0u, 13824065246716065976ull, 2114455495u, 0u, // 176 3456531783680191916ull, 1652627273u, 0u, 18152795152870396934ull, 1087132140u, 0u, 15706998763686540104ull, 2766810947u, 0u, 14328866193819101000ull, 1125404283u, 0u, 116432972241598708ull, 87354893u, 0u, 6171655951260741358ull, 2020517168u, 0u, 8679605892508274252ull, 1912397854u, 0u, 6866010066146595958ull, 3779571722u, 0u, 10637538499986329728ull, 602086027u, 0u, 4212718293477664120ull, 3898495025u, 0u, 11674318217842504024ull, 2897160666u, 0u, 16846238741743395400ull, 3710027656u, 0u, 3398066218022651170ull, 4068554727u, 0u, 13332239169458035004ull, 2788029466u, 0u, 5214052757036435538ull, 1300817049u, 0u, 12028260916387312166ull, 1905302038u, 0u, 7661125511940615458ull, 2834040250u, 0u, 10562876748884942742ull, 1892994342u, 0u, 16122341707220045194ull, 1394763901u, 0u, 16364374744409204546ull, 2646221435u, 0u, 3829590489499303974ull, 2772083420u, 0u, 11397564261045032222ull, 3458241052u, 0u, 5463161015002006330ull, 4032127459u, 0u, 12546249691198227890ull, 1338593274u, 0u, 16430373827554667924ull, 3953877704u, 0u, 9644247404292902242ull, 3559389454u, 0u, 12901438669132640656ull, 1384400970u, 0u, 16278937175019299026ull, 2212331457u, 0u, 6805216983675642992ull, 2236485404u, 0u, 738208387700386196ull, 2579675479u, 0u, 14361336625408260374ull, 3085539831u, 0u, 5955819369283231506ull, 1680884791u, 0u, // 177 7900733827253290190ull, 2755271508u, 0u, 6465722231438970748ull, 844616437u, 0u, 2058143866031597350ull, 836713670u, 0u, 6681969912456971612ull, 1305544039u, 0u, 7490546671009350864ull, 1437067685u, 0u, 11813922605015701100ull, 925139851u, 0u, 8512766739432452702ull, 452958370u, 0u, 14460483121496813908ull, 2941120595u, 0u, 17702253210870724372ull, 623306660u, 0u, 7288242844073868804ull, 368998861u, 0u, 16613273139477644868ull, 3318119069u, 0u, 3231724046572942992ull, 3602524854u, 0u, 15889932154731387540ull, 1004139698u, 0u, 18256373122460891444ull, 736677127u, 0u, 13343965026962129074ull, 621346153u, 0u, 8494867134589851736ull, 713718755u, 0u, 2939185389153030246ull, 2408404305u, 0u, 12549605826674834176ull, 2694312190u, 0u, 7488460382984324338ull, 1208439965u, 0u, 7912741801723476076ull, 978110485u, 0u, 17061907254452009758ull, 695555341u, 0u, 12902091065760635888ull, 2273932890u, 0u, 2974258832961485138ull, 1475624537u, 0u, 11865648106111927904ull, 3169934430u, 0u, 9222183298426340922ull, 1441871779u, 0u, 10629002012739593428ull, 2484087437u, 0u, 10739541300450900878ull, 2920111769u, 0u, 11870302453014965654ull, 1026458518u, 0u, 10991081007057629626ull, 2723759529u, 0u, 12878114954040202996ull, 3413762506u, 0u, 17963130689535983626ull, 3167996904u, 0u, 7686559897547178944ull, 1186218296u, 0u, // 178 4277494688849668008ull, 1416544333u, 0u, 16634785545558519638ull, 2770665160u, 0u, 7789338538683145546ull, 2541340503u, 0u, 5760587641769009288ull, 3246245461u, 0u, 10851519245645905956ull, 923365106u, 0u, 8215847222301950774ull, 1685784893u, 0u, 2953734328191618272ull, 309103216u, 0u, 10209971425386045940ull, 1095663256u, 0u, 5241482344642661184ull, 4075564108u, 0u, 11959199912603556902ull, 719430489u, 0u, 2497123027421959218ull, 1057083902u, 0u, 15604995471356388844ull, 560537644u, 0u, 6363814466048520272ull, 389562058u, 0u, 17508353430068079316ull, 4223947194u, 0u, 17476382607058615592ull, 3123286144u, 0u, 14846792929824419272ull, 1512182418u, 0u, 11165591440182151076ull, 4062297202u, 0u, 3005464509270625176ull, 2922193729u, 0u, 15285912306329971010ull, 3531980254u, 0u, 11160102643905391024ull, 1883429574u, 0u, 1881434548106376848ull, 594296649u, 0u, 14381260128214184158ull, 1877453048u, 0u, 16653110850820298862ull, 1990239880u, 0u, 12644686738031748152ull, 1232109779u, 0u, 4256801125440031360ull, 2386595437u, 0u, 7015560385532339176ull, 1650090097u, 0u, 15492101126442958646ull, 4151357816u, 0u, 16896824077562421070ull, 1778607443u, 0u, 15861408286516247668ull, 1983700222u, 0u, 16153173518085401780ull, 414925389u, 0u, 15286313423328373880ull, 3140864321u, 0u, 345065289649690960ull, 139311007u, 0u, // 179 15004879723315598942ull, 3026301275u, 0u, 6089729174300200032ull, 3139366155u, 0u, 5452126399801133034ull, 541007245u, 0u, 11840193100366054080ull, 161528248u, 0u, 11074150337497025354ull, 1764084364u, 0u, 11896643536971505392ull, 415048585u, 0u, 3347528401068138898ull, 1028539033u, 0u, 16318490083046668780ull, 184702405u, 0u, 6474585451970995212ull, 3155864593u, 0u, 7855803477018559284ull, 2417401129u, 0u, 3075972144566254242ull, 480593532u, 0u, 7733285434937216384ull, 3185696u, 0u, 13719992048081836092ull, 3038584432u, 0u, 1149951402410980432ull, 3542204061u, 0u, 6831106320416119718ull, 80744371u, 0u, 13829413331449377096ull, 1221609238u, 0u, 1686863696192672304ull, 953191538u, 0u, 11440754116730525808ull, 3074594245u, 0u, 13135131635252666512ull, 65500054u, 0u, 1604072789677157904ull, 3645831203u, 0u, 16733888478045228634ull, 197911280u, 0u, 2147460736910416470ull, 2130840090u, 0u, 16595668794063147680ull, 3567295343u, 0u, 4506686693370743372ull, 332755975u, 0u, 9680680509815937190ull, 1523114802u, 0u, 14761293371017525006ull, 3778928787u, 0u, 14354678513575948726ull, 2633738172u, 0u, 13169643324307838762ull, 3189071393u, 0u, 1174101546136316260ull, 4130078449u, 0u, 12955130501361297290ull, 2994639842u, 0u, 18309896295711102072ull, 4230676383u, 0u, 6517615081695598764ull, 4260459336u, 0u, // 180 9170737283929056590ull, 3116983968u, 0u, 8453335137521869390ull, 1780276940u, 0u, 15407066598941558598ull, 692118654u, 0u, 1239550844208916050ull, 1956648429u, 0u, 4536045751863424236ull, 3079460392u, 0u, 3764410625395335912ull, 3430790774u, 0u, 16422883504858304600ull, 3743613081u, 0u, 1290396919329104404ull, 4213897349u, 0u, 1912282108319998278ull, 3467067849u, 0u, 10421576360688290846ull, 1332670706u, 0u, 13151192665929992560ull, 2266336409u, 0u, 12454022869474215096ull, 817044138u, 0u, 14082158553186775486ull, 4078008272u, 0u, 8726052444979709206ull, 4099396746u, 0u, 2408620037864516444ull, 3240838754u, 0u, 15090093435669355556ull, 1310259584u, 0u, 2259539241763012972ull, 2218857526u, 0u, 1552581498779238640ull, 2584745387u, 0u, 2192336766953077216ull, 2234133162u, 0u, 13299131325220611022ull, 3046927830u, 0u, 17834255684032160250ull, 4067682674u, 0u, 14738104607149722792ull, 2972183105u, 0u, 16745300827648041648ull, 3496144883u, 0u, 16487020175170507188ull, 3086111430u, 0u, 4756015746974287342ull, 3772201742u, 0u, 16238317345213444764ull, 2678355590u, 0u, 6876877244517165612ull, 207847570u, 0u, 3485869435486435578ull, 1240047918u, 0u, 2706588575760093840ull, 977690721u, 0u, 984515407936376510ull, 166752188u, 0u, 8840263612269150682ull, 2648854684u, 0u, 1280082848087827296ull, 3156025436u, 0u, // 181 4780991779030288942ull, 4283898675u, 0u, 6858437907950168094ull, 1241070232u, 0u, 5838678507421787202ull, 2413652944u, 0u, 3386524436055092282ull, 239800269u, 0u, 556101556463081064ull, 1878860919u, 0u, 12271402230042129156ull, 2475734097u, 0u, 14053373531264521206ull, 3855497163u, 0u, 17729196646267036208ull, 3554087441u, 0u, 4793962071599611296ull, 419184395u, 0u, 15706593515836931290ull, 35095685u, 0u, 8262095879521580978ull, 3911172069u, 0u, 11383135760600615028ull, 816119145u, 0u, 8164895227795632718ull, 3239168905u, 0u, 7402825458429685626ull, 4061917809u, 0u, 17094155848987203142ull, 1294824869u, 0u, 7270498959997787260ull, 686790708u, 0u, 17999073385319089238ull, 4074310480u, 0u, 12393333415449512258ull, 3588577959u, 0u, 16185827439645211594ull, 4292539681u, 0u, 18336305564054960772ull, 3546916833u, 0u, 13472429518505194270ull, 898903351u, 0u, 15557698678658657006ull, 3223792776u, 0u, 10769536427350666796ull, 443141898u, 0u, 4756308984971033148ull, 3776607807u, 0u, 18127042229870974068ull, 2845990349u, 0u, 7053489444009195420ull, 11038320u, 0u, 5314489508645637156ull, 1432309361u, 0u, 6711254727424176940ull, 2476339773u, 0u, 7602508391484626098ull, 811100382u, 0u, 5332382762949841402ull, 2731745576u, 0u, 9408615560281922812ull, 7189943u, 0u, 4052512365521900172ull, 513285667u, 0u, // 182 1898016000862652068ull, 2211382u, 0u, 4702045920329413316ull, 2566065337u, 0u, 5687709478853876382ull, 2587778833u, 0u, 14701435055344925116ull, 2161254421u, 0u, 18387627048193779808ull, 14801278u, 0u, 134801161015659158ull, 2369935216u, 0u, 12208558260248705736ull, 3085095658u, 0u, 8635552854736606136ull, 3697240149u, 0u, 13494034368148734810ull, 4050414355u, 0u, 4837758639087132506ull, 241002893u, 0u, 7330161375394634740ull, 381884148u, 0u, 14202528159899905678ull, 4096682660u, 0u, 2929426462759410530ull, 2376180939u, 0u, 4192436706376917704ull, 1140265967u, 0u, 11930035013203541518ull, 2152566900u, 0u, 11871255045132853554ull, 602407481u, 0u, 17513346193393851002ull, 4159363689u, 0u, 15046113515847571136ull, 374010958u, 0u, 9020396982529048926ull, 335118838u, 0u, 3148379223803117916ull, 3535271012u, 0u, 16445234759067836502ull, 952259034u, 0u, 9006602518008943724ull, 2560221320u, 0u, 15440559000642566716ull, 1042108852u, 0u, 198566518843289476ull, 3218771929u, 0u, 6444098315453019226ull, 3815103875u, 0u, 3472693304469171388ull, 3989063407u, 0u, 11389936705188437152ull, 3344781623u, 0u, 16628720227515167932ull, 2184474805u, 0u, 1272601742968873820ull, 2525963829u, 0u, 3674938077068834010ull, 3657492608u, 0u, 587963578231852272ull, 62955709u, 0u, 13079141811415121076ull, 2944343873u, 0u, // 183 3851883992986031464ull, 1768906477u, 0u, 5164257421312746188ull, 492086422u, 0u, 10668558715833790218ull, 3701219134u, 0u, 3374747251119813690ull, 3138019251u, 0u, 10663263850581387114ull, 308143562u, 0u, 528390310827512618ull, 2360412409u, 0u, 8198403251304326778ull, 125114102u, 0u, 6462635093219102740ull, 180606766u, 0u, 13179761330541510260ull, 716452533u, 0u, 6428075066652639096ull, 947796000u, 0u, 10681653790925004298ull, 109718672u, 0u, 9042927649324554904ull, 18168017u, 0u, 14548949435705633754ull, 4177695510u, 0u, 18396925847587695514ull, 1092417259u, 0u, 7031960025225621910ull, 66239864u, 0u, 3740473399137060038ull, 702354096u, 0u, 15234145469924009090ull, 3996337516u, 0u, 7284832344009849676ull, 1525335757u, 0u, 2376438301497694594ull, 313614469u, 0u, 7773419929980259296ull, 3010987717u, 0u, 18177931638174763738ull, 3084412545u, 0u, 14643223298871818978ull, 471367263u, 0u, 13768959790637138896ull, 2589892827u, 0u, 9868243441347669566ull, 4223624312u, 0u, 7483282933043399332ull, 91390437u, 0u, 989931208590610886ull, 4107567155u, 0u, 523136680421778448ull, 2528944332u, 0u, 4161744506466469598ull, 2993180918u, 0u, 15161108716503669518ull, 2949198830u, 0u, 5357875867127107300ull, 2887709111u, 0u, 4646919452718403004ull, 487004293u, 0u, 7604184795046870830ull, 1973181204u, 0u, // 184 6114221882395460348ull, 989132727u, 0u, 15971564198130200820ull, 1771920603u, 0u, 17080373155704122020ull, 3769526862u, 0u, 18237788286682252850ull, 214215707u, 0u, 2415649549612629756ull, 3771961428u, 0u, 16757284187535020590ull, 958728606u, 0u, 13685454631365313990ull, 3407505292u, 0u, 553088159534617938ull, 773696427u, 0u, 14729608628723816592ull, 761853868u, 0u, 14527852259873534734ull, 2145238338u, 0u, 2549221125172690314ull, 2870142993u, 0u, 16710929852378187134ull, 3499683038u, 0u, 2549719989198254892ull, 1085215772u, 0u, 13356543025230511326ull, 9368625u, 0u, 8935575952640977440ull, 3513652862u, 0u, 14699310791527946174ull, 2191575900u, 0u, 11998742134271756126ull, 3956260876u, 0u, 5908598285972179712ull, 3182990518u, 0u, 5988933604813305294ull, 35004832u, 0u, 15277164577861627514ull, 3578098801u, 0u, 4915297635655082764ull, 3046066822u, 0u, 12012638425143547660ull, 2594166398u, 0u, 16125729379852646588ull, 1623928599u, 0u, 742944599337601700ull, 3271978384u, 0u, 7228900204441540624ull, 3527018713u, 0u, 8009045707788736710ull, 2079518560u, 0u, 16772803076100913808ull, 1310640773u, 0u, 3622747442585401500ull, 1740156509u, 0u, 2912711671691696012ull, 3249818525u, 0u, 663124657933716496ull, 3815544192u, 0u, 1183508142586295838ull, 789651423u, 0u, 11876819939593083472ull, 3517879177u, 0u, // 185 6519604344102512054ull, 610731989u, 0u, 92159824788362796ull, 4117168401u, 0u, 11007911512136902192ull, 3840806361u, 0u, 730768109918666872ull, 1739630634u, 0u, 7578434606896057560ull, 1520255793u, 0u, 17291349192020534834ull, 4014268084u, 0u, 8402963265022014116ull, 1242153657u, 0u, 16730097989379618514ull, 872782888u, 0u, 14618150426926592484ull, 3399080835u, 0u, 39168301289142602ull, 2940001709u, 0u, 2036357960541945120ull, 2927921694u, 0u, 12634310347318712514ull, 738479338u, 0u, 1617425409469383182ull, 3316006821u, 0u, 8073374004557649338ull, 3124397310u, 0u, 3111761945329518086ull, 2600063067u, 0u, 8818969263441743990ull, 600105190u, 0u, 9148946649352460334ull, 4257677185u, 0u, 14050215682408318768ull, 4090726198u, 0u, 4424495720618330828ull, 2712111438u, 0u, 14781305853986184654ull, 2853963163u, 0u, 15635163164548031130ull, 2139981225u, 0u, 7410115741269558606ull, 1170857351u, 0u, 1196452589516413510ull, 3191278688u, 0u, 2934171197457498042ull, 4084279911u, 0u, 7156076051444561134ull, 311347878u, 0u, 9806474093062076616ull, 3508352767u, 0u, 4399018717715289952ull, 1865946702u, 0u, 13993518469975338650ull, 3696295582u, 0u, 1052723040171942456ull, 2870483172u, 0u, 8444289425053574546ull, 1748057667u, 0u, 7602425969287957810ull, 19137351u, 0u, 8659047132888060386ull, 2190921966u, 0u, // 186 14558891059195509938ull, 1581701445u, 0u, 1123018144857359984ull, 181713219u, 0u, 17026449138078189248ull, 729711475u, 0u, 11870905863448680776ull, 3124759577u, 0u, 16764471776041249246ull, 1475299527u, 0u, 12327426067685298872ull, 1733744033u, 0u, 5205592324381319264ull, 2877289524u, 0u, 12654051881937279194ull, 2522740199u, 0u, 510346058073328568ull, 1611641012u, 0u, 9354130567653423500ull, 3393742445u, 0u, 15292912307094480154ull, 347745431u, 0u, 1704214397475186016ull, 4148388405u, 0u, 4399029177397799266ull, 3884218049u, 0u, 15596476355507811914ull, 882160101u, 0u, 3368628170525030040ull, 846507168u, 0u, 18245108690949244932ull, 3710289287u, 0u, 12946155417730668408ull, 4210587006u, 0u, 7351895156793987318ull, 1452044024u, 0u, 803965471761339440ull, 2683456721u, 0u, 12295269816058819102ull, 172975525u, 0u, 6876134594393571718ull, 2558614589u, 0u, 7746275380960739198ull, 2232172661u, 0u, 14944606479345438266ull, 3653539742u, 0u, 6886350165497261198ull, 2988694529u, 0u, 908715268296610672ull, 4018385463u, 0u, 13599588275444942222ull, 1700124521u, 0u, 12273915330326324376ull, 3262176592u, 0u, 84442168487811252ull, 3606202591u, 0u, 16618932773227839158ull, 591007480u, 0u, 14541062887896812180ull, 1911766980u, 0u, 13659799037499513702ull, 1017680407u, 0u, 200203252076756694ull, 682932778u, 0u, // 187 8779403080935822334ull, 3142899773u, 0u, 12242636634885410148ull, 1693373775u, 0u, 1916163386651083052ull, 1742901447u, 0u, 4707932240208335956ull, 2894842286u, 0u, 14694302575201775982ull, 1556904655u, 0u, 17460678107141847202ull, 2697290576u, 0u, 120061104269109376ull, 3983603375u, 0u, 14332297414965869918ull, 891183873u, 0u, 13529773796918322642ull, 1763121827u, 0u, 2493224531556161408ull, 2923541414u, 0u, 15027098958686646306ull, 81121969u, 0u, 2181524989202496974ull, 2814763315u, 0u, 8892074430781281924ull, 3196683985u, 0u, 2680199398236062302ull, 2156653454u, 0u, 8588999693842782228ull, 99508128u, 0u, 87606891379210996ull, 167684815u, 0u, 17360224611991464374ull, 3449628019u, 0u, 3259107880578243000ull, 3934132381u, 0u, 1211738279055266718ull, 4237996963u, 0u, 7715107236736527004ull, 2806734203u, 0u, 3316120732333545264ull, 4148364220u, 0u, 13316440852066639292ull, 2939797595u, 0u, 11734524505849567108ull, 4292456036u, 0u, 13013141280628507680ull, 1166461570u, 0u, 10770385513639194694ull, 3825285738u, 0u, 17700260567229693404ull, 3472044401u, 0u, 6875698556095733300ull, 3131760410u, 0u, 1816675360782005624ull, 347397926u, 0u, 1266380855738891552ull, 3876438260u, 0u, 2455189082466471434ull, 900660497u, 0u, 7319384840585111026ull, 1640842368u, 0u, 12474272206747730844ull, 3471762922u, 0u, // 188 13158355966182845818ull, 4068883271u, 0u, 1590880655630603614ull, 92052191u, 0u, 16810800853492071166ull, 2910432805u, 0u, 14313166307796742296ull, 3755672397u, 0u, 773247550813139974ull, 3396164305u, 0u, 1209716207993488768ull, 2220318630u, 0u, 7209207409347652936ull, 1499541674u, 0u, 13845588452493772598ull, 2598342418u, 0u, 1997101840692495912ull, 4237831518u, 0u, 12135247973657788784ull, 1871033108u, 0u, 6451930583037942402ull, 223117989u, 0u, 17564324231167699778ull, 2832878834u, 0u, 9842899721509490272ull, 1837375290u, 0u, 1143945265483575032ull, 2694500807u, 0u, 986385353764051160ull, 1131078208u, 0u, 13014910431642093498ull, 4055973823u, 0u, 17721780455700929128ull, 4144365255u, 0u, 1977972176607400824ull, 4215601536u, 0u, 11432185519258577808ull, 755353774u, 0u, 9559597432902994838ull, 2980012538u, 0u, 9487871371949008632ull, 1986321784u, 0u, 12068454776813469668ull, 810998873u, 0u, 15368994757153995240ull, 4050938400u, 0u, 6683093470708055852ull, 4117593063u, 0u, 2660784888096755186ull, 4276255292u, 0u, 7354806007934958872ull, 35305895u, 0u, 14150522200614711806ull, 714909235u, 0u, 6958951532190720040ull, 643283527u, 0u, 2191731056456520498ull, 1749832899u, 0u, 9238263476224347246ull, 4176947636u, 0u, 7501095315605467002ull, 3618117616u, 0u, 13876175320919029284ull, 1429172349u, 0u, // 189 16338906232519282426ull, 38356291u, 0u, 14269150839434227698ull, 3755631171u, 0u, 4184494318099961752ull, 1569341001u, 0u, 15456863693330286938ull, 1431053247u, 0u, 4361640742951902248ull, 1417065687u, 0u, 2060676610688908460ull, 1082619797u, 0u, 11790866026302843826ull, 1563479154u, 0u, 9822606540547080702ull, 1530618766u, 0u, 5502645307937101268ull, 1031882807u, 0u, 16210569366586808402ull, 1700587490u, 0u, 7044720355478543564ull, 1908218915u, 0u, 6761084008221733714ull, 3421434241u, 0u, 3616684277161471902ull, 3298691732u, 0u, 377329199127679214ull, 2138536052u, 0u, 8522679881567062878ull, 191853799u, 0u, 11788585977381722810ull, 89325524u, 0u, 64226940488623140ull, 2257668287u, 0u, 8058980299242807056ull, 1677647418u, 0u, 15236686927427798688ull, 3831438045u, 0u, 4401575350642805520ull, 1100392152u, 0u, 16035238150008729332ull, 849976895u, 0u, 12752887298291440900ull, 786956222u, 0u, 5377915704767504156ull, 3858904618u, 0u, 12952332730056352774ull, 3919142247u, 0u, 7368462987387065678ull, 69255567u, 0u, 17555925470391701182ull, 2261710520u, 0u, 13088756712098650892ull, 2879559751u, 0u, 8410589306217669792ull, 2472298200u, 0u, 3181186554179667338ull, 1315101950u, 0u, 18316418305888403540ull, 3725177498u, 0u, 4606608651538790304ull, 3137109629u, 0u, 10819156882559011582ull, 1652580742u, 0u, // 190 9118853166885229872ull, 3651886306u, 0u, 17281194802219145260ull, 2031918838u, 0u, 6710911916931662152ull, 2348106175u, 0u, 13494979649946645460ull, 3230215435u, 0u, 5803890799766869978ull, 1724765980u, 0u, 8571324099019162554ull, 3618966801u, 0u, 3986416628909984728ull, 1329206586u, 0u, 4226651813781263312ull, 794806128u, 0u, 14585834711676038056ull, 678663790u, 0u, 15165636154719148268ull, 89266189u, 0u, 2998009986074922052ull, 2232304726u, 0u, 13216045237233912818ull, 295748250u, 0u, 6615744967473945836ull, 4190721648u, 0u, 6997969441824275498ull, 733079761u, 0u, 14429552373152158016ull, 3595983509u, 0u, 12026526526835246014ull, 3358893758u, 0u, 13095941442921572140ull, 171627862u, 0u, 401288109494732492ull, 802089933u, 0u, 7921810126751086798ull, 381660011u, 0u, 18385329220658541096ull, 1492970618u, 0u, 15518341160362761498ull, 538523725u, 0u, 11086004220936196802ull, 3546425909u, 0u, 15525084936453118158ull, 2175707761u, 0u, 11574761212690790434ull, 3076316301u, 0u, 5644341295377969082ull, 388776310u, 0u, 12708646230002463404ull, 2258020868u, 0u, 6036252522984264886ull, 4046932924u, 0u, 11932312332060048316ull, 2911431604u, 0u, 15627662079975560752ull, 1657513037u, 0u, 17316061749463694148ull, 4031619704u, 0u, 13718126660320941268ull, 3135293765u, 0u, 876320907796670278ull, 4139876409u, 0u, // 191 12668516598746763058ull, 4197888341u, 0u, 1599126201462137064ull, 2913368009u, 0u, 11249221561076687514ull, 3694933812u, 0u, 11114664850117776120ull, 2937922452u, 0u, 2789502370951159694ull, 4178285520u, 0u, 1206054223899996838ull, 918915310u, 0u, 16146356557846067132ull, 2912774528u, 0u, 14865776568215896530ull, 1341146714u, 0u, 12926365277366811480ull, 3099522467u, 0u, 14327117515464109276ull, 2622999989u, 0u, 7826242696819237764ull, 3381224237u, 0u, 14755478283509900226ull, 1816519314u, 0u, 712939058602724848ull, 663225246u, 0u, 456712873414807578ull, 2207116676u, 0u, 9287687271826716510ull, 738977708u, 0u, 1893804091412439290ull, 2081238023u, 0u, 3200500565377496920ull, 1651151518u, 0u, 11564749141434850696ull, 3637068745u, 0u, 5900847718553231744ull, 262422168u, 0u, 6293158562493787972ull, 2395718173u, 0u, 5933081041548949254ull, 611893853u, 0u, 11376401727041782066ull, 868841489u, 0u, 14534318628366810364ull, 2051479919u, 0u, 11326705419358607502ull, 2456532536u, 0u, 7826622104144661906ull, 2312181557u, 0u, 358319669632452204ull, 135504053u, 0u, 3116050517906058768ull, 3842725802u, 0u, 9273176093448287804ull, 3579893265u, 0u, 12503556410744196498ull, 4057420134u, 0u, 7555787240846023086ull, 1854865986u, 0u, 3917011589692551028ull, 742607384u, 0u, 5730419511425861828ull, 3145495447u, 0u, // 192 10507248894222470092ull, 1662772018u, 0u, 15882776104723248280ull, 1045808178u, 0u, 9348291518449577308ull, 2069218897u, 0u, 8844257723995063532ull, 3172862211u, 0u, 17826827854726261808ull, 2013782049u, 0u, 5848046796326538998ull, 4202390990u, 0u, 14702678121732041276ull, 2127853534u, 0u, 12683251353133336552ull, 909978600u, 0u, 4724904340219570732ull, 4223282430u, 0u, 14342958834033781874ull, 1471490026u, 0u, 15902398005296598642ull, 1778857067u, 0u, 14676433962963936434ull, 1830425727u, 0u, 4373653559439697988ull, 1648324627u, 0u, 17609971526292888112ull, 347547172u, 0u, 11811534487134059662ull, 3234976421u, 0u, 11495586292045462130ull, 4160237608u, 0u, 2905464312929864956ull, 3049591778u, 0u, 579653157645559714ull, 3110327410u, 0u, 17940005652452889800ull, 3393561683u, 0u, 18165076074305975414ull, 960207182u, 0u, 10275174134760133622ull, 4196523938u, 0u, 6601325798672422516ull, 216899380u, 0u, 8729076657605009220ull, 1635161120u, 0u, 8232410809183372450ull, 302673780u, 0u, 9438685749168022040ull, 1999416267u, 0u, 3803347272540211232ull, 1411300581u, 0u, 14607597425836978132ull, 2068377525u, 0u, 18037467315510593254ull, 4119095034u, 0u, 9013095558834792044ull, 3895353397u, 0u, 12938715107655656654ull, 625720094u, 0u, 2077935896871351668ull, 1490993754u, 0u, 10364041029307508210ull, 3904029547u, 0u, // 193 15820974419424302362ull, 777262504u, 0u, 4515402264915368838ull, 628059444u, 0u, 7116967297791720690ull, 3104941237u, 0u, 4687077222363400094ull, 81590167u, 0u, 16052521928698755568ull, 3370409331u, 0u, 7196595324849275484ull, 3034833021u, 0u, 16007360568535983626ull, 2195478506u, 0u, 1478125920539850490ull, 2147584597u, 0u, 6601653196823160926ull, 2147960757u, 0u, 5904808241163432782ull, 3896592894u, 0u, 10808701755897734432ull, 3184552699u, 0u, 5717283329108523034ull, 2979930907u, 0u, 4550534524243312430ull, 517608571u, 0u, 8215012707022819096ull, 3180084234u, 0u, 5174781914083035120ull, 2903751837u, 0u, 926812471192956612ull, 813973763u, 0u, 4408535359088310674ull, 2494874611u, 0u, 7178906211193938174ull, 2446770590u, 0u, 10212686372900068362ull, 1896100092u, 0u, 428508152293655566ull, 3404858823u, 0u, 9567898115592233940ull, 2825402171u, 0u, 4218854276509212078ull, 1920764505u, 0u, 6761337028418131242ull, 1690288675u, 0u, 17328295353640587492ull, 1880399938u, 0u, 14683866898416578270ull, 1923424663u, 0u, 12774392000875503000ull, 3332124202u, 0u, 15127296928167592816ull, 1704103861u, 0u, 14063022555679641556ull, 580046915u, 0u, 12511288564259800544ull, 2518020857u, 0u, 4026900176457553532ull, 690518365u, 0u, 13357981914006256426ull, 2530176266u, 0u, 4180951316356886504ull, 2987852621u, 0u, // 194 16508976564057577740ull, 835075975u, 0u, 4179670679494319288ull, 898353364u, 0u, 13764359808073660610ull, 1122476477u, 0u, 18293856112320129396ull, 2398567023u, 0u, 11925809506768414432ull, 592544941u, 0u, 3972788407304348070ull, 3132977916u, 0u, 14643825929077768070ull, 2415946624u, 0u, 14492486268217029508ull, 2888422042u, 0u, 717652767108398000ull, 1508586773u, 0u, 15446158777389731064ull, 1395433910u, 0u, 12024657882316384806ull, 3014503890u, 0u, 1133071500670866524ull, 1513280037u, 0u, 2358623544037719318ull, 3161188509u, 0u, 8789751427595571230ull, 3314894383u, 0u, 7879463774557709488ull, 330681584u, 0u, 13922822078627070838ull, 3659332707u, 0u, 9215562392341352900ull, 2694791181u, 0u, 2818054770990778278ull, 3037431158u, 0u, 10712198617387433604ull, 1068507942u, 0u, 5526221054014724462ull, 2064879948u, 0u, 11065169052497639488ull, 612663934u, 0u, 258136737223073154ull, 530419771u, 0u, 10098414881313758070ull, 1213082374u, 0u, 12948882599370573060ull, 3272245354u, 0u, 17781530509212840968ull, 3789252920u, 0u, 9619015855531312784ull, 1192154909u, 0u, 9514966062747561540ull, 3620329677u, 0u, 4517521788011728398ull, 3231660136u, 0u, 8484391223059095098ull, 1719113327u, 0u, 14053584114966520080ull, 2181982922u, 0u, 8039821658160642488ull, 2032700751u, 0u, 13244427942236016758ull, 859353882u, 0u, // 195 9999311432033605606ull, 823637723u, 0u, 15623365825975312588ull, 3058169119u, 0u, 14534843411667072148ull, 1502327466u, 0u, 16009182181011932484ull, 302262963u, 0u, 228067379274813182ull, 493144418u, 0u, 8311390718886903562ull, 466986620u, 0u, 14545774639109042132ull, 2431940769u, 0u, 11951839295041771140ull, 2456919328u, 0u, 14233545675367883780ull, 3552469020u, 0u, 5457850456602672156ull, 2225890218u, 0u, 13106175100502192186ull, 1800531003u, 0u, 17302260477946280566ull, 2932771776u, 0u, 2473111788405479936ull, 2730243332u, 0u, 12264667859477318658ull, 1096014873u, 0u, 11459954209399101844ull, 182835529u, 0u, 1907683257161779208ull, 2546443152u, 0u, 3641429663679838664ull, 1225349843u, 0u, 11314974260120313058ull, 2059888290u, 0u, 8745278211995522102ull, 780241807u, 0u, 4455163003791507270ull, 299540487u, 0u, 14859403386911900596ull, 1057009422u, 0u, 17474806295383769432ull, 229831521u, 0u, 8222305439433549894ull, 12279200u, 0u, 3375907935571572572ull, 3424977958u, 0u, 11704525998484299052ull, 3200204831u, 0u, 3604279038318230790ull, 214540415u, 0u, 2115441279808688456ull, 782296385u, 0u, 13323852593724440634ull, 2017469082u, 0u, 7755983239758269942ull, 2654463715u, 0u, 16423084136731181104ull, 1671059839u, 0u, 5078195443126419286ull, 2732853990u, 0u, 16055150786271989146ull, 2355235002u, 0u, // 196 5194086743576930714ull, 1491691332u, 0u, 12482734628856124006ull, 2361326735u, 0u, 1315376051475446568ull, 3327955221u, 0u, 15906268829304056802ull, 4234789429u, 0u, 12019296697492157052ull, 3568044856u, 0u, 8244166050296835420ull, 117270199u, 0u, 10460577777526057716ull, 79952014u, 0u, 5681852820932655376ull, 1902920730u, 0u, 17253169894078981226ull, 1867019920u, 0u, 6816796512429681656ull, 1348737168u, 0u, 11658994077853602216ull, 2713971469u, 0u, 2157985360157170710ull, 3501606560u, 0u, 10305209026587390954ull, 956419328u, 0u, 10607206698055320868ull, 994569503u, 0u, 12486103525376769180ull, 2701852264u, 0u, 13706410754414328738ull, 3386722361u, 0u, 190593403422847752ull, 1044860665u, 0u, 2901945787738330384ull, 1133440630u, 0u, 10702795257730303426ull, 2243410838u, 0u, 2850329536053744064ull, 339231531u, 0u, 2015092137540122916ull, 3857530527u, 0u, 396216926286133742ull, 1048824735u, 0u, 7801851245577320486ull, 1213353030u, 0u, 14840696672859303362ull, 3257898410u, 0u, 12863332803402247722ull, 1937077758u, 0u, 3459210056924977180ull, 1461219871u, 0u, 11592028724752377318ull, 776645216u, 0u, 2449931309490120230ull, 767364970u, 0u, 6866070903762117926ull, 636776129u, 0u, 14570721763784015638ull, 2691199751u, 0u, 15388347228039672096ull, 3530551187u, 0u, 16683045472062416360ull, 3323869677u, 0u, // 197 10735030111910071772ull, 3596225251u, 0u, 7743702929250744598ull, 1443003769u, 0u, 11906230099066873514ull, 202886699u, 0u, 4167316197041073380ull, 3866981230u, 0u, 13969933157677407188ull, 2631969113u, 0u, 8342946011741665096ull, 1395067178u, 0u, 7431932661729561520ull, 2611764364u, 0u, 15864702868833416830ull, 3289041223u, 0u, 13347618455715766550ull, 1154652u, 0u, 7885594831229720100ull, 1638270219u, 0u, 2785440701409400280ull, 203987658u, 0u, 10596268535409678280ull, 3307604324u, 0u, 15361345139096723358ull, 2434449795u, 0u, 16697873739521284430ull, 162361593u, 0u, 6715364901828567514ull, 1358726983u, 0u, 7878730275085952430ull, 3351577636u, 0u, 7005698540384617162ull, 450274989u, 0u, 10856894161487395770ull, 1238696749u, 0u, 5197294359393109122ull, 170283896u, 0u, 8381092319972037900ull, 10210160u, 0u, 2060555301306328470ull, 1741557439u, 0u, 4241956344382879822ull, 2046994869u, 0u, 5676165106703026572ull, 1699282689u, 0u, 9336732754421115060ull, 1585730948u, 0u, 1991877095440288158ull, 1139856673u, 0u, 11702751443900930458ull, 119018293u, 0u, 9183962843171244422ull, 4180934820u, 0u, 17188957793316933426ull, 679299069u, 0u, 15956826950482589332ull, 2331445362u, 0u, 1886736988407440016ull, 1980811062u, 0u, 1852060596875674220ull, 921444117u, 0u, 5665957523703426504ull, 119434940u, 0u, // 198 1373048490178024302ull, 4277550065u, 0u, 11322545278534821528ull, 716445052u, 0u, 10736651136737921580ull, 3385252581u, 0u, 4905217809405372338ull, 436233604u, 0u, 12335827696842882392ull, 2657989997u, 0u, 13402075359184808700ull, 491879132u, 0u, 7055151086695300610ull, 260648121u, 0u, 9108175410713016752ull, 2257623237u, 0u, 17445032545189784818ull, 3430719010u, 0u, 15141447979753960222ull, 942649893u, 0u, 12231468322111274280ull, 1823754236u, 0u, 18279469511004035680ull, 660783132u, 0u, 18262669675741065350ull, 2116217648u, 0u, 11531639902495078118ull, 989815261u, 0u, 4888574411960686896ull, 4120209331u, 0u, 3072569855158851242ull, 3228972672u, 0u, 13652985485630037732ull, 1207675097u, 0u, 6879353969490658426ull, 3988265597u, 0u, 12450851745875906670ull, 3403887505u, 0u, 7192349787577983280ull, 1983024273u, 0u, 10347267075201283646ull, 1794205286u, 0u, 12152670260095580704ull, 3200234624u, 0u, 2726318018908342488ull, 2062336556u, 0u, 7672058071190024272ull, 2700680888u, 0u, 16148707392642901498ull, 1685242488u, 0u, 2845875794483393452ull, 1026964436u, 0u, 4837067265297910184ull, 1493547012u, 0u, 12638643180716775990ull, 4236405770u, 0u, 11038456790996789012ull, 1134214359u, 0u, 9105003820719344742ull, 964071053u, 0u, 10255955630898160132ull, 1228012830u, 0u, 17163045272171154082ull, 40923901u, 0u, // 199 9497985909241288982ull, 368156226u, 0u, 8182464451954468034ull, 338753901u, 0u, 6427867957906377756ull, 4224867559u, 0u, 8983872843625293250ull, 3022384786u, 0u, 12512687992418636116ull, 1119419311u, 0u, 8953079584185594464ull, 161637082u, 0u, 12251675169916576214ull, 948544663u, 0u, 7195622979401119306ull, 3610929898u, 0u, 8310548072970202644ull, 469189927u, 0u, 14518836770876263238ull, 1210569076u, 0u, 3543934236429472294ull, 3765447078u, 0u, 11166247692607703122ull, 2324200382u, 0u, 5690417611579645592ull, 2689175615u, 0u, 16769646356236921400ull, 1973824470u, 0u, 12276426616163834292ull, 3064393717u, 0u, 3960626751324494952ull, 4271657749u, 0u, 11190496738657036584ull, 1601177976u, 0u, 4646358036561837610ull, 2075671766u, 0u, 13306404029086765318ull, 1355960013u, 0u, 1601360126635637884ull, 591598865u, 0u, 5759674141570880520ull, 1386605675u, 0u, 18334060597687350144ull, 3341472266u, 0u, 2064006232572673992ull, 898062498u, 0u, 11065654879867649330ull, 389148320u, 0u, 9527996867489582782ull, 2359049817u, 0u, 11060889558380689206ull, 1088375738u, 0u, 3183611707219923962ull, 4067273081u, 0u, 14842068918812716804ull, 1606489685u, 0u, 12047569208458543308ull, 2266315386u, 0u, 13332759757008140386ull, 456704120u, 0u, 7756023262133206156ull, 463168070u, 0u, 4996534141696998050ull, 1614655735u, 0u, // 200 2124243671818200536ull, 4148957161u, 0u, 16805155653225316564ull, 239189784u, 0u, 16502491733000926644ull, 2725902604u, 0u, 10952597481426996034ull, 2953141930u, 0u, 11079398568732400246ull, 1406446690u, 0u, 2263983477061476536ull, 1281837631u, 0u, 3575085109271222622ull, 3703713957u, 0u, 6478501806399779700ull, 826341227u, 0u, 4315454957949548418ull, 4257470222u, 0u, 15891664834531390636ull, 2062998663u, 0u, 2047796573713234066ull, 3089106735u, 0u, 12911835472052233870ull, 3374266976u, 0u, 1545498000854393322ull, 806700514u, 0u, 4174622731153963336ull, 3758726701u, 0u, 12766558370418168726ull, 1047956027u, 0u, 15883024584379908642ull, 315905961u, 0u, 3156453896422326940ull, 267778076u, 0u, 16526088031153974056ull, 1224509333u, 0u, 17639438578204989444ull, 1216649518u, 0u, 2399743152896969646ull, 555127319u, 0u, 14995744801264522076ull, 1188372442u, 0u, 5456886493721796382ull, 642790719u, 0u, 8694856725616237734ull, 412141543u, 0u, 9661928426103295722ull, 1834991528u, 0u, 15096859509218447984ull, 1374648344u, 0u, 9090547130796045216ull, 2199219987u, 0u, 1345037594465133246ull, 2858465983u, 0u, 17007724937726777384ull, 3332822610u, 0u, 14876091601371026084ull, 1291504681u, 0u, 4517968495676770630ull, 1362977193u, 0u, 10642400579053854652ull, 489555679u, 0u, 10469389308717658078ull, 1074724053u, 0u, // 201 6288942140883815292ull, 2081082876u, 0u, 15633899061857263834ull, 217016413u, 0u, 15138096047732771722ull, 681232363u, 0u, 9271640757578793008ull, 3050586982u, 0u, 13719167825931012240ull, 2526512161u, 0u, 12907769423196580402ull, 3076160280u, 0u, 8435005298219718332ull, 3861963391u, 0u, 1227501022908450610ull, 139488501u, 0u, 2030381660975328228ull, 2344952363u, 0u, 32045842382387788ull, 3800725962u, 0u, 4083905425971006830ull, 582988989u, 0u, 5228370418413431276ull, 102281848u, 0u, 8483811670396307408ull, 1644366897u, 0u, 11775286282311184664ull, 409509047u, 0u, 17692318098324881542ull, 495399923u, 0u, 16531106704610748738ull, 1592168433u, 0u, 18375157373615021132ull, 3485883930u, 0u, 13707236392055985592ull, 1550971048u, 0u, 1159817639798507422ull, 485844590u, 0u, 6925037052469175446ull, 4124320856u, 0u, 18418225539704560028ull, 2444363454u, 0u, 2853966677457361662ull, 1720207070u, 0u, 11638034087115185750ull, 4014073587u, 0u, 12787614606859613060ull, 895885109u, 0u, 11638290149093357302ull, 3831116488u, 0u, 7580037951929856758ull, 1309801666u, 0u, 7779900224680370458ull, 1529995134u, 0u, 17034366604595595928ull, 3895255007u, 0u, 17710663259596493898ull, 1182835334u, 0u, 2876328795487267530ull, 2245973638u, 0u, 2124866479489012314ull, 609155494u, 0u, 6071708548443516330ull, 63398951u, 0u, // 202 3982366328199842940ull, 3963047987u, 0u, 5683582755848126518ull, 1192722285u, 0u, 5169538243709238818ull, 3254561876u, 0u, 1934062118281954562ull, 4055005702u, 0u, 8110701446288704314ull, 2517164149u, 0u, 9861198945029821918ull, 2037509895u, 0u, 12211813013481625738ull, 255521721u, 0u, 6280718653207462670ull, 26131552u, 0u, 9247696418383424498ull, 1309198644u, 0u, 5194645103859138734ull, 3209741026u, 0u, 4286298028070421530ull, 182461665u, 0u, 13997193187935944878ull, 1381326265u, 0u, 6155193690751794990ull, 3027665326u, 0u, 18426445769773735708ull, 904914425u, 0u, 4409707785326054108ull, 1100432753u, 0u, 11292697127467034722ull, 743758893u, 0u, 14345799842124298964ull, 2111009069u, 0u, 8091953523530469474ull, 1401771947u, 0u, 6317797394434986158ull, 1570368994u, 0u, 3356971252338422802ull, 272935554u, 0u, 16232608226310190934ull, 3248160161u, 0u, 2622996252047851166ull, 4240149223u, 0u, 16832243083466838038ull, 1535994230u, 0u, 5502543559263328236ull, 590050038u, 0u, 845008821384406468ull, 2835352083u, 0u, 3165584193591187116ull, 2413204197u, 0u, 16426360384199137886ull, 1710365345u, 0u, 18336708522698079702ull, 2749007395u, 0u, 10700914302465864096ull, 583702767u, 0u, 15326562292995864304ull, 1483600960u, 0u, 10187632988928003070ull, 665198067u, 0u, 4224478119767958268ull, 304544794u, 0u, // 203 16858104682372562260ull, 1558673743u, 0u, 14145895032556933946ull, 835018154u, 0u, 5140189396394760234ull, 344605645u, 0u, 5364325127668755694ull, 701855354u, 0u, 14787359934145013190ull, 4051301633u, 0u, 5818709913663861406ull, 3250655256u, 0u, 16350799554574905352ull, 1838808719u, 0u, 6782060809910266790ull, 3266573832u, 0u, 11023966639422577848ull, 774436753u, 0u, 7672668541328775852ull, 2039418294u, 0u, 6872847728608603024ull, 2550365910u, 0u, 8242396570564597524ull, 4204271292u, 0u, 413498310372713736ull, 472792130u, 0u, 16619050331804212532ull, 3145530937u, 0u, 15228803330364864608ull, 409935754u, 0u, 12352681432265762940ull, 1185395212u, 0u, 17242901083793483238ull, 509124151u, 0u, 17824752877967763262ull, 591078501u, 0u, 4716075612980233440ull, 2763848968u, 0u, 7546436651510744044ull, 2739537338u, 0u, 14063200380722100478ull, 3125830866u, 0u, 9576091498273122380ull, 1317993990u, 0u, 15442969208129243632ull, 1880446961u, 0u, 1983556048236571382ull, 2354737701u, 0u, 16900941590840212070ull, 938751235u, 0u, 17536952544169812562ull, 884199177u, 0u, 12624435608249449960ull, 3232394967u, 0u, 2352051750497343952ull, 473922368u, 0u, 7935964794531498884ull, 3138067665u, 0u, 16380832857862863790ull, 3678225925u, 0u, 16241691658300205240ull, 1719940874u, 0u, 12585230133345069716ull, 2930544291u, 0u, // 204 1082161106207232550ull, 1464465085u, 0u, 6142192705296686496ull, 2314184328u, 0u, 1940925432255764552ull, 679060224u, 0u, 10065477269427382582ull, 3701682072u, 0u, 6118231856174870118ull, 4228753748u, 0u, 11810894420994671792ull, 3914135983u, 0u, 17561405781349647810ull, 1582318652u, 0u, 10034991001608464250ull, 3786394932u, 0u, 10432173286001501336ull, 555775886u, 0u, 12766769958900865854ull, 4205300538u, 0u, 18290780216475946258ull, 3221695152u, 0u, 14506360053413020276ull, 1053439385u, 0u, 11785883731507066864ull, 832500314u, 0u, 4327641983671653382ull, 794765355u, 0u, 6706095277107881086ull, 239383414u, 0u, 6299453866240763862ull, 784524958u, 0u, 9197231588683850490ull, 2182989464u, 0u, 10044533250155879644ull, 1835657670u, 0u, 16027751048144220356ull, 1250975076u, 0u, 16377582576784512886ull, 624426242u, 0u, 11683018801613706624ull, 749240181u, 0u, 7015647798532423600ull, 3046520050u, 0u, 14856082835173711096ull, 2794486134u, 0u, 18405862181508307828ull, 3401532132u, 0u, 13903220722589779014ull, 1821243029u, 0u, 2950711541527271978ull, 2557671622u, 0u, 5992810896183753574ull, 169684378u, 0u, 6151159144856688844ull, 2073380119u, 0u, 1394707172295346554ull, 981553004u, 0u, 459885677604014636ull, 1548997732u, 0u, 15979004675747008822ull, 2256797060u, 0u, 12181094595218822468ull, 3680210176u, 0u, // 205 9432222609966447286ull, 3556127027u, 0u, 2546543207093339924ull, 3740053907u, 0u, 4068243016577348214ull, 2218029941u, 0u, 9213717611999701726ull, 1425221000u, 0u, 4419598559490077146ull, 1430815567u, 0u, 5931071719961016438ull, 1256217217u, 0u, 12113528541667924596ull, 1612732105u, 0u, 10480463277197141218ull, 1438580899u, 0u, 12465120370521668890ull, 2370559859u, 0u, 10038575270222401762ull, 1580084823u, 0u, 16494376242831650002ull, 1066681915u, 0u, 13741060394619673688ull, 3917941860u, 0u, 6143654588874563908ull, 2135207461u, 0u, 12261254828721808016ull, 1519520526u, 0u, 13363601151369928500ull, 4128558018u, 0u, 6857262407126770474ull, 1215152510u, 0u, 14280404349355041148ull, 1044618568u, 0u, 4922186695638552602ull, 526570953u, 0u, 11519267695520957762ull, 427617628u, 0u, 9033180311605131362ull, 4186802480u, 0u, 5167126014608264198ull, 1689961994u, 0u, 3055008470262805966ull, 2515451303u, 0u, 5037555505747373900ull, 3082225033u, 0u, 17806392124627876984ull, 3946459456u, 0u, 14825942610420793366ull, 1553522301u, 0u, 135409424507147742ull, 231063675u, 0u, 6114858228885578280ull, 1971484860u, 0u, 15203477165249940990ull, 2023407890u, 0u, 7599834078059176834ull, 3333671034u, 0u, 18442998932710462472ull, 966352080u, 0u, 3807290683558644748ull, 4188172736u, 0u, 14533343565390533714ull, 1265451978u, 0u, // 206 15664220563464437518ull, 2005810552u, 0u, 8178979912564348752ull, 388132975u, 0u, 17268019959336194206ull, 1943881652u, 0u, 3280195773043497316ull, 3994166017u, 0u, 6452368028583503372ull, 3657311731u, 0u, 13139168644536061812ull, 2718364639u, 0u, 16483127066267140098ull, 479373517u, 0u, 3460755884755528682ull, 3720197560u, 0u, 199428035346291368ull, 255437576u, 0u, 8313965491751692950ull, 1787955055u, 0u, 6236290668966839710ull, 300710907u, 0u, 15706351291494137254ull, 730562029u, 0u, 14074630480289455796ull, 3424078157u, 0u, 1470140144342331480ull, 4051971584u, 0u, 8592217864838442526ull, 3487185694u, 0u, 12089140743104653592ull, 814118739u, 0u, 5172185489782810870ull, 1903236219u, 0u, 13959503901388214478ull, 107872407u, 0u, 14874498579491296476ull, 3716753736u, 0u, 11359114488620748200ull, 2309495425u, 0u, 15543042202233307782ull, 1920697879u, 0u, 13387879811759945092ull, 3386254515u, 0u, 17341587966778333854ull, 3155537989u, 0u, 758882590906832260ull, 1182840924u, 0u, 629684323793893272ull, 1939085595u, 0u, 12361463532255052326ull, 3107078210u, 0u, 7304702689695160824ull, 3416841587u, 0u, 4670701027113913266ull, 1908021788u, 0u, 10166108416502372502ull, 3814778602u, 0u, 7633083390780068704ull, 3763864850u, 0u, 2729964835019906302ull, 4152501184u, 0u, 11201349897218476644ull, 3317091711u, 0u, // 207 16931170882497514522ull, 2145600083u, 0u, 5130220082110404740ull, 809639133u, 0u, 10121077554388040678ull, 1666204663u, 0u, 4694561163164670392ull, 3250888911u, 0u, 1828431041081257426ull, 458943724u, 0u, 17901193917188433972ull, 882515925u, 0u, 2496840570786998146ull, 3192931771u, 0u, 15726783700337023398ull, 3727683209u, 0u, 14621699782055780002ull, 1752240227u, 0u, 5641213164942568580ull, 748433192u, 0u, 7026045195530523572ull, 1913080476u, 0u, 11973862924353409956ull, 2023915247u, 0u, 3279132277735628110ull, 4083481205u, 0u, 11022369764403165366ull, 891422396u, 0u, 12779770723119564536ull, 1115410756u, 0u, 10619930990263068682ull, 3518744672u, 0u, 6264935413429473304ull, 1160609395u, 0u, 13510284166273551272ull, 205668688u, 0u, 16366168589065057242ull, 900947695u, 0u, 18098158112941761782ull, 1776367539u, 0u, 13825719253317226948ull, 134167720u, 0u, 17907841139398726460ull, 3507625381u, 0u, 164295897387156660ull, 2564050636u, 0u, 8452191924994328888ull, 1911513999u, 0u, 10939688713752295604ull, 473299220u, 0u, 12407227907539853228ull, 3462009245u, 0u, 179856117520455658ull, 2644228919u, 0u, 2743633832933235592ull, 3691836144u, 0u, 9745484646793266472ull, 3540664484u, 0u, 8723565256494480520ull, 3923254416u, 0u, 2661625509535920302ull, 1513506721u, 0u, 7745795026631988766ull, 2078275274u, 0u, // 208 11061780822501180862ull, 3869838994u, 0u, 12371274380766510978ull, 317002011u, 0u, 15251274801611020228ull, 897343052u, 0u, 9448115905688907702ull, 1836605089u, 0u, 7494421560335779750ull, 3612007509u, 0u, 18113191474218165368ull, 2923153694u, 0u, 1034873563389462668ull, 1446341686u, 0u, 2709126531202751784ull, 3086441244u, 0u, 2380441628119915486ull, 4041102476u, 0u, 10504677201248684886ull, 1010320789u, 0u, 13835224868304924048ull, 3242665313u, 0u, 16094250244523808466ull, 3191384185u, 0u, 5843920183849798264ull, 3968922755u, 0u, 6630586604210325316ull, 4015869349u, 0u, 940302096047034960ull, 3189708610u, 0u, 9202574079806415698ull, 4037378245u, 0u, 17520744921034453944ull, 2701253147u, 0u, 15715460867639792002ull, 3821185343u, 0u, 7627057599632555414ull, 410266256u, 0u, 17893603546819738470ull, 1315643536u, 0u, 16010157490578095424ull, 2433830016u, 0u, 14286726949834509482ull, 2074048981u, 0u, 745440160028065810ull, 3720953970u, 0u, 15036529877863696136ull, 1689317481u, 0u, 15703949235557860874ull, 1935974927u, 0u, 11179802677994523818ull, 1101513697u, 0u, 5289415065636416806ull, 730918251u, 0u, 7600084009002454790ull, 1348700219u, 0u, 18075849594724633432ull, 1228663877u, 0u, 13869823495566619896ull, 2052607586u, 0u, 271088906157619760ull, 1359346997u, 0u, 15811513354098814626ull, 4098000184u, 0u, // 209 9845688690418377496ull, 2347219637u, 0u, 13628020484124760234ull, 126726527u, 0u, 13347738770353083108ull, 1733000280u, 0u, 11803019659566550192ull, 1905820253u, 0u, 2349149976313939902ull, 3023623911u, 0u, 4583532727621079994ull, 1703124617u, 0u, 9009157040051677266ull, 1467821578u, 0u, 98646518877532558ull, 828846538u, 0u, 16605828607531071356ull, 2087297361u, 0u, 7803799034184615886ull, 1668908472u, 0u, 6075666208649410352ull, 2396161142u, 0u, 5454230586960760954ull, 3155013367u, 0u, 1665699463146604100ull, 1054861404u, 0u, 10759719711100806576ull, 2269645934u, 0u, 4102726127891888656ull, 2999469922u, 0u, 2906942175170969996ull, 868341699u, 0u, 12130065067245408788ull, 428522236u, 0u, 17219781646050168680ull, 1158277991u, 0u, 12765023129548561686ull, 717014500u, 0u, 3299906870220006970ull, 679232776u, 0u, 16628910194599960110ull, 1367468975u, 0u, 12217373433712563240ull, 275894969u, 0u, 17600657208197944312ull, 3342822527u, 0u, 9455199895213833572ull, 978169720u, 0u, 11465341653694478614ull, 3351361634u, 0u, 16086496480108590784ull, 460940327u, 0u, 12824117542402231796ull, 4012631882u, 0u, 16385253075259390350ull, 795057030u, 0u, 5164921151956742304ull, 2560030661u, 0u, 2717400853727860732ull, 1719058897u, 0u, 3014778563306743720ull, 1986277076u, 0u, 6000322115816137876ull, 738065178u, 0u, // 210 10532105807549854976ull, 1736058657u, 0u, 1578623410090016678ull, 4070933996u, 0u, 2704072742139810904ull, 3692839519u, 0u, 1912698050570132564ull, 2155296413u, 0u, 3311349597154624784ull, 2088822563u, 0u, 12938948108958223790ull, 2219446096u, 0u, 13824275758272413608ull, 3049198668u, 0u, 894177780789916376ull, 1455308980u, 0u, 10566919016902748416ull, 2494887729u, 0u, 14614660056621810666ull, 4080677731u, 0u, 18320178853700697244ull, 2945534514u, 0u, 7113805424853240030ull, 1821625036u, 0u, 5311862510797621126ull, 4290355633u, 0u, 13906103372249885096ull, 123396821u, 0u, 3318045006750118752ull, 1946353112u, 0u, 10475076540404257414ull, 1538860358u, 0u, 8508287549464548736ull, 1203977476u, 0u, 13084474859602698288ull, 2244828435u, 0u, 1013116946087137274ull, 2511206967u, 0u, 16229126587322296142ull, 215618599u, 0u, 17565409359414768812ull, 2461077433u, 0u, 5530833584216054260ull, 1660374209u, 0u, 3461034864609652692ull, 4077314224u, 0u, 14797609303734870506ull, 2598768692u, 0u, 12488593153812197808ull, 1858594982u, 0u, 14352891627104697670ull, 501026874u, 0u, 5855081470441960984ull, 931922708u, 0u, 3687223131826024118ull, 4002065364u, 0u, 6181321226744130160ull, 2144686723u, 0u, 10430158598698123804ull, 2583552841u, 0u, 3849292781660364062ull, 766532360u, 0u, 6865865053638934242ull, 2996303596u, 0u, // 211 7593447971499800300ull, 2443076757u, 0u, 2378313792281084680ull, 3784977034u, 0u, 16071604988001938986ull, 504012532u, 0u, 6009715406356842664ull, 742030787u, 0u, 10551653439753329638ull, 2757365815u, 0u, 2477091548412024316ull, 2560178261u, 0u, 10839224823845821668ull, 1975754389u, 0u, 3326839973506402570ull, 3258918290u, 0u, 16719197212706385030ull, 1684801583u, 0u, 11423267826536147214ull, 196271935u, 0u, 2769382610645315190ull, 1252361155u, 0u, 12713135963575637976ull, 187855751u, 0u, 5894355363326301566ull, 3136222195u, 0u, 9788618105873825142ull, 3068980280u, 0u, 4388925997572491040ull, 1874284707u, 0u, 4085374365009867932ull, 1193694689u, 0u, 11974310161971747834ull, 2111284382u, 0u, 2532323104493129814ull, 3440233493u, 0u, 2480111436491858664ull, 1665339154u, 0u, 9296247216839852850ull, 1160162159u, 0u, 5624099865659459360ull, 3366532230u, 0u, 2761356618612355226ull, 2698804833u, 0u, 3327611837613303976ull, 3835744051u, 0u, 17446321745707954824ull, 2173797151u, 0u, 11710532453360941332ull, 1435999861u, 0u, 10263853195005556492ull, 77658898u, 0u, 12477603493775784932ull, 1219213920u, 0u, 4882914624769405740ull, 3799944321u, 0u, 12006983371882148176ull, 1403992265u, 0u, 11323983415368514736ull, 2158493481u, 0u, 12522864647914747382ull, 319672892u, 0u, 14158583276882168530ull, 3774832657u, 0u, // 212 5704535935473919364ull, 2537675013u, 0u, 16797580074131059826ull, 2711397142u, 0u, 4924057228514892746ull, 697800180u, 0u, 16672568281346316984ull, 1027468739u, 0u, 4329632651297910894ull, 2746899571u, 0u, 14896670221487611716ull, 2644846396u, 0u, 13617943764923123290ull, 464041306u, 0u, 16364524442255770098ull, 3545944919u, 0u, 12919003702145491770ull, 1646369132u, 0u, 8216805397206642004ull, 4234330632u, 0u, 2069392825246750992ull, 2659063134u, 0u, 1819630535210467350ull, 1483460781u, 0u, 13572237693116190790ull, 2578307482u, 0u, 17313120106030823714ull, 1589160139u, 0u, 1617054256925099368ull, 1254424319u, 0u, 3006170717211152376ull, 346186139u, 0u, 7673318756966562568ull, 514842460u, 0u, 1579104456046395320ull, 2322077607u, 0u, 5647212539191228368ull, 775629266u, 0u, 9556359469430651212ull, 4060334718u, 0u, 4864092756541810786ull, 3649070314u, 0u, 2032203863183917286ull, 2785978284u, 0u, 4490767891385415204ull, 2877358507u, 0u, 16969957342077476942ull, 3712690394u, 0u, 15702081295856634204ull, 3863836331u, 0u, 14876748538102214800ull, 3854144963u, 0u, 13472070853036291580ull, 3311307688u, 0u, 6242979879849046546ull, 227985255u, 0u, 15268318038418071478ull, 750729717u, 0u, 1958199819034046070ull, 2716597924u, 0u, 16414930566830859946ull, 299052051u, 0u, 4137054043200102070ull, 211164902u, 0u, // 213 15211394023426562548ull, 315781098u, 0u, 6143334701861359458ull, 259756279u, 0u, 13733706574051195438ull, 1193117131u, 0u, 11810014677495749748ull, 2798126206u, 0u, 18062963555729250620ull, 489346478u, 0u, 15599943717268678304ull, 2099013451u, 0u, 8251464360725067980ull, 1434238559u, 0u, 12009411903469937074ull, 2446524283u, 0u, 13289829127522041662ull, 3171134025u, 0u, 14982226834377490256ull, 3305291015u, 0u, 13029350983812875946ull, 3376689336u, 0u, 7117753846395334588ull, 606150781u, 0u, 17504567510450436936ull, 707322773u, 0u, 2458951801636636390ull, 2808797138u, 0u, 9381347739828147094ull, 3826733053u, 0u, 6277006021141397324ull, 63948015u, 0u, 15991962907381512736ull, 491154646u, 0u, 13013569210333230216ull, 1237810216u, 0u, 4903427052602792328ull, 4235644152u, 0u, 1650857960818468640ull, 1872319449u, 0u, 14819541210372736866ull, 932962197u, 0u, 11952147437475750284ull, 1185386421u, 0u, 17177788536196310690ull, 654871177u, 0u, 15062112322675685254ull, 31669196u, 0u, 8860677668038850418ull, 4122062568u, 0u, 5529402907589639598ull, 2612524346u, 0u, 7482296273214055566ull, 2754184760u, 0u, 18203890546202029526ull, 3936254019u, 0u, 11968544459247358736ull, 2782654146u, 0u, 446249705344893514ull, 1670651075u, 0u, 17444755689416180776ull, 1252559232u, 0u, 15395856169767262648ull, 2065759045u, 0u, // 214 6080777095899316302ull, 1592120528u, 0u, 16059452688490394594ull, 3645028330u, 0u, 16518874706743701010ull, 2946000000u, 0u, 8298937861127311212ull, 2520566699u, 0u, 13884716287752710272ull, 4053827399u, 0u, 15980003899721797316ull, 2863094021u, 0u, 11198757563104530792ull, 948330832u, 0u, 642726010551329474ull, 2339539986u, 0u, 17562967579245300296ull, 3809156576u, 0u, 264120393247114852ull, 1818210553u, 0u, 15951217833004252532ull, 923479233u, 0u, 17439536473808080192ull, 2796874809u, 0u, 3349354301031054112ull, 1072831555u, 0u, 13173577401466045962ull, 623889671u, 0u, 8254177606068982536ull, 4254572764u, 0u, 17122953143460250040ull, 734891934u, 0u, 14539014393491022888ull, 2324558074u, 0u, 1066416880784832666ull, 559023169u, 0u, 10461494769995159150ull, 3527400637u, 0u, 10571657269815322616ull, 561090177u, 0u, 4218861112413441814ull, 3477517664u, 0u, 2643999926291537190ull, 3243266136u, 0u, 15854968218359792422ull, 1375709659u, 0u, 13552846936425047868ull, 2539012613u, 0u, 11371191736710531696ull, 2055441079u, 0u, 17967720408389412376ull, 3401606427u, 0u, 3657464675699636018ull, 576410974u, 0u, 6461441775210412896ull, 3849338472u, 0u, 891047198971384602ull, 468287599u, 0u, 15040730622226947496ull, 90926914u, 0u, 4118430306866868640ull, 3769751017u, 0u, 8489611634709026528ull, 924856391u, 0u, // 215 12738649565075656282ull, 2130828781u, 0u, 15390079869309461516ull, 2002022486u, 0u, 4397926544186426564ull, 2307618460u, 0u, 5860739343890879180ull, 3544310171u, 0u, 1950873867045883594ull, 4150517715u, 0u, 9320767824922963188ull, 2530234727u, 0u, 371223325849783242ull, 86204125u, 0u, 10958835567505893124ull, 1244110739u, 0u, 95922124391659352ull, 1685747933u, 0u, 12386806647545405634ull, 4012573028u, 0u, 1439240656804067422ull, 4076237414u, 0u, 12857133050886557798ull, 404691747u, 0u, 5632883082908068460ull, 1874807711u, 0u, 15077284929072262684ull, 3302845302u, 0u, 2169981944236648590ull, 2706731298u, 0u, 8953084663538082534ull, 2672596633u, 0u, 11242550811559370102ull, 2183057306u, 0u, 11039533562574037730ull, 3480012822u, 0u, 2999530753139794902ull, 3358881433u, 0u, 14640994986769538014ull, 3769881546u, 0u, 16086114850143281098ull, 2660810162u, 0u, 2156585540328101826ull, 2891848412u, 0u, 5436817744501588662ull, 2868336122u, 0u, 18144697949057536354ull, 2047524868u, 0u, 12660356576696503864ull, 2638343068u, 0u, 10206273317165059514ull, 932297362u, 0u, 701150466046949412ull, 1688232697u, 0u, 4428991318826272316ull, 4038931058u, 0u, 6970946547691783982ull, 175032330u, 0u, 8593415762584044164ull, 1786466259u, 0u, 6093330625055543516ull, 3413622048u, 0u, 12208948669449311396ull, 634389970u, 0u, // 216 14872277316828347804ull, 2595236218u, 0u, 11620735323074467764ull, 3458454284u, 0u, 16589219751467559430ull, 7803340u, 0u, 10834332954451940098ull, 1993630795u, 0u, 18220503644919013764ull, 2194415882u, 0u, 2521907397540233486ull, 2687797437u, 0u, 17590430878035263544ull, 2676935436u, 0u, 16056161009892331660ull, 2145958546u, 0u, 4115771307112866442ull, 3209814361u, 0u, 5887084465020433310ull, 3204757481u, 0u, 7255210099490379148ull, 1721435406u, 0u, 15941948293973771518ull, 3195295039u, 0u, 12359015440538355166ull, 3502267541u, 0u, 406043416413698158ull, 910753785u, 0u, 825008446292927628ull, 1248628459u, 0u, 8788210732349526398ull, 650977556u, 0u, 17179297250781980874ull, 1121700177u, 0u, 5325413642934712986ull, 2963074687u, 0u, 17038379214795567226ull, 681379984u, 0u, 6245153584528071280ull, 1036438510u, 0u, 10341148251856510162ull, 1257317855u, 0u, 18001544483596956290ull, 2959382421u, 0u, 13355155747104537598ull, 2659861808u, 0u, 933809867753353154ull, 1891716765u, 0u, 912066545714888550ull, 1405396352u, 0u, 4770140497840812154ull, 2058558042u, 0u, 7034144308694208660ull, 853631170u, 0u, 16665195533616167088ull, 2183495711u, 0u, 5525944024388837904ull, 122359206u, 0u, 14918618839614883532ull, 3407424355u, 0u, 16906938807314345902ull, 1276343734u, 0u, 5307260560520957956ull, 619181205u, 0u, // 217 14124441365672088452ull, 3274505591u, 0u, 9557192442592566604ull, 3587083784u, 0u, 7028870415911120292ull, 1782466924u, 0u, 15303982006822151618ull, 3705111986u, 0u, 16088662983559301858ull, 2616769169u, 0u, 7319954031457636194ull, 2176553789u, 0u, 8499193988699755720ull, 853176757u, 0u, 16743225027604037324ull, 2936160730u, 0u, 11545431761940139660ull, 2022628637u, 0u, 1061186662753216092ull, 1433864843u, 0u, 396188335894905538ull, 3006570381u, 0u, 3753992356025113624ull, 407197488u, 0u, 11728060152736469214ull, 3683846685u, 0u, 11144849110753500674ull, 37156035u, 0u, 5606786660087934556ull, 1086845490u, 0u, 12175408994974102566ull, 3277015511u, 0u, 3564329354746979726ull, 3089205213u, 0u, 13138238258011106486ull, 2192323018u, 0u, 10055367788698932298ull, 1227701096u, 0u, 2709864209353961282ull, 2191295833u, 0u, 5269473169781612870ull, 742244772u, 0u, 9292990054432256192ull, 45712318u, 0u, 11085101576895599396ull, 3372714954u, 0u, 14040329493558871580ull, 2108950357u, 0u, 6442416210333871412ull, 391673123u, 0u, 11238084904103716582ull, 2269456161u, 0u, 4484058754498216248ull, 3774720529u, 0u, 1988831034379012610ull, 2623711218u, 0u, 14266262295315225316ull, 1650193238u, 0u, 13508693759269986106ull, 454037826u, 0u, 1839581357424348906ull, 3457506198u, 0u, 2824268158749501538ull, 4202744720u, 0u, // 218 17779383389094533442ull, 262471845u, 0u, 4369826526911769446ull, 2561737787u, 0u, 8232001672265396724ull, 2056394235u, 0u, 369298435520075666ull, 2027190483u, 0u, 17318559872055826514ull, 1870385190u, 0u, 5227602696816119242ull, 2595331803u, 0u, 10614618482750777634ull, 3104578017u, 0u, 3220809659874922804ull, 3097563877u, 0u, 14131774465268352454ull, 3847476458u, 0u, 14553291662609689780ull, 93231261u, 0u, 16573555056628194764ull, 2660073032u, 0u, 2272988358511658306ull, 3158556211u, 0u, 10659123540751218140ull, 686425307u, 0u, 15521010763353951800ull, 2029822163u, 0u, 11251329452371451018ull, 1141542475u, 0u, 6251072750480079786ull, 807023278u, 0u, 15651247923375664574ull, 3868326360u, 0u, 15639149111828275206ull, 1303628455u, 0u, 9375265365728658448ull, 314047576u, 0u, 12325115526519447392ull, 394858921u, 0u, 5274881828498701764ull, 2501441697u, 0u, 11947251646728915614ull, 4266860868u, 0u, 10270434347184591348ull, 3123679738u, 0u, 15630129753975334528ull, 3029772611u, 0u, 9309516795250344184ull, 3996639817u, 0u, 13635491353319766262ull, 2463698149u, 0u, 12968809105656829614ull, 3672690034u, 0u, 14012863512352878708ull, 618649882u, 0u, 141210995558247602ull, 2417429400u, 0u, 5594294069270262404ull, 355862896u, 0u, 14681540445397100686ull, 4124419113u, 0u, 15718826640521071398ull, 2088813913u, 0u, // 219 16929817280445096316ull, 2014867479u, 0u, 4619614903773346800ull, 1072285414u, 0u, 11675245213251622528ull, 3560281747u, 0u, 11247485007431818510ull, 3121395497u, 0u, 9811096016122272662ull, 1230482913u, 0u, 15759002244031582008ull, 1404795122u, 0u, 17713595068324824654ull, 669172006u, 0u, 3935829569112547912ull, 317307428u, 0u, 2999804379415588560ull, 2581755517u, 0u, 17471615683157645160ull, 1369004619u, 0u, 11724189342742755496ull, 2608438632u, 0u, 13975821285634818228ull, 2935701617u, 0u, 15842306987305990904ull, 366199838u, 0u, 11499374592774817240ull, 3048779913u, 0u, 3218406750170650878ull, 3075944945u, 0u, 18178201876772194576ull, 2700928153u, 0u, 16829844693580531558ull, 2526918489u, 0u, 9056787169324824732ull, 2575466527u, 0u, 1866678458130391974ull, 2931912238u, 0u, 7583389448978613772ull, 3296296278u, 0u, 12540221363784585416ull, 1011799851u, 0u, 18031206461107031892ull, 3122721551u, 0u, 3674457645760504218ull, 3618857098u, 0u, 10012262715122874318ull, 2290433583u, 0u, 6485567848365757516ull, 2318670888u, 0u, 7120145452765100038ull, 4260696212u, 0u, 4239241891825578622ull, 421624183u, 0u, 12256504811292368540ull, 3421562154u, 0u, 10818031727845734654ull, 846488732u, 0u, 7916375044769825648ull, 81796170u, 0u, 6026610249830825662ull, 818004203u, 0u, 4373746050279542502ull, 1962367321u, 0u, // 220 912732503022009458ull, 250438440u, 0u, 6582395441091321010ull, 3667204043u, 0u, 17772110182431867254ull, 521560534u, 0u, 3346285267854971432ull, 2763145691u, 0u, 15192264491794396574ull, 1733344216u, 0u, 16250171464762605206ull, 2313536114u, 0u, 15004182847663538658ull, 1753921524u, 0u, 2603636026094608808ull, 1299213472u, 0u, 18386610689396514356ull, 2611293980u, 0u, 18069466085545843238ull, 1552667338u, 0u, 15986359086136925920ull, 1092048629u, 0u, 15641900941412095918ull, 2291255611u, 0u, 12092492530199556284ull, 1649206756u, 0u, 5775230105682941576ull, 1089497775u, 0u, 12353755579874689412ull, 3141947603u, 0u, 4474322191943826324ull, 2628885098u, 0u, 4143670568240940654ull, 1815842014u, 0u, 4047277934432870054ull, 1337776970u, 0u, 16570280098578401146ull, 1851757852u, 0u, 8296817559695134162ull, 615691076u, 0u, 1291656066664064544ull, 3243460205u, 0u, 6082854010276051800ull, 1929202557u, 0u, 11615433583952547920ull, 3379107240u, 0u, 8043391481669402810ull, 4275321162u, 0u, 15889595937393590242ull, 3483494677u, 0u, 12930412102228214886ull, 2756791371u, 0u, 17549551267608027596ull, 1745053537u, 0u, 325796074946865526ull, 3629074134u, 0u, 5203232704249783500ull, 2283321131u, 0u, 7973698347223177690ull, 2611828727u, 0u, 12654714356907223500ull, 2789490957u, 0u, 6511356677559398148ull, 3757072677u, 0u, // 221 16317403091599901122ull, 1550775606u, 0u, 10800318661667747206ull, 141331213u, 0u, 3957200361703526210ull, 2859703998u, 0u, 17731593012604976054ull, 2298304167u, 0u, 5856095482350887878ull, 3059215179u, 0u, 5132698271851774910ull, 3036383456u, 0u, 2113639536905354970ull, 455624225u, 0u, 3577665844031620906ull, 2196936691u, 0u, 6448219505833296224ull, 3774694169u, 0u, 2136780188695374604ull, 521179306u, 0u, 17009206734508616620ull, 1780494519u, 0u, 84025137387579274ull, 862177363u, 0u, 497194046378351638ull, 1404486183u, 0u, 11995199052171081780ull, 4274185363u, 0u, 4893299026746799478ull, 3319341811u, 0u, 3086058963518647262ull, 2351492043u, 0u, 9699293378531181192ull, 2638839309u, 0u, 17802385009784471776ull, 2713038110u, 0u, 18221944768183222890ull, 142255062u, 0u, 302012746378940232ull, 901026400u, 0u, 4307590246413708450ull, 233868169u, 0u, 4812945361983526254ull, 2533075623u, 0u, 15948344767941787530ull, 37294287u, 0u, 16568465805097008292ull, 1387856841u, 0u, 12722778799341134348ull, 3766508909u, 0u, 18003928303629518196ull, 2390783051u, 0u, 17950814174549395958ull, 2496101288u, 0u, 15724065996221359304ull, 1726893904u, 0u, 10891274099896509058ull, 989351677u, 0u, 893908637647043088ull, 3368521038u, 0u, 5679209887996593778ull, 2753495395u, 0u, 339804323048413434ull, 126047494u, 0u, // 222 8533798091098188828ull, 1112930783u, 0u, 18437657074878484014ull, 482069402u, 0u, 16618994187409724964ull, 3070715340u, 0u, 7065495817856417452ull, 324911656u, 0u, 1840024552189694858ull, 1522058193u, 0u, 12132434372178360738ull, 3642077042u, 0u, 14719653752327605156ull, 1653638706u, 0u, 4731246814732454954ull, 159865513u, 0u, 14534119195447691478ull, 58522607u, 0u, 10321538553525256846ull, 217710943u, 0u, 13376841645767514054ull, 592970948u, 0u, 11743197233482612932ull, 2563889652u, 0u, 679272353845955968ull, 1077274223u, 0u, 1251656209264139906ull, 2620828205u, 0u, 4646053949414763148ull, 3400246022u, 0u, 7885816894694380848ull, 3638597527u, 0u, 1390591659633676382ull, 1530733323u, 0u, 5623410181697924258ull, 35117838u, 0u, 11111681125462677660ull, 122072424u, 0u, 5996607686267647630ull, 567431086u, 0u, 18279010403950741766ull, 2415892957u, 0u, 3878778570427640776ull, 468594688u, 0u, 1748515133120465386ull, 3340575746u, 0u, 8847176478788342854ull, 740142794u, 0u, 17080379033992306190ull, 3440115037u, 0u, 13268944492386267880ull, 1861192938u, 0u, 16072497048998947650ull, 1519779433u, 0u, 15782128231782445298ull, 266555979u, 0u, 8667759758094413048ull, 473699060u, 0u, 12966625109459574374ull, 621913276u, 0u, 12358113832385320796ull, 2953204122u, 0u, 10030803668040498260ull, 2996271097u, 0u, // 223 2912004484127368420ull, 2907444611u, 0u, 9592804448175049024ull, 498567772u, 0u, 15523824936825568206ull, 3006953870u, 0u, 14323023636900179932ull, 825952782u, 0u, 17910070479990562708ull, 4193772443u, 0u, 17850146104883151278ull, 3329068255u, 0u, 15546387964651876254ull, 2572922374u, 0u, 17519088397563133820ull, 183580502u, 0u, 5708398461311278758ull, 2401842803u, 0u, 16352808799828805568ull, 1641792634u, 0u, 4214389257448924960ull, 2421496087u, 0u, 17138543005175263578ull, 2903171556u, 0u, 17787656435428193368ull, 3248660501u, 0u, 11590988984681464176ull, 3521734907u, 0u, 2736812555842130466ull, 2881073550u, 0u, 10382320015781663848ull, 3224075890u, 0u, 16577533079900182552ull, 4010322957u, 0u, 10213257663876135804ull, 3898645879u, 0u, 18118594008619749164ull, 97944190u, 0u, 2778810201903055132ull, 2777013211u, 0u, 10507017345455762924ull, 3514983598u, 0u, 6922376812935518578ull, 3441262637u, 0u, 10905916661504692508ull, 4275951042u, 0u, 11896446091706859128ull, 3549129827u, 0u, 14446162772967218612ull, 1638147691u, 0u, 10553336967655669398ull, 3286725803u, 0u, 10293083537998976710ull, 1581072508u, 0u, 8460074724324176670ull, 2671154150u, 0u, 4238363880212519474ull, 2803690671u, 0u, 15852869052089314878ull, 3189845299u, 0u, 4910805667074594546ull, 758665988u, 0u, 10135060063832536554ull, 2841550784u, 0u, // 224 5695022667666445938ull, 3584873006u, 0u, 11958387440834993048ull, 790895145u, 0u, 9831442975840628696ull, 3584634920u, 0u, 17686793651481685192ull, 4006551053u, 0u, 1015465274680169020ull, 4257615872u, 0u, 3694370739275824796ull, 1880220026u, 0u, 15947234305683666130ull, 613448578u, 0u, 11369922131816088080ull, 3336788702u, 0u, 5282229391270320652ull, 1709781561u, 0u, 16967317268295203708ull, 1077288283u, 0u, 15211842691014859522ull, 1753489421u, 0u, 12955777238705313496ull, 1639009440u, 0u, 15009032588832274306ull, 3368252514u, 0u, 17012430955615519446ull, 399225765u, 0u, 9463560250505276262ull, 449217487u, 0u, 16767807511864242050ull, 2851254994u, 0u, 6810002207148708428ull, 1629604238u, 0u, 16835226854486442106ull, 2884268299u, 0u, 1936264040513577652ull, 2258854827u, 0u, 419522954072091746ull, 3308642289u, 0u, 2092078838247514184ull, 2591107903u, 0u, 2542808598441780914ull, 341674791u, 0u, 11792860392397833480ull, 848325991u, 0u, 7205691277070076928ull, 1107705722u, 0u, 5387328023039599696ull, 2361559423u, 0u, 12538357571633709874ull, 2286794750u, 0u, 2064380724313055128ull, 2913245522u, 0u, 5458441245660959946ull, 285241419u, 0u, 13198617575047140362ull, 1877612917u, 0u, 18368982742630836408ull, 2402000878u, 0u, 4555667321956147414ull, 1321205818u, 0u, 7002181509592348526ull, 860264589u, 0u, // 225 13519622657538182518ull, 650614396u, 0u, 583531218038632118ull, 3268298733u, 0u, 10967736250106927472ull, 2760022893u, 0u, 228679584860789960ull, 1589399152u, 0u, 10360202535170551210ull, 1940879903u, 0u, 15961820660453349712ull, 1294042222u, 0u, 18318081382503794876ull, 880702352u, 0u, 2247360657959817274ull, 2788649124u, 0u, 8718097746315334690ull, 703200073u, 0u, 14995540308119891264ull, 3722595641u, 0u, 6237711385634885578ull, 2716515906u, 0u, 5224431012793114012ull, 2172202281u, 0u, 10234456316649371784ull, 1589034512u, 0u, 8831899213224786198ull, 697134411u, 0u, 14339263833120795294ull, 3217668796u, 0u, 15246354115181779884ull, 1781044410u, 0u, 12238043991062109388ull, 4118012629u, 0u, 10533784239570919736ull, 1236860455u, 0u, 1080582771960632966ull, 2623594692u, 0u, 15791648871829012466ull, 2394704140u, 0u, 181142866355277124ull, 1160747424u, 0u, 1851023365405827682ull, 1283683213u, 0u, 12353239677026012560ull, 78578252u, 0u, 3340401539450294738ull, 1350302508u, 0u, 12917450705474331238ull, 647577187u, 0u, 17623181227965700512ull, 647426327u, 0u, 4501179309899675228ull, 3995341573u, 0u, 5561249784679053050ull, 1044035706u, 0u, 5485894521982968152ull, 1611819893u, 0u, 7098257144142953738ull, 194674174u, 0u, 4678913182631984044ull, 957479769u, 0u, 5271815419956081090ull, 3024153764u, 0u, // 226 5942457264917243676ull, 3006292539u, 0u, 13030711892464979672ull, 1800543624u, 0u, 15735365369756488098ull, 1606067673u, 0u, 6985584363054057564ull, 3015244102u, 0u, 5364873553577140958ull, 2377884877u, 0u, 15057397313942965830ull, 937842924u, 0u, 5018545729857897418ull, 468637661u, 0u, 12521085561607803392ull, 663515649u, 0u, 4286284636433763476ull, 1825991310u, 0u, 9099899356395323978ull, 3446900736u, 0u, 11813560988167642442ull, 1428528172u, 0u, 17030031242600555868ull, 2674849468u, 0u, 10340130588604375978ull, 558761983u, 0u, 16845674656964674284ull, 4005271497u, 0u, 17012440033376847042ull, 3873961589u, 0u, 11513689621790264366ull, 203271251u, 0u, 18353113918865831276ull, 863667278u, 0u, 1986275442830601452ull, 2263545645u, 0u, 11606277479404869436ull, 1650278611u, 0u, 8691770381170661472ull, 4120881465u, 0u, 2600335218618913952ull, 3684240084u, 0u, 15865891047428608272ull, 3117959342u, 0u, 17777825504988208820ull, 2660531126u, 0u, 4073155673494489844ull, 250367388u, 0u, 12924599225107212280ull, 3832786597u, 0u, 8495959738381785614ull, 2213713774u, 0u, 5881003610214823104ull, 1286592464u, 0u, 2440645337061290332ull, 3316634099u, 0u, 2598757646923895396ull, 1105851703u, 0u, 3600399245937920532ull, 3141726829u, 0u, 7928478897629562850ull, 1225070847u, 0u, 16613726780226010374ull, 3824229147u, 0u, // 227 8720627906725672004ull, 1021978389u, 0u, 2235521609892605632ull, 1925752019u, 0u, 2274667918331398690ull, 842050382u, 0u, 708073756979816636ull, 953583583u, 0u, 1308652324275779322ull, 1631407922u, 0u, 3707190591654507802ull, 1774738857u, 0u, 6262908641530860896ull, 3410338977u, 0u, 14499812158662417960ull, 2040836499u, 0u, 7326282592445174316ull, 3262208891u, 0u, 8266765484871431402ull, 449664719u, 0u, 12536236831930773452ull, 3924605793u, 0u, 2560386620839384164ull, 1025213861u, 0u, 5361576535052718838ull, 1984334265u, 0u, 176137868291358952ull, 2257236666u, 0u, 1429771942343075636ull, 1795395925u, 0u, 900040301709553858ull, 1254995143u, 0u, 11318319844575266518ull, 2696690410u, 0u, 13867543409048673294ull, 2468602197u, 0u, 6384831562535312538ull, 1817496271u, 0u, 1181415765951284868ull, 3031993206u, 0u, 6804627659877798866ull, 2860185289u, 0u, 11847627653818239424ull, 1482600041u, 0u, 7309477872396465120ull, 1508604510u, 0u, 17305799153357582128ull, 2482909194u, 0u, 10833859966291673778ull, 332731956u, 0u, 517785546406729296ull, 309017749u, 0u, 17519479294897993742ull, 761730774u, 0u, 5262928437076360274ull, 1259215382u, 0u, 7512513116956515748ull, 2387174907u, 0u, 10832149999278175174ull, 3816602598u, 0u, 859355580522659964ull, 764223192u, 0u, 15831808905368197284ull, 4035769966u, 0u, // 228 15935256162835423944ull, 4056421419u, 0u, 11137279949584027906ull, 3631908941u, 0u, 15273190446447003306ull, 1094753710u, 0u, 10270358987883388496ull, 2582493179u, 0u, 14614312768469796788ull, 3351945024u, 0u, 7159134376813090374ull, 950042626u, 0u, 11576784902788522814ull, 880537884u, 0u, 2036988733155745252ull, 317176600u, 0u, 6414586436224165272ull, 2250168881u, 0u, 13826439854264969754ull, 3613029128u, 0u, 16342258912415792244ull, 1012220872u, 0u, 2670460581319525260ull, 638158829u, 0u, 15853420569123333620ull, 721318351u, 0u, 18160774485854006134ull, 650625943u, 0u, 16959991105822581792ull, 488404330u, 0u, 5121221674612360006ull, 432889247u, 0u, 4332692725581418652ull, 1493569287u, 0u, 7999831084845946698ull, 885611880u, 0u, 10459340585341666654ull, 766305943u, 0u, 5377514979402490828ull, 2455600858u, 0u, 15121135115984122292ull, 163595971u, 0u, 12392777539170359446ull, 42873059u, 0u, 9964771018403238688ull, 1112403994u, 0u, 711421249942190680ull, 2039606336u, 0u, 4877923088024277346ull, 5469527u, 0u, 8049016926455595394ull, 3364075650u, 0u, 17771322911234300072ull, 2803206890u, 0u, 1886402693442058778ull, 3168415666u, 0u, 5307560968028314074ull, 1818574523u, 0u, 2282855479559566430ull, 2075656238u, 0u, 15420768727453059340ull, 2404170603u, 0u, 13338211515615338292ull, 753187004u, 0u, // 229 13053265674595299830ull, 4251390921u, 0u, 3866263084622013170ull, 1380028654u, 0u, 6469969693500460656ull, 3441808306u, 0u, 12101120319356136566ull, 3357482004u, 0u, 5409355747323162344ull, 2773720064u, 0u, 12199209848758444000ull, 321037931u, 0u, 4122167826563997040ull, 4223965683u, 0u, 6704783628669200ull, 3144890498u, 0u, 9189991626034513222ull, 3729709578u, 0u, 280259905069029942ull, 1481153808u, 0u, 10946254529298334402ull, 2814448391u, 0u, 5111285829009635204ull, 1763392375u, 0u, 16121756711918656528ull, 222133374u, 0u, 11211474702096202704ull, 4272885617u, 0u, 11953325128701303480ull, 2114687050u, 0u, 13307790510920674476ull, 2845533342u, 0u, 17754972725570965620ull, 227372759u, 0u, 13874794829079392436ull, 780537751u, 0u, 4996257524531640822ull, 2707809234u, 0u, 10471232084920690714ull, 1581159590u, 0u, 4222626467960439618ull, 3871783480u, 0u, 2273873561838429072ull, 4049591124u, 0u, 2266689200426889862ull, 3200675227u, 0u, 2869739063405059474ull, 3345288451u, 0u, 16462009595542576340ull, 4065163113u, 0u, 12868904652221614100ull, 3983464112u, 0u, 8752236207967604630ull, 3741360967u, 0u, 16965621613184660908ull, 2557478712u, 0u, 1703794199959848062ull, 3357936694u, 0u, 5676379918457599052ull, 2251306047u, 0u, 18342544158953705896ull, 3863303462u, 0u, 13260568566937025808ull, 2464971501u, 0u, // 230 3570668397364488986ull, 2389812863u, 0u, 4438049402450832598ull, 2747782879u, 0u, 10998559487584023306ull, 2918006171u, 0u, 10236862423388707546ull, 806971624u, 0u, 7913897009113929628ull, 1392088826u, 0u, 2501151232577144668ull, 2586936188u, 0u, 13051581803382597210ull, 3791037804u, 0u, 4247269475139804894ull, 991125560u, 0u, 1466651539278922908ull, 3892096523u, 0u, 5011357473535195748ull, 676260323u, 0u, 6379511143257000052ull, 1415633578u, 0u, 10739769126104204524ull, 902841940u, 0u, 15691591346055171046ull, 1835914282u, 0u, 10048606712653654536ull, 4060060279u, 0u, 17255221977677034930ull, 2552137270u, 0u, 6110535125407080440ull, 333752427u, 0u, 3976779291922301164ull, 3802646413u, 0u, 14149473662046397070ull, 3831120729u, 0u, 18044410156388867042ull, 2919896247u, 0u, 11873872237213620648ull, 3839411005u, 0u, 1285616538240960742ull, 3514294508u, 0u, 11439733391630022196ull, 4177967368u, 0u, 9384426127219241716ull, 2629769172u, 0u, 12341952614327400972ull, 2030605411u, 0u, 14272075349824549176ull, 3726639427u, 0u, 11255311218923427952ull, 1865970991u, 0u, 13754831706299901616ull, 3076302251u, 0u, 5536664105841139344ull, 1233113099u, 0u, 17425304736991888296ull, 1756342868u, 0u, 8985859952804922800ull, 101264287u, 0u, 1063570992860276654ull, 3200336238u, 0u, 1793738961979690864ull, 4006547668u, 0u, // 231 16470843765592471460ull, 3683419236u, 0u, 10580247853891198550ull, 3208786106u, 0u, 14066699116111564066ull, 429692035u, 0u, 10772529721415928110ull, 1725556373u, 0u, 3064489360032634768ull, 4258373409u, 0u, 16764241834533211594ull, 3335351504u, 0u, 11015191415474114720ull, 346214616u, 0u, 3921811583474078034ull, 1895658694u, 0u, 17878922748592823556ull, 3433503720u, 0u, 16452453118444551298ull, 782843670u, 0u, 7715218696214535166ull, 293675306u, 0u, 6634878980788273734ull, 2857239962u, 0u, 2666239539288337114ull, 2318322363u, 0u, 1730108574612313172ull, 2080173162u, 0u, 4397599188864900724ull, 497182614u, 0u, 7012092484289203340ull, 3135422144u, 0u, 9751991199519479426ull, 384951145u, 0u, 4979128044919598192ull, 2555349581u, 0u, 2578609301540867108ull, 2199859295u, 0u, 17343963272720579470ull, 938144166u, 0u, 16646663954278730408ull, 1672643294u, 0u, 2986112901516876664ull, 1507198033u, 0u, 232117798745520926ull, 2112279653u, 0u, 17192911832461272940ull, 410683142u, 0u, 198539328281810374ull, 2851329512u, 0u, 10794150319841539830ull, 219424390u, 0u, 3119158418005278116ull, 792213705u, 0u, 3168123994288686980ull, 2182449199u, 0u, 13435357989582178944ull, 1094690168u, 0u, 10140256676522145932ull, 3024116984u, 0u, 15090814054716692560ull, 2952201110u, 0u, 6044745059037478822ull, 2501934354u, 0u, // 232 14187044751696073450ull, 2119024451u, 0u, 2653158480001818568ull, 240290607u, 0u, 14604902125584196046ull, 1063243296u, 0u, 12714084065355078448ull, 4046063853u, 0u, 9555183224354865588ull, 855591129u, 0u, 15010892064592117940ull, 2650346070u, 0u, 14032147724017284794ull, 1483474525u, 0u, 12819242273160051858ull, 3820266888u, 0u, 16104423213504125298ull, 1865905648u, 0u, 10002303831191457554ull, 3798894817u, 0u, 1942557430538592998ull, 3319953048u, 0u, 2894268710959952100ull, 2503143721u, 0u, 4312555222909606920ull, 443901635u, 0u, 14270460818490082456ull, 707870663u, 0u, 6747406001755549398ull, 754246029u, 0u, 160859722118797834ull, 3530763624u, 0u, 4036575128534534140ull, 1507638261u, 0u, 5767632283116455990ull, 3469381324u, 0u, 15014642944766624492ull, 2906933447u, 0u, 12649883906455196012ull, 1529408220u, 0u, 15283405380486694352ull, 3317095694u, 0u, 8372136650521175948ull, 2295487680u, 0u, 452955879076264994ull, 256125143u, 0u, 8536291282174706870ull, 158797031u, 0u, 7783924846533055124ull, 2066080328u, 0u, 17020220800070510154ull, 1972842399u, 0u, 3408222063382362700ull, 3057437376u, 0u, 1819628758669841812ull, 1165380182u, 0u, 338596241561013654ull, 3930615048u, 0u, 2847640649186657074ull, 4111427141u, 0u, 11433781707837085506ull, 2934732550u, 0u, 1550828814571086098ull, 802613855u, 0u, // 233 7666705388128706142ull, 2587376483u, 0u, 17095053060922034538ull, 1387312824u, 0u, 5920709039676768330ull, 4216086098u, 0u, 1495160170386993986ull, 2455224129u, 0u, 12586858727621882184ull, 855917016u, 0u, 6939305481728305266ull, 4139077575u, 0u, 4058006187170924660ull, 1165538504u, 0u, 12008729457784287012ull, 1949213103u, 0u, 1320395936607096636ull, 612851865u, 0u, 7804697516215060748ull, 3444350721u, 0u, 4328756149772023416ull, 117296773u, 0u, 11686548345256192650ull, 3795563355u, 0u, 12212189021389296368ull, 1005088483u, 0u, 11555979314468004604ull, 1268751123u, 0u, 9135087584051888994ull, 3081574728u, 0u, 11552411934817586412ull, 3777811533u, 0u, 1730689176419849392ull, 3639623369u, 0u, 7359539492831969048ull, 1706199980u, 0u, 3812524719180696260ull, 4094059916u, 0u, 3843055238009804768ull, 1051842310u, 0u, 13021435646721951692ull, 3589703590u, 0u, 3090233666321451406ull, 3406457057u, 0u, 1349732860850110196ull, 511962039u, 0u, 14459761526182805906ull, 2331502150u, 0u, 14172788215309218364ull, 4029495659u, 0u, 315431525121940290ull, 2812103047u, 0u, 5194953986555472008ull, 565664293u, 0u, 3076047688520104088ull, 1249461678u, 0u, 17197930540225568540ull, 1864650756u, 0u, 2858013103707710522ull, 3298423626u, 0u, 15737430662854905602ull, 2690146644u, 0u, 1049765464994822624ull, 2358281222u, 0u, // 234 12923494554333827206ull, 1083202686u, 0u, 13093186303306427164ull, 1359354529u, 0u, 12300673725513180828ull, 537261552u, 0u, 5950307601712315412ull, 673260821u, 0u, 15759527120154783816ull, 2703609692u, 0u, 1181598785138435624ull, 3081548781u, 0u, 2984571886649970644ull, 1951653760u, 0u, 16516149463609669594ull, 211856985u, 0u, 5489508593579949620ull, 1443441558u, 0u, 13448289436553877714ull, 999040721u, 0u, 16208885313842149426ull, 704398940u, 0u, 1903677696010100308ull, 3978383705u, 0u, 11351958520194650330ull, 1315070038u, 0u, 1352934320111541682ull, 3920949833u, 0u, 3458675141882881490ull, 1027455494u, 0u, 329959506537543912ull, 3764547392u, 0u, 9817767346497790704ull, 1629692848u, 0u, 15633896871628488872ull, 537545111u, 0u, 825209239159983770ull, 2710392052u, 0u, 9018710945433307410ull, 700518963u, 0u, 13923020299545319138ull, 2942498032u, 0u, 17773124899081123026ull, 3956831398u, 0u, 7326350971688944226ull, 204483655u, 0u, 10030583779962077788ull, 2139701602u, 0u, 12611403650090352164ull, 3752443925u, 0u, 15786682450098775410ull, 3270273579u, 0u, 4543099049311144362ull, 2071985695u, 0u, 370224630973745042ull, 4084434904u, 0u, 16987532596710753910ull, 3373850968u, 0u, 7900323587681308844ull, 4146423055u, 0u, 1329741621900318676ull, 1218213473u, 0u, 15850294490917632260ull, 129183139u, 0u, // 235 8892753677761097850ull, 3088782436u, 0u, 12318742903593616024ull, 4277939736u, 0u, 9869809396917311034ull, 895005469u, 0u, 11421318297028877704ull, 1817267054u, 0u, 2193673102797990986ull, 3611914054u, 0u, 14394724286040492702ull, 2065055021u, 0u, 4925597157106129788ull, 3203457635u, 0u, 7021686107234026742ull, 3201702661u, 0u, 588961889974478810ull, 2147833470u, 0u, 1141497802391296496ull, 578548888u, 0u, 15281690463965648954ull, 1276161902u, 0u, 17037365402624482178ull, 675327154u, 0u, 15996066759683095236ull, 552100565u, 0u, 3888627034691959192ull, 3273667788u, 0u, 17434470025796676796ull, 2474180823u, 0u, 15119164548476693102ull, 2004207885u, 0u, 14753167452041784974ull, 1607533679u, 0u, 11807774153557818326ull, 3180910690u, 0u, 504912700082286414ull, 2945157736u, 0u, 6571179316044831384ull, 869596396u, 0u, 725813059782768524ull, 1853759842u, 0u, 5006100486215879052ull, 2461781881u, 0u, 7555761806243937232ull, 2514845437u, 0u, 2513604568038333966ull, 382942038u, 0u, 6491796231993440964ull, 961136966u, 0u, 7879585477126862070ull, 3814972013u, 0u, 6817792069167876540ull, 91121708u, 0u, 10862445474413985276ull, 1638995440u, 0u, 14038789569777701978ull, 3190502985u, 0u, 3359712487080074844ull, 3110682971u, 0u, 3439723482070078250ull, 3219892180u, 0u, 6760551878170483278ull, 1705366502u, 0u, // 236 1005798875687239574ull, 3316798158u, 0u, 7361420461123716078ull, 1304386381u, 0u, 1668194083702427044ull, 4242595744u, 0u, 17408926299262668726ull, 1965369817u, 0u, 14447587869360082416ull, 1583658664u, 0u, 13863899417540258040ull, 2519239855u, 0u, 186633134794653300ull, 1502625281u, 0u, 12184090628553300432ull, 1089223807u, 0u, 5354120494018827998ull, 3370491907u, 0u, 7861936797497973324ull, 2478778491u, 0u, 12035358682839441118ull, 256131370u, 0u, 6798930809259519570ull, 3349798515u, 0u, 14461556459121971582ull, 3320594117u, 0u, 15599554241675654976ull, 764699053u, 0u, 17664730107950109166ull, 1783593606u, 0u, 3379573489014569854ull, 1513587035u, 0u, 7098135634520997702ull, 1787145283u, 0u, 10176902419761551290ull, 2214877522u, 0u, 10661219981726914404ull, 3017508126u, 0u, 15678797933211442054ull, 3701759926u, 0u, 8124806478643116514ull, 868551525u, 0u, 16405407617891988754ull, 3886888928u, 0u, 246901313795132820ull, 1752477075u, 0u, 7308998664328336968ull, 3308030047u, 0u, 11928619400641269260ull, 2206700927u, 0u, 17475994275353215746ull, 4235888570u, 0u, 5187051902638972050ull, 2506714290u, 0u, 16632069100345379122ull, 3098716682u, 0u, 6059782697465305358ull, 1985200706u, 0u, 17006414436313524346ull, 2381103353u, 0u, 12760853314891438352ull, 4037566075u, 0u, 1098946180717731982ull, 1976725317u, 0u, // 237 11282698603094837184ull, 2892474313u, 0u, 13370554189957301246ull, 3545431583u, 0u, 2438220361749425314ull, 3047853547u, 0u, 3842113434879011832ull, 2808742945u, 0u, 776533068570629714ull, 2200702079u, 0u, 13091097697210746760ull, 1936204461u, 0u, 938974334931639872ull, 2152738293u, 0u, 1618385627623701980ull, 3371702582u, 0u, 4390740542658973976ull, 3711568490u, 0u, 17700806659602931336ull, 80393449u, 0u, 5800170280284617582ull, 4029588716u, 0u, 16822785566529675436ull, 3992429560u, 0u, 2665323486022232146ull, 2062510536u, 0u, 11489602292906957794ull, 1095066223u, 0u, 18253235629386415022ull, 3387738233u, 0u, 17090465662081450694ull, 2303576667u, 0u, 11805500279204153128ull, 3923089550u, 0u, 4034786838715859458ull, 3492769654u, 0u, 17929771696532123754ull, 1982123683u, 0u, 11093207338365526500ull, 3506573669u, 0u, 13082829508021969724ull, 752134265u, 0u, 16245546467753035370ull, 2728473950u, 0u, 7024962962843372342ull, 1717775208u, 0u, 68346947140302342ull, 2438665353u, 0u, 10601199110862707652ull, 268178800u, 0u, 2455698781382009828ull, 1753468140u, 0u, 9033207985103077060ull, 3966333411u, 0u, 18425070291650367066ull, 2675766136u, 0u, 11137027239163504618ull, 2345297049u, 0u, 7823374705718344112ull, 1905703u, 0u, 13152911112805722764ull, 111499465u, 0u, 14887863359406781744ull, 424913520u, 0u, // 238 7327987909877883028ull, 2959796678u, 0u, 17664060147504105914ull, 313657985u, 0u, 12358599732931506656ull, 2057594984u, 0u, 12208210188411488774ull, 3404552661u, 0u, 13384083923885276976ull, 3132385289u, 0u, 271873383638991266ull, 3081107893u, 0u, 2100921903415889320ull, 3495084345u, 0u, 10278177251945132506ull, 2630416730u, 0u, 4091888787762780608ull, 3690342973u, 0u, 12076648966249777018ull, 3124015621u, 0u, 17434033311215189070ull, 742448006u, 0u, 16078016946742546132ull, 1308561367u, 0u, 16316615875756513226ull, 2213387916u, 0u, 17460213081700757122ull, 654493024u, 0u, 16851839964358987264ull, 1306671524u, 0u, 11453585749595649972ull, 569098327u, 0u, 653067953979794362ull, 2384984006u, 0u, 16704283243886986436ull, 2270819133u, 0u, 2258065782796347150ull, 2523124865u, 0u, 17242190715377725218ull, 3516610565u, 0u, 12149001193066226270ull, 1593688146u, 0u, 6151476981173244014ull, 2176300340u, 0u, 652374623887382252ull, 1755581388u, 0u, 11746197961049646734ull, 1333054730u, 0u, 752432328336674548ull, 2771514154u, 0u, 9027623029739838858ull, 2024175636u, 0u, 13820120195343112242ull, 615495087u, 0u, 1342326543898643560ull, 127006889u, 0u, 11431539739847389342ull, 2706459691u, 0u, 13239966234270505464ull, 3306645271u, 0u, 11676170825364064808ull, 2831846428u, 0u, 10807761424895641986ull, 259480631u, 0u, // 239 6159009627251152464ull, 4074963146u, 0u, 9798830666898941974ull, 1511087198u, 0u, 15986480209146095256ull, 3848824098u, 0u, 2692017057850751354ull, 958693366u, 0u, 773430687683478242ull, 286278400u, 0u, 4432393833869469668ull, 4040483911u, 0u, 1106503126796523062ull, 1764971248u, 0u, 7253109285049262754ull, 1159144060u, 0u, 16402429225344009484ull, 886193476u, 0u, 8271494961919311492ull, 1645148532u, 0u, 1779845241282933628ull, 3342062041u, 0u, 17602511882017893072ull, 1506342988u, 0u, 16897458250930993246ull, 331796496u, 0u, 16247811402919754488ull, 1860793462u, 0u, 3371321604180826936ull, 395234320u, 0u, 8435044784100029658ull, 3641408434u, 0u, 8906632398065448594ull, 788067907u, 0u, 14605366334418726428ull, 176421661u, 0u, 17486616714862499310ull, 3634134223u, 0u, 15404033002953373264ull, 1339819244u, 0u, 6499311370380203970ull, 826421083u, 0u, 10623273502485334008ull, 136588598u, 0u, 15133543859567843760ull, 351029939u, 0u, 2713772682805741764ull, 1080943753u, 0u, 5416742629498677344ull, 1777529508u, 0u, 2016811062840371508ull, 1086017559u, 0u, 8578598697034383466ull, 2184348742u, 0u, 11760387094287864890ull, 4026392041u, 0u, 8962097597328024052ull, 4126344607u, 0u, 10980013070869228910ull, 3727014672u, 0u, 9976803720771658988ull, 1640410544u, 0u, 4625053850969777712ull, 1509013161u, 0u, // 240 3636151512390496720ull, 1095521527u, 0u, 13978082393317477208ull, 26982739u, 0u, 10203803829901860758ull, 869101563u, 0u, 10429166967756943510ull, 2812725313u, 0u, 11469674578863405674ull, 3784260489u, 0u, 7850188743957416240ull, 3466037231u, 0u, 3299785101549675392ull, 1557756569u, 0u, 240290223416942928ull, 2727295015u, 0u, 5207734223546154632ull, 3423222295u, 0u, 1925697911729572678ull, 3314366321u, 0u, 7057331155300297800ull, 3300119079u, 0u, 17758894109149613174ull, 3747454141u, 0u, 12205144362258081554ull, 3109722120u, 0u, 6241820073322257634ull, 1288872527u, 0u, 10381194243198187838ull, 4227695804u, 0u, 13759393706468954460ull, 2862686276u, 0u, 17992552872215740772ull, 2487847586u, 0u, 1076756875288848320ull, 3392092248u, 0u, 10970949606609946348ull, 159874240u, 0u, 12317827987214287960ull, 925411391u, 0u, 1109469820032856662ull, 546535113u, 0u, 3517479482043493868ull, 1773695691u, 0u, 10265235397949927662ull, 3986150732u, 0u, 3144641980523087618ull, 2495956274u, 0u, 14902434925973909758ull, 532893109u, 0u, 17574384315872407326ull, 3012830136u, 0u, 5318923444008604770ull, 670168203u, 0u, 11700561551566404582ull, 1266146142u, 0u, 14997332612057632820ull, 4128450261u, 0u, 2809612305419332734ull, 3861543174u, 0u, 4500632309182855438ull, 2376473531u, 0u, 4604939051305482212ull, 2174954936u, 0u, // 241 6178762438801605338ull, 4003052390u, 0u, 10002167629505997274ull, 1850733052u, 0u, 8404456879750272748ull, 505226503u, 0u, 10296690258615032818ull, 951509120u, 0u, 6530142598325745194ull, 2905453670u, 0u, 12794411144547496816ull, 4168232302u, 0u, 8343903926490209302ull, 412301379u, 0u, 6034372185730472554ull, 205264606u, 0u, 4786526180420399260ull, 1732536385u, 0u, 316697335756813626ull, 467307826u, 0u, 9443585377316002368ull, 3734073196u, 0u, 10131709863685531146ull, 2428069290u, 0u, 17795739598660277160ull, 805721771u, 0u, 8589082858667042852ull, 682767339u, 0u, 6368907744050864584ull, 1762389518u, 0u, 17311042079599228618ull, 3790583191u, 0u, 2516007248253813798ull, 4135785517u, 0u, 12512056815937744806ull, 2555870161u, 0u, 2050618888691807200ull, 4044346227u, 0u, 12839779181357244054ull, 798027860u, 0u, 12289385222427883662ull, 3798207338u, 0u, 7612343009362381764ull, 529179367u, 0u, 7350894536467035960ull, 2039132792u, 0u, 8156887357950086272ull, 1250480085u, 0u, 6661778125229146154ull, 729496797u, 0u, 7386593053709217338ull, 315178540u, 0u, 11510952063805956098ull, 2518676256u, 0u, 5382069219036686814ull, 3737940183u, 0u, 8002602515289088506ull, 1954961875u, 0u, 1340264211544298686ull, 1409008306u, 0u, 17711249383505776370ull, 3401016944u, 0u, 4228008832989806056ull, 62645941u, 0u, // 242 13755303340239206032ull, 1635636515u, 0u, 5348626578084119680ull, 2189318445u, 0u, 5039671191118536334ull, 4037419121u, 0u, 13112904492876492158ull, 2548997732u, 0u, 13444742802091101960ull, 2985531291u, 0u, 396141279536646918ull, 999949680u, 0u, 6905710793508602924ull, 23161378u, 0u, 12535528654141041474ull, 2223310107u, 0u, 11599365408765998068ull, 2896522427u, 0u, 15156582513923011178ull, 3663599222u, 0u, 3558859529066585670ull, 1016625518u, 0u, 8794963498812541204ull, 4021219130u, 0u, 10234082971221304726ull, 2181850249u, 0u, 15856868672879998816ull, 773182925u, 0u, 13731563800099020696ull, 3456733845u, 0u, 9861617123380016308ull, 77986320u, 0u, 5154530682316192196ull, 3768072008u, 0u, 4643392097113992624ull, 1521572184u, 0u, 2411913659270084410ull, 1409641803u, 0u, 1652481220819617546ull, 807779287u, 0u, 12408399904428293752ull, 4162680409u, 0u, 13177151293192870378ull, 203961418u, 0u, 15900859266026010010ull, 4222381571u, 0u, 11270304532891914878ull, 3627385153u, 0u, 10119128834454359214ull, 1526255756u, 0u, 14410515381833367844ull, 3901997729u, 0u, 12943077010066276596ull, 3475534230u, 0u, 5504962664173726068ull, 982574237u, 0u, 5464935793156490026ull, 962838802u, 0u, 14212274638927448590ull, 3369351962u, 0u, 3467506107020483974ull, 2806142275u, 0u, 17234763671622190922ull, 2251249885u, 0u, // 243 8678656039093481672ull, 1788490117u, 0u, 16603833246947392660ull, 2094281863u, 0u, 515018464329723670ull, 2323730254u, 0u, 4511568764125142946ull, 461662272u, 0u, 17477736225228735672ull, 237764177u, 0u, 9650330665303871748ull, 2066854095u, 0u, 6250294736244768206ull, 3243888899u, 0u, 14707134374992722918ull, 515065294u, 0u, 10058765124194385724ull, 57646417u, 0u, 13657401889062432178ull, 524937045u, 0u, 1002991615772607888ull, 2109059488u, 0u, 1572840603718753570ull, 3799139534u, 0u, 4760882586989501354ull, 4282568904u, 0u, 6209679014485945182ull, 1534746545u, 0u, 13556323131719480482ull, 526272791u, 0u, 1219336158092387044ull, 4238710596u, 0u, 3482495886172616104ull, 1940150808u, 0u, 14006546546338388740ull, 1843977715u, 0u, 7672283115184955018ull, 3186569907u, 0u, 5515997442841494274ull, 1961061056u, 0u, 9880377436732265160ull, 739763912u, 0u, 1367776606679511616ull, 3619130845u, 0u, 14118835075589968546ull, 86087060u, 0u, 11112030347120807430ull, 2601253695u, 0u, 17807325989401167632ull, 2187272262u, 0u, 14459145312792788902ull, 43262490u, 0u, 10614896879331071022ull, 2431617746u, 0u, 13932821703028324436ull, 3332612303u, 0u, 13959495204216844502ull, 3980424268u, 0u, 13161827042068438004ull, 4207619971u, 0u, 16262452463058729994ull, 3354226115u, 0u, 15302782341722086414ull, 470314751u, 0u, // 244 4406380680039917490ull, 334018974u, 0u, 7051342352339561426ull, 3551348946u, 0u, 12875842636777372412ull, 527282696u, 0u, 5104311347793290980ull, 3641006745u, 0u, 8321694403552205374ull, 1072950186u, 0u, 1938907558843787308ull, 1523979021u, 0u, 11537894076978397072ull, 4153812047u, 0u, 8312650631166658016ull, 45833083u, 0u, 15684231144399208586ull, 3021649654u, 0u, 10587996077078613594ull, 4194650927u, 0u, 7004019811718949672ull, 3143800u, 0u, 2063870371861158222ull, 3863126621u, 0u, 16333100356847227262ull, 2666306835u, 0u, 17174847314698467374ull, 3258861580u, 0u, 11101174939136867228ull, 931774748u, 0u, 12733633404005014222ull, 3284806507u, 0u, 12088322545813723254ull, 2764431247u, 0u, 10782418220869490242ull, 1891694357u, 0u, 4027373213015880040ull, 3933115812u, 0u, 2951793202996826708ull, 1915835221u, 0u, 13436551278907349746ull, 2186673762u, 0u, 11859076298646155988ull, 3215468107u, 0u, 17298580008937155302ull, 3322537565u, 0u, 15535802285300414804ull, 2354226324u, 0u, 10064671772480937516ull, 468910467u, 0u, 5616069554420569766ull, 965442530u, 0u, 4313580457018356632ull, 3105045309u, 0u, 10964141605587778460ull, 2421071877u, 0u, 2277432077199181470ull, 4193824851u, 0u, 202235118552564218ull, 3093558458u, 0u, 5157059852611703050ull, 1338966008u, 0u, 5257824029743568684ull, 3134081775u, 0u, // 245 6855578634282551764ull, 3210196044u, 0u, 17878010788542098340ull, 3014186972u, 0u, 3691781939574237696ull, 993050029u, 0u, 2262931955273089520ull, 1186832276u, 0u, 16991847475251895372ull, 3691237291u, 0u, 9245236483649352040ull, 1185058100u, 0u, 13541239385694396304ull, 2464241773u, 0u, 12856705254720065020ull, 1730753113u, 0u, 8078109065940583026ull, 1183066114u, 0u, 9882040103305548074ull, 3327447954u, 0u, 12921931848191666536ull, 2663172886u, 0u, 12113464925745238020ull, 3321067328u, 0u, 5401887730536236728ull, 1731205854u, 0u, 114818875307160104ull, 5013835u, 0u, 3090334371391767516ull, 3609373938u, 0u, 7729373896097580194ull, 2130847377u, 0u, 5428648844531662338ull, 398217472u, 0u, 17585684481323649272ull, 3605337038u, 0u, 1083571776526816368ull, 2270116501u, 0u, 2479151427221259264ull, 807017404u, 0u, 7420953319491423308ull, 1895209691u, 0u, 6813436381737437964ull, 1137735063u, 0u, 11649081384488529888ull, 1624885731u, 0u, 17602266540867949050ull, 475933690u, 0u, 5200015908124669148ull, 3942191172u, 0u, 11179340414934338756ull, 259909004u, 0u, 16409670541840792128ull, 696822002u, 0u, 716705242655182052ull, 2684759554u, 0u, 8677264746039511692ull, 3777378385u, 0u, 14871939119862121282ull, 369423432u, 0u, 3096207381582461114ull, 3609382355u, 0u, 6201958570419330594ull, 2059645884u, 0u, // 246 4252399280958632308ull, 1779023055u, 0u, 10317844086697771204ull, 1583592917u, 0u, 1394091108771475164ull, 630870716u, 0u, 6475244213127935436ull, 1114327070u, 0u, 700286840769545568ull, 3353618886u, 0u, 31202305631480764ull, 3198796207u, 0u, 11995374257725937948ull, 3148994452u, 0u, 9172118284214327704ull, 3318375420u, 0u, 15700691793443475636ull, 1868431089u, 0u, 11185877650572711454ull, 4209707355u, 0u, 12110935522295096030ull, 2211236073u, 0u, 3131551037373260324ull, 913236170u, 0u, 11021097956962471050ull, 2004128418u, 0u, 2064630457774179260ull, 3789312245u, 0u, 17047819964631011620ull, 2154358402u, 0u, 3587391530591115802ull, 1463920291u, 0u, 11621477150245483628ull, 398537565u, 0u, 13320511835075521036ull, 3642266791u, 0u, 13269774817542176960ull, 3765620063u, 0u, 18194651709484594258ull, 482493837u, 0u, 7122795109009529112ull, 178315756u, 0u, 12860086528865707460ull, 880966152u, 0u, 7090630572148511456ull, 2470632517u, 0u, 16709107067514092950ull, 660498070u, 0u, 4089179737275615060ull, 366201479u, 0u, 16182624346932021292ull, 3825269302u, 0u, 14817604174528976108ull, 2117827962u, 0u, 12108861939031329532ull, 3342754740u, 0u, 6540683300220422854ull, 1156775361u, 0u, 17190653301371848304ull, 3644648626u, 0u, 11140377240975444896ull, 1312730437u, 0u, 4536433246623668862ull, 1023878396u, 0u, // 247 12633943626595107824ull, 4279191820u, 0u, 11438175482324185390ull, 1510275318u, 0u, 5707589151676245264ull, 2222146842u, 0u, 15071530926476424788ull, 1526619716u, 0u, 16110224397666610904ull, 958522639u, 0u, 12361256283636910088ull, 1893488019u, 0u, 7845304135913576234ull, 467854837u, 0u, 8510808445791509794ull, 3362886787u, 0u, 6538386966788491326ull, 161607948u, 0u, 15141084005107383644ull, 700204199u, 0u, 254649853341676646ull, 543956399u, 0u, 12424618629593635430ull, 905107640u, 0u, 18264587547847816346ull, 3459439646u, 0u, 11197706953264409142ull, 1176486867u, 0u, 5584049856596924698ull, 2028895075u, 0u, 2451114413843702250ull, 98091817u, 0u, 12337542159113536546ull, 2027742475u, 0u, 16290664160216262376ull, 2287069123u, 0u, 16534131412090209042ull, 1752233791u, 0u, 15350842130865624676ull, 1148696387u, 0u, 10534494444432724472ull, 1238860946u, 0u, 17740536313257294684ull, 1857630847u, 0u, 7378324001804903672ull, 92377469u, 0u, 16071717908802244996ull, 1826629699u, 0u, 768164198150698018ull, 600068677u, 0u, 509227302462143132ull, 339178999u, 0u, 13144235237620945464ull, 3888026915u, 0u, 4845369118835309460ull, 402463804u, 0u, 7755310980296758394ull, 3316140087u, 0u, 14010133058998150568ull, 3847031462u, 0u, 14494086254713001084ull, 1217360275u, 0u, 4249733722399707800ull, 3577264477u, 0u, // 248 5937980268023418876ull, 3547423251u, 0u, 14751124469636989992ull, 4040754878u, 0u, 14904507737758448146ull, 75924010u, 0u, 15803938108764876834ull, 3329201175u, 0u, 1506991386354877128ull, 3952408242u, 0u, 1812573274952404572ull, 1033078287u, 0u, 16856185132118233656ull, 3388139232u, 0u, 17437912995492770634ull, 162935353u, 0u, 14243719764432458362ull, 1591328541u, 0u, 7983788356999730674ull, 3917070865u, 0u, 2775749252123445670ull, 649052550u, 0u, 2610883396922238238ull, 3211724892u, 0u, 6699895075828789550ull, 1710791480u, 0u, 17426515533937617142ull, 837531345u, 0u, 16733967590096139958ull, 615278205u, 0u, 17686864005284346610ull, 4097580615u, 0u, 1010925102421048456ull, 790252492u, 0u, 9871307922855738526ull, 3798503579u, 0u, 203419176011818232ull, 2883355125u, 0u, 2975668194832970814ull, 558016237u, 0u, 13994661043188422760ull, 3408815226u, 0u, 18238649055480459256ull, 3361492511u, 0u, 1281411755421306896ull, 768586008u, 0u, 7835627206782821224ull, 1111842570u, 0u, 7585458733238591734ull, 920347266u, 0u, 10687394677351964066ull, 1827457122u, 0u, 17709821476765598628ull, 2635566118u, 0u, 8594334379528405440ull, 2583983712u, 0u, 8102454674860679214ull, 4081508127u, 0u, 15478676177678519090ull, 2197934519u, 0u, 6025819268667358680ull, 1814468419u, 0u, 14380836013928085288ull, 3886712769u, 0u, // 249 2235058451587819340ull, 3439144164u, 0u, 11003042795615699632ull, 153822591u, 0u, 1223423787044257918ull, 1111818505u, 0u, 5710320573614523818ull, 3698070344u, 0u, 6847693083274578024ull, 1780782496u, 0u, 13922073672587976470ull, 3801775733u, 0u, 8673098299915027972ull, 1800731280u, 0u, 8432845600645548230ull, 1790283391u, 0u, 3837028866842873324ull, 1390292164u, 0u, 4569689215197753562ull, 2495709775u, 0u, 5227998441992076012ull, 4150211179u, 0u, 5011092238599564242ull, 2679890405u, 0u, 11653595704958848680ull, 1190181310u, 0u, 5199520893729249166ull, 496153348u, 0u, 4409432087022782846ull, 2417647643u, 0u, 8810045355672570496ull, 460029367u, 0u, 15636125306871831344ull, 3778330285u, 0u, 15626650710818928568ull, 2772890906u, 0u, 12877244414915267974ull, 1362874766u, 0u, 7134730936718448258ull, 783340516u, 0u, 512816233517326594ull, 2028118927u, 0u, 2727622181959662702ull, 511521430u, 0u, 13672777922265656938ull, 868536978u, 0u, 17083857300227283028ull, 3352186110u, 0u, 17449592242775364076ull, 173569082u, 0u, 16661006853218359464ull, 1828239262u, 0u, 3204795671158718690ull, 1578400200u, 0u, 16017028083245289136ull, 3815870703u, 0u, 2944568726846780658ull, 606040708u, 0u, 624543238002324398ull, 3839049713u, 0u, 6156336767186423846ull, 143678032u, 0u, 2222619161759638952ull, 3394779400u, 0u, // 250 5523192452857664350ull, 4203098691u, 0u, 12999246463560852608ull, 102105522u, 0u, 8133785802159201418ull, 3961874706u, 0u, 12637769659005794968ull, 3541833781u, 0u, 1358251523409059524ull, 1682067735u, 0u, 7682398244213480130ull, 1488863331u, 0u, 4422585576441118174ull, 2494620421u, 0u, 9709447118049854478ull, 1716254323u, 0u, 15340444632138106878ull, 773849068u, 0u, 4668626732029495392ull, 2771981084u, 0u, 16410513066703728352ull, 3433374207u, 0u, 5065649832803312032ull, 2634380049u, 0u, 14564650495935315938ull, 2494976895u, 0u, 8382342628278902020ull, 706282577u, 0u, 9233091542538692910ull, 3436424037u, 0u, 14142511123310914170ull, 2417368765u, 0u, 7683631162793150898ull, 605169955u, 0u, 10301249665197808854ull, 1629999424u, 0u, 16649244100295731054ull, 2883869493u, 0u, 15659845677708546406ull, 3041272403u, 0u, 1366294555814522096ull, 1510397832u, 0u, 12548704108366063740ull, 287908732u, 0u, 8926701920050693072ull, 568827870u, 0u, 15610864641556873786ull, 2858755127u, 0u, 3796540485798833988ull, 874964074u, 0u, 16853922358056247076ull, 429946873u, 0u, 4184076682764936648ull, 1752025630u, 0u, 16525550592415072008ull, 942838739u, 0u, 8164246102315222370ull, 1561064914u, 0u, 13569851208889124956ull, 3368888535u, 0u, 15177595733740959952ull, 279366479u, 0u, 14806411457852506798ull, 1298499102u, 0u, // 251 6800978699911267128ull, 3307114339u, 0u, 10841266239873529532ull, 587490608u, 0u, 8002673218709702742ull, 974516906u, 0u, 1770124460209448278ull, 2830178819u, 0u, 12617929371644284960ull, 1821046450u, 0u, 5753710200878871460ull, 1071568068u, 0u, 7514428590129935340ull, 1098670436u, 0u, 14230601576114175582ull, 2608842645u, 0u, 17717403969895920934ull, 3427853633u, 0u, 15410605053208662074ull, 1852273016u, 0u, 1548451066591285926ull, 72763963u, 0u, 15532544045715498232ull, 1034823053u, 0u, 15922191313467973416ull, 3403463838u, 0u, 4797011663541536316ull, 2853197270u, 0u, 15804322528830295702ull, 3949453423u, 0u, 466180211133251562ull, 3114966104u, 0u, 12156155793120079462ull, 3686026801u, 0u, 18047713955641332596ull, 4039357996u, 0u, 13867927017786358772ull, 2479619745u, 0u, 10150596838363981676ull, 1894482306u, 0u, 10221106917429007502ull, 1385166507u, 0u, 17414552943980328370ull, 167916948u, 0u, 7221677122426170784ull, 3437195090u, 0u, 3900819091588356164ull, 26248468u, 0u, 14588535822008186940ull, 4166298775u, 0u, 4282666563557254484ull, 1059191358u, 0u, 16840699391906478744ull, 353356431u, 0u, 15505519802432397178ull, 2390830234u, 0u, 17907159989349036878ull, 4045478221u, 0u, 3607078905360753884ull, 3491214449u, 0u, 713596892864388682ull, 74310865u, 0u, 18367598772408471420ull, 912627779u, 0u, // 252 11862300127236343792ull, 2475031892u, 0u, 2411557679886190530ull, 2688049248u, 0u, 9540553262946799014ull, 1273177232u, 0u, 6429238562145785972ull, 4066237543u, 0u, 7471665602316456744ull, 2766067777u, 0u, 1400467082932920728ull, 3181623604u, 0u, 8531555002575518006ull, 2876932251u, 0u, 10742762758458681974ull, 83607487u, 0u, 10083398472947642062ull, 2695315367u, 0u, 1304159541062417156ull, 891970647u, 0u, 17427983176846505780ull, 3554012285u, 0u, 9384909235555794476ull, 3102186496u, 0u, 1975675766863194198ull, 3493004851u, 0u, 5540912145088929288ull, 1267932860u, 0u, 16193726475397150780ull, 2983960161u, 0u, 15398751016794832532ull, 2825735305u, 0u, 17782938170235682262ull, 634750908u, 0u, 13802548715584995606ull, 808656019u, 0u, 13150171274554076572ull, 3877695204u, 0u, 11553972438523179614ull, 792107960u, 0u, 4949187598601189120ull, 4144526978u, 0u, 3187682437625829850ull, 711160482u, 0u, 10506372284728518784ull, 1508527052u, 0u, 1988951223787551656ull, 2118873839u, 0u, 11221916951142532964ull, 3118503201u, 0u, 8117559772677148064ull, 3120400540u, 0u, 10894366327157600370ull, 665991639u, 0u, 1656854282179863328ull, 61525512u, 0u, 10237148813271876866ull, 2213171934u, 0u, 11056799343997539780ull, 1201394920u, 0u, 4911654952302558682ull, 1330947370u, 0u, 11617311664567953380ull, 3469855575u, 0u, // 253 16153121506507603334ull, 2873016618u, 0u, 11400233801759621706ull, 4024931840u, 0u, 5938883862594965154ull, 429638754u, 0u, 17315874173242039328ull, 144341977u, 0u, 11411248831616316268ull, 1353405919u, 0u, 2285897487922706404ull, 3810845946u, 0u, 7258377101006491902ull, 1111442256u, 0u, 5160238968658916450ull, 263101700u, 0u, 10318263844879455680ull, 557739708u, 0u, 16914197067358028182ull, 3588865943u, 0u, 17438521017362027460ull, 2800090860u, 0u, 13380982985737194086ull, 3102843655u, 0u, 11027992647474625688ull, 1185921434u, 0u, 12130367579531615918ull, 3005391955u, 0u, 7071087822062285492ull, 1441233454u, 0u, 13276994670142683910ull, 3843584465u, 0u, 5404389535792944130ull, 3239631771u, 0u, 948347893278988090ull, 2611505923u, 0u, 12330506988508692022ull, 3983631590u, 0u, 12453830670078324246ull, 3872788100u, 0u, 12788762252196037732ull, 3074071519u, 0u, 14991471545035743316ull, 584091553u, 0u, 10517319860712964148ull, 1073432121u, 0u, 6611598854043644764ull, 927093871u, 0u, 4758179850981303674ull, 862555520u, 0u, 13439487977934804108ull, 3120286653u, 0u, 8540541813639321008ull, 74406754u, 0u, 8042804322219569244ull, 1819111805u, 0u, 4223427116325662456ull, 1965508732u, 0u, 13667492744290217932ull, 4219398231u, 0u, 16974825391300804476ull, 3348804465u, 0u, 8511042525731022488ull, 2705220707u, 0u, // 254 4542137139923114164ull, 135594624u, 0u, 17476731547156508304ull, 380996838u, 0u, 5892809426340421752ull, 4026178985u, 0u, 16796582572587413808ull, 3994542781u, 0u, 12107259799620532624ull, 1293675426u, 0u, 11249504732891066814ull, 3663657418u, 0u, 6926869023369334118ull, 3872807737u, 0u, 7118631650205483550ull, 310043045u, 0u, 12818389078122642710ull, 50532378u, 0u, 14333057960774283634ull, 1337107570u, 0u, 4167808101022893026ull, 621310469u, 0u, 15434334861499413918ull, 2222815869u, 0u, 8524535463189666860ull, 3865986184u, 0u, 18024485560434518826ull, 471091446u, 0u, 13859553566484652768ull, 98217812u, 0u, 5499392959556978656ull, 1667683003u, 0u, 9226825523448293810ull, 1060849585u, 0u, 13509817991586874016ull, 1971891261u, 0u, 10794536589623434080ull, 3997218581u, 0u, 12888254113586387990ull, 387643700u, 0u, 2626907136187964616ull, 1983339207u, 0u, 1046574607010482308ull, 1889738446u, 0u, 442037850220337512ull, 926789050u, 0u, 5174875336525572336ull, 3429183349u, 0u, 3246456933459979066ull, 3940978302u, 0u, 17635602723519376148ull, 789653313u, 0u, 13367928143781328788ull, 3691955655u, 0u, 6776962340643678170ull, 4238333281u, 0u, 17798985075394830330ull, 2755150357u, 0u, 14287044076259770826ull, 892704202u, 0u, 13101641890255886992ull, 779700099u, 0u, 10965787076048039224ull, 2386757968u, 0u, // 255 10649747989152752888ull, 1705847608u, 0u, 13684863507363259484ull, 3449524257u, 0u, 10627435622065181784ull, 1503142204u, 0u, 3104395867738191844ull, 3013658552u, 0u, 8834505897066031144ull, 888188458u, 0u, 10895951035304439798ull, 3511036492u, 0u, 5131381035357322014ull, 3632253918u, 0u, 9450605878878820214ull, 1511660309u, 0u, 17754780519173864880ull, 2094241743u, 0u, 7176549202837074714ull, 3369866881u, 0u, 11494565599479983684ull, 3136744411u, 0u, 176845130751284166ull, 390808469u, 0u, 14764323033147658810ull, 1672502377u, 0u, 11596939382829169340ull, 2678675225u, 0u, 1299109556135274602ull, 2690806752u, 0u, 17521479640642101284ull, 2481649703u, 0u, 8700075195299186074ull, 3594629292u, 0u, 8251840663329522782ull, 2105604260u, 0u, 1654459396393666256ull, 1389077650u, 0u, 17733169389296381032ull, 2830179230u, 0u, 3608679321214797962ull, 2527457742u, 0u, 3166207406258662506ull, 701972227u, 0u, 8270797180279507128ull, 3223654171u, 0u, 1862021738028744136ull, 3589983972u, 0u, 8475112615221482948ull, 2088570602u, 0u, 9793361828490411412ull, 222456764u, 0u, 1731487820185798892ull, 3935260883u, 0u, 3802211380257848900ull, 850222758u, 0u, 5208108305883530370ull, 4092307385u, 0u, 10372722242675275526ull, 493323879u, 0u, 1526299337365467684ull, 614543412u, 0u, 10064205272236665558ull, 593676651u, 0u, libosl-0.8.0.orig/core/osl/bits/pieceMask.h0000644000000000000000000000656012316770314017213 0ustar rootroot#ifndef _PIECE_MASK_H #define _PIECE_MASK_H #include "osl/config.h" #include "osl/bits/ptypeTraits.h" static_assert(OSL_WORDSIZE == 64, "word size"); #include "osl/bits/pieceMask64.h" #include namespace osl { typedef PieceMask64 PieceMaskBase; /** * 駒番å·ã®ãƒ“ットセット. * 64bitã®Mask64を一ã¤ã‚‚ã—ãã¯ï¼Œ32bitã®Mask32ã‚’2æžšã§è¡¨ç¾ã™ã‚‹ï¼Ž * å„メソッドã®å¤‰æ•°å㯠num ã¯é§’番å·ã«ï¼Œ * index ã¯ãƒžã‚¹ã‚¯ã®ID(0-1)ã«ç”¨ã„られã¦ã„る. */ class PieceMask : public PieceMaskBase { public: PieceMask() {} PieceMask(const PieceMaskBase& base) : PieceMaskBase(base) {} static const mask_t numToMask(int num) { return mask_t::makeDirect(1) << PieceMask::numToOffset(num); } void setMask(int index,mask_t val) { mutableMask(index)=val; } private: mask_t& mutableMaskNum(int num) { return mutableMask(numToIndex(num)); } const mask_t getMaskNum(int num) const { return getMask(numToIndex(num)); } public: void xorMask(int index,mask_t val) { mutableMask(index)^=val; } void orMask(int index,mask_t val) { mutableMask(index)|=val; } bool test(int num) const { return (getMaskNum(num)&numToMask(num)).any(); } void set(int num) { mutableMaskNum(num)|=numToMask(num); } void flip(int num) { mutableMaskNum(num)^=numToMask(num); } void reset(int num) { mutableMaskNum(num)&= ~numToMask(num); } bool any() const { return ! none(); } const mask_t getMask(int num) const { return PieceMaskBase::getMask(num); } /** unpromote(PTYPE) ã®é§’ã®bit ã‚’*å«ã‚€*mask_tã‚’å–り出㙠*/ template const mask_t getMask() const { return getMask(PtypeFuns::indexNum); } /** unpromote(PTYPE) ã®é§’ã®bit ã ã‘å–り出㙠*/ template const mask_t selectBit() const { mask_t mask = getMask(); mask &= mask_t::makeDirect(PtypeFuns::basicType>::indexMask); return mask; } /** unpromote(PTYPE) ã®é§’ã®bit を消㙠*/ template void clearBit() { mask_t& mask = mutableMask(PtypeFuns::indexNum); mask &= ~mask_t::makeDirect(PtypeFuns::basicType>::indexMask); } /** unpromote(PTYPE) ã®é§’ã®bit ã‚’ç«‹ã¦ã‚‹ */ template void setBit() { mask_t& mask = mutableMask(PtypeFuns::indexNum); mask |= mask_t::makeDirect(PtypeFuns::basicType>::indexMask); } }; inline const PieceMask operator&(const PieceMask &m1, const PieceMask &m2) { return PieceMask64(m1.getMask(0)&m2.getMask(0)); } inline const PieceMask operator|(const PieceMask &m1, const PieceMask &m2) { return PieceMask64(m1.getMask(0)|m2.getMask(0)); } inline const PieceMask operator~(const PieceMask &m1) { return PieceMask64(~m1.getMask(0)); } inline bool operator==(const PieceMask &m1, const PieceMask &m2){ return m1.getMask(0)==m2.getMask(0) && m1.getMask(1)==m2.getMask(1); } inline bool operator!=(const PieceMask &m1, const PieceMask &m2) { return ! (m1 == m2); } std::ostream& operator<<(std::ostream& os,PieceMask const& pieceMask); } // namespace osl #endif /* _PIECE_MASK_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/king8Info.cc0000644000000000000000000001240312316770314017275 0ustar rootroot/* king8Info.cc */ #include "osl/bits/king8Info.h" #include "osl/numEffectState.h" #include "osl/additionalEffect.h" #include #include #ifndef MINIMAL std::ostream& osl::checkmate::operator<<(std::ostream& os, King8Info info) { typedef std::bitset<8> bs_t; os << bs_t(info.moveCandidate2()) << " " << bs_t(info.libertyCandidate()) << " " << bs_t(info.liberty()) << " " << bs_t(info.dropCandidate()); return os; } #endif namespace osl { namespace { /** * Pã®çŽ‰ã‚„pinã•れã¦ã„る駒以外ã‹ã‚‰ã®åˆ©ããŒã‚ã‚‹. * @param state - 盤é¢(alt(P)ã®æ‰‹ç•ªã¨ã¯é™ã‚‰ãªã„) * @param target - Pã®çމã®ä½ç½® * @param pos - 盤é¢ä¸Šã®(Pã®çމã‹ã‚‰é•·ã„利ãã®ä½ç½®ã«ã‚ã‚‹ã¨ã¯é™ã‚‰ãªã„) * @param pinned - pinã•れã¦ã„ã‚‹Pã®é§’ã®mask * @param on_baord_defense - alt(P)ã®ç›¤é¢ä¸Šã®é§’ã®ã†ã¡kingを除ã„ãŸã‚‚ã® * @param dir - diræ–¹å‘ã¸ã®attack */ template inline bool #ifdef __GNUC__ __attribute__ ((pure)) #endif hasEnoughEffect(NumEffectState const& state,Square target,Square pos, const PieceMask& pinned, const PieceMask& on_board_defense, Direction dir) { assert(state.kingSquare(P)==target); assert(pos.isOnBoard()); PieceMask pieceMask = state.effectSetAt(pos)&on_board_defense; if(pieceMask.none()) return false; PieceMask pieceMask1=pieceMask&~pinned; if(pieceMask1.any()) return true; pieceMask&=pinned; assert(pieceMask.any()); do { int num=pieceMask.takeOneBit(); Piece p=state.pieceOf(num); assert(p.isOnBoardByOwner(P)); Square pos1=p.square(); assert(Board_Table.getShortOffset(Offset32(pos,target)) == pos-target); Direction dir1=Board_Table.getShort8

(target,pos1); if(dir1==dir) return true; } while(pieceMask.any()); return false; } } } template uint64_t osl::checkmate:: King8Info::hasEffectMask(NumEffectState const& state,Square target, PieceMask pinned, PieceMask on_board_defense) { const Player altP=alt(P); Square pos=target-DirectionPlayerTraits::offset(); Piece p=state.pieceAt(pos); if(p.isEdge()) return 0ull; if(!state.hasEffectAt(P,pos)){ if(p.canMoveOn()){ // 自分ã®é§’ã‹ç©ºç™½ if(p.isEmpty()) return 0x1000000000000ull+(0x100010100ull<(Dir)); else return 0x1000000000000ull+(0x10100ull<(Dir)); } else // 相手ã®é§’ return 0ull; } const bool has_enough_effect = hasEnoughEffect(state,target,pos,pinned,on_board_defense,Dir); if(has_enough_effect){ if(p.canMoveOn()){ if(p.isEmpty()) return 0x10100010000ull<(Dir); else return 0x10000ull<(Dir); } else return 0x10000000000ull<(Dir); } else{ if(p.isEmpty()) return 0x10101010001ull<(Dir); else if(p.isOnBoardByOwner

()) return 0x10000ull<(Dir); else return 0x10001000000ull<(Dir); } } template const osl::checkmate::King8Info #if (defined __GNUC__) && (! defined GPSONE) && (! defined GPSUSIONE) __attribute__ ((noinline)) #endif osl::checkmate::King8Info::make(NumEffectState const& state,Square target, PieceMask pinned) { PieceMask on_board_defense=state.piecesOnBoard(alt(P)); on_board_defense.reset(KingTraits::index); uint64_t canMoveMask= hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense)+ hasEffectMask(state,target,pinned,on_board_defense); mask_t longMask=state.longEffectAt(target,P); while(longMask.any()){ int num=longMask.takeOneBit()+PtypeFuns::indexNum*32; Piece attacker=state.pieceOf(num); Direction d= Board_Table.getShort8

(target,attacker.square()); if((canMoveMask&(0x100< const osl::checkmate::King8Info #if (defined __GNUC__) && (! defined GPSONE) && (! defined GPSUSIONE) __attribute__ ((noinline)) #endif osl::checkmate:: King8Info::make(NumEffectState const& state, Square target) { return make

(state,target,state.pin(alt(P))); } const osl::checkmate::King8Info osl::checkmate:: King8Info::make(Player attack, NumEffectState const& state) { const Square king=state.kingSquare(alt(attack)); if (attack == BLACK) return make(state, king); else return make(state, king); } const osl::checkmate::King8Info osl::checkmate:: King8Info::makeWithPin(Player attack, NumEffectState const& state, const PieceMask& pins) { const Square king=state.kingSquare(alt(attack)); if (attack == BLACK) return make(state, king, pins); else return make(state, king, pins); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/effectContent.h0000644000000000000000000000336512316770314020101 0ustar rootroot/* effectContent.h */ #ifndef OSL_EFFECTCONTENT_H #define OSL_EFFECTCONTENT_H #include "osl/basic_type.h" namespace osl { class EffectContent { int effect; EffectContent(int value) : effect(value) { } public: EffectContent() : effect(0) { } explicit EffectContent(Offset offset) : effect(offset.intValue() << 1) { } static const EffectContent DIRECT() { return EffectContent(1); } /** * 隣ã ãŒï¼Œoffsetも与ãˆã‚‹ */ static const EffectContent DIRECT(Offset offset) { return EffectContent((offset.intValue() << 1)+1); } /** * 短ã„利ããŒã‚ã‚‹ã‹ï¼Œé–“ãŒemptyãªã‚‰é•·ã„利ããŒã‚ã‚‹ */ bool hasEffect() const { return effect; } /** * 短ã„利ããŒã‚る.長ã„利ãã®éš£ã‚‚å«ã‚€ */ bool hasUnblockableEffect() const { return (effect & 1); } /** * 返り値ãŒ0ãªã‚‰é•·ã„利ããŒãªã„, * 0以外ãªã‚‰è¾¿ã‚‹ã®ã«å¿…è¦ãªoffset * (2005/3/25 ã«ä»•様変更 - é•·ã„利ãã ãŒéš£ã®å ´åˆã‚‚offsetã‚’è¿”ã™) */ const Offset offset() const { return Offset::makeDirect(effect >> 1); } /** * 2005/3/25ã«å¤‰æ›´. */ bool hasBlockableEffect() const { return (effect & (-effect) & ~1) != 0; } int intValue() const { return effect; } }; inline bool operator==(EffectContent l, EffectContent r) { return l.intValue() == r.intValue(); } inline bool operator!=(EffectContent l, EffectContent r) { return ! (l == r); } inline bool operator<(EffectContent l, EffectContent r) { return l.intValue() < r.intValue(); } } // namespace osl #endif /* OSL_EFFECTCONTENT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/binaryIO.cc0000644000000000000000000000740612316770314017164 0ustar rootroot/* binaryIO.cc */ #include "osl/bits/binaryIO.h" #include "osl/oslConfig.h" #include #include #include #include #include #include #include namespace osl { namespace { const size_t split_limit = 8*1024; template void write_vector(std::ostream& os, const std::vector& data) { boost::iostreams::filtering_streambuf filter; filter.push(boost::iostreams::bzip2_compressor()); filter.push(os); std::ostream out(&filter); boost::archive::text_oarchive oa(out); if (data.size() <= split_limit) { oa << data; } else { for (size_t p=0; p tmp(data.begin()+p, data.begin()+std::min(p+split_limit, data.size())); oa << tmp; } } } } } void osl::misc::BinaryWriter:: write(std::ostream& os, const std::vector& data) { write_vector(os, data); } void osl::misc::BinaryWriter:: write(std::ostream& os, const std::vector& data) { write_vector(os, data); } template osl::misc::BinaryReader::BinaryReader(std::istream& is) : state(new State(is)) { } template osl::misc::BinaryReader::~BinaryReader() { } template struct osl::misc::BinaryReader::State { boost::iostreams::filtering_streambuf filter; std::unique_ptr in; std::unique_ptr ia; explicit State(std::istream &is) { if (!is) return; filter.push(boost::iostreams::bzip2_decompressor()); filter.push(is); in.reset(new std::istream(&filter)); ia.reset(new boost::archive::text_iarchive(*in)); } bool read_vector(std::vector& data) { if (! in || ! *in) return false; (*ia) >> data; return static_cast(*in); } }; template bool osl::misc::BinaryReader:: read(std::vector& data) { return state->read_vector(data); } template size_t osl::misc::BinaryReader::blockSize() { return split_limit; } template struct osl::misc::BinaryElementReader::State { BinaryReader reader; std::vector data; size_t cur; bool failed; explicit State(std::istream& is) : reader(is), cur(0), failed(!is) { } bool hasNext() { tryRead(); return cur < data.size(); } T read() { if (! hasNext()) throw std::logic_error("no data in BinaryReader::read"); return data[cur++]; } void tryRead() { if (cur < data.size()) return; data.clear(); cur = 0; try { failed = ! reader.read(data); } catch (boost::archive::archive_exception& e) { if (OslConfig::verbose() || 1) std::cerr << "read failed in BinaryReader " << e.what(); cur = data.size(); failed = true; } } }; template osl::misc::BinaryElementReader::BinaryElementReader(std::istream& is) : state(new State(is)) { } template osl::misc::BinaryElementReader::~BinaryElementReader() { } template bool osl::misc::BinaryElementReader:: hasNext() const { return state->hasNext(); } template bool osl::misc::BinaryElementReader:: failed() const { return state->failed; } template T osl::misc::BinaryElementReader::read() { return state->read(); } template class osl::misc::BinaryReader; template class osl::misc::BinaryReader; template class osl::misc::BinaryElementReader; template class osl::misc::BinaryElementReader; // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/pieceStand.h0000644000000000000000000001775012316770314017374 0ustar rootroot/* pieceStand.h */ #ifndef OSL_PIECESTAND_H #define OSL_PIECESTAND_H #include "osl/basic_type.h" #include "osl/container.h" #include #include namespace osl { class SimpleState; /** * ç‰‡æ–¹ã®æ‰‹ç•ªã®æŒé§’ã®æžšæ•°ã‚’記録ã™ã‚‹ã‚¯ãƒ©ã‚¹. * - bit field を使ã†ã¹ãã‹è¿·ã† * - 一応 king ã‚’æŒé§’ã«ã—ã¦è‰¯ã„ã“ã¨ã«ã—ã¦ãŠã * レイアウト é•·ã•:index * - reserved : 1;31 * - carry : 1; * - KING : 2;28 * - carry : 1; * - GOLD : 3;24 * - carry : 1; * - PAWN : 5;18 * - carry : 1; * - LANCE : 3;14 * - carry : 1; * - KNIGHT : 3;10 * - carry : 1; * - SILVER : 3; 6 * - carry : 1; * - BISHOP : 2; 3 * - carry : 1; * - ROOK : 2; 0 * * == を軽ãã™ã‚‹ãŸã‚ã« carry off ã®çŠ¶æ…‹ã‚’åŸºæœ¬ã¨ã™ã‚‹ */ class PieceStand { public: /** æŒé§’ã®è¡¨ç¤ºã§è‰¯ã使ã‚れる順番. KINGã‚„æˆé§’㯠-1 */ static const CArray order; static const unsigned int carryMask = 0x48822224; private: static const CArray shift; static const CArray mask; mutable unsigned int flags; public: explicit PieceStand(unsigned int value=0) : flags(value) { } explicit PieceStand(Player, const SimpleState&); PieceStand(int pawnCount, int lanceCount, int knightCount, int silverCount, int goldCount, int bishopCount, int rookCount, int kingCount) : flags(0) { add(PAWN, pawnCount); add(LANCE, lanceCount); add(KNIGHT, knightCount); add(SILVER, silverCount); add(GOLD, goldCount); add(BISHOP, bishopCount); add(ROOK, rookCount); add(KING, kingCount); } void add(Ptype type, unsigned int num=1) { assert(isBasic(type)); assert(num == (num & mask[type])); flags += (num << (shift[type])); assert(testCarries() == 0); // overflow 検出 } void sub(Ptype type, unsigned int num=1) { assert(isBasic(type)); assert(num == (num & mask[type])); assert(get(type) >= num); flags -= (num << (shift[type])); } /** * 加算å¯èƒ½ãªã‚‰åŠ ãˆã‚‹. * 速度ãŒå¿…è¦ãªã¨ã“ã‚ã§ã¯ä½¿ã£ã¦ãªã„ã®ã§ .cc ã«ç§»å‹•. */ void tryAdd(Ptype type); bool canAdd(Ptype type) const; /** * 1枚以上æŒã£ã¦ã„ã‚Œã°æ¸›ã‚‰ã™ */ void trySub(Ptype type) { if (get(type)) sub(type); } /** * 一種類ã®é§’ã—ã‹ãªã„ */ bool atMostOneKind() const; /** * pieceStandåŒå£«ã®åŠ ç®—ï¼Œæ¸›ç®—. * è¶³ã—ã¦è‰¯ã„ã®ã¯ï¼Œcarry ãŒç«‹ã£ã¦ã„ãªã„piecestandã§ * ã‹ã¤ï¼Œå«ã¾ã‚Œã‚‹é§’ãŒé«˜ã€…1㤠*/ void addAtmostOnePiece(PieceStand const& ps){ #ifndef NDEBUG const PieceStand copy(*this); #endif assert(! ps.testCarries()); assert(ps.atMostOneKind()); flags += ps.getFlags(); assert(carryUnchangedAfterAdd(copy, ps)); } void subAtmostOnePiece(PieceStand const& ps){ #ifndef NDEBUG const PieceStand copy(*this); #endif assert(! ps.testCarries()); assert(ps.atMostOneKind()); flags -= ps.getFlags(); assert(carryUnchangedAfterSub(copy, ps)); } private: bool carryUnchangedAfterAdd(const PieceStand& original, const PieceStand& other) const; bool carryUnchangedAfterSub(const PieceStand& original, const PieceStand& other) const; public: unsigned int get(Ptype type) const { return (flags >> (shift[type])) & mask[type]; } void carriesOff() const { flags &= (~carryMask); } void carriesOn() const { flags |= carryMask; } unsigned int testCarries() const { return (flags & carryMask); } bool isSuperiorOrEqualTo(PieceStand other) const { carriesOn(); other.carriesOff(); const bool result = (((flags - other.flags) & carryMask) == carryMask); carriesOff(); return result; } /** * this 㨠other ㌠BLACK ã®æŒé§’ã¨è€ƒãˆãŸæ™‚ã«ï¼Œ * this ã®æ–¹ãŒåŒã˜ã‹æ²¢å±±æŒã£ã¦ã„れã°çœŸ. */ template bool hasMoreThan(PieceStand other) const { if (P == BLACK) return isSuperiorOrEqualTo(other); else return other.isSuperiorOrEqualTo(*this); } bool hasMoreThan(Player P, PieceStand other) const { if (P == BLACK) return hasMoreThan(other); else return hasMoreThan(other); } unsigned int getFlags() const { return flags; } /** ã©ã‚Œã‹ã®é§’を一枚ã§ã‚‚æŒã£ã¦ã„ã‚‹ */ bool any() const { return flags; } /** * 種類毎㫠this 㨠other ã®æŒé§’ã®å¤šã„方をå–ã‚‹ */ const PieceStand max(PieceStand other) const { // otherä»¥ä¸Šã®æ•°æŒã£ã¦ã„ã‚‹ptypeã«å¯¾å¿œã™ã‚‹carryãŒ1ã«ãªã‚‹ï¼Ž const unsigned int mask0 = ((flags|carryMask)-other.flags) & carryMask; // ROOK BISHOP KING用ã®MASKを作る unsigned int my_mask = mask0-((mask0&0x40000024)>>2); // GOLD SILVER KNIGHT LANCE用ã®MASKを作る my_mask -= (mask0&0x08022200)>>3; // PAWN用ã®MASKã®ã¿æ®‹ã™ my_mask -= (mask0&0x00800000)>>5; // my_mask ãŒ1ã®ptypeã®æ•°ã¯è‡ªåˆ†ã‹ã‚‰ï¼Œ0ã®ptypeã¯otherã®ã¨ã“ã‚ã®å€¤ã‚’ return PieceStand((flags&my_mask)|(other.flags&~my_mask)); } /** * 種類毎㫠this 㨠other ã®æŒé§’ã®å¤šã„方をå–ã‚‹ (max ã®alternative) */ const PieceStand max2(PieceStand other) const { // otherä»¥ä¸Šã®æ•°æŒã£ã¦ã„ã‚‹ptypeã«å¯¾å¿œã™ã‚‹carryãŒ1ã«ãªã‚‹ï¼Ž const unsigned int diff0=((flags|carryMask)-other.flags); const unsigned int mask0=diff0&carryMask; // ROOK BISHOP KING GOLD SILVER KNIGHT LANCE用ã®MASKを作る const unsigned int mask02=(mask0&0x40000024u)+(mask0&0x48022224u); unsigned int my_mask=mask0-(mask02>>3); // PAWN用ã®MASKã®ã¿æ®‹ã™ my_mask -= (mask0&0x00800000)>>5; // my_mask ãŒ1ã®ptypeã®æ•°ã¯è‡ªåˆ†ã‹ã‚‰ï¼Œ0ã®ptypeã¯otherã®ã¨ã“ã‚ã®å€¤ã‚’ return PieceStand((other.flags+(diff0&my_mask))&~carryMask); } const PieceStand nextStand(Player pl, Move move) const { assert(move.isNormal()); PieceStand result = *this; if (move.player() == pl) { if (const Ptype ptype = move.capturePtype()) { result.add(unpromote(ptype)); } else if (move.isDrop()) { const Ptype ptype = move.ptype(); assert(get(ptype)); result.sub(ptype); } } return result; } const PieceStand nextStand(Move move) const { return nextStand(move.player(), move); } const PieceStand previousStand(Player pl, Move move) const { assert(move.isNormal()); PieceStand result = *this; if (move.player() == pl) { if (const Ptype ptype = move.capturePtype()) { const Ptype before = unpromote(ptype); assert(get(before)); result.sub(before); } else if (move.isDrop()) { const Ptype ptype = move.ptype(); result.add(ptype); } } return result; } const PieceStand previousStand(Move move) const { return previousStand(move.player(), move); } }; inline bool operator==(PieceStand l, PieceStand r) { assert(! l.testCarries()); assert(! r.testCarries()); return l.getFlags() == r.getFlags(); } inline bool operator!=(PieceStand l, PieceStand r) { return ! (l == r); } inline bool operator<(PieceStand l, PieceStand r) { assert(! l.testCarries()); assert(! r.testCarries()); return l.getFlags() < r.getFlags(); } std::ostream& operator<<(std::ostream&, PieceStand l); struct PieceStandIO { /** * æŒé§’ã®æ•°ã‚’空白区切ã§å‡ºåŠ›ã™ã‚‹. 数値処ç†ç”¨é€” */ static std::ostream& writeNumbers(std::ostream&, const PieceStand& stand); static std::istream& readNumbers(std::istream&, PieceStand& stand); }; } // namespace osl #endif /* OSL_PIECESTAND_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/bitXmask.h0000644000000000000000000000214412316770314017066 0ustar rootroot/* bitXmask.h */ #ifndef OSL_BITXMASK_H #define OSL_BITXMASK_H #include "osl/basic_type.h" #include namespace osl { namespace container { /** * X座標ã®bitset */ class BitXmask { int mask; public: BitXmask() : mask(0) {} void clearAll() { mask = 0; } void set(int x) { mask |= (1 << x); } void clear(int x) { mask &= ~(1 << x); } void set(Square position) { set(position.x()); } void clear(Square position) { clear(position.x()); } bool isSet(int x) const { return mask & (1< namespace osl { namespace effect { union Byte8 { unsigned long long lv; CArray uc; } #ifdef __GNUC__ __attribute__((aligned(8))) #endif ; /** * 盤é¢ä¸Šã®é§’ãŒã€Œé»’ã‹ã‚‰è¦‹ãŸã€æ–¹å‘ã«é•·ã„利ãã‚’ã¤ã‘られã¦ã„る時ã«ï¼Œ * 利ãã‚’ã¤ã‘ã¦ã„ã‚‹é§’ã®ç•ªå·ã‚’å¾—ã‚‹ * ãŸã¨ãˆã°ï¼ŒUã®æ™‚ã¯ä¸‹ã‹ã‚‰ä¸Šæ–¹å‘ã®é•·ã„利ããŒã¤ã„ã¦ã„ã‚‹ã‚‚ã®ã¨ã™ã‚‹ï¼Ž * ãã®æ–¹å‘ã®åˆ©ããŒã¤ã„ã¦ã„ãªã„å ´åˆã¯EMPTY_NUM(0x80)を入れã¦ãŠã. */ class EffectedNum { private: Byte8 b8; public: EffectedNum() { clear(); } void clear(){ #define E(n) ((static_cast(EMPTY_NUM)<<((n)*8))) b8.lv= E(0)|E(1)|E(2)|E(3)|E(4)|E(5)|E(6)|E(7); #undef E } int operator[](Direction d) const{ assert(0<=d && d<=7); return b8.uc[d]; } unsigned char& operator[](Direction d){ assert(0<=d && d<=7); return b8.uc[d]; } }; class EffectedNumTable { CArray contents #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; public: EffectedNumTable() { clear(); } EffectedNumTable(SimpleState const&); const EffectedNum& operator[](int i) const { return contents[i]; } void clear(); EffectedNum& operator[](int i){ return contents[i]; } }; bool operator==(const EffectedNumTable&,const EffectedNumTable&); std::ostream& operator<<(std::ostream&,const EffectedNumTable&); } using effect::EffectedNumTable; } #endif // _EFFECTED_NUM_TABLE_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/effectedNumTable.cc0000644000000000000000000000304512316770314020640 0ustar rootroot/* effectedNumTable.cc */ #include "osl/bits/effectedNumTable.h" #include "osl/bits/ptypeTable.h" #include "osl/bits/boardTable.h" #include void osl::effect::EffectedNumTable::clear() { for(int i=0;i<40;i++) contents[i].clear(); } osl::effect::EffectedNumTable::EffectedNumTable(SimpleState const& state) { clear(); for(int num=32;num<=39;num++){ osl::Piece p=state.pieceOf(num); if(!p.isOnBoard()) continue; int moveMask=Ptype_Table.getMoveMask(p.ptype()); for(int i=0;i<8;i++){ Direction d=static_cast(i); if(p.owner()==WHITE) d=inverse(d); Direction longD=shortToLong(d); if((moveMask&dirToMask(longD))==0) continue; Offset o=Board_Table.getOffsetForBlack(static_cast(i)); Square pos=p.square()+o; Piece p1; for(;(p1=state.pieceAt(pos)).isEmpty();pos+=o) ; if(pos.isEdge()) continue; int num1=p1.number(); contents[num1][static_cast(i)]=num1; } } } std::ostream& osl::effect::operator<<(std::ostream& os,osl::EffectedNumTable const& et) { os << "[\n"; for(int num=0;num<=39;num++){ os << " ["; for(int d=0;d<7;d++) os << et[num][static_cast(d)] << ","; os << et[num][static_cast(7)] << "],\n"; } return os << "]\n"; } bool osl::effect::operator==(EffectedNumTable const& e1, EffectedNumTable const& e2) { for(int i=0;i<8;i++){ for(int num=0;num<=39;num++){ if(e1[num][static_cast(i)]!=e2[num][static_cast(i)]) return false; } } return true; } libosl-0.8.0.orig/core/osl/bits/numSimpleEffect.cc0000644000000000000000000001771012316770314020535 0ustar rootroot/* numSimpleEffect.cc */ #include "osl/bits/numSimpleEffect.h" #if (defined(__i386__) || defined(__x86_64__)) && !defined(OSL_NO_SSE) #include typedef __v2di v2di; #endif #include void osl::effect:: NumSimpleEffectTable::init(const SimpleState& state) { std::fill(effects.begin(), effects.end(),NumBitmapEffect()); for(int num=0;num<40;num++){ if (state.isOnBoard(num)){ Piece p=state.pieceOf(num); doEffect(state,p); } } } void osl::effect:: NumSimpleEffectTable::copyFrom(const NumSimpleEffectTable& src) { this->effected_mask = src.effected_mask; this->mobilityTable = src.mobilityTable; this->changed_effects = src.changed_effects; this->changed_effect_pieces = src.changed_effect_pieces; this->effected_changed_mask = src.effected_changed_mask; #if (defined(__i386__) || defined(__x86_64__)) && !defined(OSL_NO_SSE) { v2di en0=*((v2di*)&src.effectedNumTable[0]); v2di en2=*((v2di*)&src.effectedNumTable[2]); v2di en4=*((v2di*)&src.effectedNumTable[4]); v2di en6=*((v2di*)&src.effectedNumTable[6]); v2di en8=*((v2di*)&src.effectedNumTable[8]); v2di en10=*((v2di*)&src.effectedNumTable[10]); v2di en12=*((v2di*)&src.effectedNumTable[12]); v2di en14=*((v2di*)&src.effectedNumTable[14]); v2di en16=*((v2di*)&src.effectedNumTable[16]); v2di en18=*((v2di*)&src.effectedNumTable[18]); *((v2di*)&(*this).effectedNumTable[0])=en0; *((v2di*)&(*this).effectedNumTable[2])=en2; *((v2di*)&(*this).effectedNumTable[4])=en4; *((v2di*)&(*this).effectedNumTable[6])=en6; *((v2di*)&(*this).effectedNumTable[8])=en8; *((v2di*)&(*this).effectedNumTable[10])=en10; *((v2di*)&(*this).effectedNumTable[12])=en12; *((v2di*)&(*this).effectedNumTable[14])=en14; *((v2di*)&(*this).effectedNumTable[16])=en16; *((v2di*)&(*this).effectedNumTable[18])=en18; v2di en20=*((v2di*)&src.effectedNumTable[20]); v2di en22=*((v2di*)&src.effectedNumTable[22]); v2di en24=*((v2di*)&src.effectedNumTable[24]); v2di en26=*((v2di*)&src.effectedNumTable[26]); v2di en28=*((v2di*)&src.effectedNumTable[28]); v2di en30=*((v2di*)&src.effectedNumTable[30]); v2di en32=*((v2di*)&src.effectedNumTable[32]); v2di en34=*((v2di*)&src.effectedNumTable[34]); v2di en36=*((v2di*)&src.effectedNumTable[36]); v2di en38=*((v2di*)&src.effectedNumTable[38]); *((v2di*)&(*this).effectedNumTable[20])=en20; *((v2di*)&(*this).effectedNumTable[22])=en22; *((v2di*)&(*this).effectedNumTable[24])=en24; *((v2di*)&(*this).effectedNumTable[26])=en26; *((v2di*)&(*this).effectedNumTable[28])=en28; *((v2di*)&(*this).effectedNumTable[30])=en30; *((v2di*)&(*this).effectedNumTable[32])=en32; *((v2di*)&(*this).effectedNumTable[34])=en34; *((v2di*)&(*this).effectedNumTable[36])=en36; *((v2di*)&(*this).effectedNumTable[38])=en38; } #else for(int i=0;i<40;i++) (*this).effectedNumTable[i]=src.effectedNumTable[i]; #endif #if (defined(__i386__) || defined(__x86_64__)) && !defined(OSL_NO_SSE) { v2di e18=*((v2di*)&src.effects[18]); v2di e20=*((v2di*)&src.effects[20]); v2di e22=*((v2di*)&src.effects[22]); v2di e24=*((v2di*)&src.effects[24]); v2di e26=*((v2di*)&src.effects[26]); v2di e34=*((v2di*)&src.effects[34]); v2di e36=*((v2di*)&src.effects[36]); v2di e38=*((v2di*)&src.effects[38]); v2di e40=*((v2di*)&src.effects[40]); v2di e42=*((v2di*)&src.effects[42]); *((v2di*)&(*this).effects[18])=e18; *((v2di*)&(*this).effects[20])=e20; *((v2di*)&(*this).effects[22])=e22; *((v2di*)&(*this).effects[24])=e24; *((v2di*)&(*this).effects[26])=e26; *((v2di*)&(*this).effects[34])=e34; *((v2di*)&(*this).effects[36])=e36; *((v2di*)&(*this).effects[38])=e38; *((v2di*)&(*this).effects[40])=e40; *((v2di*)&(*this).effects[42])=e42; v2di e50=*((v2di*)&src.effects[50]); v2di e52=*((v2di*)&src.effects[52]); v2di e54=*((v2di*)&src.effects[54]); v2di e56=*((v2di*)&src.effects[56]); v2di e58=*((v2di*)&src.effects[58]); v2di e66=*((v2di*)&src.effects[66]); v2di e68=*((v2di*)&src.effects[68]); v2di e70=*((v2di*)&src.effects[70]); v2di e72=*((v2di*)&src.effects[72]); v2di e74=*((v2di*)&src.effects[74]); *((v2di*)&(*this).effects[50])=e50; *((v2di*)&(*this).effects[52])=e52; *((v2di*)&(*this).effects[54])=e54; *((v2di*)&(*this).effects[56])=e56; *((v2di*)&(*this).effects[58])=e58; *((v2di*)&(*this).effects[66])=e66; *((v2di*)&(*this).effects[68])=e68; *((v2di*)&(*this).effects[70])=e70; *((v2di*)&(*this).effects[72])=e72; *((v2di*)&(*this).effects[74])=e74; v2di e82=*((v2di*)&src.effects[82]); v2di e84=*((v2di*)&src.effects[84]); v2di e86=*((v2di*)&src.effects[86]); v2di e88=*((v2di*)&src.effects[88]); v2di e90=*((v2di*)&src.effects[90]); v2di e98=*((v2di*)&src.effects[98]); v2di e100=*((v2di*)&src.effects[100]); v2di e102=*((v2di*)&src.effects[102]); v2di e104=*((v2di*)&src.effects[104]); v2di e106=*((v2di*)&src.effects[106]); *((v2di*)&(*this).effects[82])=e82; *((v2di*)&(*this).effects[84])=e84; *((v2di*)&(*this).effects[86])=e86; *((v2di*)&(*this).effects[88])=e88; *((v2di*)&(*this).effects[90])=e90; *((v2di*)&(*this).effects[98])=e98; *((v2di*)&(*this).effects[100])=e100; *((v2di*)&(*this).effects[102])=e102; *((v2di*)&(*this).effects[104])=e104; *((v2di*)&(*this).effects[106])=e106; v2di e114=*((v2di*)&src.effects[114]); v2di e116=*((v2di*)&src.effects[116]); v2di e118=*((v2di*)&src.effects[118]); v2di e120=*((v2di*)&src.effects[120]); v2di e122=*((v2di*)&src.effects[122]); v2di e130=*((v2di*)&src.effects[130]); v2di e132=*((v2di*)&src.effects[132]); v2di e134=*((v2di*)&src.effects[134]); v2di e136=*((v2di*)&src.effects[136]); v2di e138=*((v2di*)&src.effects[138]); *((v2di*)&(*this).effects[114])=e114; *((v2di*)&(*this).effects[116])=e116; *((v2di*)&(*this).effects[118])=e118; *((v2di*)&(*this).effects[120])=e120; *((v2di*)&(*this).effects[122])=e122; *((v2di*)&(*this).effects[130])=e130; *((v2di*)&(*this).effects[132])=e132; *((v2di*)&(*this).effects[134])=e134; *((v2di*)&(*this).effects[136])=e136; *((v2di*)&(*this).effects[138])=e138; v2di e146=*((v2di*)&src.effects[146]); v2di e148=*((v2di*)&src.effects[148]); v2di e150=*((v2di*)&src.effects[150]); v2di e152=*((v2di*)&src.effects[152]); v2di e154=*((v2di*)&src.effects[154]); *((v2di*)&(*this).effects[146])=e146; *((v2di*)&(*this).effects[148])=e148; *((v2di*)&(*this).effects[150])=e150; *((v2di*)&(*this).effects[152])=e152; *((v2di*)&(*this).effects[154])=e154; } #else for(int x=1;x<=9;x++) for(int y=1;y<=9;y++) this->effects[Square(x,y).index()]=src.effects[Square(x,y).index()]; #endif } bool osl::effect::operator==(const NumSimpleEffectTable& et1,const NumSimpleEffectTable& et2) { for(int y=1;y<=9;y++) for(int x=9;x>0;x--){ Square pos(x,y); if (!(et1.effectSetAt(pos)==et2.effectSetAt(pos))) return false; } if (! (et1.effected_mask == et2.effected_mask)) return false; if(!(et1.mobilityTable==et2.mobilityTable)) return false; if(!(et1.effectedNumTable==et2.effectedNumTable)) return false; // intentionally ignore history dependent members: changed_effects, changed_effect_pieces, effected_changed_mask return true; } #ifndef MINIMAL std::ostream& osl::effect::operator<<(std::ostream& os,const NumSimpleEffectTable& effectTable) { os << "Effect" << std::endl; for(int y=1;y<=9;y++){ for(int x=9;x>0;x--){ Square pos(x,y); os << effectTable.effectSetAt(pos) << " "; } os << std::endl; } os << "Effect" << std::endl; for(int y=1;y<=9;y++){ for(int x=9;x>0;x--){ Square pos(x,y); os << effectTable.effectSetAt(pos) << " "; } os << std::endl; } return os; } #endif // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/align16New.h0000644000000000000000000000115512316770314017220 0ustar rootroot/* align16new.h */ #ifndef OSL_ALIGN16NEW_H #define OSL_ALIGN16NEW_H #include #include namespace osl { namespace misc { struct Align16New { static const int Alignment = 16; static void *operator new(size_t size); static void *operator new[](size_t size); static void operator delete(void *ptr, size_t size); static void operator delete[](void *ptr, size_t size); protected: ~Align16New() {} // for safety in public inheritance }; } } #endif /* OSL_ALIGN16NEW_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/ptypeTable.h0000644000000000000000000001046312316770314017420 0ustar rootroot/* ptypeTable.h */ #ifndef OSL_PTYPETABLE_H #define OSL_PTYPETABLE_H #include "osl/basic_type.h" #include "osl/bits/ptypeTraits.h" #include "osl/bits/effectContent.h" #include "osl/container.h" #include "osl/bits/offset32.h" #include "osl/bits/mask.h" namespace osl { class PtypeTable { private: CArray numMaskLows; CArray numIndices; CArray names; CArray csaNames; CArray betterToPromote; CArray moveMasks; CArray indexMins; CArray indexLimits; CArray2d canDropLimit; // ã“れらã®2次元é…列ã¯2^nã«ãã‚ãˆã¦ãŠã„ãŸæ–¹ãŒé€Ÿã„. CArray2d effectTable; CArray2d effectTableNotLongU; CArray2d shortMoveMask; template void initPtypeSub(Int2Type isBasic); template void initPtypeSub(Int2Type isBasic); template void initPtype(); public: PtypeTable(); private: void init(); public: unsigned int getShortMoveMask(Player p,PtypeO ptypeo,Direction dir) const { return shortMoveMask[playerToIndex(p)][static_cast(dir)] & (1<<(ptypeo-PTYPEO_MIN)); } mask_t getMaskLow(Ptype ptype) const { return numMaskLows[ptype]; } int getIndex(Ptype) const { return 0; } /** * é…ãã¦è‰¯ã„? */ bool hasLongMove(Ptype ptype) const { return getIndexMin(unpromote(ptype))>=32; } bool isBetterToPromote(Ptype ptype) const { return betterToPromote[ptype]; } int getCanDropLimit(Player player,Ptype ptype) const { assert(isValid(ptype) && !isPromoted(ptype)); return canDropLimit[playerToIndex(player)][ptype]; } bool canDropTo(Player pl, Ptype ptype, Square pos) const { if (pl == BLACK) return pos.y() >= getCanDropLimit(BLACK,ptype); else return pos.y() <= getCanDropLimit(WHITE,ptype); } const char *getName(Ptype ptype) const { return names[ptype]; } const char *getCsaName(Ptype ptype) const { return csaNames[ptype]; } int getMoveMask(Ptype ptype) const { return moveMasks[ptype]; } int getIndexMin(Ptype ptype) const { assert(isBasic(ptype)); return indexMins[ptype]; } int getIndexLimit(Ptype ptype) const { assert(isBasic(ptype)); return indexLimits[ptype]; } static int getKingIndex(Player p) { assert(isValid(p)); if (p==BLACK) return KingTraits::index; else return KingTraits::index; } /** * fromã«ã„ã‚‹ptypeoãŒtoã«åˆ©ãã‚’æŒã¤ã‹? * @param ptypeo - é§’ã®ç¨®é¡ž * @param from - é§’ã®ä½ç½® * @param to - 利ãã‚’ãƒã‚§ãƒƒã‚¯ã™ã‚‹ãƒžã‚¹ã®ä½ç½® */ const EffectContent getEffect(PtypeO ptypeo,Square from, Square to) const { assert(from.isOnBoard() && to.isOnBoard()); return getEffect(ptypeo,Offset32(to,from)); } const EffectContent& getEffect(PtypeO ptypeo,Offset32 offset32) const { assert(isValidPtypeO(ptypeo)); return effectTable[ptypeo-PTYPEO_MIN][offset32.index()]; } private: EffectContent& effect(PtypeO ptypeo,Offset32 offset32) { assert(isValidPtypeO(ptypeo)); const int i1 = ptypeo-PTYPEO_MIN; const int i2 = offset32.index(); return effectTable[i1][i2]; } public: /** ptypeo ãŒï¼Œè‡ªåˆ†ã‹ã‚‰ offset ã®ã¨ã“ã‚ã«åйãã‚’æŒã¤ã‹? U除ã */ const EffectContent getEffectNotLongU(PtypeO ptypeo, Square from, Square to) const { assert(isValidPtypeO(ptypeo)); assert(from.isOnBoard() && to.isOnBoard()); Offset32 offset32=Offset32(to,from); return effectTableNotLongU[ptypeo-PTYPEO_MIN][offset32.index()]; } bool hasUnblockableEffect(PtypeO attacker, Square from, Square to) const { const EffectContent effect = getEffect(attacker, from, to); return effect.hasUnblockableEffect(); } }; extern const PtypeTable Ptype_Table; } // namespace osl #endif /* OSL_PTYPETABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/boardTable.h0000644000000000000000000001444412316770314017351 0ustar rootroot/* directionTable.h */ #ifndef OSL_BOARD_TABLE_H #define OSL_BOARD_TABLE_H #include "osl/basic_type.h" #include "osl/container.h" #include "osl/bits/offset32.h" namespace osl { class BoardTable { CArray directions; // 上ä½ã¯offsetãŒï¼Œä¸‹ä½3bitã¯directionãŒå…¥ã‚‹ï¼Žã€€ CArray short8Offset; CArray short8Dir; CArray short_offsets; CArray short_offsets_not_knight; #ifndef MINIMAL CArray space_counts; #endif public: static const CArray offsets; static const CArray dxs; static const CArray dys; private: template void setDirections(); template void setKnightDirections(); void init(); public: /** * é»’ã«ã¨ã£ã¦ã®offsetを返㙠*/ const Offset getOffsetForBlack(Direction dir) const{ return offsets[static_cast(dir)]; } int getDxForBlack(Direction dir) const{ return dxs[static_cast(dir)]; } int getDyForBlack(Direction dir) const{ return dys[static_cast(dir)]; } template const Offset getOffset(Direction dir) const{ return getOffsetForBlack(dir)*sign(P); } const Offset getOffset(Player pl,Direction dir) const{ if (pl==BLACK) return getOffset(dir); else return getOffset(dir); } /** * next position from pos for player P. * ç­”ãˆãŒ isOnBoard ã¨ã¯é™ã‚‰ãªã„ */ const Square nextSquare(Player P, Square pos, Direction dr) const { assert(pos.isOnBoard()); const Offset offset = getOffset(P, dr); return pos + offset; } BoardTable(); /** @param P ã©ã¡ã‚‰ã®Playerã«ã¨ã£ã¦ã®æ–¹å‘ã‹ã‚’指定 */ template Direction getLongDirection(Offset32 offset32) const { assert(offset32.isValid()); const Offset32 blackOffset32 = offset32.blackOffset32

(); Direction ret=directions[blackOffset32.index()]; assert(isValid(ret)); return ret; } Direction getLongDirection(Player P, Offset32 offset32) const { if (P == BLACK) return getLongDirection(offset32); else return getLongDirection(offset32); } /** @param P ã©ã¡ã‚‰ã®Playerã«ã¨ã£ã¦ã®æ–¹å‘ã‹ã‚’指定 */ template Direction getLongDirection(Square from, Square to) const { return getLongDirection

(Offset32(to,from)); } #ifndef MINIMAL /** * fromã¨toãŒé•·ã„利ãã‚’æŒã¤ä½ç½®ã«ã‚る時,間ã®ãƒžã‚¹ã®æ•°ã‚’求ã‚ã‚‹ * 一致ã—ã¦ã„る時ã¯0 * ã¨ãªã‚Šã‚‚0 * 関係ãªã„時ã¯-1 */ int spaceCounts(Square from,Square to) const { Offset32Wide offset32(from,to); return space_counts[offset32.index()]; } #endif /** * Longã®åˆ©ãã®å¯èƒ½æ€§ã®ã‚ã‚‹offsetã®å ´åˆã¯, å復ã«ä½¿ã† offsetã‚’ * Shortã®åˆ©ãã®offsetã®å ´åˆã¯ãれ自身を返ã™. * 利ãã®å¯èƒ½æ€§ã®ãªã„å ´åˆã¯0を返㙠*/ const Offset getShortOffset(Offset32 offset32) const{ assert(offset32.isValid()); return short_offsets[offset32.index()]; } /** * Longã®åˆ©ãã®å¯èƒ½æ€§ã®ã‚ã‚‹offsetã®å ´åˆã¯, å復ã«ä½¿ã† offsetã‚’ * Knight以外ã®Shortã®åˆ©ãã®offsetã®å ´åˆã¯ãれ自身を返ã™. * Knightã®åˆ©ã, 利ãã®å¯èƒ½æ€§ã®ãªã„å ´åˆã¯0を返㙠*/ const Offset getShortOffsetNotKnight(Offset32 offset32) const{ assert(offset32.isValid()); return short_offsets_not_knight[offset32.index()]; } /** * 8æ–¹å‘ã«ã„ãªã„å ´åˆã‚‚é©å½“ãªã‚‚ã®ã‚’è¿”ã™ï¼Ž */ Offset getShort8OffsetUnsafe(Square from,Square to) const{ int i=(int)(to.uintValue())-(int)(from.uintValue())-Offset::ONBOARD_OFFSET_MIN; return Offset::makeDirect(short8Offset[i]); } /** * 8æ–¹å‘ã«ã„ãªã„å ´åˆã‚‚é©å½“ãªã‚‚ã®ã‚’è¿”ã™ï¼Ž */ template Direction getShort8Unsafe(Square from,Square to) const{ if(P==BLACK) return static_cast(short8Dir[(int)(to.uintValue())-(int)(from.uintValue())-Offset::ONBOARD_OFFSET_MIN]); else return static_cast(short8Dir[(int)(from.uintValue())-(int)(to.uintValue())-Offset::ONBOARD_OFFSET_MIN]); } Direction getShort8Unsafe(Player P, Square from,Square to) const{ if(P==BLACK) return getShort8Unsafe(from, to); else return getShort8Unsafe(from, to); } template Direction getShort8(Square from,Square to) const{ assert(from.isOnBoard() && to.isOnBoard()); assert(from.x()==to.x() || from.y()==to.y() || abs(from.x()-to.x())==abs(from.y()-to.y())); return getShort8Unsafe

(from,to); } template Direction getShort8(Square from,Square to,Offset& o) const{ assert(from.isOnBoard() && to.isOnBoard()); assert(from.x()==to.x() || from.y()==to.y() || abs(from.x()-to.x())==abs(from.y()-to.y())); int i=(int)(to.uintValue())-(int)(from.uintValue())-Offset::ONBOARD_OFFSET_MIN; o=Offset::makeDirect(short8Offset[i]); Direction d=static_cast(short8Dir[i]); if(P==BLACK) return d; else return inverse(d); } /** * p0, p1ã®é–“ã«tãŒã‚ã‚‹ã‹ã©ã†ã‹. * (t,p0), (t,p1)ã®ã©ã¡ã‚‰ã‹ãŒ8æ–¹å‘ã§ã‚る時ã«ã®ã¿å‘¼ã³å‡ºã™ã“㨠* 他方も8æ–¹å‘ã§ãªã„ã¨ã—ãŸã‚‰knightã®é–¢ä¿‚ */ bool isBetween(Square t,Square p0,Square p1) const { int i1=(int)(t.uintValue())-(int)(p0.uintValue())-Offset::ONBOARD_OFFSET_MIN; int i2=(int)(p1.uintValue())-(int)(t.uintValue())-Offset::ONBOARD_OFFSET_MIN; assert(short8Dir[i1]!=DIRECTION_INVALID_VALUE || short8Dir[i2]!=DIRECTION_INVALID_VALUE); return short8Dir[i1]==short8Dir[i2]; } bool isBetweenSafe(Square t,Square p0,Square p1) const { if (getShortOffsetNotKnight(Offset32(t, p0)).zero()) return false; return isBetween(t, p0, p1); } }; extern const BoardTable Board_Table; } // namespace osl #endif /* OSL_BOARD_TABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/pieceMask64.h0000644000000000000000000000364312316770314017364 0ustar rootroot/* pieceMask64.h */ #ifndef PIECEMASK64_H #define PIECEMASK64_H #include "osl/bits/mask.h" namespace osl { namespace container { class PieceMask64 { protected: Mask64 mask; public: static int numToIndex(int) { return 0; } static int numToOffset(int num) { return num; } PieceMask64() { resetAll(); } explicit PieceMask64(misc::Mask64 const& m) : mask(m) {} protected: misc::Mask64& mutableMask(int) { return mask; } public: const misc::Mask64& getMask(int) const { return mask; } void resetAll() { mask=misc::Mask64::makeDirect(0uLL); } void setAll() { mask=misc::Mask64::makeDirect(0xffffffffffuLL); } PieceMask64& operator^=(const PieceMask64& o) { mask ^= o.mask; return *this; } PieceMask64& operator&=(const PieceMask64& o) { mask &= o.mask; return *this; } PieceMask64& operator|=(const PieceMask64& o) { mask |= o.mask; return *this; } PieceMask64& operator-=(const PieceMask64& o) { mask -= o.mask; return *this; } PieceMask64& operator+=(const PieceMask64& o) { mask += o.mask; return *this; } bool none() const { return mask.none(); } bool hasMultipleBit() const { if (none()) return false; return mask.hasMultipleBit(); } /** * bit ã®æ•°ã‚’2ã¾ã§æ•°ãˆã‚‹ * @return 0,1,2 (2ã®å ´åˆã¯2以上) */ int countBit2() const { if (none()) return 0; return mask.countBit2(); } int #ifdef __GNUC__ __attribute__ ((pure)) #endif countBit() const { return mask.countBit(); } int takeOneBit() { assert(!none()); return mask.takeOneBit(); } }; } // namespace container using container::PieceMask64; } // namespace osl #endif /* PIECEMASK64_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/construct.h0000644000000000000000000000365712316770314017342 0ustar rootroot/* construct.h */ #ifndef OSL_CONSTRUCT_H #define OSL_CONSTRUCT_H #include #include #include #include #include #include namespace osl { class Piece; class Move; class Square; namespace rating { class RatedMove; } namespace misc { namespace detail { /** use raw memory copy instead of placement new not to test a given pointer is null */ template struct BitCopyTraits { static const bool value=boost::is_pod::value; }; template <> struct BitCopyTraits { static const bool value=true; }; template <> struct BitCopyTraits { static const bool value=true; }; template <> struct BitCopyTraits { static const bool value=true; }; template <> struct BitCopyTraits { static const bool value=true; }; } template inline void construct(T1* ptr, const T2& value, typename boost::enable_if >::type * =0) { assert(ptr); *ptr = T1(value); } template inline void construct(T1* ptr, const T2& value, typename boost::disable_if >::type * =0) { assert(ptr); ::new(ptr) T1(value); } template inline void destroy(T *ptr) { ptr->~T(); } template inline void destroy(ForwardIterator first, ForwardIterator last) { typedef typename std::iterator_traits::value_type value_type; if (boost::has_trivial_destructor::value) return; for (; first != last; ++first) destroy(&*first); } } } #endif /* OSL_CONSTRUCT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/mask.cc0000644000000000000000000000060112316770314016371 0ustar rootroot#include "osl/bits/mask.h" #include #include namespace osl { static_assert(sizeof(mask_t) == 8, "64bit"); } std::ostream& osl::misc::operator<<(std::ostream& os,const osl::mask_t& mask) { return os << "mask(0x" << std::setbase(16) << mask.value() << std::setbase(10) << ')'; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/mask.h0000644000000000000000000002246112316770314016243 0ustar rootroot#ifndef OSL_MISC_MASK_H #define OSL_MISC_MASK_H #include "osl/config.h" #include #include namespace osl { namespace misc { /** * x86 bsf 命令 */ template struct Bsf; template <> struct Bsf { static int bsf(unsigned int mask) { assert(mask); #ifdef __x86_64__ int ret; __asm__("bsfl %1,%0" : "=r"(ret) : "r"(mask)); return ret; #else /* ã“れ以下㯠32bit 環境 */ # ifdef __i386__ int ret; __asm__("bsfl %1,%0" : "=r"(ret) : "r"(mask)); return ret; # elif defined __GNUC__ return __builtin_ctzl(mask); # else for (int i=0;i<32;i++) if (mask & (1< struct Bsf { static unsigned short bsf(unsigned short mask) { assert(mask); #ifdef __x86_64__ unsigned short ret; __asm__("bsfw %1,%0" : "=r"(ret) : "r"(mask)); return ret; #else /* ã“れ以下㯠32bit 環境 */ # ifdef __i386__ unsigned short ret; __asm__("bsfw %1,%0" : "=r"(ret) : "r"(mask)); return ret; # else return __builtin_ctzl(mask); # endif #endif } }; template <> struct Bsf { static int bsf(unsigned long long mask) { assert(mask); #ifdef __x86_64__ long long ret; __asm__("bsfq %1,%0" : "=r"(ret) : "r"(mask)); return static_cast(ret); #else /* ã“れ以下㯠32bit 環境 */ unsigned int mask32 = static_cast(mask); if (mask32) return Bsf::bsf(mask32); mask32 = static_cast(mask >> 32); return 32+Bsf::bsf(mask32); #endif } }; template struct Bsr; template <> struct Bsr { static int bsr(unsigned int mask) { assert(mask); #ifdef __x86_64__ int ret; __asm__("bsrl %1,%0" : "=r"(ret) : "r"(mask)); return ret; #else /* ã“れ以下㯠32bit 環境 */ # ifdef __i386__ int ret; __asm__("bsrl %1,%0" : "=r"(ret) : "r"(mask)); return ret; # elif __GNUC__ return __builtin_clzl(mask); # else for (int i=31; i>=0; --i) if (mask & (1< struct Bsr { static int bsr(unsigned long long mask) { assert(mask); #ifdef __x86_64__ long long ret; __asm__("bsrq %1,%0" : "=r"(ret) : "r"(mask)); return static_cast(ret); #else /* ã“れ以下㯠32bit 環境 */ unsigned int mask32 = static_cast(mask >> 32); if (mask32) return 32+Bsr::bsr(mask32); mask32 = static_cast(mask); return Bsr::bsr(mask32); #endif } }; struct BitOp { template static int bsf(Integer mask) { return Bsf::bsf(mask); } template static int bsr(Integer mask) { return Bsr::bsr(mask); } template static int takeOneBit(Integer& mask){ assert(mask); const int num=bsf(mask); mask &= mask-1; return num; } template static int #ifdef __GNUC__ __attribute__ ((const)) #endif countBit(Integer mask) { int count=0; while (mask) { ++count; mask &= (mask-1); } return count; } template static bool hasMultipleBit(Integer mask){ assert(mask); return (mask & (mask-1)); } /** * non-zeroã®maskã®setã•れã¦ã„るビットをLSBã‹ã‚‰æŽ¢ã—,ãã®ãƒ“ットã ã‘ãŒsetã•れãŸmaskã‚’è¿”ã™. */ template static Integer lowestBit(Integer mask){ assert(mask); return static_cast(mask & (-mask)); } }; #if 0 /** * bitæ•°ãŒå¤šã„時ã¯? * population count㯠* Cray, CDC Cyber series, Alliant FX/80. * UltraSPARC, Alpha 21264 * Intel x86 has the parity of a byte *#define bitcount(n) \ * (tmp = n - ((n >> 1) & 033333333333) - ((n >> 2) & 011111111111), \ * tmp = ((tmp + (tmp >> 3)) & 030707070707), \ * tmp = (tmp + (tmp >> 6)), \ * tmp = (tmp + (tmp >> 12) + (tmp >> 24)) & 077) * */ inline int countBitDense(unsigned int mask) { mask = ((mask>>1)&0x55555555)+(mask&0x55555555); mask = ((mask>>2)&0x33333333)+(mask&0x33333333); mask = ((mask>>4)+mask)&0xf0f0f0f; mask = (mask>>8)+mask; return ((mask>>16)+mask)&0x3f; } #endif } // namespace misc namespace misc { template class GeneralMask { Integer mask; private: GeneralMask(Integer value) : mask(value) {} public: GeneralMask() : mask(0) {} static const GeneralMask makeDirect(Integer value) { return GeneralMask(value); } GeneralMask& operator&=(const GeneralMask& r) { mask &= r.mask; return *this; } GeneralMask& operator|=(const GeneralMask& r) { mask |= r.mask; return *this; } GeneralMask& operator^=(const GeneralMask& r) { mask ^= r.mask; return *this; } GeneralMask& operator-=(const GeneralMask& r) { mask -= r.mask; return *this; } GeneralMask& operator+=(const GeneralMask& r) { mask += r.mask; return *this; } GeneralMask& operator<<=(int shift) { mask <<= shift; return *this; } GeneralMask& operator>>=(int shift) { mask >>= shift; return *this; } const GeneralMask operator~() const { return GeneralMask(~mask); } int bsf() const { return BitOp::bsf(mask); } int bsr() const { return BitOp::bsr(mask); } /** * non-zeroã®maskã®setã•れã¦ã„るビットをLSBã‹ã‚‰æŽ¢ã—,ãã®ç•ªå·ã‚’返㙠* 副作用ã¨ã—ã¦maskã®å¯¾å¿œã™ã‚‹ãƒ“ットをクリアã™ã‚‹ * @param mask - 対象ã¨ã™ã‚‹ãƒ‡ãƒ¼ã‚¿(non-zero) * @return - ã©ã®ãƒ“ット㋠*/ int takeOneBit() { return BitOp::takeOneBit(mask); } /** * non-zeroã®maskãŒè¤‡æ•°ãƒ“ットセットã•れã¦ã„ã‚‹ã‹ã©ã†ã‹ã‚’è¿”ã™. * @param mask - 対象ã¨ã™ã‚‹ãƒ‡ãƒ¼ã‚¿(non-zero) * @return - 複数ビットãŒã‚»ãƒƒãƒˆã•れã¦ã„ã‚‹ã‹ï¼Ÿ */ bool hasMultipleBit() const { return BitOp::hasMultipleBit(mask); } /** * non-zeroã®maskã«ã‚»ãƒƒãƒˆã•れã¦ã„ã‚‹ãƒ“ãƒƒãƒˆã®æ•°ã‚’2ã¾ã§æ•°ãˆã‚‹ï¼Ž * @param mask - 対象ã¨ã™ã‚‹ãƒ‡ãƒ¼ã‚¿(non-zero) * @return 1,2 (2ã®å ´åˆã¯2以上) */ int countBit2() const { assert(mask); return (mask & (mask-1)) ? 2 : 1; } /** * mask ã«ã‚»ãƒƒãƒˆã•れã¦ã„ã‚‹ãƒ“ãƒƒãƒˆã®æ•°ã‚’æ•°ãˆã‚‹ï¼Ž * ã‚ã¾ã‚Šé€Ÿããªã„. */ int #ifdef __GNUC__ __attribute__ ((pure)) #endif countBit() const { return BitOp::countBit(mask); } /** * non-zeroã®maskã®setã•れã¦ã„るビットをLSBã‹ã‚‰æŽ¢ã—,ãã®ãƒ“ットã ã‘ãŒsetã•れãŸmaskã‚’è¿”ã™. * @param mask - 対象ã¨ã™ã‚‹ãƒ‡ãƒ¼ã‚¿(non-zero) * @return - ãã®ãƒ“ットã ã‘ãŒsetã•れãŸmask */ GeneralMask lowestBit() const { return BitOp::lowestBit(mask); } bool none() const { return mask == 0; } bool any() const { return ! none(); } Integer value() const { return mask; } }; template inline bool operator==(const GeneralMask& l, const GeneralMask& r) { return l.value() == r.value(); } template inline bool operator!=(const GeneralMask& l, const GeneralMask& r) { return ! (l == r); } template inline bool operator<(const GeneralMask& l, const GeneralMask& r) { return l.value() < r.value(); } template inline const GeneralMask operator&(GeneralMask l, GeneralMask r) { GeneralMask result = l; return result &= r; } template inline const GeneralMask operator|(GeneralMask l, GeneralMask r) { GeneralMask result = l; return result |= r; } template inline const GeneralMask operator^(GeneralMask l, GeneralMask r) { GeneralMask result = l; return result ^= r; } template inline const GeneralMask operator<<(GeneralMask m, int shift) { GeneralMask result = m; return result <<= shift; } template inline const GeneralMask operator>>(GeneralMask m, int shift) { GeneralMask result = m; return result >>= shift; } typedef GeneralMask Mask64; typedef unsigned long long mask_int_t; typedef GeneralMask mask_t; std::ostream& operator<<(std::ostream&, const mask_t&); } // namespace misc using misc::mask_int_t; using misc::mask_t; using misc::Mask64; using misc::BitOp; } // namespace osl #endif // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/boardMask.cc0000644000000000000000000000407612316770314017353 0ustar rootroot/* boardMask.cc */ #include "osl/bits/boardMask.h" #include "osl/bits/centering5x3.h" #include #ifndef MINIMAL std::ostream& osl::container::operator<<(std::ostream& os, const BoardMask& mask) { for(int y=1; y<=9; ++y) { for(int x=9; x>=1; --x) { const Square p(x,y); os << mask.test(p); } os << std::endl; } return os; } #endif osl::container:: BoardMaskTable5x5::BoardMaskTable5x5() { for (int cx=1; cx<=9; ++cx) { for (int cy=1; cy<=9; ++cy) { const int min_x = std::max(1, cx - 2); const int max_x = std::min(9, cx + 2); const int min_y = std::max(1, cy - 2); const int max_y = std::min(9, cy + 2); BoardMask mask; mask.clear(); for (int x=min_x; x<=max_x; ++x) { for (int y=min_y; y<=max_y; ++y) { mask.set(Square(x,y)); } } data[Square(cx,cy).index()] = mask; } } } osl::container:: BoardMaskTable3x3::BoardMaskTable3x3() { for (int cx=1; cx<=9; ++cx) { for (int cy=1; cy<=9; ++cy) { const int min_x = std::max(1, cx - 1); const int max_x = std::min(9, cx + 1); const int min_y = std::max(1, cy - 1); const int max_y = std::min(9, cy + 1); BoardMask mask; mask.clear(); for (int x=min_x; x<=max_x; ++x) { for (int y=min_y; y<=max_y; ++y) { mask.set(Square(x,y)); } } data[Square(cx,cy).index()] = mask; } } } osl::container:: BoardMaskTable5x3Center::BoardMaskTable5x3Center() { for (int cx=1; cx<=9; ++cx) { for (int cy=1; cy<=9; ++cy) { const Square center = Centering5x3::adjustCenter(Square(cx, cy)); const int min_x = std::max(1, center.x() - 2); const int max_x = std::min(9, center.x() + 2); const int min_y = std::max(1, center.y() - 1); const int max_y = std::min(9, center.y() + 1); BoardMask mask; mask.clear(); for (int x=min_x; x<=max_x; ++x) { for (int y=min_y; y<=max_y; ++y) { mask.set(Square(x,y)); } } data[Square(cx,cy).index()] = mask; } } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/bitXmask.cc0000644000000000000000000000057712316770314017234 0ustar rootroot/* bitXmask.cc */ #include "osl/bits/bitXmask.h" #include std::ostream& osl::container::operator<<(std::ostream& os,const BitXmask mask){ for(int i=1;i<=9;i++) os << ((mask.intValue()>>i)&1); return os; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/numBitmapEffect.h0000644000000000000000000001066012316770314020357 0ustar rootroot#ifndef OSL_NUM_BITMAP_EFFECT_H #define OSL_NUM_BITMAP_EFFECT_H #include "osl/basic_type.h" #include "osl/bits/ptypeTraits.h" #include "osl/bits/pieceMask.h" namespace osl { namespace effect { /** * ç¾åœ¨ã®å®šç¾© (2005/3/4以é™) * - 0-39 : 0-39ã®åˆ©ã * - 40-47 : 32-39ã®é•·ã„利ã * - 48-53 : é»’ã®åˆ©ãã®æ•°(sentinelã‚’åˆã‚ã›ã¦6bit) * - 54-59 : 白ã®åˆ©ãã®æ•°(sentinelã‚’åˆã‚ã›ã¦6bit) * * 以å‰ã®å®šç¾© (2004/4/13以é™) * - 0-39 : 0-39ã®åˆ©ã * - 40-47 : 32-39ã®é•·ã„利ã * * 以å‰ã®å®šç¾© * - 0-31 : 0-31ã®ç›´æŽ¥åйã * - 32-39 : 32-39ã®çŸ­ã„効ã(obsolete ãŠã‚ˆã³32-39ã®çŸ­ã„間接効ã) * - 40-47 : 32-39ã®é•·ã„効ã(obsoleteãŠã‚ˆã³32-39ã®é•·ã„間接効ã) */ class NumBitmapEffect : public PieceMask { public: NumBitmapEffect(){ resetAll(); } template static NumBitmapEffect playerEffect(){ NumBitmapEffect ret; if (P == BLACK) ret.flip(48); else ret.flip(54); return ret; } static NumBitmapEffect playerEffect(Player pl){ mask_t mask1=numToMask(54); mask1-=numToMask(48); mask1&=mask_t::makeDirect(pl); mask1+=numToMask(48); NumBitmapEffect ret; ret.setMask(1,mask1); assert((pl==BLACK && ret==playerEffect()) || (pl==WHITE && ret==playerEffect())); return ret; } template static mask_t playerEffectMask(){ if (P == BLACK) { mask_t mask1=numToMask(54); mask1-=numToMask(48); return mask1; } else { mask_t mask1=numToMask(60); mask1-=numToMask(54); return mask1; } } static mask_t playerEffectMask(Player pl){ mask_t mask1=numToMask(60); mask1-=numToMask(48); mask1&=mask_t::makeDirect(pl); // pl==BLACK -> mask1 = 0 // pl==WHITE -> mask1 = 0x0fff0000(32bit), 0x0fff000000000000(64bit) mask_t mask2=numToMask(54); mask2-=numToMask(48); // mask2 = 0x3f0000(32bit), 0x3f000000000000(64bit) mask1^=mask2; // pl==BLACK -> mask1 = 0x3f0000(32bit), 0x3f000000000000(64bit) // pl==WHITE -> mask2 = 0x0fc00000(32bit), 0x0fc0000000000000(64bit) assert((pl==BLACK && mask1==playerEffectMask()) || (pl==WHITE && mask1==playerEffectMask())); return mask1; } int countEffect(Player pl) const { int shift=48+(6&pl); mask_t mask=getMask(1); mask>>=numToOffset(shift); mask&=mask_t::makeDirect(0x3f); return static_cast(mask.value()); } template static NumBitmapEffect makeEffect(int num){ NumBitmapEffect effect=playerEffect

(); effect.flip(num); return effect; } enum Op{ Add,Sub, }; template NumBitmapEffect& opEqual(NumBitmapEffect const& rhs){ if (OP == Add) *this+=rhs; else *this-=rhs; return *this; } static const mask_t longEffectMask() { #if OSL_WORDSIZE == 64 return mask_t::makeDirect(0xff0000000000uLL); #elif OSL_WORDSIZE == 32 return mask_t::makeDirect(0xff00u); #endif } #if OSL_WORDSIZE == 64 static const int longToNumOffset=-8; #elif OSL_WORDSIZE == 32 static const int longToNumOffset=32-8; #endif static const mask_t makeLongMask(int num) { return mask_t::makeDirect(0x101) << PieceMask::numToOffset(num); } template static NumBitmapEffect makeLongEffect(int num){ assert(32<=num && num<=39); NumBitmapEffect effect=NumBitmapEffect::playerEffect

(); effect.orMask(1,makeLongMask(num)); return effect; } static NumBitmapEffect makeLongEffect(Player pl,int num){ assert(32<=num && num<=39); NumBitmapEffect effect=NumBitmapEffect::playerEffect(pl); effect.orMask(1,makeLongMask(num)); return effect; } // utility methods const mask_t selectLong() const { return (getMask(1) & longEffectMask()); } bool hasLong() const { return selectLong().any(); } template const mask_t selectLong() const { return selectLong() & mask_t::makeDirect(PtypeFuns::indexMask << 8); } template bool hasLong() const { return selectLong().any(); } template bool hasAny() const { return (getMask(PtypeFuns::indexNum) & mask_t::makeDirect(PtypeFuns::indexMask)).any(); } }; } // namespace effect } // namespace osl #endif // _NUM_BITMAP_EFFECT_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/tables.cc0000644000000000000000000001213112316770314016711 0ustar rootroot#include "osl/basic_type.h" // #include "osl/liberty8Table.h" #include "osl/bits/pieceTable.h" #include "osl/bits/boardTable.h" #include "osl/bits/ptypeTable.h" // #include "osl/hashKey.h" #if 0 #include "osl/move_generator/addEffect8Table.h" #include "osl/progress/ptypeProgress.h" #include "osl/progress/effect5x3Table.h" #include "osl/pathEncoding.h" #include "osl/effect/moveSignature.h" #include "osl/centering3x3.h" #endif #include "osl/bits/centering5x3.h" #include "osl/checkmate/immediateCheckmateTable.h" #if 0 #include "osl/effect_util/neighboring8Effect.h" #include "osl/effect_util/sendOffSquare.h" #endif #include "osl/eval/openMidEndingEval.h" #include "osl/bits/boardMask.h" namespace osl { const CArray BoardTable::offsets = { { DirectionTraits(0)>::blackOffset(), DirectionTraits(1)>::blackOffset(), DirectionTraits(2)>::blackOffset(), DirectionTraits(3)>::blackOffset(), DirectionTraits(4)>::blackOffset(), DirectionTraits(5)>::blackOffset(), DirectionTraits(6)>::blackOffset(), DirectionTraits(7)>::blackOffset(), DirectionTraits(8)>::blackOffset(), DirectionTraits(9)>::blackOffset(), DirectionTraits(10)>::blackOffset(), DirectionTraits(11)>::blackOffset(), DirectionTraits(12)>::blackOffset(), DirectionTraits(13)>::blackOffset(), DirectionTraits(14)>::blackOffset(), DirectionTraits(15)>::blackOffset(), DirectionTraits(16)>::blackOffset(), DirectionTraits(17)>::blackOffset() } }; const CArray BoardTable::dxs = { { DirectionTraits(0)>::blackDx, DirectionTraits(1)>::blackDx, DirectionTraits(2)>::blackDx, DirectionTraits(3)>::blackDx, DirectionTraits(4)>::blackDx, DirectionTraits(5)>::blackDx, DirectionTraits(6)>::blackDx, DirectionTraits(7)>::blackDx, DirectionTraits(8)>::blackDx, DirectionTraits(9)>::blackDx, DirectionTraits(10)>::blackDx, DirectionTraits(11)>::blackDx, DirectionTraits(12)>::blackDx, DirectionTraits(13)>::blackDx, DirectionTraits(14)>::blackDx, DirectionTraits(15)>::blackDx, DirectionTraits(16)>::blackDx, DirectionTraits(17)>::blackDx } }; const CArray BoardTable::dys = { { DirectionTraits(0)>::blackDy, DirectionTraits(1)>::blackDy, DirectionTraits(2)>::blackDy, DirectionTraits(3)>::blackDy, DirectionTraits(4)>::blackDy, DirectionTraits(5)>::blackDy, DirectionTraits(6)>::blackDy, DirectionTraits(7)>::blackDy, DirectionTraits(8)>::blackDy, DirectionTraits(9)>::blackDy, DirectionTraits(10)>::blackDy, DirectionTraits(11)>::blackDy, DirectionTraits(12)>::blackDy, DirectionTraits(13)>::blackDy, DirectionTraits(14)>::blackDy, DirectionTraits(15)>::blackDy, DirectionTraits(16)>::blackDy, DirectionTraits(17)>::blackDy } }; } namespace osl { const PieceTable Piece_Table; const BoardTable Board_Table; // PtypeTable depends on BoardTable const PtypeTable Ptype_Table; #if 0 // BoardTable, PtypeTable -> Liberty8Table const effect::Liberty8Table effect::Liberty8_Table; #endif #ifndef DFPNSTATONE const eval::PtypeEvalTable eval::Ptype_Eval_Table; eval::ml::OpenMidEndingPtypeTable eval::ml::OpenMidEndingEval::Piece_Value; #endif #if 0 #ifndef MINIMAL const effect::MoveSignatureTable effect::Move_Signature_Table; #endif const PathEncodingTable Path_Encoding_Table; #endif const Centering5x3::Table Centering5x3::table; #if 0 const effect_util::Neighboring8Effect::Table Neighboring8Effect::table; #endif const container::BoardMaskTable5x5 container::Board_Mask_Table5x5; const container::BoardMaskTable3x3 container::Board_Mask_Table3x3; const container::BoardMaskTable5x3Center container::Board_Mask_Table5x3_Center; const checkmate::ImmediateCheckmateTable checkmate::Immediate_Checkmate_Table; } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/align16New.cc0000644000000000000000000000173712316770314017364 0ustar rootroot/* align16New.cc */ #include "osl/bits/align16New.h" #include #include void * osl::misc::Align16New::operator new(size_t size) { char *ptr = ::new char[size+Alignment]; for (int i=0; i(ptr + i + 1) % Alignment == 0) { *(ptr + i) = i + 1; // std::cerr << ">> " << (long)ptr << " => " << (long)(ptr + i + 1) << "\n"; return ptr + i + 1; } } assert(0); abort(); } void * osl::misc::Align16New::operator new[](size_t size) { return operator new(size); } void osl::misc::Align16New::operator delete(void *ptr, size_t /*size*/) { char *p = static_cast(ptr); int offset = *(p-1); ::delete(p - offset); // std::cerr << "<< " << (long)p << " => " << (long)(p - offset) << "\n"; } void osl::misc::Align16New::operator delete[](void *ptr, size_t size) { return operator delete(ptr, size); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/quadInt.h0000644000000000000000000001062612316770314016715 0ustar rootroot/* quadInt.h */ #ifndef EVAL_CONTAINER_QUAD_INT_H #define EVAL_CONTAINER_QUAD_INT_H #include "osl/config.h" #include "osl/container.h" #include "osl/bits/align16New.h" #if (defined __INTEL_COMPILER || defined __clang__) # include # ifdef __INTEL_COMPILER # define __builtin_ia32_pxor128 _mm_xor_pd # endif # define __builtin_ia32_psubd128 _mm_sub_epi32 # define __builtin_ia32_paddd128 _mm_add_epi32 #endif #ifndef OSL_NO_SSE #if (defined __x86_64__) || (defined __i386__) # ifndef OSL_USE_SSE # define OSL_USE_SSE 1 # endif #else # warning "QuadInt without SSE" #endif #endif namespace osl { namespace container { #ifdef OSL_USE_SSE # ifdef __INTEL_COMPILER typedef __v4si v4si; typedef __v2di v2di; # else typedef int v4si __attribute__ ((vector_size (16))); typedef long long v2di __attribute__ ((vector_size (16))); # endif #endif struct QuadInt : public misc::Align16New { union XMM{ CArray iv; CArray llv; #ifdef OSL_USE_SSE v4si v4; v2di v2; #endif } v #ifdef OSL_USE_SSE __attribute__((aligned(16))) #endif ; QuadInt(){ clear(); } QuadInt(QuadInt const& si){ #if OSL_USE_SSE v.v4=si.v.v4; #else v.llv = si.v.llv; #endif } QuadInt& operator=(QuadInt const& si) { #if OSL_USE_SSE v.v4=si.v.v4; #else v.llv = si.v.llv; #endif return *this; } void clear() { #if OSL_USE_SSE v.v4=(v4si){ 0, 0, 0, 0 }; #else v.llv[0] = v.llv[1] = 0; #endif } int& operator[](int i) { return v.iv[i]; } const int& operator[](int i) const { return v.iv[i]; } QuadInt operator-() const{ QuadInt ret; ret -= *this; return ret; } QuadInt& operator+=(QuadInt const& si){ #if OSL_USE_SSE v.v4=__builtin_ia32_paddd128(v.v4,si.v.v4); #else for(int i=0;i<4;i++) v.iv[i]+=si.v.iv[i]; #endif return *this; } QuadInt& operator-=(QuadInt const& si){ #if OSL_USE_SSE v.v4=__builtin_ia32_psubd128(v.v4,si.v.v4); #else for(int i=0;i<4;i++) v.iv[i]-=si.v.iv[i]; #endif return *this; } QuadInt& operator*=(int scale){ #if OSL_USE_SSE41 XMM val; unsigned long long scalescale=(unsigned long long )((unsigned int)scale); scalescale|=scalescale<<32ull; val.v2=__builtin_ia32_vec_set_v2di(val.v2,(long long)scalescale,0); val.v2=__builtin_ia32_vec_set_v2di(val.v2,(long long)scalescale,1); v.v4=__builtin_ia32_pmulld128(v.v4,val.v4); #else for(int i=0;i<4;i++) v.iv[i]*=scale; #endif return *this; } static size_t size() { return 4; } }; inline QuadInt operator+(QuadInt const& si0,QuadInt const& si1) { QuadInt ret(si0); ret+=si1; return ret; } inline QuadInt operator-(QuadInt const& si0,QuadInt const& si1) { QuadInt ret(si0); ret-=si1; return ret; } inline QuadInt operator*(QuadInt const& si0,int scale) { QuadInt ret(si0); ret*=scale; return ret; } inline bool operator==(QuadInt const& l,QuadInt const& r) { return l.v.llv[0] == r.v.llv[0] && l.v.llv[1] == r.v.llv[1]; } inline bool operator<(QuadInt const& l,QuadInt const& r) { if (l.v.llv[0] != r.v.llv[0]) return (l.v.llv[0] < r.v.llv[0]); return l.v.llv[1] < r.v.llv[1]; } class QuadIntPair { CArray v; public: QuadIntPair() {} const QuadInt& operator[](int i) const{ return v[i]; } const QuadInt& operator[](Player pl) const{ return v[pl]; } QuadInt& operator[](int i){ return v[i]; } QuadInt& operator[](Player pl){ return v[pl]; } QuadIntPair& operator+=(QuadIntPair const& a){ v[0]+=a.v[0]; v[1]+=a.v[1]; return *this; } QuadIntPair& operator-=(QuadIntPair const& a){ v[0]-=a.v[0]; v[1]-=a.v[1]; return *this; } }; inline QuadIntPair operator+(QuadIntPair const& si0,QuadIntPair const& si1) { QuadIntPair ret(si0); ret+=si1; return ret; } inline QuadIntPair operator-(QuadIntPair const& si0,QuadIntPair const& si1) { QuadIntPair ret(si0); ret-=si1; return ret; } inline bool operator==(QuadIntPair const& l,QuadIntPair const& r) { return l[0] == r[0] && l[1] == r[1]; } } using container::QuadInt; using container::QuadIntPair; } #endif // EVAL_CONTAINER_QUAD_INT_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/pieceMask.cc0000644000000000000000000000103412316770314017340 0ustar rootroot#include "osl/bits/pieceMask.h" #include #include #include static_assert(sizeof(osl::PieceMask) == 8, "piecemask size"); #ifndef MINIMAL std::ostream& osl::operator<<(std::ostream& os,const PieceMask& pieceMask){ os << '(' << std::setbase(16) << std::setfill('0') << std::setw(12) << pieceMask.getMask(0).value() << std::setbase(10) << ')'; os << std::bitset<64>(pieceMask.getMask(0).value()); return os; } #endif // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/squareCompressor.cc0000644000000000000000000000145612316770314021024 0ustar rootroot/* squareCompressor.cc */ #include "osl/bits/squareCompressor.h" #include "osl/basic_type.h" #include namespace osl { CArray SquareCompressor::positionToIndex; class SquareCompressor::Initializer { public: Initializer() { std::fill(positionToIndex.begin(), positionToIndex.end(), -1); int cur = 0; positionToIndex[0] = cur++; for (int x=1; x<=9; ++x) { for (int y=1; y<=9; ++y) { positionToIndex[Square(x,y).index()] = cur++; } } assert(cur == 82); } }; namespace { SquareCompressor::Initializer init; } // anonymous namespace } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/centering5x3.h0000644000000000000000000000123612316770314017623 0ustar rootroot/* centering5x3.h */ #ifndef OSL_CENTERING5X3_H #define OSL_CENTERING5X3_H #include "osl/basic_type.h" #include "osl/container.h" namespace osl { /** * 5x3ãŒç›¤ä¸Šã«ãŠã•ã¾ã‚‹ã‚ˆã†ã«ä¸­å¿ƒã‚’調整 */ struct Centering5x3 { struct Table { CArray centers; Table(); }; static const Square adjustCenterNaive(Square); static const Table table; static const Square adjustCenter(Square src) { return table.centers[src.index()]; } }; } // namespace osl #endif /* OSL_CENTERING5X3_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/core/osl/bits/pieceTable.cc0000644000000000000000000000072512316770314017502 0ustar rootroot/* pieceTable.cc */ #include "osl/bits/pieceTable.h" #include "osl/bits/ptypeTraits.h" template void osl::PieceTable::initPtype() { for (int num=PtypeTraits::indexMin; num::indexLimit; num++) { ptypes[num]=T; } } osl::PieceTable::PieceTable() { initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); } libosl-0.8.0.orig/core/osl/bits/pieceTable.h0000644000000000000000000000115612316770314017343 0ustar rootroot/* pieceTable.h */ #ifndef OSL_PIECE_TABLE_H #define OSL_PIECE_TABLE_H #include "osl/basic_type.h" #include "osl/container.h" namespace osl { class PieceTable { private: CArray ptypes; template void initPtype(); public: PieceTable(); Ptype getPtypeOf(int num) const{ assert(validNumber(num)); return ptypes[num]; } static bool validNumber(int num) { return 0<=num && num<=39; } }; extern const PieceTable Piece_Table; } #endif /* OSL_PIECE_TABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/king8Info.h0000644000000000000000000001360412316770314017143 0ustar rootroot/* king8Info.h */ #ifndef OSL_CHECKMATE_KING8INFO_H #define OSL_CHECKMATE_KING8INFO_H #include "osl/numEffectState.h" #include "osl/additionalEffect.h" #include namespace osl { namespace checkmate { /** * 敵玉ã®8è¿‘å‚ã®çŠ¶æ…‹ã‚’è¡¨ã™. 王手ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã‚‚å«ã‚€ã“ã¨ã«ã™ã‚‹ï¼Ž * Dirã¯ç›¸æ‰‹ã®çމã«å¯¾ã—ã¦Diræ–¹å‘ã§çŽ‹æ‰‹ã‚’ã‹ã‘ã‚‹ä½ç½® * 0-7 : 敵玉以外ã®åˆ©ããŒãªã,自分ã®åˆ©ããŒã‚る空白 * (駒を打ã¤å€™è£œã¨ãªã‚Šã†ã‚‹ç‚¹) * 8-15 : 敵玉ãŒDirã«ç§»å‹•å¯èƒ½(王手ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã¯é•·ã„利ãã‚‚å»¶ã°ã™) * 16-23 : 空白ã‹å‘³æ–¹ã®é§’(åˆ©ãæ¬¡ç¬¬ã§ã¯ç§»å‹•å¯èƒ½ã«ãªã‚‹) * 24-31 : 敵玉以外ã®åˆ©ããŒãªã,自分ã®åˆ©ããŒã‚る空白,敵駒 * (OLD * 24-31 : 敵玉以外ã®åˆ©ããŒãªã,自分ã®åˆ©ããŒ2ã¤ä»¥ä¸Šã‚る空白,敵駒 * (é§’ã‚’å‹•ã‹ã™å€™è£œã¨ãªã‚Šã†ã‚‹ç‚¹) ) * 32-39 : 空白(駒打ã¡çŽ‹æ‰‹ã®å€™è£œ) * 40-47 : 味方ã®åˆ©ã(kingã®åˆ©ãã‚‚å«ã‚“ã§ã„ã‚‹)ãŒã‚る空白,敵駒 * 48-51 : 敵玉ãŒDirã«ç§»å‹•å¯èƒ½(王手ãŒã‹ã‹ã£ã¦ã„ã‚‹å ´åˆã¯é•·ã„利ãã‚‚å»¶ã°ã™)ãªæ•° */ class King8Info { uint64_t value; public: explicit King8Info(uint64_t v) : value(v) { } template static const King8Info make(NumEffectState const& state,Square king, PieceMask pinned); template static const King8Info make(NumEffectState const& state,Square king); /** alt(attack) ã®king ã«ã¤ã„ã¦è¨ˆç®— */ static const King8Info make(Player attack, NumEffectState const& state); /** alt(attack) ã®king ã«ã¤ã„ã¦è¨ˆç®—. pinãŒæ—¢ã«æ±‚ã¾ã£ã¦ã„ã‚‹ */ static const King8Info makeWithPin(Player attack, NumEffectState const& state, const PieceMask& pinned); uint64_t uint64Value() const { return value; } /** 0-7 bit 目を返㙠*/ unsigned int dropCandidate() const { return (unsigned int)(value&0xffull); } /** 8-15 bit 目を 0-7bitã«shiftã—ã¦è¿”ã™ */ unsigned int liberty() const { return (unsigned int)((value>>8)&0xffull); } /** 0-15bit */ unsigned int libertyDropMask() const { return (unsigned int)(value&0xffffull); } /** 16-23 bit 目を 0-7bitã«shiftã—ã¦è¿”ã™ */ unsigned int libertyCandidate() const { return (unsigned int)((value>>16)&0xffull); } /** 24-31 bit 目を 0-7bitã«shiftã—ã¦è¿”ã™ */ unsigned int moveCandidate2() const { return (unsigned int)((value>>24)&0xffull); } unsigned int spaces() const { return (unsigned int)((value>>32)&0xffull); } unsigned int moves() const { return (unsigned int)((value>>40)&0xffull); } /** libertyã®æ•° */ unsigned int libertyCount() const { return (unsigned int)((value>>48)&0xfull); } template unsigned int moveCandidateDir(NumEffectState const& state,Square target) const{ if((value & (1ull<<(24+Dir)))==0) return 0; Square pos=target-DirectionPlayerTraits::offset(); if(state.countEffect(P,pos)<2 && !effect_util::AdditionalEffect::hasEffect(state,pos,P)) return 0; return 1; } template unsigned int countMoveCandidate(NumEffectState const& state) const { const Player altP=alt(P); Square king=state.kingSquare(); return moveCandidateDir(state,king)+ moveCandidateDir(state,king)+ moveCandidateDir(state,king)+ moveCandidateDir(state,king)+ moveCandidateDir(state,king)+ moveCandidateDir(state,king)+ moveCandidateDir(state,king)+ moveCandidateDir(state,king); } unsigned int countMoveCandidate(Player player, NumEffectState const& state) const { if(player==BLACK) return countMoveCandidate(state); else return countMoveCandidate(state); } template unsigned int moveCandidateMask(NumEffectState const& state) const { const Player altP=alt(P); Square king=state.kingSquare(); return (moveCandidateDir(state,king)<(state,king)<(state,king)<(state,king)<(state,king)<(state,king)<(state,king)<(state,king)< bool hasMoveCandidate(NumEffectState const& state) const { const Player altP=alt(P); Square king=state.kingSquare(); if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; if(moveCandidateDir(state,king)!=0) return true; return false; } private: /** * alt(P)ã®çމã«Dirã®æ–¹å‘ã§è¿«ã‚‹canMoveMaskを計算ã™ã‚‹. * @param P(template) - 攻撃å´ã®player * @param Dir(template) - 敵玉ã«è¿«ã‚‹æ–¹å‘(shortã®8æ–¹å‘) * @param state - åˆæœŸçŠ¶æ…‹ * @param target - alt(P)ã®çމãŒã‚ã‚‹potision */ template static uint64_t #ifdef __GNUC__ __attribute__ ((pure)) #endif hasEffectMask(NumEffectState const& state,Square target, PieceMask pinned, PieceMask on_board_defense); }; std::ostream& operator<<(std::ostream&, King8Info); } // namespace checkmate using checkmate::King8Info; } // namespace osl #endif /* OSL_CHECKMATE_KING8INFO_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/centering5x3.cc0000644000000000000000000000164712316770314017767 0ustar rootroot/* centering5x3.cc */ #include "osl/bits/centering5x3.h" #include "osl/basic_type.h" osl::Centering5x3:: Table::Table() { centers.fill(Square::STAND()); for (int y=1; y<=9; ++y) { for (int x=1; x<=9; ++x) { const Square src = Square(x,y); centers[src.index()] = adjustCenterNaive(src); } } } namespace { int adjustCenterX(int x) { if (x < 3) return 3; else if (x > 7) return 7; return x; } int adjustCenterY(int y) { if (y == 1) return y+1; else if (y == 9) return y-1; return y; } } // anonymous namespace const osl::Square osl:: Centering5x3::adjustCenterNaive(Square src) { const int x = adjustCenterX(src.x()); const int y = adjustCenterY(src.y()); return Square(x, y); } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/numSimpleEffect.tcc0000644000000000000000000000730712316770314020722 0ustar rootroot#ifndef OSL_NUM_SIMPLE_EFFECT_TCC #define OSL_NUM_SIMPLE_EFFECT_TCC #include "osl/bits/numSimpleEffect.h" #include "osl/bits/king8Info.h" #include "osl/bits/pieceTable.h" #include "osl/csa.h" #include template void osl::effect:: NumSimpleEffectTable::doEffect(const SimpleState& state,PtypeO ptypeo,Square pos,int num) { switch((int)ptypeo){ case NEW_PTYPEO(WHITE,PAWN): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,LANCE): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,KNIGHT): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,SILVER): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,PPAWN): case NEW_PTYPEO(WHITE,PLANCE): case NEW_PTYPEO(WHITE,PKNIGHT): case NEW_PTYPEO(WHITE,PSILVER): case NEW_PTYPEO(WHITE,GOLD): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,BISHOP): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,PBISHOP): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,ROOK): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,PROOK): doEffectBy(state,pos,num); break; case NEW_PTYPEO(WHITE,KING): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,PAWN): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,LANCE): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,KNIGHT): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,SILVER): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,PPAWN): case NEW_PTYPEO(BLACK,PLANCE): case NEW_PTYPEO(BLACK,PKNIGHT): case NEW_PTYPEO(BLACK,PSILVER): case NEW_PTYPEO(BLACK,GOLD): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,BISHOP): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,PBISHOP): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,ROOK): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,PROOK): doEffectBy(state,pos,num); break; case NEW_PTYPEO(BLACK,KING): doEffectBy(state,pos,num); break; default: assert(0); } return; } template void osl::effect:: NumSimpleEffectTable::doEffectBy(const SimpleState& state,Square pos,int num) { if(UC){ if(T==LANCE || T==BISHOP || T==PBISHOP || T==ROOK || T==PROOK) setChangedPieces(NumBitmapEffect::makeLongEffect

(num)); else setChangedPieces(NumBitmapEffect::makeEffect

(num)); } doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectShort(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); doEffectLong(state,pos,num); } #endif /* OSL_NUM_SIMPLE_EFFECT_TCC */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/ptypeTable.cc0000644000000000000000000000771312316770314017562 0ustar rootroot/* ptypeTable.cc */ #include "osl/bits/ptypeTable.h" #include "osl/bits/boardTable.h" osl::PtypeTable::PtypeTable() { init(); { // guard assert(&effect(newPtypeO(WHITE,ROOK), Offset32(2,8)) == &getEffect(newPtypeO(WHITE,ROOK), Offset32(2,8))); assert(getEffect(newPtypeO(BLACK,PPAWN), Offset32(Square(7,1),Square(8,1))) == EffectContent::DIRECT()); } } template void osl::PtypeTable::initPtypeSub(Int2Type) { initPtypeSub(Int2Type()); numMaskLows[static_cast(T)]=mask_t::makeDirect(PtypeFuns::indexMask); numIndices[static_cast(T)]=PtypeFuns::indexNum; if(canPromote(T)){ numMaskLows[static_cast(promote(T))]=mask_t::makeDirect(PtypeFuns::indexMask); numIndices[static_cast(promote(T))]=PtypeFuns::indexNum; } /** é»’ */ canDropLimit[0][static_cast(T)]=PtypeTraits::dropBlackFromY; /** 白 */ canDropLimit[1][static_cast(T)]=Square::reverseY(PtypeTraits::dropBlackFromY); indexMins[static_cast(T)]=PtypeTraits::indexMin; indexLimits[static_cast(T)]=PtypeTraits::indexLimit; } template void osl::PtypeTable::initPtypeSub(Int2Type /*is_basic*/) { names[static_cast(T)]=PtypeTraits::name(); csaNames[static_cast(T)]=PtypeTraits::csaName(); moveMasks[static_cast(T)]=PtypeTraits::moveMask; betterToPromote[static_cast(T)]=PtypeTraits::betterToPromote; } template void osl::PtypeTable::initPtype() { initPtypeSub(Int2Type::isBasic>()); } void osl::PtypeTable::init() { numMaskLows.fill(); numIndices.fill(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); initPtype(); effectTable.fill(); effectTableNotLongU.fill(); shortMoveMask.fill(); static_assert(sizeof(EffectContent) == 4, "size"); assert(&effect(newPtypeO(WHITE,ROOK), Offset32(2,8)) == &getEffect(newPtypeO(WHITE,ROOK), Offset32(2,8))); assert(! getEffect(newPtypeO(BLACK,ROOK), Offset32(-1,8)).hasEffect()); for(int ptype=PTYPE_MIN;ptype<=PTYPE_MAX;ptype++){ for(int j=DIRECTION_MIN;j<=DIRECTION_MAX;j++){ Direction dir=static_cast(j); if((moveMasks[ptype]&(1<(dir)!=LONG_U){ effectTableNotLongU[ptype-PTYPEO_MIN][offset32.index()]=effectTable[ptype-PTYPEO_MIN][offset32.index()]; effectTableNotLongU[ptype-16-PTYPEO_MIN][(-offset32).index()]=effectTable[ptype-16-PTYPEO_MIN][(-offset32).index()]; } } } else{ shortMoveMask[0][dir]|=1<<(ptype-PTYPEO_MIN); shortMoveMask[1][dir]|=1<<(ptype-16-PTYPEO_MIN); effectTable[ptype-PTYPEO_MIN][offset32.index()]=EffectContent::DIRECT(); effectTable[ptype-16-PTYPEO_MIN][(-offset32).index()]=EffectContent::DIRECT(); assert(! getEffect(newPtypeO(BLACK,ROOK),Offset32(-1,8)).hasEffect()); } } } } } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/numSimpleEffect.h0000644000000000000000000003034312316770314020374 0ustar rootroot#ifndef OSL_NUM_SIMPLE_EFFECT_H #define OSL_NUM_SIMPLE_EFFECT_H #include "osl/simpleState.h" #include "osl/bits/numBitmapEffect.h" #include "osl/bits/boardMask.h" #include "osl/bits/bitXmask.h" #include "osl/bits/effectedNumTable.h" #include "osl/mobility/mobilityTable.h" namespace osl { namespace checkmate { class King8Info; } namespace effect { class NumSimpleEffectTable; bool operator==(const NumSimpleEffectTable&,const NumSimpleEffectTable&); std::ostream& operator<<(std::ostream&, const NumSimpleEffectTable&); /** * å±€é¢å…¨ä½“ã®åˆ©ãデータ. */ class NumSimpleEffectTable { protected: CArray effects #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; CArray changed_effects; // each player /** set of pieces whose effect changed by previous move */ NumBitmapEffect changed_effect_pieces; public: CArray effected_mask; CArray effected_changed_mask; /** mobility */ mobility::MobilityTable mobilityTable; /** effected num */ EffectedNumTable effectedNumTable; /** * ã‚ã‚‹ä½ç½®ã‹ã‚‰ã‚ã‚‹æ–¹å‘ã«çŸ­ã„利ããŒã‚る時ã«ï¼Œãã®æ–¹å‘ã®åˆ©ãã‚’æ›´æ–°ã™ã‚‹. * @param P(template) - ã‚ã‚‹ä½ç½®ã«ã‚ã‚‹é§’ã®æ‰€æœ‰è€… * @param T(template) - ã‚ã‚‹ä½ç½®ã«ã‚ã‚‹é§’ã®ç¨®é¡ž * @param D(template) - é§’ã®æ‰€æœ‰è€…ã®ç«‹å ´ã‹ã‚‰è¦‹ãŸæ–¹å‘ * @param OP(template) - 利ãã‚’è¶³ã™ã‹ï¼Œæ¸›ã‚‰ã™ã‹ * @param pos - é§’ã®ä½ç½® * @param num - é§’ç•ªå· */ template void doEffectShort(const SimpleState& state,Square pos,int num) { if ((PtypeTraits::moveMask & DirectionTraits

::mask)!=0) { const Square target = pos+DirectionPlayerTraits::offset(); effects[target.index()].template opEqual(NumBitmapEffect::makeEffect

(num)); if(UC){ int posIndex=BoardMask::index(pos); changed_effects[P].set(posIndex+BoardMask::getIndexOffset()); int num1; if(Piece::isPieceNum(num1=state.pieceAt(target).number())){ if(OP==NumBitmapEffect::Add){ effected_mask[P].set(num1); } else{ // OP==Sub if((effects[target.index()].getMask(1)&NumBitmapEffect::playerEffectMask(P)).none()){ effected_mask[P].reset(num1); } } effected_changed_mask[P].set(num1); } } } } /** * ã‚ã‚‹ä½ç½®ã‹ã‚‰ã‚ã‚‹æ–¹å‘ã«é•·ã„利ããŒã‚る時ã«ï¼Œãã®æ–¹å‘ã®åˆ©ãã‚’æ›´æ–°ã™ã‚‹. * @param P(template) - ã‚ã‚‹ä½ç½®ã«ã‚ã‚‹é§’ã®æ‰€æœ‰è€… * @param T(template) - ã‚ã‚‹ä½ç½®ã«ã‚ã‚‹é§’ã®ç¨®é¡ž * @param Dir(template) - é»’ã®ç«‹å ´ã‹ã‚‰è¦‹ãŸæ–¹å‘ * @param OP(template) - 利ãã‚’è¶³ã™ã‹ï¼Œæ¸›ã‚‰ã™ã‹ * @param state - 盤é¢(å‹•ã‹ã—ãŸå¾Œ) * @param pos - é§’ã®ä½ç½® * @param num - é§’ç•ªå· */ template void doEffectLong(const SimpleState& state,Square pos,int num) { if ((PtypeTraits::moveMask & DirectionTraits::directionByBlack>::mask)!=0) { int posIndex; if(UC){ posIndex=BoardMask::index(pos); } const Offset offset=DirectionPlayerTraits::offset(); assert(!offset.zero()); NumBitmapEffect effect=NumBitmapEffect::makeLongEffect

(num); const Direction SD=longToShort(Dir); if(OP==NumBitmapEffect::Sub){ Square ePos=mobilityTable.get(longToShort(Dir),num); int count=((SD==D || SD==DL || SD==DR) ? ePos.y()-pos.y() : ( (SD==U || SD==UL || SD==UR) ? pos.y()-ePos.y() : ( SD==L ? ePos.x()-pos.x() : pos.x()-ePos.x()))); assert(0<=count && count<=9); if(UC){ for(int i=1;i(); effects[pos.index()].template opEqual(effect); changed_effects[P].set(posIndex); } Piece p; mobilityTable.set(longToShort(Dir),num,Square::STAND()); int num1=state.pieceAt(ePos).number(); if (!Piece::isEdgeNum(num1)){ effectedNumTable[num1][SD]=EMPTY_NUM; effects[ePos.index()].template opEqual(effect); effected_changed_mask[P].set(num1); posIndex+=BoardMask::getIndexOffset(); changed_effects[P].set(posIndex); if((effects[ePos.index()].getMask(1)&NumBitmapEffect::playerEffectMask(P)).none()){ effected_mask[P].reset(num1); } } } else{ for(int i=0;i(effect); } int num1=state.pieceAt(ePos).number(); if (!Piece::isEdgeNum(num1)) effectedNumTable[num1][SD]=EMPTY_NUM; } } else{ // OP==Add for (;;) { pos=pos+offset; if(UC){ posIndex+=BoardMask::getIndexOffset(); changed_effects[P].set(posIndex); } effects[pos.index()].template opEqual(effect); // effect内ã«emptyã‚’å«ã‚€ã‚ˆã†ã«ã—ãŸã‚‰çŸ­ããªã‚‹ int num1=state.pieceAt(pos).number(); if (!Piece::isEmptyNum(num1)){ if(UC){ mobilityTable.set(longToShort(Dir),num,pos); if(!Piece::isEdgeNum(num1)){ effectedNumTable[num1][SD]=num; changed_effects[P].set(posIndex); effected_mask[P].set(num1); effected_changed_mask[P].set(num1); } } else if(!Piece::isEdgeNum(num1)){ effectedNumTable[num1][SD]=num; } break; } } } } } /** * ã‚る種類ã®é§’ãŒæŒã¤åˆ©ãã‚’æ›´æ–°ã™ã‚‹. * @param P(template) - ã‚ã‚‹ä½ç½®ã«ã‚ã‚‹é§’ã®æ‰€æœ‰è€… * @param T(template) - ã‚ã‚‹ä½ç½®ã«ã‚ã‚‹é§’ã®ç¨®é¡ž * @param OP(template) - 利ãã‚’è¶³ã™ã‹ï¼Œæ¸›ã‚‰ã™ã‹ * @param state - 盤é¢(å‹•ã‹ã—ãŸå¾Œ) * @param pos - é§’ã®ä½ç½® * @param num - é§’ç•ªå· */ template void doEffectBy(const SimpleState& state,Square pos,int num); /** * ã‚る種類ã®é§’ãŒæŒã¤åˆ©ãã‚’æ›´æ–°ã™ã‚‹. * @param OP(template) - 利ãã‚’è¶³ã™ã‹ï¼Œæ¸›ã‚‰ã™ã‹ * @param state - 盤é¢(å‹•ã‹ã—ãŸå¾Œ) * @param ptypeo - é§’ã®ç¨®é¡ž * @param pos - é§’ã®ä½ç½® * @param num - é§’ç•ªå· */ template void doEffect(const SimpleState& state,PtypeO ptypeo,Square pos,int num); /** * ã‚ã‚‹é§’ãŒæŒã¤åˆ©ãã‚’æ›´æ–°ã™ã‚‹. * @param OP(template) - 利ãã‚’è¶³ã™ã‹ï¼Œæ¸›ã‚‰ã™ã‹ * @param state - 盤é¢(å‹•ã‹ã—ãŸå¾Œ) * @param p - é§’ */ template void doEffect(const SimpleState& state,Piece p) { doEffect(state,p.ptypeO(),p.square(),p.number()); } /** * 盤é¢ã®ãƒ‡ãƒ¼ã‚¿ã‚’å…ƒã«åˆæœŸåŒ–ã™ã‚‹. * @param state - ç›¤é¢ */ void init(const SimpleState& state); /** * コンストラクタ. */ NumSimpleEffectTable(const SimpleState& state) { assert(reinterpret_cast(this) % 16 == 0); init(state); } /** * ã‚ã‚‹ä½ç½®ã®åˆ©ãデータをå–り出ã™. * @param pos - ä½ç½® */ const NumBitmapEffect effectSetAt(Square pos) const { return effects[pos.index()]; } /** * posã«é§’を設置/削除ã—ã¦é•·ã„利ãをブロック/å»¶é•·ã™ã‚‹éš›ã®åˆ©ããƒ‡ãƒ¼ã‚¿ã®æ›´æ–°. * @param OP(template) - 利ãã‚’è¶³ã™ã‹ï¼Œæ¸›ã‚‰ã™ã‹ * @param state - å±€é¢ã®çŠ¶æ…‹ posã«é§’ã‚’ç½®ãå‰ã§ã‚‚後ã§ã‚‚よㄠ* @param pos - 変化ã™ã‚‹ä½ç½® */ template void doBlockAt(const SimpleState& state,Square pos,int piece_num); friend bool operator==(const NumSimpleEffectTable& et1,const NumSimpleEffectTable& et2); /* * */ const BoardMask changedEffects(Player pl) const{ return changed_effects[pl]; } const NumBitmapEffect changedPieces() const { return changed_effect_pieces; } const PieceMask effectedMask(Player pl) const { return effected_mask[playerToIndex(pl)]; } const PieceMask effectedChanged(Player pl) const { return effected_changed_mask[playerToIndex(pl)]; } void setChangedPieces(NumBitmapEffect const& effect) { changed_effect_pieces |= effect; } void clearChangedEffects(){ changed_effects[0].clear(); changed_effects[1].clear(); changed_effect_pieces.resetAll(); } void invalidateChangedEffects(){ changed_effects[0].invalidate(); changed_effects[1].invalidate(); changed_effect_pieces.setAll(); } void clearEffectedChanged(){ effected_changed_mask[0].resetAll(); effected_changed_mask[1].resetAll(); } /** 主è¦éƒ¨åˆ†ã‚’高速ã«ã‚³ãƒ”ーã™ã‚‹. 盤ã®å¤–ã‚„ç›´å‰ã®åˆ©ãã®å¤‰åŒ–ãªã©ã®æƒ…å ±ã¯ã‚³ãƒ”ーã•れãªã„*/ void copyFrom(const NumSimpleEffectTable& src); }; inline bool operator!=(const NumSimpleEffectTable& et1,const NumSimpleEffectTable& et2) { return !(et1==et2); } } // namespace effect using effect::NumBitmapEffect; } // namespace osl /** * posã«é§’を設置/削除ã—ã¦é•·ã„利ãをブロック/å»¶é•·ã™ã‚‹éš›ã®åˆ©ããƒ‡ãƒ¼ã‚¿ã®æ›´æ–°. * xorãªã®ã§posã«å…ƒã€…é§’ãŒã‚ã£ã¦ï¼Œå–ã‚Šé™¤ãæ™‚ã«ã‚‚呼ã³å‡ºã›ã‚‹ï¼Ž * @param state - å±€é¢ã®çŠ¶æ…‹ posã«é§’ã‚’ç½®ãå‰ã§ã‚‚後ã§ã‚‚よㄠ* @param pos - 変化ã™ã‚‹ä½ç½® */ template void osl::effect:: NumSimpleEffectTable::doBlockAt(const SimpleState& state,Square pos,int piece_num) { if(UC){ setChangedPieces(effects[pos.index()]); } mask_t mask1 =((effects[pos.index()].getMask(1)) & NumBitmapEffect::longEffectMask()); while (mask1.any()){ int num=mask1.takeOneBit()+NumBitmapEffect::longToNumOffset; assert(32<=num && num<=39); Piece p1=state.pieceOf(num); Player pl1=p1.owner(); assert(p1.ptype()!=PPAWN); Square pos1=p1.square(); Offset offset0; Direction d=Board_Table.getShort8(pos1,pos,offset0); if(OP==NumBitmapEffect::Sub){ Square endSquare=mobilityTable.get(d,num); NumBitmapEffect effect=NumBitmapEffect::makeLongEffect(pl1,num); Piece p; Square pos2=pos+offset0; int pos2Index, offset81; if(UC){ int posIndex=BoardMask::index(pos); pos2Index=BoardMask::index(pos2); offset81=pos2Index-posIndex; } for(;pos2!=endSquare;pos2+=offset0){ if(UC){ changed_effects[pl1].set(pos2Index); pos2Index+=offset81; } effects[pos2.index()].template opEqual(effect); } effects[pos2.index()].template opEqual(effect); int num1=state.pieceAt(endSquare).number(); if (!Piece::isEdgeNum(num1)){ effectedNumTable[num1][d]=EMPTY_NUM; if(UC){ changed_effects[pl1].set(pos2Index); if((effects[endSquare.index()].getMask(1)&NumBitmapEffect::playerEffectMask(pl1)).none()){ effected_mask[pl1].reset(num1); } effected_changed_mask[pl1].set(num1); mobilityTable.set(d,num,pos); } } else mobilityTable.set(d,num,pos); effectedNumTable[piece_num][d]=num; } else{ NumBitmapEffect effect=NumBitmapEffect::makeLongEffect(pl1,num); Square pos2=pos+offset0; int pos2Index, offset81; if(UC){ int posIndex=BoardMask::index(pos); pos2Index=BoardMask::index(pos2); offset81=pos2Index-posIndex; } for(;;){ int num1=state.pieceAt(pos2).number(); if(!Piece::isEmptyNum(num1)){ if(UC){ mobilityTable.set(d,num,pos2); if(!Piece::isEdgeNum(num1)){ effectedNumTable[num1][d]=num; effects[pos2.index()].template opEqual(effect); changed_effects[pl1].set(pos2Index); effected_mask[pl1].set(num1); effected_changed_mask[pl1].set(num1); } } else if(!Piece::isEdgeNum(num1)){ effectedNumTable[num1][d]=num; effects[pos2.index()].template opEqual(effect); } break; } if(UC){ changed_effects[pl1].set(pos2Index); pos2Index+=offset81; } effects[pos2.index()].template opEqual(effect); pos2+=offset0; } } } } #endif // OSL_NUM_SIMPLE_EFFECT_H // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/offset32.h0000644000000000000000000000350512316770314016741 0ustar rootroot/* offset32.h */ #ifndef OSL_OFFSET32_H #define OSL_OFFSET32_H #include "osl/basic_type.h" namespace osl { /** * 差㌠uniqã«ãªã‚‹ã‚ˆã†ãªåº§æ¨™ã®å·®åˆ†. * x*32+yåŒå£«ã®å·®ã‚’å–ã‚‹ * ã¡ã‚‡ã£ã¨ã ã‘溢れã¦ã‚‚良ㄠ*/ template class Offset32Base { enum { MIN = -(Width*32+Width), MAX = (Width*32+Width), }; public: static const unsigned int SIZE=(MAX-MIN+1); private: int offset32; explicit Offset32Base(int o) : offset32(o) { } public: Offset32Base(Square to, Square from) : offset32(to.indexForOffset32()-from.indexForOffset32()) { assert((to.x()-from.x() >= -Width) && (to.x()-from.x() <= Width) && (to.y()-from.y() >= -Width) && (to.y()-from.y() <= Width)); assert(MIN<=offset32 && offset32<=MAX); } Offset32Base(int dx,int dy) : offset32(dx*32+dy) { assert(-Width2<=dx && dx<=Width2 && -Width2<=dy && dy<=Width2); } unsigned int index() const { return offset32 - MIN; } bool isValid() const { return MIN <=offset32 && offset32 <= MAX; } /** * Player P ã‹ã‚‰ã¿ãŸ offset を黒番ã®ã‚‚ã®ã«å¤‰æ›´ã™ã‚‹ */ template const Offset32Base blackOffset32() const { return P == BLACK ? *this : Offset32Base(-offset32); } const Offset32Base operator-() const { return Offset32Base(-offset32); } private: // these functions are *intentionally* unimplemented for the moment. // don't forget the fact that x or y can be negative. int dx(Offset32Base offset32); int dy(Offset32Base offset32); }; typedef Offset32Base<8,9> Offset32; typedef Offset32Base<10,10> Offset32Wide; } // namespace osl #endif /* OSL_OFFSET32_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/binaryIO.h0000644000000000000000000000202412316770314017015 0ustar rootroot/* binaryIO.h */ #ifndef OSL_BINARYIO_H #define OSL_BINARYIO_H #include #include #include namespace osl { namespace misc { struct BinaryWriter { static void write(std::ostream&, const std::vector& data); static void write(std::ostream&, const std::vector& data); }; template class BinaryReader { public: explicit BinaryReader(std::istream& is); ~BinaryReader(); bool read(std::vector& data); static size_t blockSize(); private: struct State; std::unique_ptr state; }; template class BinaryElementReader { public: explicit BinaryElementReader(std::istream& is); ~BinaryElementReader(); T read(); bool hasNext() const; bool failed() const; private: struct State; std::unique_ptr state; }; } } #endif /* OSL_BINARYIO_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/ptypeTraits.h0000644000000000000000000003515112316770314017640 0ustar rootroot/* ptypeTraits.h */ #ifndef OSL_PTYPETRAITS_H #define OSL_PTYPETRAITS_H #include "osl/basic_type.h" #include "osl/bits/directionTraits.h" namespace osl { template struct PtypeTraits; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; /** æ‰“ã¡æ­©è©°ã‚’除ã„ã¦è€ƒãˆã‚‹ã¨ promoteã¯å¸¸ã«å¾— */ static const bool betterToPromote=false; static const char *name() { return "PTYPE_EMPTY";} static const char *csaName() { return "..";} static const int moveMask=0; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; static const bool betterToPromote=false; static const char *name() { return "PTYPE_EDGE";} static const char *csaName() { return "XX";} static const int moveMask=0; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=false; static const bool betterToPromote=false; static const Ptype moveType=GOLD; static const char *name() { return "GOLD";} static const char *csaName() { return "KI";} static const int indexMin=26; static const int indexLimit=30; static const int dropBlackFromY=1; static const int dropBlackToY=9; static const Ptype basicType=GOLD; static const int moveMask= DirectionTraits

    ::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=true; static const bool betterToPromote=true; static const Ptype moveType=PAWN; static const Ptype basicType=PAWN; static const char *name() { return "PAWN";} static const char *csaName() { return "FU";} static const int indexMin=0; static const int indexLimit=18; static const int dropBlackFromY=2; static const int dropBlackToY=9; static const int mayPromoteToY=4; static const int moveMask=DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; // ç–‘å• falseã®æ–¹ãŒã‚ˆã„ã®ã§ã¯? static const bool betterToPromote=true; static const Ptype moveType=GOLD; static const char *name() { return "PPAWN";} static const char *csaName() { return "TO";} static const int moveMask=PtypeTraits::moveMask; static const Ptype basicType=PAWN; static const int indexMin=PtypeTraits::indexMin; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=true; static const bool betterToPromote=false; static const Ptype moveType=LANCE; static const Ptype basicType=LANCE; static const char *name() { return "LANCE";} static const char *csaName() { return "KY";} static const int indexMin=32; static const int indexLimit=36; static const int dropBlackFromY=2; static const int dropBlackToY=9; static const int mayPromoteToY=9; static const int moveMask=DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; static const bool betterToPromote=false; static const Ptype moveType=GOLD; static const char *name() { return "PLANCE";} static const char *csaName() { return "NY";} static const int moveMask=PtypeTraits::moveMask; static const Ptype basicType=LANCE; static const int indexMin=PtypeTraits::indexMin; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=true; static const bool betterToPromote=false; static const Ptype moveType=KNIGHT; static const Ptype basicType=KNIGHT; static const char *name() { return "KNIGHT";} static const char *csaName() { return "KE";} static const int indexMin=18; static const int indexLimit=22; static const int dropBlackFromY=3; static const int dropBlackToY=9; static const int mayPromoteToY=5; static const int moveMask=DirectionTraits::mask|DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; static const bool betterToPromote=false; static const Ptype moveType=GOLD; static const char *name() { return "PKNIGHT";} static const char *csaName() { return "NK";} static const int moveMask=PtypeTraits::moveMask; static const Ptype basicType=KNIGHT; static const int indexMin=PtypeTraits::indexMin; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=true; static const bool betterToPromote=false; static const Ptype moveType=SILVER; static const Ptype basicType=SILVER; static const char *name() { return "SILVER";} static const char *csaName() { return "GI";} static const int indexMin=22; static const int indexLimit=26; static const int dropBlackFromY=1; static const int dropBlackToY=9; static const int mayPromoteToY=4; static const int moveMask= DirectionTraits
      ::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits
      ::mask |DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; static const bool betterToPromote=false; static const Ptype moveType=GOLD; static const char *name() { return "PSILVER";} static const char *csaName() { return "NG";} static const int moveMask=PtypeTraits::moveMask; static const Ptype basicType=SILVER; static const int indexMin=PtypeTraits::indexMin; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=true; static const bool betterToPromote=true; static const Ptype moveType=BISHOP; static const Ptype basicType=BISHOP; static const char *name() { return "BISHOP";} static const char *csaName() { return "KA";} static const int indexMin=36; static const int indexLimit=38; static const int dropBlackFromY=1; static const int dropBlackToY=9; static const int mayPromoteToY=9; static const int moveMask= DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; // ç–‘å• falseã®æ–¹ãŒã‚ˆã„ã®ã§ã¯? static const bool betterToPromote=true; static const Ptype moveType=PBISHOP; static const char *name() { return "PBISHOP";} static const char *csaName() { return "UM";} static const int moveMask= DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask; static const Ptype basicType=BISHOP; static const int indexMin=PtypeTraits::indexMin; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=true; static const bool betterToPromote=true; static const Ptype moveType=ROOK; static const Ptype basicType=ROOK; static const char *name() { return "ROOK";} static const char *csaName() { return "HI";} static const int indexMin=38; static const int indexLimit=40; static const int dropBlackFromY=1; static const int dropBlackToY=9; static const int mayPromoteToY=9; static const int moveMask= DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask; }; template <> struct PtypeTraits { static const bool isBasic=false; static const bool canPromote=false; // ç–‘å• falseã®æ–¹ãŒã‚ˆã„ã®ã§ã¯? static const bool betterToPromote=true; static const Ptype moveType=PROOK; static const char *name() { return "PROOK";} static const char *csaName() { return "RY";} static const int moveMask= DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask |DirectionTraits
        ::mask|DirectionTraits::mask |DirectionTraits
        ::mask|DirectionTraits::mask; static const Ptype basicType=ROOK; static const int indexMin=PtypeTraits::indexMin; }; template <> struct PtypeTraits { static const bool isBasic=true; static const bool canPromote=false; static const bool betterToPromote=false; static const Ptype moveType=KING; static const Ptype basicType=KING; static const char *name() { return "KING";} static const char *csaName() { return "OU";} static const int indexMin=30; static const int indexLimit=32; static const int dropBlackFromY=1; static const int dropBlackToY=9; static const int moveMask= DirectionTraits::mask|DirectionTraits::mask |DirectionTraits::mask|DirectionTraits::mask |DirectionTraits
          ::mask|DirectionTraits::mask |DirectionTraits
          ::mask|DirectionTraits::mask; }; template struct PtypeFunsSub; template struct PtypeFunsSub { static const uint64_t indexMask=(-1LL<<(PtypeTraits::indexMin))^(-1LL<<(PtypeTraits::indexLimit)); static const Ptype promotePtype=static_cast(static_cast(T)-8); static const Ptype basicType = T; }; template struct PtypeFunsSub { static const uint64_t indexMask=static_cast(0); // static const Ptype promotePtype=PTYPE_EMPTY; static const Ptype promotePtype=T; static const Ptype basicType = PtypeTraits::basicType; }; template struct PtypeFuns { #if OSL_WORDSIZE == 64 static const unsigned int indexNum=0; #elif OSL_WORDSIZE == 32 static const unsigned int indexNum=(PtypeTraits::indexMin >> 5); #endif static const bool hasLongMove=(PtypeTraits::indexMin>=32); static const uint64_t indexMask=PtypeFunsSub::isBasic>::indexMask; static const Ptype promotePtype=PtypeFunsSub::canPromote>::promotePtype; static const Ptype basicType=PtypeFunsSub::isBasic>::basicType; }; /** * ã‚ã‚‹æ–¹å‘ã«ã‚ã‚‹é§’ãŒç§»å‹•å¯èƒ½ã‹ã‚’表ã™. * (basicTypeã ã‘ã¯ç¢ºå®šã—ã¦ã„ã‚‹ãŒï¼Œpromote済ã¿ã‹ã©ã†ã‹ã¯ã‚ã‹ã‚‰ãªã„å ´åˆ) */ enum MoveConstraint { /** å¯èƒ½ã§ãªã„ */ CannotMove, /** promote済ã¿ã®é§’ã®å ´åˆã«ã®ã¿å¯èƒ½ */ OnlyPromoted, /** promoteã—ã¦ã„ãªã„é§’ã®å ´åˆã«ã®ã¿å¯èƒ½ */ OnlyBasic, /** promoteã—ã¦ã„よã†ãŒï¼Œã„ã¾ã„ãŒå¯èƒ½ */ NoConstraint, }; template struct PtypeDirectionTraits { static const bool hasMove=(PtypeTraits::moveMask & DirectionTraits::mask)!=0; static const bool canMove= (PtypeTraits::moveMask & DirectionTraits::mask)!=0 || (PtypeTraits::moveMask & DirectionTraits::longDir>::mask)!=0; static const MoveConstraint moveConstraint = (PtypeDirectionTraits::canMove ? (PtypeDirectionTraits::promotePtype,D>::canMove ? NoConstraint : OnlyBasic ) : (PtypeDirectionTraits::promotePtype,D>::canMove ? OnlyPromoted : CannotMove)); }; template struct KingTraits { static const int index=PtypeTraits::indexMin+playerToIndex(T); }; template struct PtypePlayerTraits { static bool canDropTo(Square pos) { static_assert(PtypeTraits::isBasic, "canDropTo"); if (PtypeTraits::dropBlackFromY == 1) return true; if (P==BLACK) return pos.y() >= PtypeTraits::dropBlackFromY; else return pos.y() <= Square::reverseY(PtypeTraits::dropBlackFromY); } /** * posã«ã‚ã‚‹é§’ãŒpromoteã™ã‚‹å¯èƒ½æ€§ãŒã‚ã‚‹ã‹? * 先手BISHOPãŒ49,58,59,69ãªã©ã«ã„ã‚‹å ´åˆã¯å¯èƒ½æ€§ãŒãªã„ãŒï¼Œã“ã®æ™‚点ã§ã¯æŽ’除ã—ãªã„ */ static bool mayPromote(Square pos) { static_assert(PtypeTraits::isBasic&&PtypeTraits::canPromote, "mayPromote"); if (PtypeTraits::mayPromoteToY == 9) return true; if (P==BLACK) return pos.y() <= PtypeTraits::mayPromoteToY; else return pos.y() >= Square::reverseY(PtypeTraits::mayPromoteToY); } /** * posã«ã‚ã‚‹Tã®é§’ãŒpromoteã™ã‚‹æ‰‹ã—ã‹ãªã„ */ static bool mustPromote(Square pos) { if(P==BLACK){ if(T==PAWN || T==LANCE) return pos.yEq<2>(); else if(T==KNIGHT) return pos.yLe<4>(); else return false; } else{ if(T==PAWN || T==LANCE) return pos.yEq<8>(); else if(T==KNIGHT) return pos.yGe<6>(); else return false; } } /** * posã«ã‚ã‚‹Tã®é§’ãŒã©ã®æ–¹å‘ã«å‹•ã„ã¦ã‚‚promoteå¯èƒ½ */ static bool canPromote(Square pos) { if(P==BLACK){ if(T==PAWN || T==LANCE) return pos.yLe<4>(); else if(T==KNIGHT) return pos.yLe<5>(); else return pos.yLe<3>(); } else{ if(T==PAWN || T==LANCE) return pos.yGe<6>(); else if(T==KNIGHT) return pos.yGe<5>(); else return pos.yGe<7>(); } } /** * posã«ã‚ã‚‹Tã®é§’ãŒpromoteå¯èƒ½ãªdirectionã«å‹•ãæ™‚ã ã‘promoteå¯èƒ½ * shortã®æ™‚ã¯ãã®æ™‚ã®ã¿YES */ static bool checkPromote(Square pos) { if(P==BLACK){ if(T==SILVER) return pos.yEq<4>(); else if(T==LANCE || T==ROOK || T==BISHOP) return true; else return false; } else{ if(T==SILVER) return pos.yEq<6>(); else if(T==LANCE || T==ROOK || T==BISHOP) return true; else return false; } } /** * posã«ã‚ã‚‹Tã®é§’ã¯æ¬¡ã«çµ¶å¯¾ã«promoteã§ããªã„ */ static bool noPromote(Square pos) { if(P==BLACK){ if(T==PAWN || T==SILVER) return pos.yGe<5>(); else if(T==KNIGHT) return pos.yGe<6>(); else if(T==LANCE || T==ROOK || T==BISHOP) return false; else return true; } else{ if(T==PAWN || T==SILVER) return pos.yLe<5>(); else if(T==KNIGHT) return pos.yLe<4>(); else if(T==LANCE || T==ROOK || T==BISHOP) return false; else return true; } } }; } // namespace osl #endif /* OSL_PTYPETRAITS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/squareCompressor.h0000644000000000000000000000202512316770314020657 0ustar rootroot/* squareCompressor.h */ #ifndef OSL_POSITIONCOMPRESSOR_H #define OSL_POSITIONCOMPRESSOR_H #include "osl/basic_type.h" #include "osl/container.h" namespace osl { /** * Square ã‚’ [0..81] ã«åœ§ç¸®ã™ã‚‹ * 0: é§’å°ï¼Œ1..81 盤上 */ struct SquareCompressor { private: /** 本当ã¯const ã«ã—ãŸã„ã‘ã©åˆæœŸåŒ–ãŒæ‰‹é–“ãªã®ã§å¾Œå›žã— */ static CArray positionToIndex; public: class Initializer; friend class Initializer; static int compress(Square pos) { const int result = positionToIndex[pos.index()]; assert(result >= 0); return result; } static Square #ifdef __GNUC__ __attribute__ ((noinline)) #endif melt(int index) { assert(0 <= index); assert(index < 82); if (index == 0) return Square::STAND(); --index; return Square(index/9+1, index%9+1); } }; } // namespace osl #endif /* OSL_POSITIONCOMPRESSOR_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/bits/directionTraits.h0000644000000000000000000002270412316770314020457 0ustar rootroot/* directionTraits.h */ #ifndef OSL_DIRECTIONTRAITS_H #define OSL_DIRECTIONTRAITS_H #include "osl/basic_type.h" namespace osl { template struct DirectionTraitsGen; template<> struct DirectionTraitsGen
            { static const int blackDx=1; static const int blackDy=-1; static const bool canPromoteTo=true; static const Direction altDir=DR; static const Direction longDir=LONG_UL; static const Direction primDir=UL; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=0; static const int blackDy=-1; static const bool canPromoteTo=true; static const Direction altDir=D; static const Direction longDir=LONG_U; static const Direction primDir=U; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=-1; static const int blackDy=-1; static const bool canPromoteTo=true; static const Direction altDir=DL; static const Direction longDir=LONG_UR; static const Direction primDir=UR; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=1; static const int blackDy=0; static const bool canPromoteTo=false; static const Direction altDir=R; static const Direction longDir=LONG_L; static const Direction primDir=L; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=-1; static const int blackDy=0; static const bool canPromoteTo=false; static const Direction altDir=L; static const Direction longDir=LONG_R; static const Direction primDir=L; static const int ptypeMask= (1< struct DirectionTraitsGen
            { static const int blackDx=1; static const int blackDy=1; static const bool canPromoteTo=false; static const Direction altDir=UR; static const Direction longDir=LONG_DL; static const Direction primDir=UR; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=0; static const int blackDy=1; static const bool canPromoteTo=false; static const Direction altDir=U; static const Direction longDir=LONG_D; static const Direction primDir=U; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=-1; static const int blackDy=1; static const bool canPromoteTo=false; static const Direction altDir=UL; static const Direction longDir=LONG_DR; static const Direction primDir=UL; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=1; static const int blackDy=-2; static const bool canPromoteTo=true; // no meaning static const Direction altDir=UUL; static const Direction longDir=UUL; static const Direction primDir=UUL; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const int blackDx=-1; static const int blackDy=-2; static const bool canPromoteTo=true; // no meaning static const Direction altDir=UUR; static const Direction longDir=UUR; static const Direction primDir=UUR; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=true; static const Direction altDir=LONG_DR; static const Direction longDir=LONG_UL; static const Direction primDir=UL; static const int blackDx=DirectionTraitsGen
              ::blackDx; static const int blackDy=DirectionTraitsGen
                ::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=true; static const Direction altDir=LONG_D; static const Direction longDir=LONG_U; static const Direction primDir=U; static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=true; static const Direction altDir=LONG_DL; static const Direction longDir=LONG_UR; static const Direction primDir=UR; static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=false; static const Direction altDir=LONG_R; static const Direction longDir=LONG_L; static const Direction primDir=L; static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=false; static const Direction altDir=LONG_L; static const Direction longDir=LONG_R; static const Direction primDir=L; static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=false; static const Direction altDir=LONG_UR; static const Direction longDir=LONG_DL; static const Direction primDir=UR; static const int blackDx=DirectionTraitsGen
                ::blackDx; static const int blackDy=DirectionTraitsGen
                ::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=false; static const Direction altDir=LONG_U; static const Direction longDir=LONG_D; static const Direction primDir=U; static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const int ptypeMask= (1< struct DirectionTraitsGen{ static const bool canPromoteTo=false; static const Direction altDir=LONG_UL; static const Direction longDir=LONG_DR; static const Direction primDir=UL; static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const int ptypeMask= (1< struct DirectionTraits{ // ã“れらを関数ã«ã™ã‚‹ã¨æŠ¼ã—è¾¼ã‚られる static const unsigned int mask=1<(Dir); static const bool isLong=(static_cast(Dir) >= LONG_UL); static const int blackDx=DirectionTraitsGen::blackDx; static const int blackDy=DirectionTraitsGen::blackDy; static const Offset blackOffset() { return Offset(blackDx,blackDy); } static const bool canPromoteTo=DirectionTraitsGen::canPromoteTo; static const Direction longDir=DirectionTraitsGen::longDir; static const int ptypeMask=DirectionTraitsGen::ptypeMask; static const int ptypeMaskNotKing=DirectionTraitsGen::ptypeMask & ~(1<::primDir; static const Direction altDir=DirectionTraitsGen::altDir; }; template struct DirectionPlayerTraits; template struct DirectionPlayerTraits{ static const Offset offset() { return DirectionTraits::blackOffset(); } static const Direction directionByBlack=Dir; }; template const Direction DirectionPlayerTraits::directionByBlack; template struct DirectionPlayerTraits{ static const Offset offset() { return -DirectionTraits::blackOffset(); } static const Direction directionByBlack=DirectionTraitsGen::altDir; }; template const Direction DirectionPlayerTraits::directionByBlack; template Offset Offset::make() { return DirectionPlayerTraits::offset(); } } // namespace osl #endif /* OSL_DIRECTIONTRAITS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/core/osl/hashKey.h0000644000000000000000000001374312316770314015746 0ustar rootroot/* hashKey.h */ #ifndef OSL_HASH_KEY_H #define OSL_HASH_KEY_H #include "osl/basic_type.h" #include "osl/bits/pieceStand.h" #include "osl/simpleState.h" #include namespace osl { namespace hash { struct BoardKey96 : public std::pair { BoardKey96() {} BoardKey96(const std::pair& src) : std::pair(src) { } uint32_t signature() const { return second; } size_t size() const { return 2; } uint64_t operator[](size_t i) const { return i ? first : second; } }; class HashGenTable; struct HashKey128Layout { uint64_t board64; uint32_t board32, piece_stand; }; /** * 手番をå«ã‚“ã ç›¤é¢ã®çŠ¶æ…‹ã®ãƒãƒƒã‚·ãƒ¥å€¤ã‚’ä¿æŒã™ã‚‹ãŸã‚ã®ã‚¯ãƒ©ã‚¹. * Board 96bit + é§’å°(piece stand) 32bit */ class HashKey128 : private HashKey128Layout { friend class HashGenTable; public: HashKey128() { board64 = board32 = piece_stand = 0; } HashKey128(uint64_t h0, uint32_t h1, uint32_t s) { board64 = h0; board32 = h1; piece_stand = s; } HashKey128(const HashKey128Layout& src) : HashKey128Layout(src) { } const BoardKey96 boardKey() const { return std::make_pair(board64, board32); } uint64_t boardKey64() const { return board64; } uint64_t signature() const { return board32; } /** æŒé§’ã‚‚å«ã‚“ã 64bitã®ãƒãƒƒã‚·ãƒ¥ */ uint64_t hash64() const { return board64 + pieceStand64(); } uint64_t pieceStand64() const { return Stand_Hash.toUint64(pieceStand()); } const PieceStand pieceStand() const{ return PieceStand(piece_stand); } const PieceStand blackStand() const { return PieceStand(piece_stand); } void setPieceStand(const PieceStand& p) { piece_stand=p.getFlags(); } /** * é§’å°ã®æƒ…報を除ã„ã¦åŒã˜ã‹ã©ã†ã‹. * 手番ãŒç•°ãªã‚‹ã‚‚ã®ã¯ç•°ãªã‚‹ã¨å®šç¾©ã™ã‚‹ */ bool isSameBoard(const HashKey128& key) const { return boardKey() == key.boardKey(); } HashKey128& operator+=(const HashKey128& r) { board64 += r.board64; board32 += r.board32; PieceStand new_stand(piece_stand); new_stand.addAtmostOnePiece(r.pieceStand()); piece_stand = new_stand.getFlags(); return *this; } HashKey128& operator-=(const HashKey128& r) { board64 -= r.board64; board32 -= r.board32; PieceStand new_stand(piece_stand); new_stand.subAtmostOnePiece(r.pieceStand()); piece_stand = new_stand.getFlags(); return *this; } void add(Move move) { board64 += move.intValue(); } void changeTurn() { board64 ^= static_cast(1); } void setPlayer(Player p) { board64 &= ~static_cast(1); board64 |= playerToIndex(p); } bool playerBit() const { return board64 & 1; } bool isPlayerOfTurn(Player p) const { return playerBit() == playerToIndex(p); } Player turn() const { return isPlayerOfTurn(BLACK) ? BLACK : WHITE; } /** * 乱数ã§åˆæœŸåŒ–. * pieceStandã«ã¯è§¦ã‚‰ãªã„ */ void setRandom(); size_t size() const { return 2; } uint64_t operator[](size_t i) const { return i ? board64 : board32; } struct StandHash { CArray HashMajorPawn; CArray HashPiece; StandHash(); uint64_t toUint64(PieceStand stand) const { int major_pawn = stand.get(PAWN)*9 + stand.get(ROOK)*3 + stand.get(BISHOP); int pieces = stand.get(GOLD)*125 + stand.get(SILVER)*25 + stand.get(KNIGHT)*5 + stand.get(LANCE); return HashMajorPawn[major_pawn] + HashPiece[pieces]; } }; static const StandHash Stand_Hash; }; inline bool operator==(const HashKey128& l, const HashKey128& r) { return l.boardKey() == r.boardKey() && l.pieceStand() == r.pieceStand(); } inline bool operator!=(const HashKey128& l, const HashKey128& r) { return !(l==r); } /** * setç­‰ã§ä½¿ã†ãŸã‚ã®ã¿ã®ä¸ç­‰å·. * full orderã§ã‚ã‚‹ã“ã¨ä»¥å¤–ã«æ·±ã„æ„味ã¯ãªã„ */ inline bool operator<(const HashKey128& l, const HashKey128& r) { if (l.pieceStand() < r.pieceStand()) return true; else if (r.pieceStand() < l.pieceStand()) return false; return l.boardKey() < r.boardKey(); } typedef HashKey128 HashKeyBase; typedef BoardKey96 BoardKey; class HashKey : public HashKeyBase { public: HashKey() :HashKeyBase(){} HashKey(const SimpleState&); const HashKey newHashWithMove(Move move) const; const HashKey newMakeMove(Move) const; const HashKey newUnmakeMove(Move) const; void dumpContents(std::ostream& os) const; void dumpContentsCerr() const; static const HashKey readFromDump(const std::string&); static const HashKey readFromDump(std::istream&); }; std::ostream& operator<<(std::ostream& os,const HashKey& h); class HashGenTable { static const CArray2d key; public: static void addHashKey(HashKey& hk,Square sq,PtypeO ptypeo) { assert(sq.isValid() && isValidPtypeO(ptypeo)); hk += HashKey128(key[sq.index()][ptypeo-PTYPEO_MIN]); } static void subHashKey(HashKey& hk,Square sq,PtypeO ptypeo) { assert(sq.isValid() && isValidPtypeO(ptypeo)); hk -= HashKey128(key[sq.index()][ptypeo-PTYPEO_MIN]); } }; } // namespace hash using hash::HashKey; using hash::HashGenTable; using hash::BoardKey; } // namespace osl namespace std { template struct hash; template <> struct hash{ unsigned long operator()(const osl::HashKey& h) const { return h.signature(); } }; template<> struct hash { unsigned long operator()(const osl::BoardKey& h) const { return h.signature(); } }; } // namespace stl #endif /* OSL_HASH_KEY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/0000755000000000000000000000000012316770314016021 5ustar rootrootlibosl-0.8.0.orig/core/osl/mobility/rookMobility.h0000644000000000000000000001173412316770314020663 0ustar rootroot/* rookMobility.h */ #ifndef MOBILITY_ROOK_MOBILITY_H #define MOBILITY_ROOK_MOBILITY_H #include "osl/mobility/countMobility.h" #include "osl/bits/boardTable.h" namespace osl { namespace mobility { /** * 盤上ã®é£›è»ŠãŠã‚ˆã³ç«œã®å‹•ã‘るマス */ struct RookMobility { public: /** * 縦方å‘, * P : é§’pã®æŒã¡ä¸» * countAll : 利ãã«é–¢ä¿‚ãªãå‹•ã‘るマス * countSafe : 相手ã®åˆ©ããŒãªã„å‹•ã‘るマス * 両方を求ã‚ã‚‹ */ template static void countVerticalBoth(const NumEffectState& state,Piece p,int& countAll,int& countSafe){ assert(p.ptype()==ROOK || p.ptype()==PROOK); assert(p.isOnBoard()); assert(p.owner()==P); const Square pos=p.square(); countMobilityBoth(P,state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); countMobilityBoth(P,state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); } static void countVerticalBoth(Player pl,const NumEffectState& state,Piece p,int& countAll,int& countSafe){ if(pl==BLACK) countVerticalBoth(state,p,countAll,countSafe); else countVerticalBoth(state,p,countAll,countSafe); } /** * 縦方å‘,利ãã«é–¢ä¿‚ãªãå‹•ã‘ã‚‹ãƒžã‚¹ã®æ•° */ template static int countVerticalAll(const NumEffectState& state,int num){ // const Square pos=p.square(); const Square posU=state.mobilityOf(U,num); const Square posD=state.mobilityOf(D,num); int count=posD.y()-posU.y()-2+ (state.pieceAt(posU).template canMoveOn

                () ? 1 : 0)+ (state.pieceAt(posD).template canMoveOn

                () ? 1 : 0); return count; } template static int countVerticalAll(const NumEffectState& state,Piece p){ return countVerticalAll

                (state,p.number()); } static int countVerticalAll(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countVerticalAll(state,p); else return countVerticalAll(state,p); } /** * 縦方å‘,相手ã®åˆ©ããŒãªã„å‹•ã‘るマスを求ã‚ã‚‹ */ template static int countVerticalSafe(const NumEffectState& state,Piece p){ const Square pos=p.square(); return countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset())+ countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset()); } static int countVerticalSafe(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countVerticalSafe(state,p); else return countVerticalSafe(state,p); } /** * 横方å‘, * P : é§’pã®æŒã¡ä¸» * countAll : 利ãã«é–¢ä¿‚ãªãå‹•ã‘るマス * countSafe : 相手ã®åˆ©ããŒãªã„å‹•ã‘るマス * 両方を求ã‚ã‚‹ */ template static void countHorizontalBoth(const NumEffectState& state,Piece p,int& countAll,int& countSafe){ assert(p.ptype()==ROOK || p.ptype()==PROOK); assert(p.isOnBoard()); assert(p.owner()==P); const Square pos=p.square(); countMobilityBoth(P,state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); countMobilityBoth(P,state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); } static void countHorizontalBoth(Player pl,const NumEffectState& state,Piece p,int& countAll,int& countSafe){ if(pl==BLACK) countHorizontalBoth(state,p,countAll,countSafe); else countHorizontalBoth(state,p,countAll,countSafe); } template static int countHorizontalAll(const NumEffectState& state,int num) { const Square posR=state.mobilityOf(R,num); const Square posL=state.mobilityOf(L,num); int count=(posL.x()-posR.x()-2)+ (state.pieceAt(posR).template canMoveOn

                () ? 1 : 0)+ (state.pieceAt(posL).template canMoveOn

                () ? 1 : 0); return count; } /** * 横方å‘,利ãã«é–¢ä¿‚ãªãå‹•ã‘ã‚‹ãƒžã‚¹ã®æ•° */ template static int countHorizontalAll(const NumEffectState& state,Piece p){ return countHorizontalAll

                (state,p.number()); } static int countHorizontalAll(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countHorizontalAll(state,p); else return countHorizontalAll(state,p); } /** * 横方å‘,相手ã®åˆ©ããŒãªã„å‹•ã‘るマスを求ã‚ã‚‹ */ template static int countHorizontalSafe(const NumEffectState& state,Piece p){ const Square pos=p.square(); return countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset())+ countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset()); } static int countHorizontalSafe(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countHorizontalSafe(state,p); else return countHorizontalSafe(state,p); } }; } } #endif /* MOBILITY_ROOK_MOBILITY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/mobilityTable.cc0000644000000000000000000000352212316770314021132 0ustar rootroot/* mobilityTable.cc */ #include "osl/mobility/mobilityTable.h" #include "osl/bits/ptypeTable.h" #include "osl/bits/boardTable.h" #include osl::mobility::MobilityTable::MobilityTable(osl::SimpleState const& state) { for(int num=32;num<=39;num++){ osl::Piece p=state.pieceOf(num); if(!p.isOnBoard()) continue; int moveMask=Ptype_Table.getMoveMask(p.ptype()); for(int i=0;i<8;i++){ Direction d=static_cast(i); if(p.owner()==WHITE) d=inverse(d); d=shortToLong(d); if((moveMask&dirToMask(d))==0) continue; Offset o=Board_Table.getOffsetForBlack(static_cast(i)); Square pos=p.square()+o; for(;state.pieceAt(pos).isEmpty();pos+=o) ; if(state.pieceAt(pos)==Piece::EDGE()) pos-=o; this->set(static_cast(i),num,pos); } } } std::ostream& osl::mobility::operator<<(std::ostream& os,osl::mobility::MobilityContent const& mc) { os << "["; for(int i=0;i<7;i++) os << mc.get(static_cast(i)) << ","; return os << mc.get(static_cast(7)) << "]"; } std::ostream& osl::mobility::operator<<(std::ostream& os,osl::mobility::MobilityTable const& mt) { os << "MobilityTable(\n"; for(int num=32;num<=39;num++){ os << "num=" << num << ",["; for(int i=0;i<8;i++){ Direction d=static_cast(i); os << " " << mt.get(d,num); } os << "]\n"; } return os << ")" << std::endl; } bool osl::mobility::operator==(MobilityTable const& mt1, MobilityTable const& mt2) { for(int num=32;num<=39;num++){ for(int i=0;i<8;i++){ Direction d=static_cast(i); if(mt1.get(d,num)!=mt2.get(d,num) ) return false; } } return true; } /* ------------------------------------------------------------------------- */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/countMobility.h0000644000000000000000000000406712316770314021042 0ustar rootroot/* countMobility.h */ #ifndef MOBILITY_COUNT_MOBILITY_H #define MOBILITY_COUNT_MOBILITY_H #include "osl/numEffectState.h" namespace osl { namespace mobility { /** * P : é§’pã®æŒã¡ä¸» * All : countAllを求ã‚ã‚‹ã‹ã©ã†ã‹? * Safe : countAllを求ã‚ã‚‹ã‹ã©ã†ã‹? * countAll : 利ãã«é–¢ä¿‚ãªãå‹•ã‘るマス * countSafe : 相手ã®åˆ©ããŒãªã„å‹•ã‘るマス * 両方を求ã‚ã‚‹ */ template inline void countMobilityBoth(const NumEffectState& state,Square pos,Offset o,int& countAll,int& countSafe){ assert(pos.isOnBoard()); assert(!o.zero()); Piece p; for(pos+=o;(p=state.pieceAt(pos)).isEmpty();pos+=o){ if(All) countAll++; if(Safe && !state.hasEffectAt(pos)) countSafe++; } if(p.canMoveOn

                ()){ if(All) countAll++; if(Safe && !state.hasEffectAt(pos)) countSafe++; } } inline void countMobilityBoth(Player P,const NumEffectState& state,Square pos,Offset o,int& countAll,int& countSafe){ if(P==BLACK) countMobilityBoth(state,pos,o,countAll,countSafe); else countMobilityBoth(state,pos,o,countAll,countSafe); } /** * 利ãã«é–¢ä¿‚ãªãå‹•ã‘ã‚‹ãƒžã‚¹ã®æ•° */ inline int countMobilityAll(Player pl,const NumEffectState& state,Square pos,Offset o) { int ret=0,dummy=0; if(pl==BLACK) countMobilityBoth(state,pos,o,ret,dummy); else countMobilityBoth(state,pos,o,ret,dummy); return ret; } /** * 相手ã®åˆ©ããŒãªã„å‹•ã‘るマスを求ã‚ã‚‹ */ inline int countMobilitySafe(Player pl,const NumEffectState& state,Square pos,Offset o) { int ret=0,dummy=0; if(pl==BLACK) countMobilityBoth(state,pos,o,dummy,ret); else countMobilityBoth(state,pos,o,dummy,ret); return ret; } } } #endif /* MOBILITY_ROOK_MOBILITY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/kingMobility.h0000644000000000000000000000254112316770314020635 0ustar rootroot/* kingMobility.h */ #ifndef _KING_MOBILITY_H #define _KING_MOBILITY_H #include "osl/basic_type.h" #include "osl/container.h" #include "osl/config.h" #include #ifndef OSL_USE_SSE #if !(defined _MSC_VER) && ! defined OSL_NO_SSE #define OSL_USE_SSE 1 #endif #endif namespace osl { namespace mobility { #if OSL_USE_SSE typedef long long v2di __attribute__ ((vector_size (16))); #endif class KingMobility{ union b128{ CArray,2> uc16; unsigned long long ul[2]; #if OSL_USE_SSE v2di v2; #endif } v #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; public: KingMobility() { assert(reinterpret_cast(this) % 16 == 0); } const CArray& operator[](Player p) const{ return v.uc16[p]; } CArray& operator[](Player p){ return v.uc16[p]; } KingMobility& operator=(KingMobility const& km){ #if OSL_USE_SSE v.v2=km.v.v2; #else v.uc16=km.v.uc16; #endif return *this; } bool operator==(KingMobility const& km) const{ #if 0 && OSL_USE_SSE41 return __builtin_ia32_ptestz128(v.v2,km.v.v2); #else return ((v.ul[0]^km.v.ul[0])|(v.ul[1]^km.v.ul[1]))==0; #endif } }; } using mobility::KingMobility; } #endif /* _KING_MOBILITY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/lanceMobility.h0000644000000000000000000000475212316770314020775 0ustar rootroot/* lanceMobility.h */ #ifndef MOBILITY_LANCE_MOBILITY_H #define MOBILITY_LANCE_MOBILITY_H #include "osl/mobility/countMobility.h" namespace osl { namespace mobility { /** * 盤上ã®é¦™è»Šã®å‹•ã‘るマス */ struct LanceMobility { public: /** * 縦方å‘, * P : é§’pã®æŒã¡ä¸» * countAll : 利ãã«é–¢ä¿‚ãªãå‹•ã‘るマス * countSafe : 相手ã®åˆ©ããŒãªã„å‹•ã‘るマス * 両方を求ã‚ã‚‹ */ template static void countBoth(const NumEffectState& state,Piece p,int& countAll,int& countSafe){ assert(p.ptype()==LANCE); assert(p.isOnBoard()); assert(p.owner()==P); const Square pos=p.square(); countMobilityBoth(P,state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); } static void countBoth(Player pl,const NumEffectState& state,Piece p,int& countAll,int &countSafe){ if(pl==BLACK) countBoth(state,p,countAll,countSafe); else countBoth(state,p,countAll,countSafe); } /** * 縦方å‘,利ãã«é–¢ä¿‚ãªãå‹•ã‘ã‚‹ãƒžã‚¹ã®æ•° */ template static int countAll(const NumEffectState& state,Square pos,int num){ const Square pos1=state.mobilityOf(DirectionPlayerTraits::directionByBlack,num); int count=(P==BLACK ? pos.y()-pos1.y() : pos1.y()- pos.y())-1+ (state.pieceAt(pos1).template canMoveOn

                () ? 1 : 0); return count; } template static int countAll(const NumEffectState& state,Piece p){ assert(p.ptype()==LANCE); assert(p.isOnBoard()); assert(p.owner()==P); return countAll

                (state,p.square(),p.number()); } static int countAll(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countAll(state,p); else return countAll(state,p); } /** * 縦方å‘,相手ã®åˆ©ããŒãªã„å‹•ã‘るマスを求ã‚ã‚‹ */ template static int countSafe(const NumEffectState& state,Piece p){ assert(p.ptype()==LANCE); assert(p.isOnBoard()); assert(p.owner()==P); const Square pos=p.square(); return countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset()); } static int countSafe(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countSafe(state,p); else return countSafe(state,p); } }; } } #endif /* MOBILITY_LANCE_MOBILITY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/mobilityTable.h0000644000000000000000000000365612316770314021004 0ustar rootroot/* mobilityTable.h */ #ifndef _MOBILITY_TABLE_H #define _MOBILITY_TABLE_H #include "osl/basic_type.h" #include "osl/simpleState.h" #include #include namespace osl { namespace mobility { union V4 { unsigned int lv; CArray uc; } #ifdef __GNUC__ __attribute__((aligned(4))) #endif ; /** * é§’æ¯Žã«æŒ‡å®šã®æ–¹å‘ã®åˆ©ãã‚’æŒã¤æœ€å¾Œã®Square. * 自分ã®é§’ã¸ã®åˆ©ãã‚‚å«ã‚€ * EDGEã¾ã§ã„ã * æ–¹å‘ã¯ã€Œé»’ã€ã‹ã‚‰è¦‹ãŸæ–¹å‘ã«å›ºå®š * ãã‚‚ãã‚‚ãã¡ã‚‰ã«åˆ©ããŒãªã„å ´åˆã‚„STANDã«ã‚ã‚‹å ´åˆã¯0 */ class MobilityContent { V4 v; public: MobilityContent() { clear(); } void clear(){ v.lv=0u; } const Square get(Direction d) const{ return Square::makeDirect(v.uc[((unsigned int)d)>>1]); } void set(Direction d,Square pos){ v.uc[((unsigned int)d)>>1]=static_cast(pos.uintValue()); } }; std::ostream& operator<<(std::ostream& os,MobilityContent const& mc); /** * 駒番å·ã‹ã‚‰MobilityContentã‚’å¾—ã‚‹ */ class MobilityTable { CArray table #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; public: MobilityTable(){} MobilityTable(SimpleState const& state); void set(Direction d,int num,Square pos){ assert(0<=(int)d && (int)d<=7); return table[num-32].set(d,pos); } const Square get(Direction d,int num) const{ assert(0<=(int)d && (int)d<=7); return table[num-32].get(d); } friend bool operator==(const MobilityTable& mt1,const MobilityTable& mt2); }; std::ostream& operator<<(std::ostream& os,MobilityTable const& mt); bool operator==(const MobilityTable&,const MobilityTable&); } using mobility::MobilityTable; } #endif /* _MOBILITY_TABLE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/mobility/bishopMobility.h0000644000000000000000000001012312316770314021164 0ustar rootroot/* bishopMobility.h */ #ifndef MOBILITY_BISHOP_MOBILITY_H #define MOBILITY_BISHOP_MOBILITY_H #include "osl/mobility/countMobility.h" #include namespace osl { namespace mobility { /** * 盤上ã®è§’ãŠã‚ˆã³é¦¬ãŒå‹•ã‘ã‚‹ãƒžã‚¹ã®æ•°ã‚’æ•°ãˆã‚‹ */ struct BishopMobility { public: /** * æ–œã‚æ–¹å‘, * P : é§’pã®æŒã¡ä¸» * countAll : 利ãã«é–¢ä¿‚ãªãå‹•ã‘るマス * countSafe : 相手ã®åˆ©ããŒãªã„å‹•ã‘るマス * 両方を求ã‚ã‚‹ */ template static void countBoth(const NumEffectState& state,Piece p,int& countAll,int& countSafe){ assert(p.ptype()==BISHOP || p.ptype()==PBISHOP); assert(p.isOnBoard()); assert(p.owner()==P); const Square pos=p.square(); countMobilityBoth(state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); countMobilityBoth(state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); countMobilityBoth(state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); countMobilityBoth(state,pos,DirectionPlayerTraits::offset(),countAll,countSafe); } static void countBoth(Player pl,const NumEffectState& state,Piece p,int& countAll,int& countSafe){ if(pl==BLACK) countBoth(state,p,countAll,countSafe); else countBoth(state,p,countAll,countSafe); } /** * æ–œã‚æ–¹å‘,利ãã«é–¢ä¿‚ãªãå‹•ã‘ã‚‹ãƒžã‚¹ã®æ•° */ template static int countAll(const NumEffectState& state,int num){ const Square posUL=state.mobilityOf(UL,num); const Square posUR=state.mobilityOf(UR,num); const Square posDL=state.mobilityOf(DL,num); const Square posDR=state.mobilityOf(DR,num); int count=posDR.y()-posUL.y()+ posDL.y()-posUR.y()-4+ (state.pieceAt(posUR).template canMoveOn

                () ? 1 : 0)+ (state.pieceAt(posDR).template canMoveOn

                () ? 1 : 0)+ (state.pieceAt(posUL).template canMoveOn

                () ? 1 : 0)+ (state.pieceAt(posDL).template canMoveOn

                () ? 1 : 0); return count; } template static int countAll(const NumEffectState& state,Piece p){ assert(p.ptype()==BISHOP || p.ptype()==PBISHOP); assert(p.isOnBoard()); assert(p.owner()==P); return countAll

                (state,p.number()); } static int countAll(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countAll(state,p); else return countAll(state,p); } template static int countAllDir(const NumEffectState& state,Piece p){ assert(p.ptype()==BISHOP || p.ptype()==PBISHOP); assert(p.isOnBoard()); assert(p.owner()==P); assert(Dir == UL || Dir == UR || Dir == DL || Dir == DR); Direction dir = (P == BLACK ? Dir : inverse(Dir)); const Square pos = state.mobilityOf(dir, p.number()); int count = std::abs(pos.y() - p.square().y()) - 1 + (state.pieceAt(pos).template canMoveOn

                () ? 1 : 0); return count; } template static int countAllDir(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countAllDir(state,p); else return countAllDir(state,p); } /** * æ–œã‚æ–¹å‘,相手ã®åˆ©ããŒãªã„å‹•ã‘るマスを求ã‚ã‚‹ */ template static int countSafe(const NumEffectState& state,Piece p){ assert(p.ptype()==BISHOP || p.ptype()==PBISHOP); assert(p.isOnBoard()); assert(p.owner()==P); const Square pos=p.square(); return countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset())+ countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset())+ countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset())+ countMobilitySafe(P,state,pos,DirectionPlayerTraits::offset()); } static int countSafe(Player pl,const NumEffectState& state,Piece p){ if(pl==BLACK) return countSafe(state,p); else return countSafe(state,p); } }; } } #endif /* MOBILITY_BISHOP_MOBILITY_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/simpleState.h0000644000000000000000000002260512316770314016641 0ustar rootroot/* simpleState.h */ #ifndef OSL_SIMPLE_STATE_H #define OSL_SIMPLE_STATE_H #include "osl/basic_type.h" #include "osl/bits/ptypeTable.h" #include "osl/bits/boardTable.h" #include "osl/bits/ptypeTraits.h" #include "osl/bits/pieceMask.h" #include "osl/bits/bitXmask.h" #include "osl/bits/effectContent.h" #include "osl/container.h" #include namespace osl { enum Handicap{ HIRATE, // KYOUOCHI, // KAKUOCHI, }; class SimpleState; std::ostream& operator<<(std::ostream& os,const SimpleState& state); /** * 盤上ã®é§’ã®ã¿ã‚’比較ã™ã‚‹ï¼ˆæŒã¡é§’ã¯è¦‹ãªã„). * ãªãŠã€é§’番ã«éžä¾å­˜ãªå±€é¢æ¯”較をã—ãŸã„å ´åˆã¯ã€osl::record::CompactBoardã‚„ * osl::hash::HashKeyを用ã„ã‚‹. */ bool operator==(const SimpleState& st1,const SimpleState& st2); class SimpleState { private: friend std::ostream& operator<<(std::ostream& os,const SimpleState& state); friend bool operator==(const SimpleState& st1,const SimpleState& st2); typedef SimpleState state_t; public: static const bool hasPawnMask=true; protected: CArray board #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; /** * å…¨ã¦ã®pieceãŒç™»éŒ²ã•れã¦ã„ã‚‹ */ CArray pieces #ifdef __GNUC__ __attribute__((aligned(16))) #endif ; CArray stand_mask; CArray pawnMask; CArray,2> stand_count; /** 手番 */ Player player_to_move; PieceMask used_mask; public: // 生æˆã«é–¢ã™ã‚‹ã‚‚ã® explicit SimpleState(); explicit SimpleState(Handicap h); // public継承ã•ã›ã‚‹ã«ã¯ï¼Œvirtual destructorを定義ã™ã‚‹ï¼Ž virtual ~SimpleState(); /** 盤é¢ãŒç©ºã®çŠ¶æ…‹ã«åˆæœŸåŒ– */ void init(); /** ãƒãƒ³ãƒ‡ã‚£ã«å¿œã˜ãŸåˆæœŸçŠ¶æ…‹ã«åˆæœŸåŒ– */ void init(Handicap h); // private: void initPawnMask(); public: const Piece pieceOf(int num) const{ return pieces[num]; } void setPieceOf(int num,Piece p) { pieces[num]=p; } template const Piece kingPiece() const{ return pieceOf(KingTraits

                ::index); } const Piece kingPiece(Player P) const{ assert(isValid(P)); if (P==BLACK) return kingPiece(); else return kingPiece(); } template Square kingSquare() const{ return kingPiece

                ().square(); } Square kingSquare(Player player) const{ assert(isValid(player)); if (player==BLACK) return kingSquare(); else return kingSquare(); } template static int nthLimit() { return PtypeTraits::indexLimit - PtypeTraits::indexMin; } /** * unpromote(PTYPE)ã®n番目ã®é§’を帰ã™. * * 駒番å·ã«ä¾å­˜ã™ã‚‹ã®ã§é †ç•ªã¯ä¸å®š. */ template const Piece nth(int n) const { assert(0 <= n && n < nthLimit()); return pieceOf(PtypeTraits::indexMin+n); } void setBoard(Square sq,Piece piece) { board[sq.index()]=piece; } protected: PieceMask& standMask(Player p) { return stand_mask[p]; } public: const PieceMask& standMask(Player p) const { return stand_mask[p]; } const PieceMask& usedMask() const {return used_mask;} bool isOffBoard(int num) const{ return standMask(BLACK).test(num) || standMask(WHITE).test(num); } // protected: /** (internal) */ void clearPawn(Player pl,Square sq){ pawnMask[pl].clear(sq); } /** (internal) */ void setPawn(Player pl,Square sq){ pawnMask[pl].set(sq); } public: bool isPawnMaskSet(Player player, int x) const { return pawnMask[player].isSet(x); } template bool isPawnMaskSet(int x)const {return isPawnMaskSet(P,x); } /** xã®ç­‹ã«æ­©ã‚’打ã¦ã‚‹ */ bool canDropPawnTo(Player player, int x) const { return hasPieceOnStand(player) && ! isPawnMaskSet(player, x); } void setPiece(Player player,Square sq,Ptype ptype); void setPieceAll(Player player); /** * @param sq 㯠isOnboardを満ãŸã™ Square ã®12è¿‘å‚(8è¿‘å‚+桂馬ã®åˆ©ã) * ! isOnBoard(sq) ã®å ´åˆã¯ PIECE_EDGE を返㙠*/ const Piece pieceAt(Square sq) const { return board[sq.index()];} const Piece operator[](Square sq) const { return pieceAt(sq);} const Piece* getPiecePtr(Square sq) const { return &board[sq.index()];} const Piece pieceOnBoard(Square sq) const { assert(sq.isOnBoard()); return pieceAt(sq); } bool isOnBoard(int num) const { return pieceOf(num).isOnBoard(); } /** * æŒé§’ã®æžšæ•°ã‚’æ•°ãˆã‚‹ */ int countPiecesOnStand(Player pl,Ptype ptype) const { assert(isBasic(ptype)); return stand_count[pl][ptype-PTYPE_BASIC_MIN]; } /** å¾Œæ–¹äº’æ› */ template int countPiecesOnStand(Player pl) const { return countPiecesOnStand(pl, Type); } bool hasPieceOnStand(Player player,Ptype ptype) const{ return countPiecesOnStand(player, ptype)!=0; } template bool hasPieceOnStand(Player P) const { return countPiecesOnStand(P, T); } private: int countPiecesOnStandBit(Player pl,Ptype ptype) const { return (standMask(pl).getMask(0) & Ptype_Table.getMaskLow(ptype)).countBit(); } public: /** * diffæ–¹å‘ã«ã‚ã‚‹Piece を求ã‚ã‚‹. * @return 盤外ãªã‚‰PTYPE_EDGE */ Piece nextPiece(Square cur, Offset diff) const { assert(! diff.zero()); cur += diff; while (pieceAt(cur) == Piece::EMPTY()) cur += diff; return pieceAt(cur); } void setTurn(Player player) { player_to_move=player; } Player turn() const{ return player_to_move; } /** * 手番を変更ã™ã‚‹ */ void changeTurn() { player_to_move = alt(player_to_move); } // check bool isConsistent(bool show_error=true) const; /** エラー表示をã™ã‚‹ã‹ã©ã†ã‹ã‚’templateパラメータã«ã—ãŸé«˜é€ŸåŒ–版 */ template bool isAlmostValidMove(Move move) const; /** * åˆæ³•手ã‹ã©ã†ã‹ã‚’ç°¡å˜ã«æ¤œæŸ»ã™ã‚‹ï¼Žå±€é¢ã«ä¾å­˜ã™ã‚‹ãƒã‚§ãƒƒã‚¯ã®ã¿ï¼Ž * ルール上指ã›ãªã„手ã§ã‚ã‚‹å¯èƒ½æ€§ãŒã‚ã‚‹å ´åˆã¯ï¼ŒisValidMove を用ã„る. * * å±€é¢ã«ä¾å­˜ã™ã‚‹æ¤œæŸ»ã§ã‚‚,玉ã®ç´ æŠœãや王手を防ã„ã§ã„ã‚‹ã‹ï¼Œ * åƒæ—¥æ‰‹ï¼Œæ‰“æ­©è©°ã‹ã©ã†ã‹ã¯æ¤œæŸ»ã—ãªã„. */ bool isAlmostValidMove(Move move,bool show_error=true) const; /** * åˆæ³•手ã‹ã©ã†ã‹ã‚’検査ã™ã‚‹ï¼Ž * isValidMoveByRule, isAlmostValidMove ã‚’ãŠã“ãªã†ï¼Ž * 玉ã®ç´ æŠœãや王手を防ã„ã§ã„ã‚‹ã‹ï¼Œ * åƒæ—¥æ‰‹ï¼Œæ‰“æ­©è©°ã‹ã©ã†ã‹ã¯æ¤œæŸ»ã—ãªã„. */ bool isValidMove(Move move,bool show_error=true) const; protected: template bool isAlmostValidDrop(Move move) const; template bool testValidityOtherThanEffect(Move move) const; public: /** * 盤é¢ä»¥å¤–ã®éƒ¨åˆ†ã®å則ã®ãƒã‚§ãƒƒã‚¯ * */ static bool isValidMoveByRule(Move move,bool show_error); /** * @param from - マスã®ä½ç½® * @param to - マスã®ä½ç½® * @param offset - fromã‹ã‚‰toã¸ã®short offset * fromã¨toãŒã‚¯ã‚¤ãƒ¼ãƒ³ã§åˆ©ããŒã‚ã‚‹ä½ç½®é–¢ä¿‚ã«ã‚ã‚‹ã¨ã„ã†å‰æ * ã§ï¼Œé–“ãŒå…¨éƒ¨ç©ºç™½ã‹ã‚’ãƒã‚§ãƒƒã‚¯ * @param pieceExistsAtTo - toã«å¿…ãšé§’ãŒã‚ã‚‹ (toãŒç©ºç™½ã§ã‚‚å‹•ã) */ bool isEmptyBetween(Square from, Square to,Offset offset,bool pieceExistsAtTo=false) const #ifdef __GNUC__ __attribute__ ((pure)) #endif { assert(from.isOnBoard()); assert(! offset.zero()); assert(offset==Board_Table.getShortOffset(Offset32(to,from))); Square sq=from+offset; for (; pieceAt(sq).isEmpty(); sq+=offset) { if (!pieceExistsAtTo && sq==to) return true; } return sq==to; } /** * @param from - マスã®ä½ç½® * @param to - マスã®ä½ç½® * fromã¨toãŒã‚¯ã‚¤ãƒ¼ãƒ³ã§åˆ©ããŒã‚ã‚‹ä½ç½®é–¢ä¿‚ã«ã‚ã‚‹ã¨ã„ã†å‰æ * ã§ï¼Œé–“ãŒå…¨éƒ¨ç©ºç™½ã‹ã‚’ãƒã‚§ãƒƒã‚¯ */ bool #ifdef __GNUC__ __attribute__ ((pure)) #endif isEmptyBetween(Square from, Square to,bool noSpaceAtTo=false) const{ assert(from.isOnBoard()); Offset offset=Board_Table.getShortOffset(Offset32(to,from)); assert(! offset.zero()); return isEmptyBetween(from,to,offset,noSpaceAtTo); } /** dump: 自分を cerr ã«è¡¨ç¤ºã™ã‚‹ã€‚abort å‰ãªã©ã«ãƒ‡ãƒãƒƒã‚°ã«ä½¿ã† */ bool dump() const; /** * from ã§è¡¨ç¾ã•れãŸPieceã‚’new_ownerã®æŒé§’ã«ã—ãŸå±€é¢ã‚’作る. */ const SimpleState emulateCapture(Piece from, Player new_owner) const; /** * from ã‹ã‚‰to ã« ptypeã®æŒé§’を一枚渡ã—ãŸå±€é¢ã‚’作る. */ const SimpleState emulateHandPiece(Player from, Player to, Ptype ptype) const; const SimpleState rotate180() const; const SimpleState flipHorizontal() const; }; } // namespace osl #endif /* OSL_SIMPLE_STATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/additionalEffect.h0000644000000000000000000000352712316770314017576 0ustar rootroot#ifndef OSL_ADDITIONAL_EFFECT_H #define OSL_ADDITIONAL_EFFECT_H #include "osl/numEffectState.h" namespace osl { namespace effect_util { /** * 追加利ãを求ã‚ã‚‹ */ struct AdditionalEffect { private: static void find(const NumEffectState&, Square target, const PieceVector& direct_effects, PieceVector& black, PieceVector& white); template static int count(const NumEffectState&, Square target, Player attack); public: /** * target ã« attack ã®è¿½åŠ åˆ©ããŒä¸€ã¤ã§ã‚‚ã‚ã‚‹ã‹ï¼Ž * 相手ã®å½±åˆ©ããŒå…ˆã«ã‚ã‚‹å ´åˆã¯å¯¾è±¡ã¨ã—ãªã„. */ static bool hasEffect(const NumEffectState&, Square target, Player attack); static bool hasEffectStable(const NumEffectState&, Square target, Player attack); /** * target ã« attack ã®è¿½åŠ åˆ©ãを二ã¤ã¾ã§æ•°ãˆã‚‹. * 相手ã®å½±åˆ©ãã®é§’以é™ã¯å¯¾è±¡ã¨ã—ãªã„. */ static int count2(const NumEffectState&, Square target, Player attack); /** * target ã«å¯¾ã™ã‚‹è¿½åŠ åˆ©ãã®ã‚ã‚‹ Piece ã‚’ black, white ã«æ±‚ã‚ã‚‹. * [*] +KI -HI +HI ã®å ´åˆï¼Œ-HIã‚‚+HIもカウント. */ static void find(const NumEffectState&, Square target, PieceVector& black, PieceVector& white); static void count(const NumEffectState&, Square target, int& black, int& white); static int count(const NumEffectState& state, Player pl, Square target) { int black, white; count(state, target, black, white); return (pl == BLACK) ? black : white; } }; } // namespace effect_util using effect_util::AdditionalEffect; } // namespace osl #endif /* OSL_ADDITIONAL_EFFECT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/basic_type.h0000644000000000000000000011120612566322565016475 0ustar rootroot#ifndef OSL_BASIC_TYPE_H #define OSL_BASIC_TYPE_H #include "osl/config.h" #include #include #include namespace osl{ enum Player{ BLACK=0, WHITE= -1 }; constexpr Player alt(Player player){ return static_cast(-1-static_cast(player)); } constexpr int playerToIndex(Player player){ return -static_cast(player); } constexpr Player indexToPlayer(int n) { // assert(n == 0 || n == 1) return static_cast(-n); } constexpr int sign(Player player){ // int ret=1+(static_cast(player)<<1); // assert(ret==1 || ret== -1); return 1+(static_cast(player)<<1); } constexpr int playerToMask(Player player){ return static_cast(player); } // These codes are intentionally DECLARED and NOT IMPLEMENTED. // you will get link error here if you write code such as "value += v * piece.owner() == BLACK ? 1.0 : -1.0;" int operator+(Player, int); int operator+(int, Player); int operator-(Player, int); int operator-(int, Player); int operator*(Player, int); int operator*(int, Player); int operator/(Player, int); int operator/(int, Player); /** * castç­‰ã§ä½œã‚‰ã‚ŒãŸplayerãŒæ­£ã—ã„ã‹ã©ã†ã‹ã‚’返㙠*/ bool isValid(Player player); #if 0 template struct PlayerTraits; template<> struct PlayerTraits{ static const int offsetMul=1; static const int index=0; static const int mask=0; static const Player opponent=WHITE; }; template<> struct PlayerTraits{ static const int offsetMul=-1; static const int index=1; static const int mask= -1; static const Player opponent=BLACK; }; #endif std::ostream& operator<<(std::ostream& os,Player player); namespace misc { // Int2Type by LOKI template struct Int2Type{ enum { value=v }; }; template struct Type2Type{}; template struct Player2Type{ enum { value=P }; }; struct EmptyType{}; } // namespace misc using misc::Int2Type; using misc::Player2Type; /** é§’ã®ç¨®é¡žã‚’4ビットã§ã‚³ãƒ¼ãƒ‰åŒ–ã™ã‚‹ */ enum Ptype { PTYPE_EMPTY=0, PTYPE_EDGE=1, PPAWN=2, PLANCE=3, PKNIGHT=4, PSILVER=5, PBISHOP=6, PROOK=7, KING=8, GOLD=9, PAWN=10, LANCE=11, KNIGHT=12, SILVER=13, BISHOP=14, ROOK=15, PTYPE_MIN=0, PTYPE_BASIC_MIN=KING, PTYPE_PIECE_MIN=2, PTYPE_MAX=15, }; const int PTYPE_SIZE=PTYPE_MAX-PTYPE_MIN+1; std::istream& operator>>(std::istream& is, Ptype& ptype); std::ostream& operator<<(std::ostream& os,const Ptype ptype); /** * intç­‰ã‹ã‚‰castã—ã¦ä½œã£ãŸptypeãŒï¼Œæ­£ã—ã„範囲ã«å…¥ã£ã¦ã„ã‚‹ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯ */ bool isValid(Ptype ptype); /** * ptypeãŒç©ºç™½ã‚„EDGEã§ãªã„ã‹ã®ãƒã‚§ãƒƒã‚¯ */ constexpr bool isPiece(Ptype ptype) { // assert(isValid(ptype)); return static_cast(ptype)>=PTYPE_PIECE_MIN; } /** * ptypeãŒåŸºæœ¬åž‹(promoteã—ã¦ã„ãªã„)ã‹ã®ãƒã‚§ãƒƒã‚¯ */ inline bool isBasic(Ptype ptype) { assert(isValid(ptype)); return static_cast(ptype)>PROOK; } /** * ptypeãŒpromote後ã®åž‹ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯ */ inline bool isPromoted(Ptype ptype) { assert(isPiece(ptype)); return static_cast(ptype)(ptype)>GOLD; } /** * ptypeãŒpromote後ã®åž‹ã®æ™‚ã«ï¼Œpromoteå‰ã®åž‹ã‚’è¿”ã™ï¼Ž * promoteã—ã¦ã„ãªã„åž‹ã®æ™‚ã¯ãã®ã¾ã¾è¿”ã™ */ inline Ptype unpromote(Ptype ptype) { assert(isPiece(ptype)); Ptype ret=static_cast(static_cast(ptype)|8); assert(isPiece(ret)); return ret; } constexpr Ptype unpromoteSafe(Ptype ptype) { return (! isPiece(ptype)) ? ptype : unpromote(ptype); } /** * promoteå¯èƒ½ãªptypeã«å¯¾ã—ã¦ï¼Œpromote後ã®åž‹ã‚’返㙠* promoteä¸å¯ã®ptypeを与ãˆã¦ã¯ã„ã‘ãªã„. */ inline Ptype promote(Ptype ptype) { assert(canPromote(ptype)); Ptype ret=static_cast(static_cast(ptype)-8); assert(isPiece(ret)); return ret; } inline bool isMajorBasic(Ptype ptype) { return ptype >= 14; } inline bool isMajor(Ptype ptype) { assert(isPiece(ptype)); return isMajorBasic(unpromote(ptype)); } inline bool isMajorNonPieceOK(Ptype ptype) { return (static_cast(ptype)|8)>=14; } /** * Player + Ptype [-15, 15] * PtypeO ã® O 㯠Owner ã® O */ enum PtypeO { PTYPEO_MIN= PTYPE_EMPTY-16, PTYPEO_MAX= 15, }; #define NEW_PTYPEO(player,ptype) static_cast(static_cast(ptype)-(16&static_cast(player))) inline unsigned int ptypeOIndex(PtypeO ptypeo) { const int result = ptypeo - PTYPEO_MIN; assert(result >= 0); return result; } inline PtypeO newPtypeO(Player player,Ptype ptype) { return static_cast(static_cast(ptype)-(16&static_cast(player))); } inline Ptype getPtype(PtypeO ptypeO) { return static_cast(static_cast(ptypeO)& 15); } /** pieceã‚’promoteã•ã›ã‚‹. promoteä¸å¯ã®ptypeを与ãˆã¦ã¯ã„ã‘ãªã„.*/ inline PtypeO promote(PtypeO ptypeO) { assert(canPromote(getPtype(ptypeO))); PtypeO ret=static_cast(static_cast(ptypeO)-8); assert(isPiece(getPtype(ret))); return ret; } /** pieceを引数次第ã§promoteã•ã›ã‚‹ */ inline PtypeO promoteWithMask(PtypeO ptypeO,int promoteMask) { assert(promoteMask==0 || promoteMask==0x800000); PtypeO ret=static_cast(static_cast(ptypeO)-(promoteMask>>20)); return ret; } /** pieceã‚’unpromoteã•ã›ã‚‹. promoteã—ã¦ã„ãªã„ptypeを与ãˆã¦ã‚‚よㄠ*/ inline PtypeO unpromote(PtypeO ptypeO) { return static_cast(static_cast(ptypeO)|8); } bool isValidPtypeO(int ptypeO); /** * EMPTY, EDGEã§ã¯ãªã„ */ inline bool isPiece(PtypeO ptypeO) { assert(isValidPtypeO(ptypeO)); return isPiece(getPtype(ptypeO)); } inline Player getOwner(PtypeO ptypeO) { assert(isPiece(ptypeO)); return static_cast(static_cast(ptypeO)>>31); } /** unpromoteã™ã‚‹ã¨å…±ã«ï¼Œownerã‚’å転ã™ã‚‹ï¼Ž */ inline PtypeO captured(PtypeO ptypeO) { assert(isPiece(ptypeO)); return static_cast((static_cast(ptypeO)|8)^(~15)); } /** owner ã‚’å転ã™ã‚‹ */ inline PtypeO alt(PtypeO ptypeO) { assert(isPiece(ptypeO)); return static_cast(static_cast(ptypeO)^(~15)); } /** * Pieceã®æ™‚ã«ã¯owner ã‚’å転ã™ã‚‹ * */ inline PtypeO altIfPiece(PtypeO ptypeO) { int v=static_cast(ptypeO); return static_cast(v^((1-(v&15))&~15)); } inline bool canPromote(PtypeO ptypeO) { return canPromote(getPtype(ptypeO)); } /** * ptypeO㌠promote済ã¿ã‹ã©ã†ã‹ */ inline bool isPromoted(PtypeO ptypeO) { assert(isValidPtypeO(ptypeO)); return isPromoted(getPtype(ptypeO)); } const PtypeO PTYPEO_EMPTY=newPtypeO(BLACK,PTYPE_EMPTY); const PtypeO PTYPEO_EDGE __attribute__((unused)) = newPtypeO(WHITE,PTYPE_EDGE); std::ostream& operator<<(std::ostream& os,const PtypeO ptypeO); const int PTYPEO_SIZE=PTYPEO_MAX-PTYPEO_MIN+1; enum Direction{ SHORT_DIRECTION_MIN=0, SHORT8_DIRECTION_MIN=0, UL=0, U=1, UR=2, L=3, R=4, DL=5, D=6, DR=7, SHORT8_DIRECTION_MAX=7, UUL=8, UUR=9, LONG_DIRECTION_MIN=10, LONG_UL=10, LONG_U=11, LONG_UR=12, LONG_L=13, LONG_R=14, LONG_DL=15, LONG_D=16, LONG_DR=17, LONG_DIRECTION_MAX=17, DIRECTION_MIN=0, SHORT_DIRECTION_MAX=9, SHORT_DIRECTION_SIZE=10, DIRECTION_MAX=17, DIRECTION_INVALID_VALUE=18, DIRECTION_SIZE=18 }; constexpr bool isShort(Direction d){ return d<=SHORT_DIRECTION_MAX; } constexpr bool isShort8(Direction d){ return d<=SHORT8_DIRECTION_MAX; } constexpr bool isLong(Direction d){ return d>=LONG_DIRECTION_MIN; } constexpr Direction inverseUnsafe(Direction d){ return static_cast(7 - d); } constexpr Direction inverse(Direction d){ //assert(isShort8(d)) return inverseUnsafe(d); } /** * 8æ–¹å‘ã«ã¤ã„ã¦ï¼Œprimitiveãª4æ–¹å‘を求ã‚ã‚‹ */ constexpr Direction primDir(Direction d){ //assert(isShort8(d)) return (d<4) ? d : inverse(d); } /** * 8æ–¹å‘ã«ã¤ã„ã¦ï¼Œprimitiveãª4æ–¹å‘を求ã‚ã‚‹ * dã¨ã—ã¦knight, INVALIDãªã©ã‚‚æ¥ã‚‹ */ constexpr Direction primDirUnsafe(Direction d){ return (d<4) ? d : inverseUnsafe(d); } bool isValid(Direction d); constexpr Direction longToShort(Direction d){ //assert(isLong(d)) return static_cast(static_cast(d)-LONG_UL); } /** * 引数㫠longDirを与ãˆã¦ã¯ã„ã‘ãªã„ */ constexpr Direction shortToLong(Direction d){ //assert(isShort(d)) return static_cast(static_cast(d)+LONG_UL); } constexpr int dirToMask(Direction dir){ return (1<(dir)); } std::ostream& operator<<(std::ostream& os,const Direction d); /** * 座標. * 盤é¢ã®ã‚¤ãƒ³ãƒ‡ãƒƒã‚¯ã‚¹ * X, Yã‚‚1-9ã®ç¯„囲ã§è¡¨ã™ * Xã¯å³ã‹ã‚‰æ•°ãˆã‚‹ï¼ŽYã¯ä¸Šã‹ã‚‰æ•°ãˆã‚‹ * ãªãŠé§’å°ã¯0 *

                   * (A0)  ......................... (00)
                   * (A1)  ......................... (01)
                   * (A2) 92 82 72 62 52 42 32 22 12 (02)
                   * (A3) 93 83 73 63 53 43 33 23 13 (03)
                   * (A4) 94 84 74 64 54 44 34 24 14 (04)
                   * (A5) 95 85 75 65 55 45 35 25 15 (05)
                   * (A6) 96 86 76 66 56 46 36 26 16 (06)
                   * (A7) 97 87 77 67 57 47 37 27 17 (07)
                   * (A8) 98 88 78 68 58 48 38 28 18 (08)
                   * (A9) 99 89 79 69 59 49 39 29 19 (09)
                   * (AA) 9A 8A 7A 6A 5A 4A 3A 2A 1A (0A)
                   * (AB) ...........................(0B)
                   * (AC) ...........................(0C)
                   * (AD) ...........................(0D)
                   * (AE) ...........................(0E)
                   * (AF) ...........................(0F) 
                   * 
                */ class Square; bool operator==(Square l, Square r); /** * 座標ã®å·®åˆ† */ class Offset { public: enum { OFFSET_MIN=-0x100, ONBOARD_OFFSET_MIN=-0x88, OFFSET_ZERO=0, ONBOARD_OFFSET_MAX=0x88, OFFSET_MAX=0x100, ONBOARD_OFFSET_SIZE=0x88*2+1 }; static const int BOARD_HEIGHT=16; private: int offset; explicit Offset(int o) : offset(o) { } public: static const Offset makeDirect(int value) { return Offset(value); } int intValue() const { return offset; } public: static int makeOffset(int dx,int dy) { return dx*BOARD_HEIGHT + dy; } Offset(int dx,int dy) : offset(makeOffset(dx,dy)) { } Offset(Player, Direction); Offset() : offset(OFFSET_ZERO) { } template static Offset make(); // defined in directionTraits.h static const Offset ZERO() { return Offset(OFFSET_ZERO); } int #ifdef __GNUC__ __attribute__ ((pure)) #endif dx() const; int #ifdef __GNUC__ __attribute__ ((pure)) #endif dy() const; unsigned int index() const { return offset - OFFSET_MIN; } Offset& operator+=(Offset other) { offset += other.offset; return *this; } Offset& operator-=(Offset other){ offset -= other.offset; return *this; } const Offset operator+(Offset other) const { Offset result(*this); return result += other; } const Offset operator-(const Offset other) const { Offset result(*this); return result -= other; } const Offset operator*(const int mult) const { return static_cast(static_cast(offset)*mult); } const Offset operator-() const { return Offset(-offset); } /** * Player P ã‹ã‚‰ã¿ãŸ offset を黒番ã®ã‚‚ã®ã«å¤‰æ›´ã™ã‚‹ */ template const Offset blackOffset() const { return (P==BLACK) ? *this : -(*this); } bool zero() const { return offset == OFFSET_ZERO; } }; /** * @obsolete */ inline Offset newOffset(int dx,int dy){ return Offset(dx,dy); } inline bool operator==(Offset l, Offset r) { return l.intValue() == r.intValue(); } inline bool operator!=(Offset l, Offset r) { return ! (l == r); } inline bool operator<(Offset l, Offset r) { return l.intValue() < r.intValue(); } std::ostream& operator<<(std::ostream&, Offset); } #include "bits/directionTraits.h" namespace osl { class Square { unsigned int square; explicit Square(int p) : square(p) { } public: static const Square makeDirect(int value) { return Square(value); } unsigned int uintValue() const { return square; } enum { PIECE_STAND=0, MIN=0, SIZE=0x100 }; Square() : square(PIECE_STAND) { } static const Square STAND() { return Square(PIECE_STAND); } Square(int x, int y) : square((x*Offset::BOARD_HEIGHT)+y+1) { assert(square < SIZE); } /** * assertãªã—ã«ä½œã‚‹ */ static const Square makeNoCheck(int x, int y) { return Square((x*Offset::BOARD_HEIGHT)+y+1); } static const Square nth(unsigned int i) { return Square(i+MIN); } /** * 将棋ã¨ã—ã¦ã®X座標を返ã™. Squareã®å†…部表ç¾ã«ä¾å­˜ã—ãªã„. */ int x() const { return square >> 4; } /** * 将棋ã¨ã—ã¦ã®Y座標を返ã™. Squareã®å†…部表ç¾ã«ä¾å­˜ã—ãªã„. */ int y() const { return (square&0xf)-1; } /** * y+1を返㙠*/ int y1() const { return square&0xf; } unsigned int index() const { return square - MIN; } static unsigned int indexMax() { return SIZE - MIN; } int indexForOffset32() const { return square + (square&0xf0); } bool isPieceStand() const { return square == PIECE_STAND; } bool isOnBoardSlow() const; /** * 盤é¢ä¸Šã‚’表ã™ã‹ã©ã†ã‹ã®åˆ¤å®šï¼Ž * 1<=x() && x()<=9 && 1<=y() && y()<=9 * Squareã®å†…部表ç¾ã«ä¾å­˜ã™ã‚‹ï¼Ž */ bool isOnBoard() const { return (0xffffff88&(square-0x12)& ((unsigned int)((square&0x77)^0x12)+0xffffff77))==0; } /** * onBoardã‹ã‚‰8è¿‘å‚ã®ã‚ªãƒ•セットを足ã—ãŸç‚¹ãŒedgeã‹ã©ã†ã‹ã®åˆ¤å®š * ãã“ãã“速ããªã£ãŸï¼Ž */ bool isEdge() const { assert(!isPieceStand() && 0<=x() && x()<=10 && 0<=y() && y()<=10); return (0x88&(square-0x12)&((square&0x11)+0xf7))!=0; } bool isValid() const; const Square squareForBlack(Player player) const { return (player == BLACK) ? *this : makeDirect(Square(9,9).uintValue()+Square(1,1).uintValue()-uintValue()); } /** * 後手ã®å ´åˆã¯ç›¤é¢ã‚’引ã£ãり返ã™. * PIECE_STANDã®å ´åˆã¯æ‰±ãˆãªã„. */ template const Square squareForBlack() const{ return squareForBlack(P); } const Square rotate180() const { return squareForBlack(); } const Square rotate180EdgeOK() const { Square ret=makeDirect(Square(9,9).uintValue()+Square(1,1).uintValue()-uintValue()); return ret; } const Square rotate180Safe() const { if (isPieceStand()) return *this; return squareForBlack(); } const Square flipHorizontal() const { if (isPieceStand()) return *this; return Square(10-x(), y()); } static const Square onBoardMax(){ return Square(9,9); } static const Square onBoardMin(){ return Square(1,1); } /** * squareãŒONBOARD_MINã¨ONBOARD_MAXã®é–“ã«ã‚ã‚‹ */ bool isOnBoardRegion() const { return static_cast(index()-onBoardMin().index()) <= static_cast(onBoardMax().index()-onBoardMin().index()); } Square& operator++() { square += 1; return *this; } static int reverseX(int x) { return 10-x; } static int reverseY(int y) { return 10-y; } public: template static bool canPromoteY(int y) { return P == BLACK ? y <= 3 : y >= 7; } template bool canPromote() const{ return canPromote(P); } bool canPromote(Player player) const { if (player==BLACK) return (uintValue()&0xf)<=4; else return (uintValue()&0x8)!=0; } /** * 2ã¤ã®Square(onBoardã§ã‚ã‚‹ã“ã¨ãŒå‰æ)ãŒï¼Œ * xãŒç­‰ã—ã„ã‹yãŒç­‰ã—ã„ */ bool isULRD(Square sq) const{ assert(isOnBoard() && sq.isOnBoard()); unsigned int v=uintValue() ^ sq.uintValue(); return (((v+0xefull)^v)&0x110ull)!=0x110ull; } /** * 2ã¤ã®Square(onBoardã§ã‚ã‚‹ã“ã¨ãŒå‰æ)ã®xãŒç­‰ã—ã„ */ bool isUD(Square sq) const{ assert(isOnBoard() && sq.isOnBoard()); unsigned int v=uintValue() ^ sq.uintValue(); return (v&0xf0)==0; } /** * sqãŒPlayer Pã«ã¨ã£ã¦ä¸Š */ template bool isU(Square sq) const{ assert(isOnBoard() && sq.isOnBoard()); unsigned int v=uintValue() ^ sq.uintValue(); if(P==BLACK) return ((v|(uintValue()-sq.uintValue()))&0xf0)==0; else return ((v|(sq.uintValue()-uintValue()))&0xf0)==0; } /** * 2ã¤ã®Square(onBoardã§ã‚ã‚‹ã“ã¨ãŒå‰æ)ã®yãŒç­‰ã—ã„ */ bool isLR(Square sq) const{ assert(isOnBoard() && sq.isOnBoard()); unsigned int v=uintValue() ^ sq.uintValue(); return (v&0xf)==0; } Square& operator+=(Offset offset) { square += offset.intValue(); return *this; } Square& operator-=(Offset offset) { square -= offset.intValue(); return *this; } const Square operator+(Offset offset) const { Square result(*this); return result+=offset; } const Square operator-(Offset offset) const { Square result(*this); return result-=offset; } const Offset operator-(Square other) const { return Offset::makeDirect(square - other.square); } template bool yEq() { return (uintValue()&0xf)==(Y+1); } template typename std::enable_if::type yLe() { return (uintValue()&0xf)<=(Y+1); } template typename std::enable_if::type yLe() { return (uintValue()&0xc)==0; } template typename std::enable_if::type yGe() { return (uintValue()&0xf)>=(Y+1); } template typename std::enable_if::type yGe() { return (uintValue()&0x8)!=0; } template const Square neighbor() const { return *this + DirectionPlayerTraits::offset(); } template const Square back() const { return neighbor(); } const Square neighbor(Player P, Direction D) const; const Square back(Player P, Direction D) const; bool isNeighboring8(Square to) const; }; inline bool operator==(Square l, Square r) { return l.uintValue() == r.uintValue(); } inline bool operator!=(Square l, Square r) { return ! (l == r); } inline bool operator<(Square l, Square r) { return l.uintValue() < r.uintValue(); } inline bool operator>(Square l, Square r) { return l.uintValue() > r.uintValue(); } std::ostream& operator<<(std::ostream&, Square); class Piece; inline bool operator==(Piece l, Piece r); const int EMPTY_NUM=0x80; const int EDGE_NUM=0x40; /** * é§’. * é§’ã¯ptypeo(-15 - 15), 番å·(0-39), ãƒã‚¸ã‚·ãƒ§ãƒ³(0-0xff)ã‹ã‚‰ãªã‚‹ * 上ä½16 bitã§ptypeo, 8bitã§ç•ªå·, 8bitã§ãƒã‚¸ã‚·ãƒ§ãƒ³ã¨ã™ã‚‹ï¼Ž * 空ãマス㯠黒,PTYPE_EMPTY, ç•ªå· 0x80, ãƒã‚¸ã‚·ãƒ§ãƒ³ 0 * 盤外㯠白,PTYPE_EDGE, ç•ªå· 0x40, ãƒã‚¸ã‚·ãƒ§ãƒ³ 0 */ class Piece { int piece; Piece(int p) : piece(p) { } public: static const int SIZE=40; static const Piece makeDirect(int value) { return Piece(value); } int intValue() const { return piece; } static const Piece EMPTY() { return Piece(BLACK,PTYPE_EMPTY,EMPTY_NUM,Square::STAND()); } static const Piece EDGE() { return Piece(WHITE,PTYPE_EDGE,EDGE_NUM,Square::STAND()); } static const int BitOffsetPtype=16; static const int BitOffsetPromote=BitOffsetPtype+3; static const int BitOffsetMovePromote=BitOffsetPromote+4; Piece(Player owner, Ptype ptype, int num, Square square) : piece((static_cast(owner)<<20) +(static_cast(ptype)<((piece>>BitOffsetPtype)&0xf); } PtypeO ptypeO() const { return static_cast(piece>>BitOffsetPtype); } int number() const { return ((piece&0xff00)>>8); } const Square square() const { return Square::makeDirect(piece&0xff); } Piece& operator+=(Offset offset) { piece += offset.intValue(); return *this; } void setSquare(Square square) { piece = (piece&0xffffff00)+square.uintValue(); } public: /** * piece ãŒãƒ—レイヤーPã®æŒã¡ç‰©ã§ã‹ã¤ãƒœãƒ¼ãƒ‰ä¸Šã«ã‚ã‚‹é§’ã®å ´åˆã¯ true. * 敵ã®é§’ã ã£ãŸã‚Šï¼Œé§’å°ã®é§’ã ã£ãŸã‚Šï¼ŒPiece::EMPTY(), PIECE_EDGEã®å ´åˆã¯ false * @param P(template) - プレイヤー * @param piece - */ template bool isOnBoardByOwner() const { return isOnBoardByOwner(P); } /** * isOnBoardByOwner ã®é€šå¸¸é–¢æ•°ã®ãƒãƒ¼ã‚¸ãƒ§ãƒ³. */ bool isOnBoardByOwner(Player owner) const { if(owner==BLACK) return static_cast(static_cast(piece)&0x800000ff)>0; else return static_cast((-piece)&0x800000ff)>0; } /* æˆã‚‹. PROMOTEä¸å¯ãªpieceã«é©ç”¨ä¸å¯ */ const Piece promote() const { assert(canPromote(ptype())); return Piece(piece-0x80000); } /* æˆã‚Šã‚’戻ã™. PROMOTEä¸å¯ãªpieceã«é©ç”¨å¯ */ const Piece unpromote() const { return Piece((int)piece|0x80000); } /** * å–られãŸpieceを作æˆ. unpromoteã—ã¦ï¼ŒSquareã¯0ã« * ç›¸æ‰‹ã®æŒã¡ã‚‚ã®ã«ã™ã‚‹ */ const Piece captured() const { // return (Piece)((((int)piece|0x80000)&0xffffff00)^0xfff00000); // ã‚’optimizeã™ã‚‹ return Piece((piece&0xfff7ff00)^0xfff80000); } const Piece promoteWithMask(int promote_mask) const { assert(! (isPromoted() && promote_mask)); assert(promote_mask==0 || promote_mask==(1<<23)); return Piece(piece - (promote_mask>>(BitOffsetMovePromote-BitOffsetPromote))); } const Piece checkPromote(bool promotep) const { return Piece(piece - (promotep<<19)); } /** * promoteã—ãŸé§’ã‹ã©ã†ã‹ã‚’ãƒã‚§ãƒƒã‚¯ã™ã‚‹ */ bool isPromoted() const { return (piece&(1<<19))==0; } /** * promoteã—ã¦ã„ãªã„OnBoardã®é§’ã§ã‚ã‚‹ã“ã¨ã®ãƒã‚§ãƒƒã‚¯ * Lanceä½ã—ã‹ä½¿ã„é“ãŒãªã„? */ bool isOnBoardNotPromoted() const{ int mask=piece&((1<<19)|0xff); return mask>(1<<19); } bool isPromotedNotKingGold() const { assert(ptype()!=KING && ptype()!=GOLD); return isPromoted(); } bool isEmpty() const { return (piece&0x8000)!=0; } static bool isEmptyNum(int num) { return (num&0x80)!=0; } bool isEdge() const { return (piece&0x4000)!=0; } static bool isEdgeNum(int num){ assert(!isEmptyNum(num)); return (num&0x40)!=0; } static bool isPieceNum(int num){ return (num&0xc0)==0; } template bool isPtype() const{ return (piece&0xf0000)==((T)<(piece)>=0; } Player owner() const { assert(isPiece()); return static_cast(piece>>20); } private: public: /** Player Pã®é§’ãŒï¼Œthisã®ä¸Šã«ç§»å‹•ã§ãã‚‹ã‹? * PIECE_EMPTY 0x00008000 * BLACK_PIECE 0x000XxxYY X>=2, YY>0 * PIECE_EDGE 0xfff14000 * WHITE_PIECE 0xfffXxxYY X>=2, YY>0 * @return thisãŒç›¸æ‰‹ã®é§’ã‹EMPTYãªã‚‰true * @param P 手番 */ template bool canMoveOn() const { return canMoveOn(P); } bool canMoveOn(Player pl) const{ return pl == BLACK ? ((piece+0xe0000)&0x104000)==0 : piece>=0; } bool isOnBoard() const { assert(square().isValid()); return ! square().isPieceStand(); } }; inline bool operator<(Piece l, Piece r) { return l.intValue() < r.intValue(); } inline bool operator==(Piece l, Piece r) { return l.intValue() == r.intValue(); } inline bool operator!=(Piece l, Piece r) { return ! (l == r); } std::ostream& operator<<(std::ostream& os,const Piece piece); } /** move 関係ã§ã¤ã‹ã¾ãˆæ‰€ã®ãªã„エラーãŒã§ã‚‹ã¨ãã«å®šç¾©ã™ã‚‹ */ // #define MOVE_DEBUG #ifdef MOVE_DEBUG # include # define move_assert(x) assert(x) #else # define move_assert(x) #endif // 2009/12/10 以å‰ã®fromãŒä¸‹ä½ã«ã‚るパターン㨠// operator< ã‚’åŒã˜ã«ã—ãŸã„時ã«å®šç¾©ã™ã‚‹ï¼Ž // #define PRESERVE_MOVE_ORDER namespace osl { class SimpleState; /** 16bit 表ç¾*/ enum Move16 { MOVE16_NONE = 0, }; /** * 圧縮ã—ã¦ã„ãªã„ moveã®è¡¨ç¾ . * - invalid: isInvalid ä»¥å¤–ã®æ¼”ç®—ã¯ã§ããªã„ * - declare_win: isInvalid ä»¥å¤–ã®æ¼”ç®—ã¯ã§ããªã„ * - pass: from, to, ptype, oldPtype ã¯ã¨ã‚Œã‚‹ï¼Žplayer()ã¯ã¨ã‚Œãªã„. * * Pieceã¨promotepã‚’ãã‚ãˆã‚‹ -> 変ãˆã‚‹ï¼Ž * 下ä½ã‹ã‚‰ * 2009/12/10ã‹ã‚‰ * - to : 8 bit * - from : 8 bit * - capture ptype : 4 bit * - dummy : 3 bit * - promote? : 1 bit * - ptype : 4 bit - promote moveã®å ´åˆã¯promote後ã®ã‚‚ã® * - owner : signed * 2009/12/10ä»¥å‰ * - from : 8 bit * - to : 8 bit * - dummy : 3 bit * - promote? : 1 bit * - capture ptype : 4 bit * - ptype : 4 bit - promote moveã®å ´åˆã¯promote後ã®ã‚‚ã® * - owner : signed */ class Move { public: static const int BitOffsetPromote=Piece::BitOffsetMovePromote; // 23 private: int move; explicit Move(int value) : move(value) { } enum { INVALID_VALUE = (1<<8), DECLARE_WIN = (2<<8), BLACK_PASS = 0, WHITE_PASS = (-1)<<28, }; public: int intValue() const { return move; } /** é§’ã‚’å–らãªã„手を [0, 16305] ã«map */ unsigned int hash() const; /** 一局é¢è¾ºã‚Šã®åˆæ³•æ‰‹ã®æœ€å¤§å€¤ * é‡è¤‡ã—ã¦æ‰‹ã‚’生æˆã™ã‚‹ã“ã¨ãŒã‚ã‚‹å ´åˆã¯ï¼Œ600ã§ã¯ä¸è¶³ã‹ã‚‚ã—れãªã„ */ static const unsigned int MaxUniqMoves=600; private: void init(Square from, Square to, Ptype ptype, Ptype capture_ptype, bool is_promote, Player player) { move = (to.uintValue() + (from.uintValue()<<8) + (static_cast(capture_ptype)<<16) + (static_cast(is_promote)<(ptype)<<24) + (static_cast(player)<<28)); } public: Move() : move(INVALID_VALUE) { } /** INVALID ã§ã‚‚ PASS ã§ã‚‚ãªã„. isValid()ã‹ã©ã†ã‹ã¯åˆ†ã‹ã‚‰ãªã„.*/ bool isNormal() const { // PASS ã‚„ INVALID 㯠to() ㌠00 return move & 0x00ff; } bool isPass() const { return (move & 0xffff) == 0; } static const Move makeDirect(int value) { return Move(value); } static const Move PASS(Player P) { return Move(P<<28); } static const Move INVALID() { return Move(INVALID_VALUE); } static const Move DeclareWin() { return Move(DECLARE_WIN); } /** * 移動 */ Move(Square from, Square to, Ptype ptype, Ptype capture_ptype, bool is_promote, Player player) { move_assert(from.isValid()); move_assert(to.isOnBoard()); move_assert(isValid(ptype)); move_assert(isValid(capture_ptype)); move_assert(isValid(player)); init(from, to, ptype, capture_ptype, is_promote, player); move_assert(isValid()); } /** * drop */ Move(Square to, Ptype ptype, Player player) { move_assert(to.isOnBoard()); move_assert(isValid(ptype)); move_assert(isValid(player)); init(Square::STAND(), to, ptype, PTYPE_EMPTY, false, player); move_assert(isValid()); } static const Move fromMove16(Move16, const SimpleState&); Move16 toMove16() const; const Square from() const { assert(! isInvalid()); move_assert(isValidOrPass()); const Square result = Square::makeDirect((move>>8) & 0xff); return result; } const Square to() const { assert(! isInvalid()); move_assert(isValidOrPass()); const Square result = Square::makeDirect(move & 0xff); return result; } /** fromã¨toã‚’ã¾ã¨ã‚ã¦åŒä¸€æ€§ã®åˆ¤å®šãªã© */ unsigned int fromTo() const { return move & 0xffff; } /** * pieceã«ä½¿ã†ãŸã‚ã®maskãªã®ã§ */ int promoteMask() const { assert(isNormal()); return (static_cast(move)&(1<((move >> 24) & 0xf); return result; } /** 移動後ã®Ptype, i.e., æˆã‚‹æ‰‹ã ã£ãŸå ´åˆæˆã£ãŸå¾Œ */ PtypeO ptypeO() const { assert(! isInvalid()); const PtypeO result = static_cast(move >> 24); return result; } /** 移動å‰ã®PtypeO, i.e., æˆã‚‹æ‰‹ã ã£ãŸå ´åˆæˆã‚‹å‰ */ PtypeO oldPtypeO() const { assert(! isInvalid()); const PtypeO result = static_cast((move>>24)+((move >> (BitOffsetPromote-3))&8)); return result; } /** 移動å‰ã®Ptype, i.e., æˆã‚‹æ‰‹ã ã£ãŸå ´åˆæˆã‚‹å‰ */ Ptype oldPtype() const { assert(! isInvalid()); move_assert(isValidOrPass()); const PtypeO old_ptypeo = static_cast((move>>24)+((move >> (BitOffsetPromote-3))&8)); return getPtype(old_ptypeo); } Ptype capturePtype() const { assert(isNormal()); const Ptype result = static_cast((move>>16)&0xf); return result; } PtypeO capturePtypeO() const { assert(isCapture()); return newPtypeO(alt(player()), capturePtype()); } PtypeO capturePtypeOSafe() const { if (! isCapture()) return PTYPEO_EMPTY; return capturePtypeO(); } Player player() const { assert(! isInvalid()); const Player result = static_cast(move>>28); return result; } bool isValid() const; /** state ã« apply å¯èƒ½ã§ãªã„å ´åˆã«true */ bool isInvalid() const { return static_cast(move-1) < DECLARE_WIN; } bool isValidOrPass() const { return isPass() || isValid(); } Move newFrom(Square new_from) const { assert(isNormal()); int result = static_cast(intValue()); result &= ~(0xff00); result += (new_from.uintValue()<<8); return makeDirect(result); } Move newAddFrom(Square new_from) const { assert(isNormal()); assert(from().uintValue()==0); int result = static_cast(intValue()); result += (new_from.uintValue()<<8); return makeDirect(result); } /** * no capture moveã‹ã‚‰capture moveを作る */ const Move newAddCapture(Piece capture) const { assert(! isCapture()); return makeDirect(intValue()+(capture.intValue()&0xf0000)); } const Move newCapture(Piece capture) const { return makeDirect((intValue()&0xfff0ffff)+(capture.intValue()&0xf0000)); } const Move newCapture(Ptype capture) const { return makeDirect((intValue()&0xfff0ffff) +(static_cast(capture)<(newPtype)<<24)); } template static bool ignoreUnpromote(Ptype ptype,Square from,Square to){ switch(ptype){ case PAWN: return to.canPromote

                (); case BISHOP: case ROOK: return to.canPromote

                () || from.canPromote

                (); case LANCE: return (P==BLACK ? to.y()==2 : to.y()==8); default: return false; } } /** * åˆæ³•手ã§ã¯ã‚ã‚‹ãŒï¼Œæ‰“æ­©è©°ã‚絡ã¿ä»¥å¤–ã§ã¯æœ‰åˆ©ã«ã¯ãªã‚‰ãªã„手. * TODO é…ã„ */ template bool ignoreUnpromote() const{ assert(player()==P); if(isDrop()) return false; return ignoreUnpromote

                (ptype(),from(),to()); } bool ignoreUnpromote() const{ if(player()==BLACK) return ignoreUnpromote(); else return ignoreUnpromote(); } /** * Moveã‚’unpromoteã™ã‚‹ã¨cutUnpromoteãªMoveã«ãªã‚‹ */ template bool hasIgnoredUnpromote() const{ assert(player()==P); if(!isPromotion()) return false; switch(ptype()){ case PPAWN: return (P==BLACK ? to().y()!=1 : to().y()!=9); case PLANCE: return (P==BLACK ? to().y()==2 : to().y()==8); case PBISHOP: case PROOK: return true; default: return false; } } bool hasIgnoredUnpromote() const{ if(player()==BLACK) return hasIgnoredUnpromote(); else return hasIgnoredUnpromote(); } const Move rotate180() const; }; inline bool operator<(Move lhs, Move rhs) { #ifdef PRESERVE_MOVE_ORDER int l=lhs.intValue(); l=(l&0xffff0000)+((l>>8)&0xff)+((l<<8)&0xff00); int r=rhs.intValue(); r=(r&0xffff0000)+((r>>8)&0xff)+((r<<8)&0xff00); return l struct hash; template <> struct hash { unsigned long operator()(osl::Move m) const { return m.intValue(); } }; } // namespace stl #endif /* OSL_BASIC_TYPE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; coding:utf-8 // ;;; End: libosl-0.8.0.orig/core/osl/enterKing.h0000644000000000000000000000143212316770314016270 0ustar rootroot/* enterKing.h */ #ifndef OSl_ENTERKING_H #define OSl_ENTERKING_H #include "osl/numEffectState.h" namespace osl { namespace enter_king { struct EnterKing { static bool #ifdef __GNUC__ __attribute__ ((pure)) #endif canDeclareWin(const NumEffectState& state); template static bool #ifdef __GNUC__ __attribute__ ((pure)) #endif canDeclareWin(const NumEffectState& state); static bool canDeclareWin(const NumEffectState& state, int &drops); template static bool canDeclareWin(const NumEffectState& state, int &drops); }; } // namespace enter_king using enter_king::EnterKing; } // namespace osl #endif /* OSl_ENTERKING_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/usi.h0000644000000000000000000000353412316770314015147 0ustar rootroot/* usi.h */ #ifndef OSL_USI_H #define OSL_USI_H #include "osl/numEffectState.h" #include #include #include namespace osl { namespace usi { const Move strToMove(const std::string&, const NumEffectState&); PtypeO charToPtypeO(char); const std::string show(Move); const std::string show(PtypeO); const std::string show(Piece); const std::string show(const NumEffectState&); class ParseError : public std::invalid_argument { public: ParseError(const std::string& msg = "") : invalid_argument(msg) { } }; /** * 盤é¢ã‚’å–å¾—ã™ã‚‹. * board文字列ãŒä¸æ­£ãªã¨ãã¯ã€ParseErrorãŒthrowã•れる. * @param board USIã®æ–‡å­—列 * @param state boardã®è§£æžçµæžœãŒå‡ºåŠ›ã•れる */ void parseBoard(const std::string& board, NumEffectState&); /** [sfen | startpos ] moves ... */ void parse(const std::string& line, NumEffectState&); void parse(const std::string& line, NumEffectState& initial, std::vector& moves); NumEffectState makeState(const std::string& line); } /** * gnushogi ã§ä½¿ã‚れるフォーマット. * 何種類ã‹ã‚る. */ namespace psn { class ParseError : public std::invalid_argument { public: ParseError(const std::string& msg = "") : invalid_argument(msg) { } }; const Move strToMove(const std::string&, const SimpleState&); const Square strToPos(const std::string&); Ptype charToPtype(char); const std::string show(Move); const std::string show(Square); char show(Ptype); /** decorate capture by 'x', promote by '+', and unpromote by '=' */ const std::string showXP(Move); } } // osl #endif /* OSL_USI_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/random.cc0000644000000000000000000000041212316770314015755 0ustar rootroot#include "osl/random.h" #include #include unsigned int osl::misc::random() { static std::mt19937 mt_random; return mt_random(); } unsigned int osl::misc::time_seeded_random() { static std::mt19937 mt_random(time(0)); return mt_random(); } libosl-0.8.0.orig/core/osl/config.h0000644000000000000000000000123412316770314015607 0ustar rootroot#ifndef OSL_CONFIG_H #define OSL_CONFIG_H #include #define OSL_WORDSIZE 64 #ifndef MINIMAL # define ALLOW_KING_ABSENCE #endif // for helgrind or drd // #define OSL_USE_RACE_DETECTOR #ifdef OSL_USE_RACE_DETECTOR # ifndef OSL_NO_SSE # define OSL_NO_SSE 1 # endif #endif #ifdef _MSC_VER #pragma warning( disable : 4099 ) #pragma warning( disable : 4146 ) #pragma warning( disable : 4244 ) #pragma warning( disable : 4267 ) #pragma warning( disable : 4661 ) #pragma warning( disable : 4800 ) #pragma warning( disable : 4805 ) #pragma warning( disable : 4906 ) #pragma warning( disable : 4996 ) #define OSL_NO_SSE 1 #endif #endif /* _OSL_CONFIG_H */ libosl-0.8.0.orig/core/osl/oslConfig.h0000644000000000000000000001142612316770314016271 0ustar rootroot/* oslConfig.h */ #ifndef OSL_OSLCONFIG_H #define OSL_OSLCONFIG_H #include "osl/config.h" #include #include #include #include #include #include #include namespace osl { /** osl ã®å®Ÿè¡Œç’°å¢ƒã«é–¢ã™ã‚‹æŒ‡å®š */ struct OslConfig { static const int MaxThreads=64; /** compileæ™‚ã«æŒ‡å®šã•れãŸãƒ‡ã‚£ãƒ¬ã‚¯ãƒˆãƒªã‚’è¿”ã™. å®Ÿè¡Œæ™‚ã®æŒ‡å®šã¯ç’°å¢ƒå¤‰æ•°ãŒåŸºæœ¬ */ static const std::string& home(const std::string& initialize_if_first_invocation=""); static const char * home_c_str(); static const std::string gpsusiConf(); /** テストケースã®ãƒ‡ãƒ¼ã‚¿ */ static const std::string testPrivate(); static const std::string testPublic(); static const char *testPrivateFile(const std::string& filename); static const char *testPublicFile(const std::string& filename); static const char *testCsaFile(const std::string& filename); /** 標準ã®å®šè·¡ãƒ•ァイルを返㙠* @param filename specify to use non-standard file * (absolute path, or home()/data/filename otherwise) */ static const char *openingBook(const std::string& filenamme=""); static void setVerbose(bool verbose); static bool verbose(); static void showOslHome(); static void setNumCPUs(int ncpu); static int concurrency(); static int dfpnMaxDepth(); static void setDfpnMaxDepth(int); enum UsiMode { NoUSI, PortableUSI, ExtendedUSI }; static UsiMode usiMode(); static void setUsiMode(UsiMode new_mode=PortableUSI); static bool usiModeInSilent(); static void setUsiSilent(bool silent=true); static bool searchExactValueInOneReply(); static void setSearchExactValueInOneReply(bool new_value); static size_t residentMemoryUse(); static size_t memoryUseLimit() { return static_cast(memory_use_limit * memory_use_percent / 100.0); } static void setMemoryUseLimit(size_t limit) { memory_use_limit = limit; } static double memoryUseRatio() { return residentMemoryUse() * 1.0 / memoryUseLimit(); } static bool isMemoryLimitEffective() { return memory_use_limit != memory_use_limit_system_max && residentMemoryUse() > 0; } static void setMemoryUsePercent(double limit) { assert(limit > 0.0 && limit <= 100.0); limit = std::max(0.01, limit); limit = std::min(100.0, limit); memory_use_percent = limit; } /** @return standard deviation of normal distribution */ static unsigned int evalRandom() { return eval_random; } static void setEvalRandom(unsigned int sigma) { eval_random = sigma; } static void setUsiOutputPawnValue(int new_value) { usi_output_pawn_value = new_value; } static int usiOutputPawnValue() { return usi_output_pawn_value; } /** @return 0 not testing, 1 short test, 2 long test */ static int inUnitTest() { return in_unit_test; } static bool inUnitTestShort() { return in_unit_test == 1; } static bool inUnitTestLong() { return in_unit_test == 2; } static void setInUnitTest(int new_value) { in_unit_test = new_value; } /** è©•ä¾¡é–¢æ•°ç­‰ã‚’åˆæœŸåŒ–. mainã®ä¸­ã§ä¸€åº¦å‘¼ã¶å¿…è¦ãŒã‚ã‚‹ */ static void setUp(); static bool hasByoyomi(); static void setHasByoyomi(bool); static bool healthCheck(); static int resignThreshold(); static std::string configuration(); private: static const std::string makeHome(const std::string& first_try=""); static const std::string makeTest(); static const std::string makeTestPublic(); static bool isGoodDir(const std::string&); static void trySetDir(std::string&, const std::string&); static void showOslHome(const std::string&); static size_t memory_use_limit; static double memory_use_percent; static const size_t memory_use_limit_system_max; static unsigned int eval_random; static bool is_verbose; static const int default_ncpus; static int num_cpu; static volatile UsiMode usi_mode; static volatile bool usi_mode_silent; static int usi_output_pawn_value; static bool search_exact_value_in_one_reply, has_byoyomi; static volatile bool force_root_window; static volatile int root_window_alpha, root_window_beta; static volatile int in_unit_test; static int dfpn_max_depth; public: static std::mutex lock_io; // designed to be called before main static void registerInitializer(std::function); }; struct SetUpRegister { SetUpRegister(std::function f) { OslConfig::registerInitializer(f); } }; struct NoMoreMemory : std::runtime_error { NoMoreMemory() : std::runtime_error("memory exhausted") { } }; } #endif /* OSL_OSLCONFIG_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/progress.cc0000644000000000000000000005647512321267666016374 0ustar rootroot#include "osl/progress.h" #include "osl/eval/weights.h" #include "osl/eval/midgame.h" #include "osl/eval/minorPiece.h" #include "osl/additionalEffect.h" #include "osl/bits/centering5x3.h" #include "osl/oslConfig.h" #include #include bool osl::progress::ml:: operator==(const NewProgressData& l, const NewProgressData& r) { return l.progresses == r.progresses && l.attack5x5_progresses == r.attack5x5_progresses && l.stand_progresses == r.stand_progresses && l.effect_progresses == r.effect_progresses && l.defenses == r.defenses && l.rook == r.rook && l.bishop == r.bishop && l.gold == r.gold && l.silver == r.silver && l.promoted == r.promoted && l.king_relative_attack == r.king_relative_attack && l.king_relative_defense == r.king_relative_defense && l.non_pawn_ptype_attacked_pair == r.non_pawn_ptype_attacked_pair && l.non_pawn_ptype_attacked_pair_eval == r.non_pawn_ptype_attacked_pair_eval; } osl::CArray osl::progress::ml::NewProgress::attack_relative; osl::CArray osl::progress::ml::NewProgress::defense_relative; osl::CArray osl::progress::ml::NewProgress::stand_weight; osl::CArray osl::progress::ml::NewProgress::attack5x5_weight; osl::CArray osl::progress::ml::NewProgress::attack5x5_x_weight; osl::CArray osl::progress::ml::NewProgress::attack5x5_y_weight; osl::CArray osl::progress::ml::NewProgress::effectstate_weight; osl::CArray osl::progress::ml::NewProgress::king_relative_weight; osl::CArray osl::progress::ml::NewProgress::attacked_ptype_pair_weight; osl::CArray osl::progress::ml::NewProgress::pawn_facing_weight; osl::CArray osl::progress::ml::NewProgress::promotion37_weight; osl::CArray osl::progress::ml::NewProgress::piecestand7_weight; int osl::progress::ml::NewProgress::max_progress; bool osl::progress::ml::NewProgress::initialized_flag; bool osl::progress::ml::NewProgress::setUp(const char *filename) { if (initialized_flag) return true; static CArray effect_weight; static CArray effect_x_weight, effect_y_weight; static CArray effect_defense_weight; static CArray effect_per_effect; static CArray effect_per_effect_defense; static CArray effect_per_effect_y, effect_per_effect_x; std::ifstream is(filename); int read_count = 0; osl::eval::ml::Weights weights(25); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effect_weight[i] = val; ++read_count; } for (size_t i = 0; i < 225; ++i) { int val; is >> val; effect_x_weight[i] = val; ++read_count; } for (size_t i = 0; i < 225; ++i) { int val; is >> val; effect_y_weight[i] = val; ++read_count; } weights.resetDimension(25); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effect_defense_weight[i] = val; ++read_count; } weights.resetDimension(225); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effect_per_effect[i] = val; ++read_count; } weights.resetDimension(225); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effect_per_effect_defense[i] = val; ++read_count; } weights.resetDimension(2025); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effect_per_effect_y[i] = val; ++read_count; } weights.resetDimension(2025); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effect_per_effect_x[i] = val; ++read_count; } weights.resetDimension(Piece::SIZE); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; stand_weight[i] = val; ++read_count; } weights.resetDimension(1125); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; attack5x5_weight[i] = val; ++read_count; } weights.resetDimension(75); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; effectstate_weight[i] = val; ++read_count; } weights.resetDimension(5625); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; attack5x5_x_weight[i] = val; ++read_count; } weights.resetDimension(10125); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; attack5x5_y_weight[i] = val; ++read_count; } weights.resetDimension(4284); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; king_relative_weight[i] = val; ++read_count; } weights.resetDimension(262144); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; attacked_ptype_pair_weight[i] = val; ++read_count; } weights.resetDimension(10); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; pawn_facing_weight[i] = val; ++read_count; } weights.resetDimension(16); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; promotion37_weight[i] = val; ++read_count; } weights.resetDimension(56); for (size_t i = 0; i < weights.dimension(); ++i) { int val; is >> val; piecestand7_weight[i] = val; ++read_count; } { int val; is >> val; max_progress = val; ++read_count; #ifdef EVAL_QUAD while (((max_progress/ProgressScale) % 3) && max_progress > 0) --max_progress; #endif } for(int king_x=1;king_x<=9;king_x++){ for(int king_y=1;king_y<=9;king_y++){ Square king(king_x,king_y); int king_index=(king_x-1)*9+king_y-1; const Square center = Centering5x3::adjustCenter(king); const int min_x = center.x() - 2; const int min_y = center.y() - 1; int i=0; for (int dx=0; dx<5; ++dx) { for (int dy=0; dy<3; ++dy,++i) { const Square target(min_x+dx,min_y+dy); int index0=king_index*15+i; int index_a=index0*10; int index_d=index0*10; attack_relative[index_a]= effect_weight[index(king, target)] + effect_x_weight[indexX(king, target)] + effect_y_weight[indexY(king, target)]; defense_relative[index_d]= effect_defense_weight[index(king, target)]; for(int count=0;count<=8;count++){ attack_relative[index_a+count+1]= effect_per_effect[indexPerEffect(king, target, count)] + effect_per_effect_y[indexPerEffectY(king, target, count)] + effect_per_effect_x[indexPerEffectX(king, target, count)]; defense_relative[index_d+count+1]= effect_per_effect_defense[indexPerEffect(king, target, count)]; } } } } } for(int king_x=1;king_x<=5;king_x++) for(int promoted=0;promoted<=4;promoted++) for(int silver=0;silver<=4;silver++) for(int gold=0;gold<=4;gold++) for(int bishop=0;bishop<=2;bishop++) for(int rook=0;rook<=2;rook++){ int index0=promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook))); int index1=king_x - 1 + 5 * (promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook)))); attack5x5_x_weight[index1]+=attack5x5_weight[index0]; } for (int i=0; i(is); if (!initialized_flag) { std::cerr << "Failed to load NewProgress data " << read_count << " from file " << filename << std::endl; } return initialized_flag; } bool osl::progress::ml::NewProgress::setUp() { return setUp(defaultFilename().c_str()); } std::string osl::progress::ml::NewProgress::defaultFilename() { std::string filename = OslConfig::home(); filename += "/data/progress.txt"; return filename; } template void osl::progress::ml::NewProgress::progressOne( const NumEffectState &state, int &attack, int &defense) { const Square king = state.kingSquare

                (); const Square center = Centering5x3::adjustCenter(king); const int min_x = center.x() - 2; const int min_y = center.y() - 1; attack = defense = 0; Square kingRel=king; if(P==WHITE){ kingRel=kingRel.rotate180(); } int index0=((kingRel.x()-1)*9+kingRel.y()-1)*15; int index_a=index0*10 + (P==WHITE ? 10*14 : 0); for (int dx=0; dx<5; ++dx) { for (int dy=0; dy<3; ++dy) { const Square target(min_x+dx,min_y+dy); const int attack_count = state.countEffect(alt(P), target); const int defense_count = state.countEffect(P, target); attack += attack_count *attack_relative[index_a]+ attack_relative[index_a+std::min(attack_count,8)+1]; defense += defense_count * defense_relative[index_a]+ defense_relative[index_a+std::min(defense_count,8)+1]; if(P==BLACK){ index_a+=10; } else{ index_a-=10; } } } } template void osl::progress::ml::NewProgress::updateAttack5x5PiecesAndState( const NumEffectState &state) { const Square king = state.kingSquare

                (); const int min_x = std::max(1, king.x() - 2); const int max_x = std::min(9, king.x() + 2); const int min_y = std::max(1, king.y() - 2); const int max_y = std::min(9, king.y() + 2); effect_progresses[P] = 0; PieceMask mask; for (int y = min_y; y <= max_y; ++y) { for (int x = min_x; x <= max_x; ++x) { const Square target(x, y); const NumBitmapEffect effect = state.effectSetAt(target); const int effect_diff = effect.countEffect(alt(P)) - effect.countEffect(P); const int x_diff = std::abs(x - king.x()); const int y_diff = (P == WHITE ? king.y() - y : y - king.y()); int index = std::max(std::min(effect_diff, 2), -2) + 2 + 5 * x_diff + 5 * 3 * (y_diff + 2); effect_progresses[P] += effectstate_weight[index]; mask |= effect; } } updateAttack5x5Pieces

                (mask, state); } template void osl::progress::ml::NewProgress::updateAttack5x5Pieces( PieceMask mask, const NumEffectState& state) { const Player attack = alt(P); mask &= state.piecesOnBoard(attack); rook[attack] = mask.selectBit().countBit(); bishop[attack] = mask.selectBit().countBit(); gold[attack] = mask.selectBit().countBit(); silver[attack] = (mask & ~state.promotedPieces()).selectBit().countBit(); PieceMask promoted_pieces = mask & state.promotedPieces(); promoted_pieces.clearBit(); promoted_pieces.clearBit(); promoted[attack] = std::min(promoted_pieces.countBit(), 4); } template int osl::progress::ml::NewProgress::attack5x5Value( const NumEffectState &state) const { const Player attack = alt(P); int king_x = state.kingSquare

                ().x(); if (king_x > 5) king_x = 10 - king_x; const int king_y = (P == BLACK ? state.kingSquare

                ().y() : 10 - state.kingSquare

                ().y()); return (attack5x5_x_weight[index5x5x( rook[attack] + state.countPiecesOnStand(attack), bishop[attack] + state.countPiecesOnStand(attack), gold[attack] + state.countPiecesOnStand(attack), silver[attack] + state.countPiecesOnStand(attack), promoted[attack], king_x)] + attack5x5_y_weight[index5x5y( rook[attack] + state.countPiecesOnStand(attack), bishop[attack] + state.countPiecesOnStand(attack), gold[attack] + state.countPiecesOnStand(attack), silver[attack] + state.countPiecesOnStand(attack), promoted[attack], king_y)]); } void osl::progress::ml::NewProgress::updatePieceKingRelativeBonus( const NumEffectState &state) { const CArray kings = {{ state.kingSquare(BLACK), state.kingSquare(WHITE), }}; king_relative_attack.fill(0); king_relative_defense.fill(0); for (int i = 0; i < Piece::SIZE; ++i) { const Piece piece = state.pieceOf(i); if (piece.ptype() == osl::KING || !piece.isOnBoard()) continue; Player pl = piece.owner(); const int index_attack = indexRelative(piece.owner(), kings[alt(pl)], piece); const int index_defense = indexRelative(piece.owner(), kings[pl], piece) + 2142; king_relative_attack[pl] += king_relative_weight[index_attack]; king_relative_defense[pl] += king_relative_weight[index_defense]; } } template void osl::progress::ml::NewProgress:: updateNonPawnAttackedPtypePairOne(const NumEffectState& state) { PieceMask attacked = state.effectedMask(alt(Owner)) & state.piecesOnBoard(Owner); attacked.reset(state.kingPiece().number()); mask_t ppawn = state.promotedPieces().getMask() & attacked.selectBit(); attacked.clearBit(); attacked.orMask(PtypeFuns::indexNum, ppawn); PieceVector pieces; while (attacked.any()) { const Piece piece = state.pieceOf(attacked.takeOneBit()); pieces.push_back(piece); } typedef eval::ml::NonPawnAttackedPtypePair feature_t; int result = 0; MultiInt result_eval; for (size_t i=0; i(state); updateNonPawnAttackedPtypePairOne(state); } void osl::progress::ml::NewProgress:: updatePawnFacing(const NumEffectState& state) { PieceMask attacked = state.effectedMask(WHITE) & state.piecesOnBoard(BLACK); mask_t pawn = attacked.selectBit() & ~(state.promotedPieces().getMask()); int count = 0; while (pawn.any()) { const Piece p(state.pieceOf(pawn.takeOneBit()+PtypeFuns::indexNum*32)); if (state.hasEffectByPtypeStrict(WHITE, p.square())) ++count; } pawn_facing = pawn_facing_weight[count]; } template void osl::progress::ml:: NewProgress::promotion37One(const NumEffectState& state, int rank) { typedef eval::ml::Promotion37 feature_t; CArray count = {{ 0 }}; for (int x=1; x<=9; ++x) { const Square target(x, rank); if (! state[target].isEmpty()) continue; int a = state.countEffect(P, target); const int d = state.countEffect(alt(P), target); if (a > 0 && a == d) a += AdditionalEffect::hasEffect(state, target, P); if (a <= d) continue; const Ptype ptype = state.findCheapAttack(P, target).ptype(); if (isPiece(ptype) && ! isPromoted(ptype)) count[ptype]++; } for (int p=PTYPE_BASIC_MIN; p<=PTYPE_MAX; ++p) { if (count[p] > 0) { promotion37 += promotion37_weight[p]; promotion37_eval += feature_t::table[p]*sign(P); } if (count[p] > 1) { promotion37 += promotion37_weight[p-8]*(count[p]-1); promotion37_eval += feature_t::table[p-8]*(sign(P)*(count[p]-1)); } } } void osl::progress::ml::NewProgress:: updatePromotion37(const NumEffectState& state) { promotion37 = 0; promotion37_eval = MultiInt(); promotion37One(state, 3); promotion37One(state, 7); } void osl::progress::ml::NewProgress:: updatePieceStand7(const NumEffectState& state) { piecestand7 = 0; for (int z=0; z<2; ++z) { CArray stand = {{ 0 }}; int filled = 0; for (Ptype ptype: PieceStand::order) if (state.hasPieceOnStand(indexToPlayer(z), ptype)) stand[filled++] = ptype-PTYPE_BASIC_MIN; for (int i=0; i(state, progresses[BLACK], defenses[WHITE]); progressOne(state, progresses[WHITE], defenses[BLACK]); updateAttack5x5PiecesAndState(state); updateAttack5x5PiecesAndState(state); attack5x5_progresses[BLACK] = attack5x5Value(state); attack5x5_progresses[WHITE] = attack5x5Value(state); stand_progresses.fill(0); for (Ptype ptype: PieceStand::order) { const int black_count = state.countPiecesOnStand(BLACK, ptype); const int white_count = state.countPiecesOnStand(WHITE, ptype); for (int j = 0; j < black_count; ++j) { stand_progresses[WHITE] += stand_weight[Ptype_Table.getIndexMin(ptype) + j]; } for (int j = 0; j < white_count; ++j) { stand_progresses[BLACK] += stand_weight[Ptype_Table.getIndexMin(ptype) + j]; } } updatePieceKingRelativeBonus(state); updateNonPawnAttackedPtypePair(state); updatePawnFacing(state); updatePromotion37(state); updatePieceStand7(state); } template inline void osl::progress::ml::NewProgress::updateMain( const NumEffectState &new_state, Move last_move) { const Player altP=alt(P); assert(new_state.turn()==altP); assert(last_move.player()==P); const Square kb = new_state.kingSquare(), kw = new_state.kingSquare(); const BoardMask mb = new_state.changedEffects(BLACK), mw = new_state.changedEffects(WHITE); const bool king_move = last_move.ptype() == KING; if ((king_move && altP == BLACK) || mb.anyInRange(Board_Mask_Table5x3_Center.mask(kw)) || mw.anyInRange(Board_Mask_Table5x3_Center.mask(kw))) { progressOne(new_state,progresses[WHITE],defenses[BLACK]); } if ((king_move && altP == WHITE) || mw.anyInRange(Board_Mask_Table5x3_Center.mask(kb)) || mb.anyInRange(Board_Mask_Table5x3_Center.mask(kb))) { progressOne(new_state,progresses[BLACK],defenses[WHITE]); } const Ptype captured = last_move.capturePtype(); if (last_move.isDrop()) { const int count = new_state.countPiecesOnStand(P, last_move.ptype()) + 1; const int value = stand_weight[Ptype_Table.getIndexMin(last_move.ptype()) + count - 1]; stand_progresses[altP] -= value; } else if (captured != PTYPE_EMPTY) { Ptype ptype = unpromote(captured); const int count = new_state.countPiecesOnStand(P, ptype); const int value = stand_weight[(Ptype_Table.getIndexMin(ptype) + count - 1)]; stand_progresses[altP] += value; } if (king_move) { updatePieceKingRelativeBonus(new_state); } else { const CArray kings = {{ new_state.kingSquare(BLACK), new_state.kingSquare(WHITE), }}; if (!last_move.isDrop()) { const int index_attack = indexRelative

                (kings[altP], last_move.oldPtype(), last_move.from()); const int index_defense = indexRelative

                (kings[P], last_move.oldPtype(), last_move.from()) + 2142; king_relative_attack[P] -= king_relative_weight[index_attack]; king_relative_defense[P] -= king_relative_weight[index_defense]; } { const int index_attack = indexRelative

                (kings[altP], last_move.ptype(), last_move.to()); const int index_defense = indexRelative

                (kings[P], last_move.ptype(), last_move.to()) + 2142; king_relative_attack[P] += king_relative_weight[index_attack]; king_relative_defense[P] += king_relative_weight[index_defense]; } if (captured != PTYPE_EMPTY) { const int index_attack = indexRelative(kings[P], captured, last_move.to()); const int index_defense = indexRelative(kings[altP], captured, last_move.to()) + 2142; king_relative_attack[altP] -= king_relative_weight[index_attack]; king_relative_defense[altP] -= king_relative_weight[index_defense]; } } updateNonPawnAttackedPtypePair(new_state); updatePawnFacing(new_state); updatePromotion37(new_state); updatePieceStand7(new_state); } template void osl::progress::ml::NewProgress::updateSub( const NumEffectState &new_state, Move last_move) { const Player altP=alt(P); assert(new_state.turn()==altP); if (last_move.isPass()) return; const Square kb = new_state.kingSquare(), kw = new_state.kingSquare(); const BoardMask mb = new_state.changedEffects(BLACK), mw = new_state.changedEffects(WHITE); const bool king_move = last_move.ptype() == KING; const Ptype captured = last_move.capturePtype(); if ((king_move && altP == BLACK) || mb.anyInRange(Board_Mask_Table5x5.mask(kw)) || mw.anyInRange(Board_Mask_Table5x5.mask(kw))) { updateAttack5x5PiecesAndState(new_state); attack5x5_progresses[WHITE] = attack5x5Value(new_state); } else if (altP == WHITE &&(last_move.isDrop() || captured != PTYPE_EMPTY)) { attack5x5_progresses[WHITE] = attack5x5Value(new_state); } if ((king_move && altP == WHITE) || mw.anyInRange(Board_Mask_Table5x5.mask(kb)) || mb.anyInRange(Board_Mask_Table5x5.mask(kb))) { updateAttack5x5PiecesAndState(new_state); attack5x5_progresses[BLACK] = attack5x5Value(new_state); } else if (altP == BLACK && (last_move.isDrop() || captured != PTYPE_EMPTY)) { attack5x5_progresses[BLACK] = attack5x5Value(new_state); } updateMain

                (new_state, last_move); } osl::progress::ml::NewProgressDebugInfo osl::progress::ml::NewProgress::debugInfo() const { NewProgressDebugInfo info; info.black_values[NewProgressDebugInfo::ATTACK_5X3] = progresses[0]; info.black_values[NewProgressDebugInfo::DEFENSE_5X3] = defenses[0]; info.black_values[NewProgressDebugInfo::ATTACK5X5] = attack5x5_progresses[0]; info.black_values[NewProgressDebugInfo::STAND] = stand_progresses[0]; info.black_values[NewProgressDebugInfo::EFFECT5X5] = effect_progresses[0]; info.black_values[NewProgressDebugInfo::KING_RELATIVE_ATTACK] = king_relative_attack[0]; info.black_values[NewProgressDebugInfo::KING_RELATIVE_DEFENSE] = king_relative_defense[0]; info.black_values[NewProgressDebugInfo::NON_PAWN_ATTACKED_PAIR] = non_pawn_ptype_attacked_pair[0]; info.white_values[NewProgressDebugInfo::ATTACK_5X3] = progresses[1]; info.white_values[NewProgressDebugInfo::DEFENSE_5X3] = defenses[1]; info.white_values[NewProgressDebugInfo::ATTACK5X5] = attack5x5_progresses[1]; info.white_values[NewProgressDebugInfo::STAND] = stand_progresses[1]; info.white_values[NewProgressDebugInfo::EFFECT5X5] = effect_progresses[1]; info.white_values[NewProgressDebugInfo::KING_RELATIVE_ATTACK] = king_relative_attack[1]; info.white_values[NewProgressDebugInfo::KING_RELATIVE_DEFENSE] = king_relative_defense[1]; info.white_values[NewProgressDebugInfo::NON_PAWN_ATTACKED_PAIR] = non_pawn_ptype_attacked_pair[1]; return info; } namespace osl { namespace progress { namespace ml { template void osl::progress::ml::NewProgress::updateSub(const NumEffectState &new_state,Move last_move); template void osl::progress::ml::NewProgress::updateSub(const NumEffectState &new_state,Move last_move); } } } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/0000755000000000000000000000000012316770314017343 5ustar rootrootlibosl-0.8.0.orig/core/osl/move_classifier/shouldPromoteCut.h0000644000000000000000000000305212316770314023034 0ustar rootroot/* shouldPromoteCut.h */ #ifndef _SEARCH_SHOULDPROMOTECUT_H #define _SEARCH_SHOULDPROMOTECUT_H #include "osl/basic_type.h" #include "osl/bits/ptypeTable.h" namespace osl { /** * 探索ã§å‰å‘ãæžåˆˆã—ã¦è‰¯ã„æ¡ä»¶ã‚’ä¸€æ™‚çš„ã«æ›¸ã„ã¦ãŠã * * 効果を把æ¡ã—ãŸã‚‰æ‰‹ç”Ÿæˆã®æ®µéšŽã§ cut ã™ã‚‹ã®ãŒ better * TODO: ã‚ã¨ï¼Œ2段目ã¸ã®é¦™ã¯å¿…ãšæˆã‚‹ãƒã‚§ãƒƒã‚¯ã‚’ã„れる */ struct ShouldPromoteCut { template static bool canIgnore(Ptype ptype, Square from, Square to) { assert(! from.isPieceStand()); return (ptype==LANCE && (P==BLACK ? to.y()==2 : to.y()==8)) || (isBasic(ptype) && Ptype_Table.isBetterToPromote(ptype) && (to.canPromote

                () || from.canPromote

                ())); } /** * dropã§ãªã„ã“ã¨ãŒç¢ºå®šã—ã¦ã„ã‚‹å ´åˆ */ template static bool canIgnoreMove(Move move) { assert(! move.isDrop()); return canIgnore(move.ptype(), move.from(), move.to()); } /** * drop ã¯é€šã™ãƒã‚§ãƒƒã‚¯æœ‰ã‚Š */ template static bool canIgnoreAndNotDrop(Move move) { return (! move.isDrop()) && canIgnoreMove(move); } static bool canIgnoreAndNotDrop(Move move) { if (move.player() == BLACK) return canIgnoreAndNotDrop(move); else return canIgnoreAndNotDrop(move); } }; } // osl #endif /* _SHOULDPROMOTECUT_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/pawnDropCheckmate.h0000644000000000000000000000676212316770314023126 0ustar rootroot/* pawnDropCheckmate.h */ #ifndef OSL_MOVE_CLASSIFIER_PAWNDROPCHECKMATE_H #define OSL_MOVE_CLASSIFIER_PAWNDROPCHECKMATE_H #include "osl/numEffectState.h" #include "osl/bits/king8Info.h" namespace osl { namespace move_classifier { /** * 打歩詰ã®åˆ¤å®š. * @param P 指手(攻撃)å´ */ template struct PawnDropCheckmate { /** * kingSquare ã«å±…ã‚‹ alt(P)ã®çŽ‰ãŒ dir æ–¹å‘ã«é€ƒã’られるã‹. */ static bool canEscape(const NumEffectState& state, Square kingSquare, Direction dir, Square dropAt); /** 王ãŒå‰ä»¥å¤–ã«ç§»å‹•å¯èƒ½ã‹ */ static bool escape7(const NumEffectState& state, Square kingSquare, Square to); static bool isMember(const NumEffectState& state, Ptype ptype,Square from,Square to) { // 打歩 if (! from.isPieceStand()) return false; if (ptype != PAWN) return false; const Player Opponent = alt(P); const Piece king = state.template kingPiece(); const Square king_position = king.square(); // DirectionPlayerTraits? // 玉頭 if (king_position != (to + DirectionPlayerTraits::offset())) return false; // 玉ã§å–れãªã„ if (! state.hasEffectAt(P, to)) return false; if (King8Info(state.Iking8Info(Opponent)).liberty() != 0) return false; // 玉以外ã®é§’ã§å–れãªã„ if (state.safeCaptureNotByKing(to, king) != Piece::EMPTY()) return false; // ã©ã“ã«ã‚‚逃ã’られãªã„ return escape7(state, king_position, to); } }; } // namespace move_classifier } // namespace osl template bool #ifdef __GNUC__ __attribute__ ((pure)) #endif osl::move_classifier::PawnDropCheckmate

                :: canEscape(const NumEffectState& state, Square kingSquare, Direction dir, Square dropAt) { const Player Opponent = alt(P); const Square target = kingSquare + Board_Table.getOffset(Opponent, dir); const Piece p = state.pieceAt(target); if (p.isOnBoardByOwner()) return false; // 自分ã®é§’ãŒã„ãŸã‚‰ç§»å‹•ä¸èƒ½ if (target.isEdge()) return false; Piece attacker; if (! state.template hasEffectAt

                (target, attacker)) return true; // 利ããŒãªã„ if (attacker == Piece::EMPTY()) return false; // 攻撃å´ã«è¤‡æ•°ã®åˆ©ã assert(attacker.owner() == P); // drop ã«ã‚ˆã‚Šãµã•ãŒã‚ŒãŸåˆ©ããªã‚‰é€ƒã’られる // -OU // XXX+FU+HI // ã®å ´åˆã®XXXãªã©ï¼Ž const Offset shortOffset = Board_Table.getShortOffsetNotKnight(Offset32(target,dropAt)); if (shortOffset.zero()) return false; const Square attackFrom = attacker.square(); return shortOffset == Board_Table.getShortOffsetNotKnight(Offset32(dropAt,attackFrom)); } template bool #ifdef __GNUC__ __attribute__ ((pure)) #endif osl::move_classifier::PawnDropCheckmate

                :: escape7(const NumEffectState& state, Square king_position, Square to) { // U ã¯æ­© if (canEscape(state, king_position, UL, to)) return false; if (canEscape(state, king_position, UR, to)) return false; if (canEscape(state, king_position, L, to)) return false; if (canEscape(state, king_position, R, to)) return false; if (canEscape(state, king_position, DL, to)) return false; if (canEscape(state, king_position, D, to)) return false; if (canEscape(state, king_position, DR, to)) return false; return true; } #endif /* OSL_MOVE_CLASSIFIER_PAWNDROPCHECKMATE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/classifierTraits.h0000644000000000000000000000055312316770314023032 0ustar rootroot/* classifierTraits.h */ #ifndef OSL_CLASSIFIERTRAITS_H #define OSL_CLASSIFIERTRAITS_H namespace osl { namespace move_classifier { template struct ClassifierTraits { static const bool drop_suitable = true; }; } } #endif /* OSL_CLASSIFIERTRAITS_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/kingOpenMove.cc0000644000000000000000000000431312316770314022254 0ustar rootroot#include "osl/move_classifier/kingOpenMove.h" #include "osl/numEffectState.h" template template bool osl::move_classifier::KingOpenMove

                :: isMemberMain(const NumEffectState& state, Ptype, Square from, Square to, Square exceptFor) { assert(! from.isPieceStand()); Square king_position=state.template kingSquare

                (); if (king_position.isPieceStand()) return false; /** * 守ã£ã¦ã„る玉ãŒå‹•ã状æ³ã§ã¯å‘¼ã°ãªã„ */ assert(king_position != from); /** * openã«ãªã£ã¦ã—ã¾ã†ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯ */ Offset offset=Board_Table.getShortOffsetNotKnight(Offset32(king_position,from)); /** * 移動元ãŒçŽ‹ã®8æ–¹å‘ã§ãªã„ã‹ * openã«ãªã‚‰ãªã„ */ if(offset.zero() || offset==Board_Table.getShortOffsetNotKnight(Offset32(king_position,to))) return false; if(!state.isEmptyBetween(from,king_position,offset,true)) return false; Square pos=from; Piece p; for(pos-=offset;;pos-=offset){ // TODO: exceptFor を毎回ãƒã‚§ãƒƒã‚¯ã™ã‚‹å¿…è¦ãŒã‚ã‚‹ã®ã¯offsetæ–¹å‘ã®æ™‚ã ã‘ if (! ((hasException && (pos == exceptFor)) || (p=state.pieceAt(pos), p.isEmpty()))) break; assert(pos.isOnBoard()); } /** * ãã®ptypeoãŒãã®offsetã‚’å‹•ãã¨ã—ã¦æŒã¤ã‹ * 注: æŒã¤ => safe ã§ãªã„ => false を返㙠*/ if (! p.isOnBoardByOwner()) return false; return Ptype_Table.getEffect(p.ptypeO(),pos,king_position).hasEffect(); } namespace osl { // explicit template instantiation template struct move_classifier::KingOpenMove; template struct move_classifier::KingOpenMove; template bool move_classifier::KingOpenMove::isMemberMain(const NumEffectState&, Ptype,Square,Square,Square); template bool move_classifier::KingOpenMove::isMemberMain(const NumEffectState&, Ptype,Square,Square,Square); template bool move_classifier::KingOpenMove::isMemberMain(const NumEffectState&, Ptype,Square,Square,Square); template bool move_classifier::KingOpenMove::isMemberMain(const NumEffectState&, Ptype,Square,Square,Square); } // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/safeMove.h0000644000000000000000000000236712316770314021271 0ustar rootroot/* safeMove.h */ #ifndef OSL_MOVE_CLASSIFIER_SAFE_MOVE_H #define OSL_MOVE_CLASSIFIER_SAFE_MOVE_H #include "osl/move_classifier/kingOpenMove.h" #include "osl/move_classifier/classifierTraits.h" #include "osl/numEffectState.h" namespace osl { namespace move_classifier { /** * 元々,手番ã®çމã«çŽ‹æ‰‹ãŒã‹ã‹ã£ã¦ã„ãªã„状態ã§è‡ªæ®ºæ‰‹ã§ãªã„ã“ã¨ã‚’ãƒã‚§ãƒƒã‚¯. * DropMoveã®æ™‚ã«ã¯å‘¼ã¹ãªã„ */ template struct SafeMove { static bool isMember(const NumEffectState& state, Ptype ptype,Square from,Square to) { assert(! from.isPieceStand()); assert(state.pieceOnBoard(from).owner() == P); /** * 元々王手ãŒã‹ã‹ã£ã¦ã„ãªã„ã¨ä»®å®šã—ã¦ã„ã‚‹ã®ã§ï¼Œè‡ªåˆ†ã‚’ * å–り除ã„ãŸä¸Šã§hasEffectByを呼ã°ãªãã¦ã‚‚良ㄠ*/ if (ptype==KING) return ! state.template hasEffectAt(to); return ! KingOpenMove

                ::isMember(state,ptype,from,to); } }; template struct ClassifierTraits > { static const bool drop_suitable = false; static const bool result_if_drop = true; }; } } #endif /* OSL_MOVE_CLASSIFIER_SAFE_MOVE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/check_.h0000644000000000000000000000155112316770314020732 0ustar rootroot/* check_.h */ #ifndef OSL_MOVE_CLASSIFIER_CHECK_H #define OSL_MOVE_CLASSIFIER_CHECK_H #include "osl/move_classifier/openCheck.h" #include "osl/move_classifier/directCheck.h" namespace osl { namespace move_classifier { /** * @param 指ã™å´, alt(P)ã«çŽ‹æ‰‹ã‚’ã‹ã‘られるã‹åˆ¤å®š */ template struct Check { /** * promote move ã®æ™‚ ptypeã¯promote後ã®ã‚‚ã® */ static bool isMember(const NumEffectState& state, Ptype ptype,Square from,Square to){ if (DirectCheck

                ::isMember(state,ptype,to)) return true; if (from.isPieceStand()) return false; return OpenCheck

                ::isMember(state,ptype,from,to); } }; } // namespace move_classifier } // namespace osl #endif /* _MOVE_CLASSIFIER_CHECK_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/directCheck.h0000644000000000000000000000217512316770314021731 0ustar rootroot/* directCheck.h */ #ifndef OSL_MOVE_CLASSIFIER_DIRECTCHECK_H #define OSL_MOVE_CLASSIFIER_DIRECTCHECK_H #include "osl/basic_type.h" namespace osl { namespace move_classifier { template struct DirectCheck { static bool isMember(const NumEffectState& state, Ptype ptype, Square to) { /** * 最åˆã‹ã‚‰çŽ‹æ‰‹ã¨ã„ã†ã“ã¨ã¯ãªã„. */ assert(!state.template hasEffectAt

                (state.template kingSquare())); /** * stateã‚’å‹•ã‹ã—ã¦ã„ãªã„ã®ã§ï¼Œfromã«ã‚ã‚‹é§’ãŒtoã‹ã‚‰ã®åˆ©ãã‚’ * blockã™ã‚‹ã“ã¨ã¯ * ã‚ã‚‹ãŒï¼Œblockã•れãŸåˆ©ããŒçŽ‹æ‰‹ã ã£ãŸã¨ã™ã‚‹ã¨ï¼Œå‹•ã‹ã™å‰ã‹ã‚‰çŽ‹æ‰‹ * ã ã£ãŸã¨ã—ã¦çŸ›ç›¾ã™ã‚‹ã®ã§OK */ return state.hasEffectIf(newPtypeO(P,ptype),to, state.template kingSquare()); } template static bool isMember(const State& state, Ptype ptype, Square /*from*/, Square to) { return isMember(state, ptype, to); } }; } // namespace move_classifier } // namespace osl #endif /* _DIRECTCHECK_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/kingOpenMove.h0000644000000000000000000000427512316770314022125 0ustar rootroot/* kingOpenMove.h */ #ifndef OSL_MOVE_CLASSIFIER_KING_OPEN_MOVE_H #define OSL_MOVE_CLASSIFIER_KING_OPEN_MOVE_H #include "osl/move_classifier/classifierTraits.h" #include "osl/numEffectState.h" namespace osl { namespace move_classifier { /** * Pã®çŽ‹ã‚’open checkã«ã™ã‚‹æ‰‹ã§ãªã„ã“ã¨ã‚’ãƒã‚§ãƒƒã‚¯. * - P==move playerã®æ™‚ã¯è‡ªæ®ºæ‰‹ã‹ã©ã†ã‹ã®ãƒã‚§ãƒƒã‚¯ã«ä½¿ã†. * 王ãŒå‹•ãå ´åˆã«ã¯å‘¼ã¹ãªã„ * - P!=move playerã®æ™‚ã¯é€šå¸¸ã®open checkã‹ã©ã†ã‹ã«ä½¿ã†. * - DropMoveã®æ™‚ã«ã¯å‘¼ã¹ãªã„ */ template struct KingOpenMove { /** * king ãŒ59 * rookãŒ51->61ã®æ™‚,差㯠* OFFSET -8 -> U * OFFSET +8 -> D * ã¨ã¯ãªã‚‹ã®ã§ï¼Œä¸€ç›´ç·šã®ã‚ˆã†ãªæ°—ãŒã™ã‚‹ï¼ŽãŸã ã—,ãã‚‚ã¨ã‚‚, * 59 - 51ã¯pinã«ã¯ãªã‚‰ãªã„ã—,今㯠U -> Dã¯openã§ã¯ãªã„ã¨ã—ã¦ã„ã‚‹ã®ã§OK */ static bool isMember(const NumEffectState& state, Ptype /*ptype*/,Square from,Square to) { int num=state.pieceAt(from).number(); assert(Piece::isPieceNum(num)); if(!state.pinOrOpen(P).test(num)) return false; // from to kingãŒä¸€ç›´ç·šã«ä¸¦ã¹ã° false Square king=state.kingSquare

                (); return Board_Table.getShort8Unsafe

                (king,to) != Board_Table.getShort8

                (king,from); } /** * @param exceptFor ã“ã“ã‹ã‚‰ã®åˆ©ãã¯é™¤å¤– */ static bool isMember(const NumEffectState& state, Ptype ptype,Square from,Square to, Square exceptFor) { return isMemberMain(state, ptype, from, to, exceptFor); } private: template static bool #ifdef __GNUC__ __attribute__ ((pure)) #endif isMemberMain(const NumEffectState& state, Ptype ptype,Square from,Square to, Square exceptFor); }; template struct ClassifierTraits > { static const bool drop_suitable = false; static const bool result_if_drop = false; }; } // namespace move_classifier } // namespace osl #endif /* OSL_MOVE_CLASSIFIER_NOT_KING_OPEN_MOVE_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/openCheck.h0000644000000000000000000000151712316770314021417 0ustar rootroot/* openCheck.h */ #ifndef _MOVE_CLASSIFIER_OPENCHECK_H #define _MOVE_CLASSIFIER_OPENCHECK_H #include "osl/move_classifier/classifierTraits.h" #include "osl/move_classifier/kingOpenMove.h" #include "osl/numEffectState.h" namespace osl { namespace move_classifier { template struct OpenCheck { static bool isMember(const NumEffectState& state, Ptype ptype,Square from,Square to) { return KingOpenMove::isMember(state,ptype,from,to); } }; template struct ClassifierTraits > { static const bool drop_suitable = false; static const bool result_if_drop = false; }; } // namespace move_classifier } // namespace osl #endif /* _MOVE_CLASSIFIER_OPENCHECK_H */ // ;;; Local Variables: // ;;; mode:c++ // ;;; c-basic-offset:2 // ;;; End: libosl-0.8.0.orig/core/osl/move_classifier/moveAdaptor.h0000644000000000000000000000275512316770314022006 0ustar rootroot/* moveAdaptor.h */ #ifndef OSL_MOVE_CLASSIFIER_MOVE_ADAPTOR_H #define OSL_MOVE_CLASSIFIER_MOVE_ADAPTOR_H #include "osl/numEffectState.h" #include "osl/move_classifier/classifierTraits.h" namespace osl { namespace move_classifier { template struct MoveAdaptor { static bool isMember(const NumEffectState& state, Move m) { return Classifier::isMember(state, m.ptype(), m.from(), m.to()); } }; template