void Position::move(const Move m) { // std::cerr << "Position::move(" << m.toString() << ");" << std::endl; // move_history.emplace_back(m); updateHashKey (m, m.from()); // needs to know square where moving tower is, i.e., pre or post move value -= moveValue (m, m.from()); // " bitb.move(m.from(), m.to(), turn); std::swap(tower[m.to()], tower[m.from()]); // swap towers assert (bitb.isOfficer(m.to(), turn) == tower[m.to()].isOfficer()); if (m.isOnPromotionSquare() && !tower[m.to()].isOfficer()) { // move promotes tower[m.to()].promote(); bitb.bits[turn+2] |= (1<<m.to()); } if (m.isJump()) { unsigned int other = !turn; for (unsigned int j = 0; j<m.size(); j++) { // captures unsigned int over = m.over(j); const bool iso = tower[over].isOfficer(); tower[m.to()].push_back(tower[over].pop()); // add captured stone to turns tower if ( iso && !tower[over].isOfficer()) bitb.degrade (over, other); else if (!iso && tower[over].isOfficer()) bitb.promote (over, other); // bitb.setGrade(over, other, tower[over].isOfficer()); if (tower[over].empty()) { // last stone of tower captured bitb.erase(over, other); } else if (tower[over].color() == turn) { // color switch bitb.switchColor(over, turn); } // if color remains same after hit, nothing to do. } } checkTowerKeys (m); // beside constructor only place where hash keys for a tower may not exist updateHashKey (m, m.to()); // needs to know square where moving tower is, i.e., pre or post move value += moveValue (m, m.to()); // " pos_stack.emplace(pos_key); assert(pos_key == generateKey()); assert(value == evaluateTowers()); switchTurn(); }
void ConfigManager::moveValue(lua_State* from, lua_State* to) { switch(lua_type(from, -1)){ case LUA_TNIL: lua_pushnil(to); break; case LUA_TBOOLEAN: lua_pushboolean(to, lua_toboolean(from, -1)); break; case LUA_TNUMBER: lua_pushnumber(to, lua_tonumber(from, -1)); break; case LUA_TSTRING: { size_t len; const char* str = lua_tolstring(from, -1, &len); lua_pushlstring(to, str, len); } break; case LUA_TTABLE: lua_newtable(to); lua_pushnil(from); // First key while(lua_next(from, -2)){ // Move value to the other state moveValue(from, to); // Value is popped, key is left // Move key to the other state lua_pushvalue(from, -1); // Make a copy of the key to use for the next iteration moveValue(from, to); // Key is in other state. // We still have the key in the 'from' state ontop of the stack lua_insert(to, -2); // Move key above value lua_settable(to, -3); // Set the key } default: break; } // Pop the value we just read lua_pop(from, 1); }
void Position::undo(const Move m) { // std::cerr << "Position::undo(" << m.toString() << ");" << std::endl; // move_history.pop_back(); switchTurn(); value -= moveValue (m, m.to()); updateHashKey (m, m.to()); bitb.move(m.to(), m.from(), turn); std::swap(tower[m.to()], tower[m.from()]); if (m.isPromotion()) { tower[m.from()].degrade(); bitb.bits[turn+2] &= ~(1<<m.from()); } if (m.isJump()) { unsigned int other = !turn; for (unsigned int j = m.size(); j; j--) { // cause unsigned unsigned int over = m.over(j-1); // substract here if (tower[over].empty()) { // last stone of tower was captured bitb.set(over, tower[m.from()].back()); } else if (tower[over].color() == turn) { // color change bitb.switchColor(over, other); } const bool iso = tower[over].isOfficer(); tower[over].push(tower[m.from()].pop_back()); // restore stone on top of tower if ( iso && !tower[over].isOfficer()) bitb.degrade (over, other); else if (!iso && tower[over].isOfficer()) bitb.promote (over, other); } } updateHashKey (m, m.from()); value += moveValue (m, m.from()); pos_stack.pop(); assert(pos_key == generateKey()); assert(value == evaluateTowers()); }
void ConfigManager::getConfigValue(const std::string& key, lua_State* toL) { lua_getglobal(L, key.c_str()); moveValue(L, toL); }