00001 #include "osl/record/record.h"
00002 #include "osl/record/csaIOError.h"
00003 #include "osl/apply_move/applyMove.h"
00004 #include <stack>
00005 #include <iostream>
00006
00007 osl::record::
00008 MoveRecord::MoveRecord(const Move& mv, int ni)
00009 : move(mv), nodeIndex(ni), time(0)
00010 {
00011 }
00012
00013 namespace osl
00014 {
00015 namespace record
00016 {
00017 IRecordStream::~IRecordStream(){}
00018
00019 ORecordStream::~ORecordStream(){}
00020
00021 const Move MoveRecord::getMove() const { return move; }
00022
00023 int MoveRecord::getNodeIndex() const { return nodeIndex; }
00024
00025 void MoveRecord::setTime(int t){
00026 time=t;
00027 }
00028
00029 void NodeRecord::addMoveRecord(int moveIndex){
00030 moves.push_back(moveIndex);
00031 }
00032
00033
00034 Record::Record(){ init(); }
00035
00036 void Record::init(){
00037 version="";
00038 playerNames[0]=playerNames[1]="";
00039 nrs.clear();
00040 nrs.push_back(NodeRecord());
00041 initialState.init(HIRATE);
00042 result = UNKNOWN;
00043 }
00044
00045 void Record::load(IRecordStream& irs){
00046 irs.load(this);
00047 }
00048 void Record::save(ORecordStream& ){
00049
00050 }
00051
00052 void Record::setVersion(const std::string& str){
00053 version=str;
00054 }
00055 void Record::setPlayer(Player player,const std::string& str){
00056 playerNames[player]=str;
00057 }
00058 const std::string& Record::getPlayer(Player player) const{
00059 return playerNames[player];
00060 }
00061 void Record::setInitialState(const SimpleState& state){
00062 initialState=state;
00063 initialState.initPawnMask();
00064 }
00065 const NumEffectState Record::getInitialState() const {
00066 if (! initialState.isConsistent(true))
00067 {
00068 const char *msg = "Record: bad initial state";
00069 std::cerr << msg << " " << __FILE__ << " " << __LINE__ << "\n";
00070 throw CsaIOError(msg);
00071 }
00072 return NumEffectState(initialState);
00073 }
00074 int Record::addNodeRecord(){
00075 nrs.push_back(NodeRecord());
00076 return nrs.size()-1;
00077 }
00078 int Record::addMoveRecord(const MoveRecord& moveRecord){
00079 mrs.push_back(moveRecord);
00080 return mrs.size()-1;
00081 }
00082 NodeRecord* Record::nodeOf(int index){
00083 return &nrs.at(index);
00084 }
00085 const NodeRecord* Record::nodeOf(int index) const{
00086 return &nrs.at(index);
00087 }
00088 MoveRecord* Record::moveOf(int index){
00089 if (static_cast<size_t>(index) >= mrs.size())
00090 return NULL;
00091 else
00092 return &mrs.at(index);
00093 }
00094 const MoveRecord* Record::moveOf(int index) const {
00095 if (static_cast<size_t>(index) >= mrs.size())
00096 return NULL;
00097 else
00098 return &mrs.at(index);
00099 }
00100 NodeRecord& Record::operator[](int index){
00101 return nrs.at(index);
00102 }
00103
00104 void RecordVisitor::addMoveAndAdvance(Move move){
00105 assert(state->isValidMove(move));
00106
00107 int newNode=rec->addNodeRecord();
00108 int newMove=rec->addMoveRecord(MoveRecord(move,newNode));
00109 (*rec)[nodeIndex].addMoveRecord(newMove);
00110 nodeIndex=newNode;
00111 lastMoveIndex=newMove;
00112
00113 assert(state->isConsistent() || ((std::cerr << move <<"\n"<< *state),0));
00114 ApplyMoveOfTurn::doMove(*state, move);
00115 assert(state->isConsistent() || ((std::cerr << move <<"\n"<< *state),0));
00116 for(boost::ptr_vector<record::RecordVisitorObserver>::iterator each = observers.begin(); each != observers.end(); ++each){
00117 each->update(this);
00118 }
00119 }
00120
00121
00122 std::ostream& operator<<(std::ostream& os,const MoveRecord & mr){
00123 return os << "MoveRecord(" <<
00124 mr.getNodeIndex() << ')';
00125 }
00126 #ifndef MINIMAL
00127 std::ostream& operator<<(std::ostream& os,Record & r){
00128 os << "Record(";
00129 os << "version=" << r.getVersion()
00130 << ",BLACK=" << r.getPlayer(BLACK)
00131 << ",WHITE=" << r.getPlayer(WHITE);
00132 os << ",initial=" << std:: endl << r.getInitialState() << std::endl;
00133 SimpleState initial_state=r.getInitialState();
00134 SimpleState state=initial_state;
00135 RecordVisitor visitor;
00136 visitor.setState(&state);
00137 visitor.setRecord(&r);
00138 NodeRecord* node=visitor.getNode();
00139 while(node->size()>0){
00140 int moveIndex=node->at(0);
00141 MoveRecord* mr=r.moveOf(moveIndex);
00142 Move move=mr->getMove();
00143 os << move << "," << mr->getTime() << "," << mr->getComment() << std::endl;
00144 node=r.nodeOf(mr->getNodeIndex());
00145 ApplyMoveOfTurn::doMove(state, move);
00146 assert(state.isConsistent());
00147 }
00148 os << state;
00149 os << initial_state;
00150 return os << ')';
00151 }
00152 #endif
00153
00154 const vector<Move> Record::getMoves() const {
00155 vector<Move> moves;
00156 vector<int> dummy_time;
00157 getMoves(moves, dummy_time);
00158 return moves;
00159 }
00160
00161 int readInt(std::istream& is)
00162 {
00163 int ret=0;
00164 CArray<char,4> cs;
00165 is.read(&cs[0],4);
00166 for (int i=0;i<4;i++) {
00167 ret = (ret<<8)|(cs[i]&255);
00168 }
00169 return ret;
00170 }
00171
00172 void
00173 writeInt(std::ostream& os, int n)
00174 {
00175 CArray<char,4> buf;
00176 for (int i = 0; i < 4; i++)
00177 {
00178 buf[i] = (n >> (8 * (4 - i - 1))) & 255;
00179 }
00180 os.write(&buf[0], 4);
00181 }
00182
00183 }
00184 }
00185
00186 void osl::record::
00187 Record::getMoves(vector<Move>& moves, vector<int>& times,
00188 vector<std::string>& comments,
00189 vector<SearchInfo>& info) const
00190 {
00191 const NodeRecord* node=nodeOf(0);
00192 while(node->size()>0){
00193 const int moveIndex=node->at(0);
00194 const MoveRecord* mr=moveOf(moveIndex);
00195 const Move move=mr->getMove();
00196 moves.push_back(move);
00197 times.push_back(mr->getTime());
00198 comments.push_back(mr->getComment());
00199 info.push_back(mr->info);
00200
00201 node=nodeOf(mr->getNodeIndex());
00202 }
00203 }
00204
00205 void osl::record::
00206 Record::getMoves(vector<Move>& moves, vector<int>& times) const
00207 {
00208 vector<std::string> dummy_comments;
00209 vector<SearchInfo> dummy_info;
00210 getMoves(moves, times, dummy_comments, dummy_info);
00211 }
00212
00213 osl::record::
00214 RecordVisitor::~RecordVisitor()
00215 {
00216 }
00217
00218
00219
00220
00221