Changeset 239
- Timestamp:
- 03/09/07 16:38:11 (1 year ago)
- Files:
-
- 06/libkombilo/Makefile (modified) (1 diff)
- 06/libkombilo/abstractboard.cpp (modified) (1 diff)
- 06/libkombilo/cpptest.cpp (modified) (4 diffs)
- 06/libkombilo/libkombilo.i (modified) (1 diff)
- 06/libkombilo/process.py (modified) (2 diffs)
- 06/libkombilo/search.cpp (modified) (30 diffs)
- 06/libkombilo/search.h (modified) (13 diffs)
- 06/libkombilo/testsearch.py (modified) (3 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
06/libkombilo/Makefile
r210 r239 2 2 g++ -o cpptest -lsqlite3 -lboost_filesystem cpptest.o search.o sgfparser.o abstractboard.o 3 3 4 cpptest.o: cpptest.cpp 4 cpptest.o: cpptest.cpp search.h abstractboard.h sgfparser.h 5 5 g++ -c cpptest.cpp 6 6 7 search.o: search.cpp 7 search.o: search.cpp search.h abstractboard.h sgfparser.h 8 8 g++ -c search.cpp 9 9 10 sgfparser.o: sgfparser.cpp 10 sgfparser.o: sgfparser.cpp sgfparser.h 11 11 g++ -c sgfparser.cpp 12 12 13 abstractboard.o: abstractboard.cpp 13 abstractboard.o: abstractboard.cpp abstractboard.h 14 14 g++ -c abstractboard.cpp 15 15 06/libkombilo/abstractboard.cpp
r225 r239 84 84 if (DEBUG_ABSTRACTBOARD) printf("AB::abstractBoard(int) 0\n"); 85 85 boardsize = bs; 86 if (boardsize < 3) throw BoardError(); 86 if (boardsize < 3) throw BoardError(); // FIXME 87 87 status = new char[boardsize*boardsize+1]; 88 88 for (int i = 0; i < boardsize*boardsize; i++) 06/libkombilo/cpptest.cpp
r230 r239 29 29 gl.start_processing(); 30 30 directory_iterator end_itr; 31 string path = "/home/ug/go/kombilo/06/libkombilo";31 // string path = "/home/ug/go/kombilo/06/libkombilo"; 32 32 // string path = "/home/ug/go/gtl/reviews"; 33 // string path = "/home/ug/go/gogod06/2000"; 33 string path = "/home/ug/go/gogod06/1998"; 34 int counter = 0; 34 35 for(directory_iterator it(path); it != end_itr; ++it) { 35 36 string n = it->string(); … … 46 47 } 47 48 infile.close(); 48 gl.process(sgf.c_str(), path.c_str(), n.c_str()); 49 int flags = CHECK_FOR_DUPLICATES; // |OMIT_DUPLICATES; 50 if (gl.process(sgf.c_str(), path.c_str(), n.c_str(), "", flags)) 51 if (gl.process_results() & IS_DUPLICATE) printf("is duplicate: %d\n", counter); 52 counter++; 49 53 } 50 54 } 51 55 gl.finalize_processing(); 52 printf(" Processed %d games.\n", gl.size());56 printf("Now %d games in db.\n", gl.size()); 53 57 } 54 58 printf("%d games.\n", gl.size()); … … 90 94 91 95 // -------------------- do pattern search -------------------------------------- 92 gl.search(p, &so);96 // gl.search(p, &so); 93 97 94 98 // ------------------- print some information about current list of games ------------ 95 printf("num games: %d, num hits: %d\n", gl.size(), gl.numHits());99 // printf("num games: %d, num hits: %d\n", gl.size(), gl.numHits()); 96 100 // vector<string> res = gl.currentEntriesAsStrings(); 97 101 // for(vector<string>::iterator it = res.begin(); it != res.end(); it++) … … 100 104 101 105 // ------------------- print some statistics ------------------------------------------ 102 printf("Search pattern:\n"); 103 printf("%s\n", p.printPattern().c_str()); 104 printf("Continuations:\n"); 105 for(int y=0; y<p.sizeY; y++) { 106 for(int x=0; x<p.sizeX; x++) { 107 printf("%c", gl.lookupLabel(x,y)); 106 // printf("Search pattern:\n"); 107 // printf("%s\n", p.printPattern().c_str()); 108 // printf("Continuations:\n"); 109 // for(int y=0; y<p.sizeY; y++) { 110 // for(int x=0; x<p.sizeX; x++) { 111 // printf("%c", gl.lookupLabel(x,y)); 112 // } 113 // printf("\n"); 114 // } 115 // printf("\n"); 116 // printf("Statistics:\n"); 117 // printf("num hits: %d, num switched: %d, B wins: %d, W wins: %d\n", gl.num_hits, gl.num_switched, gl.Bwins, gl.Wwins); 118 119 // printf("Continuation | Black ( B wins / W wins ) | White (B wins / W wins) |\n"); 120 // for(int y=0; y<p.sizeY; y++) { 121 // for(int x=0; x<p.sizeX; x++) { 122 // if (gl.lookupLabel(x,y) != '.') { 123 // Continuation cont = gl.lookupContinuation(x,y); 124 // printf(" %c | %3d[%3d] ( %3d / %3d ) | %3d[%3d] ( %3d / %3d) | %1.1f / %1.1f \n", 125 // gl.lookupLabel(x,y), cont.B, cont.tB, cont.wB, cont.lB, cont.W, cont.tW, cont.wW, cont.lW, 126 // cont.wW*100.0/cont.W, cont.wB*100.0/cont.B); 127 // } 128 // } 129 // } 130 131 // ------------------- check for duplicates --------------------------------- 132 gl.reset(); 133 int nd = gl.find_duplicates(19); 134 printf("duplicates:\n"); 135 for(int i=0; i<nd; i++) { 136 // 1st method: retrieve_duplicates_VI 137 // vector<int> dupl_vector = gl.retrieve_duplicates_VI(i); 138 // for(vector<int>::iterator it = dupl_vector.begin(); it != dupl_vector.end(); it++) { 139 // printf("%s%s\n", gl.currentEntryAsString(*it).c_str(), gl.getSignature(*it).c_str()); 140 // } 141 142 // 2nd method: retrieve_duplicates_PI 143 int * dupl_vector = gl.retrieve_duplicates_PI(i); 144 int j = 0; 145 while(dupl_vector[j] != -1) { 146 printf("%s%s\n", gl.currentEntryAsString(dupl_vector[j]).c_str(), gl.getSignature(dupl_vector[j]).c_str()); 147 j++; 108 148 } 109 printf("\n"); 110 } 111 printf("\n"); 112 printf("Statistics:\n"); 113 printf("num hits: %d, num switched: %d, B wins: %d, W wins: %d\n", gl.num_hits, gl.num_switched, gl.Bwins, gl.Wwins); 149 delete [] dupl_vector; 114 150 115 printf("Continuation | Black ( B wins / W wins ) | White (B wins / W wins) |\n"); 116 for(int y=0; y<p.sizeY; y++) { 117 for(int x=0; x<p.sizeX; x++) { 118 if (gl.lookupLabel(x,y) != '.') { 119 Continuation cont = gl.lookupContinuation(x,y); 120 printf(" %c | %3d[%3d] ( %3d / %3d ) | %3d[%3d] ( %3d / %3d) | %1.1f / %1.1f \n", 121 gl.lookupLabel(x,y), cont.B, cont.tB, cont.wB, cont.lB, cont.W, cont.tW, cont.wW, cont.lW, 122 cont.wW*100.0/cont.W, cont.wB*100.0/cont.B); 123 } 124 } 151 printf("--------------------------------------------------- \n"); 125 152 } 126 153 06/libkombilo/libkombilo.i
r191 r239 5 5 namespace std { 6 6 %template(vectors) vector<string>; 7 %template(vectori) vector<int>; 7 8 }; 8 9 06/libkombilo/process.py
r219 r239 31 31 for filename in filenames: 32 32 # print filename 33 counter += 134 33 try: 35 34 file = open(filename) … … 41 40 42 41 path, fn = os.path.split(filename) 43 gl.process(sgf, path, fn) 42 if gl.process(sgf, path, fn, '', CHECK_FOR_DUPLICATES_STRICT): 43 if gl.process_results() & IS_DUPLICATE: 44 print 'duplicate', counter 45 else: print 'SGF error' 46 counter += 1 47 44 48 gl.finalize_processing() 45 49 print 'Processed %d games in %.2f seconds' % (counter, time.time()-starttime) 06/libkombilo/search.cpp
r230 r239 858 858 void Algorithm::branchpoint_process() {} 859 859 void Algorithm::endOfVariation_process() {} 860 void Algorithm::endgame_process( ) {}860 void Algorithm::endgame_process(bool commit) {} 861 861 void Algorithm::finalize_process() {} 862 862 int Algorithm::readDB(sqlite3* DB) { return 0; } … … 877 877 sprintf(sql, "create table if not exists algo_signature_%d ( id integer primary key, signature varchar(12) );", boardsize); 878 878 int rc = sqlite3_exec(db, sql, 0, 0, 0); 879 if (rc != SQLITE_OK) throw DBError(); 880 sprintf(sql, "create index if not exists sig_idx on algo_signature_%d(signature);", boardsize); 881 rc = sqlite3_exec(db, sql, 0, 0, 0); 879 882 if (rc != SQLITE_OK) throw DBError(); 880 883 } … … 972 975 } 973 976 974 void Algo_signature::endgame_process() throw(DBError) { 975 char* min_signature = symmetrize(signature, boardsize); 977 void Algo_signature::endgame_process(bool commit) throw(DBError) { 978 if (commit) { 979 char* min_signature = symmetrize(signature, boardsize); 980 char sql[100]; 981 sprintf(sql, "insert into algo_signature_%d (id, signature) values (?,?);", boardsize); 982 if (dbinsert1blob(db, sql, gid, min_signature, 12)) throw DBError(); 983 // for(int i=0; i<12; i++) printf("%c", min_signature[i]); printf("\n"); 984 delete [] min_signature; 985 } 976 986 delete [] signature; 987 } 988 989 void Algo_signature::finalize_process() { 990 } 991 992 char* Algo_signature::get_current_signature() { 993 return symmetrize(signature, boardsize); 994 } 995 996 vector<int> Algo_signature::search_signature(char* sig) { 997 // to be used during processing! (because we need the db) 977 998 char sql[100]; 978 sprintf(sql, "insert into algo_signature_%d (id, signature) values (?,?);", boardsize); 979 if (dbinsert1blob(db, sql, gid, min_signature, 12)) throw DBError(); 980 // for(int i=0; i<12; i++) printf("%c", min_signature[i]); printf("\n"); 981 delete [] min_signature; 982 } 983 984 void Algo_signature::finalize_process() { 985 } 986 999 sprintf(sql, "select id from algo_signature_%d where signature=? order by id", boardsize); 1000 sqlite3_stmt *ppStmt=0; 1001 vector<int> result; 1002 int rc = sqlite3_prepare(db, sql, -1, &ppStmt, 0); 1003 if (rc != SQLITE_OK || ppStmt==0) throw DBError(); 1004 rc = sqlite3_bind_blob(ppStmt, 1, sig, 12, SQLITE_TRANSIENT); 1005 if (rc != SQLITE_OK || ppStmt==0) throw DBError(); 1006 do { 1007 rc = sqlite3_step(ppStmt); 1008 if (rc != SQLITE_DONE && rc != SQLITE_ROW) throw DBError(); 1009 if (rc == SQLITE_ROW) { 1010 result.push_back(sqlite3_column_int(ppStmt, 0)); 1011 } 1012 } while (rc == SQLITE_ROW); 1013 rc = sqlite3_finalize(ppStmt); 1014 if (rc != SQLITE_OK) throw DBError(); 1015 return result; 1016 } 987 1017 988 1018 Algo_finalpos::Algo_finalpos(int bsize) : Algorithm(bsize) { … … 1048 1078 } 1049 1079 1050 void Algo_finalpos::endgame_process() throw(DBError) { 1051 char sql[100]; 1052 sprintf(sql, "insert into algo_finalpos_%d (id, data) values (?,?);", boardsize); 1053 if (dbinsert1blob(db, sql, gid, fp, 100)) throw DBError(); 1080 void Algo_finalpos::endgame_process(bool commit) throw(DBError) { 1081 if (commit) { 1082 char sql[100]; 1083 sprintf(sql, "insert into algo_finalpos_%d (id, data) values (?,?);", boardsize); 1084 if (dbinsert1blob(db, sql, gid, fp, 100)) throw DBError(); 1085 } 1054 1086 delete [] fp; 1055 1087 } … … 1226 1258 } 1227 1259 1260 bool Algo_finalpos::equal(unsigned int i1, unsigned int i2) { 1261 // not to be used during processing 1262 // i1, i2 correspond to game id's 1263 sqlite3_stmt *ppStmt=0; 1264 char sql[100]; 1265 sprintf(sql, "select data from algo_finalpos_%d where id = %d or id = %d", boardsize, i1, i2); 1266 int rc = sqlite3_prepare(db, sql, -1, &ppStmt, 0); 1267 if (rc != SQLITE_OK || ppStmt==0) return false; // FIXME: catch certain errors, (and/or throw DBError?) 1268 if (sqlite3_step(ppStmt) == SQLITE_ROW) { 1269 char* dd1 = (char*)sqlite3_column_blob(ppStmt, 0); 1270 char* d1 = new char[100]; 1271 for(int i=0; i<100; i++) d1[i] = dd1[i]; // FIXME: is this necessary? 1272 if (sqlite3_step(ppStmt) == SQLITE_ROW) { 1273 char* d2 = (char*)sqlite3_column_blob(ppStmt, 0); 1274 for(int i=0; i<100; i++) 1275 if (d1[i] != d2[i]) { 1276 delete [] d1; 1277 sqlite3_finalize(ppStmt); 1278 return false; 1279 } 1280 delete [] d1; 1281 sqlite3_finalize(ppStmt); 1282 return true; 1283 } 1284 delete [] d1; 1285 } 1286 sqlite3_finalize(ppStmt); 1287 return false; 1288 } 1289 1290 bool Algo_finalpos::equals_current(unsigned int id1) { 1291 // to be used only during processing 1292 // id1 here corresponds to a game id 1293 bool result = true; 1294 sqlite3_stmt *ppStmt=0; 1295 char sql[100]; 1296 sprintf(sql, "select data from algo_finalpos_%d where id = %d", boardsize, id1); 1297 int rc = sqlite3_prepare(db, sql, -1, &ppStmt, 0); 1298 if (rc != SQLITE_OK || ppStmt==0) return false; // FIXME: catch certain errors, (and/or throw DBError?) 1299 if (sqlite3_step(ppStmt) == SQLITE_ROW) { 1300 char* d = (char*)sqlite3_column_blob(ppStmt, 0); 1301 for(int i=0; i<100; i++) 1302 if (d[i] != fp[i]) { 1303 result = false; 1304 break; 1305 } 1306 } else result = false; 1307 sqlite3_finalize(ppStmt); 1308 return result; 1309 } 1310 1228 1311 1229 1312 Algo_movelist::Algo_movelist(int bsize) : Algorithm(bsize) { … … 1335 1418 } 1336 1419 1337 void Algo_movelist::endgame_process() throw(DBError) { 1338 char* ml = new char[movelist.size()]; 1339 int mlIndex = 0; 1340 for(vector<char>::iterator it = movelist.begin(); it != movelist.end(); it++) { 1341 ml[mlIndex++] = *it; 1342 } 1343 char sql[100]; 1344 sprintf(sql, "insert into algo_movelist_%d (id, movelist, fpC) values (?, ?, ?);", boardsize); 1345 if (dbinsert2blobs(db, sql, gid, ml, mlIndex, fpC, 50)) throw DBError(); 1346 delete [] ml; 1420 void Algo_movelist::endgame_process(bool commit) throw(DBError) { 1421 if (commit) { 1422 char* ml = new char[movelist.size()]; 1423 int mlIndex = 0; 1424 for(vector<char>::iterator it = movelist.begin(); it != movelist.end(); it++) { 1425 ml[mlIndex++] = *it; 1426 } 1427 char sql[100]; 1428 sprintf(sql, "insert into algo_movelist_%d (id, movelist, fpC) values (?, ?, ?);", boardsize); 1429 if (dbinsert2blobs(db, sql, gid, ml, mlIndex, fpC, 50)) throw DBError(); 1430 delete [] ml; 1431 } 1347 1432 delete [] fpC; 1348 1433 } … … 2056 2141 #endif 2057 2142 2143 HashFEntry::HashFEntry(hashtype HASHCODE, char* BUF, int LENGTH) { 2144 hashCode = HASHCODE; 2145 buf = BUF; 2146 length = LENGTH; 2147 } 2148 2149 HashFEntry::HashFEntry(const HashFEntry& hfe) { 2150 hashCode = hfe.hashCode; 2151 length = hfe.length; 2152 buf = new char[length]; 2153 for(int i=0; i<length; i++) buf[i] = hfe.buf[i]; 2154 } 2155 2156 HashFEntry::~HashFEntry() { 2157 if (buf) { 2158 delete [] buf; 2159 buf = 0; 2160 } 2161 } 2162 2058 2163 HashhitF::HashhitF(int GAMEID, char ORIENTATION, char* blob) { 2059 2164 gameid = GAMEID; … … 2135 2240 buf[6+2*i] = mn.data[i]%256; 2136 2241 } 2242 hash_vector.push_back(HashFEntry(hashCode, buf, 5+2*mn.length)); 2243 return 0; 2244 } 2245 2246 int Algo_hash_full::insert_all_hashes() { 2137 2247 char sql[100]; 2138 2248 sprintf(sql, "insert into algo_hash_full_%d (hash, gameid, hit) values (?,?,?);", boardsize); … … 2140 2250 int rc = sqlite3_prepare(db, sql, -1, &ppStmt, 0); 2141 2251 if (rc != SQLITE_OK || ppStmt==0) return rc; 2142 rc = sqlite3_bind_int64(ppStmt, 1, hashCode); 2143 if (rc != SQLITE_OK) return rc; 2144 rc = sqlite3_bind_int(ppStmt, 2, gid); 2145 if (rc != SQLITE_OK) return rc; 2146 rc = sqlite3_bind_blob(ppStmt, 3, buf, 5+2*mn.length, SQLITE_TRANSIENT); 2147 if (rc != SQLITE_OK) return rc; 2148 rc = sqlite3_step(ppStmt); 2149 if (rc != SQLITE_DONE) return rc; 2252 for(vector<HashFEntry>::iterator it = hash_vector.begin(); it != hash_vector.end(); it++) { 2253 rc = sqlite3_bind_int64(ppStmt, 1, it->hashCode); 2254 if (rc != SQLITE_OK) return rc; 2255 rc = sqlite3_bind_int(ppStmt, 2, gid); 2256 if (rc != SQLITE_OK) return rc; 2257 rc = sqlite3_bind_blob(ppStmt, 3, it->buf, it->length, SQLITE_TRANSIENT); 2258 if (rc != SQLITE_OK) return rc; 2259 rc = sqlite3_step(ppStmt); 2260 if (rc != SQLITE_DONE) return rc; 2261 rc = sqlite3_reset(ppStmt); 2262 if (rc != SQLITE_OK) return rc; 2263 } 2150 2264 rc = sqlite3_finalize(ppStmt); 2151 2265 if (rc != SQLITE_OK) return rc; 2152 delete [] buf;2266 hash_vector.clear(); 2153 2267 return 0; // success 2154 2268 } … … 2264 2378 } 2265 2379 2266 void Algo_hash_full::endgame_process( ) throw(DBError) {2380 void Algo_hash_full::endgame_process(bool commit) throw(DBError) { 2267 2381 for(vector<pair<hashtype, ExtendedMoveNumber>* >::iterator it = lfc->begin(); it != lfc->end(); it++) { 2268 2382 Move* continuation = 0; … … 2271 2385 delete *it; 2272 2386 } 2387 if (commit) { 2388 int rc = insert_all_hashes(); 2389 if (rc) printf("ouch %d\n",rc); 2390 } else hash_vector.clear(); 2273 2391 delete lfc; 2274 2392 delete moveNumber; … … 2420 2538 2421 2539 int Algo_hash::insert_hash(hashtype hashCode, int pos) { 2422 // printf("insert %lld\n", hashCode); 2540 hash_vector.push_back(make_pair(hashCode, pos)); 2541 return 0; 2542 } 2543 2544 int Algo_hash::insert_all_hashes() { 2545 // printf("insert all hashes %d\n", hash_vector.size()); 2423 2546 char sql[200]; 2424 2547 sprintf(sql, "insert into algo_hash_%d_%s (hash, gameid, position) values (?,?,?);", boardsize, dbnameext.c_str()); … … 2426 2549 int rc = sqlite3_prepare(db, sql, -1, &ppStmt, 0); 2427 2550 if (rc != SQLITE_OK || ppStmt==0) return rc; 2428 rc = sqlite3_bind_int64(ppStmt, 1, hashCode);2429 if (rc != SQLITE_OK) return rc;2430 2551 rc = sqlite3_bind_int(ppStmt, 2, gid); 2431 2552 if (rc != SQLITE_OK) return rc; 2432 rc = sqlite3_bind_int(ppStmt, 3, pos); 2433 if (rc != SQLITE_OK) return rc; 2434 rc = sqlite3_step(ppStmt); 2435 if (rc != SQLITE_DONE) return rc; 2553 for(vector<pair<hashtype, int> >::iterator it = hash_vector.begin(); it != hash_vector.end(); it++) { 2554 // printf("insert %d %d\n", it->first, it->second); 2555 rc = sqlite3_bind_int64(ppStmt, 1, it->first); 2556 if (rc != SQLITE_OK) return rc; 2557 rc = sqlite3_bind_int(ppStmt, 3, it->second); 2558 if (rc != SQLITE_OK) return rc; 2559 rc = sqlite3_step(ppStmt); 2560 if (rc != SQLITE_DONE) return rc; 2561 rc = sqlite3_reset(ppStmt); 2562 if (rc != SQLITE_OK) return rc; 2563 } 2436 2564 rc = sqlite3_finalize(ppStmt); 2437 2565 if (rc != SQLITE_OK) return rc; … … 2481 2609 it->changed = false; 2482 2610 pair<hashtype,int> phi = it->cHC(); 2483 if (insert_hash(phi.first, phi.second) != 0) throw DBError(); 2611 insert_hash(phi.first, phi.second); 2612 // printf("insert hash CORNER %d %d\n", phi.first, phi.second); 2484 2613 } 2485 2614 } … … 2522 2651 } 2523 2652 2524 void Algo_hash::endgame_process( ) {2653 void Algo_hash::endgame_process(bool commit) { 2525 2654 for(vector<HashInstance>::iterator it = hi->begin(); it != hi->end(); it++) 2526 2655 it->finalize(); 2656 if (commit) { 2657 int rc = insert_all_hashes(); 2658 if (rc) printf("ouch %d\n",rc); 2659 hash_vector.clear(); 2660 } else hash_vector.clear(); 2527 2661 } 2528 2662 … … 2678 2812 } 2679 2813 } 2680 if (ns > maxNumStones) return make_pair(NOT_HASHABLE,0);2814 if (ns < 3 || ns > maxNumStones) return make_pair(NOT_HASHABLE,0); 2681 2815 2682 2816 // make sure all hash keys are unique … … 3357 3491 if (rootNodeTags.find("RE") == string::npos) rootNodeTags += ",RE"; 3358 3492 if (rootNodeTags.find("DT") == string::npos) rootNodeTags += ",DT"; 3493 3494 algos |= ALGO_FINALPOS | ALGO_MOVELIST; // these are mandatory at the moment 3359 3495 } 3360 3496 … … 3441 3577 3442 3578 GameList::GameList(char* DBNAME, string ORDERBY, string FORMAT, ProcessOptions* p_options, int cache) throw(DBError) { 3579 duplicates = 0; 3443 3580 labels = 0; 3444 3581 continuations = 0; … … 3671 3808 if (labels) delete [] labels; 3672 3809 if (continuations) delete [] continuations; 3810 if (duplicates) delete duplicates; 3673 3811 delete [] dbname; 3674 3812 if (all) { … … 3780 3918 3781 3919 void GameList::makeIndexHit(int index, vector<Hit* > * hits) { 3782 int start = current; 3783 int end = oldList->size(); 3784 int m = start; 3785 while (start < end) { 3786 m = (end+start)/2; 3787 if (index == (*oldList)[m].first) { 3788 currentList->push_back((*oldList)[m]); 3789 if (hits) { 3790 if ((*all)[(*oldList)[m].second]->hits) delete (*all)[(*oldList)[m].second]->hits; 3791 (*all)[(*oldList)[m].second]->hits = hits; 3792 } 3793 break; 3794 } else { 3795 if (index < (*oldList)[m].first) end = m; 3796 else start = m+1; 3797 } 3798 } 3799 current = m; 3920 int m = get_current_index(index, ¤t); 3921 if (m != -1) { 3922 currentList->push_back((*oldList)[m]); 3923 if (hits) { 3924 if ((*all)[(*oldList)[m].second]->hits) delete (*all)[(*oldList)[m].second]->hits; 3925 (*all)[(*oldList)[m].second]->hits = hits; 3926 } 3927 } 3800 3928 } 3801 3929 3802 3930 void GameList::makeIndexCandidate(int index, vector<Candidate* > * candidates) { 3803 int start = current; 3804 int end = oldList->size(); 3805 int m = start; 3806 while (start < end) { 3807 m = (end+start)/2; 3808 if (index == (*oldList)[m].first) { 3809 currentList->push_back((*oldList)[m]); 3810 if (candidates) { 3811 if ((*all)[(*oldList)[m].second]->candidates) delete (*all)[(*oldList)[m].second]->candidates; 3812 (*all)[(*oldList)[m].second]->candidates = candidates; 3813 } 3814 break; 3815 } else { 3816 if (index < (*oldList)[m].first) end = m; 3817 else start = m+1; 3818 } 3819 } 3820 current = m; 3931 int m = get_current_index(index, ¤t); 3932 if (m != -1) { 3933 currentList->push_back((*oldList)[m]); 3934 if (candidates) { 3935 if ((*all)[(*oldList)[m].second]->candidates) delete (*all)[(*oldList)[m].second]->candidates; 3936 (*all)[(*oldList)[m].second]->candidates = candidates; 3937 } 3938 } 3821 3939 } 3822 3940 … … 3895 4013 if (rc != SQLITE_OK) throw DBError(); 3896 4014 return result; 4015 } 4016 4017 void GameList::insert_duplicate(int i1, int i2, vector<vector<int> >* dupl) { 4018 int ii1 = get_current_index_CL(i1); 4019 int ii2 = get_current_index_CL(i2); 4020 // printf("insert_duplicate %d, %d\n", ii1, ii2); 4021 if (ii1 == -1 || ii2 == -1) return; 4022 bool inserted = false; 4023 for(vector<vector<int> >::iterator it = dupl->begin(); it != dupl->end(); it++) { 4024 vector<int>::iterator i = it->begin(); 4025 while(i != it->end() && *i != ii1 && *i != ii2) i++; 4026 if (i == it->end()) continue; 4027 int insert = ii1; 4028 if (*i == ii1) insert = ii2; 4029 while (i != it->end() && *i != insert) i++; 4030 if (i == it->end()) it->push_back(insert); 4031 sort(it->begin(), it->end()); 4032 inserted = true; 4033 break; 4034 } 4035 if (!inserted) { 4036 vector<int> new_list; 4037 if (ii1 < ii2) { 4038 new_list.push_back(ii1); 4039 new_list.push_back(ii2); 4040 } else { 4041 new_list.push_back(ii2); 4042 new_list.push_back(ii1); 4043 } 4044 dupl->push_back(new_list); 4045 } 4046 } 4047 4048 int GameList::find_duplicates(int bs, bool strict) throw(DBError) { 4049 int bs_index = 0; 4050 if (duplicates) delete duplicates; 4051 duplicates = new vector<vector<int> >; 4052 if (strict) { 4053 vector<int>::iterator it = boardsizes.begin(); 4054 while (it != boardsizes.end() && *it != bs) { 4055 bs_index++; 4056 it++; 4057 } 4058 if (it == boardsizes.end()) { 4059 return 0; 4060 } 4061 } 4062 sort(currentList->begin(), currentList->end()); 4063 sqlite3_stmt *ppStmt=0; 4064 char sql[200]; 4065 sprintf(sql, "select as1.id,as2.id from algo_signature_%d as1 join algo_signature_%d as2 on as1.signature = as2.signature where as1.id < as2.id;", bs, bs); 4066 int rc = sqlite3_prepare(db, sql, -1, &ppStmt, 0); 4067 if (rc != SQLITE_OK || ppStmt==0) throw DBError(); 4068 do { 4069 rc = sqlite3_step(ppStmt); 4070 if (rc != SQLITE_DONE && rc != SQLITE_ROW) throw DBError(); 4071 if (rc == SQLITE_ROW) { 4072 if (!strict || ((Algo_finalpos*)algo_ps[20*bs_index+algo_finalpos])->equal(sqlite3_column_int(ppStmt, 0), sqlite3_column_int(ppStmt, 1))) 4073 insert_duplicate(sqlite3_column_int(ppStmt, 0), sqlite3_column_int(ppStmt, 1), duplicates); 4074 } 4075 } while (rc == SQLITE_ROW); 4076 rc = sqlite3_finalize(ppStmt); 4077 if (rc != SQLITE_OK) throw DBError(); 4078 sort(currentList->begin(), currentList->end(), sndcomp); 4079 return duplicates->size(); 4080 } 4081 4082 vector<int> GameList::retrieve_duplicates_VI(unsigned int i) { 4083 if (i>=duplicates->size()) return vector<int>(); 4084 return (*duplicates)[i]; 4085 } 4086 4087 int* GameList::retrieve_duplicates_PI(unsigned int i) { 4088 if (i>=duplicates->size()) return 0; 4089 int* result = new int[(*duplicates)[i].size()+1]; 4090 int j = 0; 4091 for(vector<int>::iterator it = (*duplicates)[i].begin(); it != (*duplicates)[i].end(); it++) 4092 result[j++] = *it; 4093 result[(*duplicates)[i].size()] = -1; 4094 return result; 4095 } 4096 4097 4098 int GameList::get_current_index(int id, int* start) { 4099 // use this in between start_sorted() and end_sorted() only! 4100 int end = oldList->size(); 4101 int m = *start; 4102 while (*start < end) { 4103 m = (end+*start)/2; 4104 if (id == (*oldList)[m].first) { 4105 *start = m; 4106 return m; 4107 } else { 4108 if (id < (*oldList)[m].first) end = m; 4109 else *start = m+1; 4110 } 4111 } 4112 return -1; 4113 } 4114 4115 int GameList::get_current_index_CL(int id, int start) { 4116 // use this in between start_sorted() and end_sorted() only! 4117 int end = currentList->size(); 4118 int m = start; 4119 while (start < end) { 4120 m = (end+start)/2; 4121 if (id == (*currentList)[m].first) return m; 4122 else { 4123 if (id < (*currentList)[m].first) end = m; 4124 else start = m+1; 4125 } 4126 } 4127 return -1; 3897 4128 } 3898 4129 … … 3996 4227 3997 4228 string GameList::currentEntryAsString(int i) { 3998 if (i < 0 || i >= (int)currentList->size()) return ""; 3999 else return (*all)[(*currentList)[i].second]->gameInfoStr + resultsStr((*all)[(*currentList)[i].second]); 4229 if (i < 0 || i >= (int)currentList->size()) { 4230 return ""; 4231 } else return (*all)[(*currentList)[i].second]->gameInfoStr + resultsStr((*all)[(*currentList)[i].second]); 4000 4232 } 4001 4233 … … 4278 4510 } 4279 4511 4280 int GameList::process(const char* sgf, const char* path, const char* fn, const char* DBTREE) throw(SGFError,DBError) { 4512 int GameList::process(const char* sgf, const char* path, const char* fn, 4513 const char* DBTREE, int flags) throw(SGFError,DBError) { 4514 process_results_vector.clear(); 4281 4515 const char* dbtree = ""; 4282 4516 if (DBTREE) dbtree = DBTREE; … … 4286 4520 c = new Cursor(sgf, 1); // parse sgf sloppily 4287 4521 } catch (SGFError) { 4288 return 1;4522 return 0; 4289 4523 } 4290 4524 … … 4294 4528 while (root) { 4295 4529 current++; 4530 int return_val = 0; 4296 4531 // if (!(current%1000)) { 4297 4532 // char* sql = "end transaction;"; … … 4319 4554 if (sz=="") sz = "19"; 4320 4555 int bs = atoi(sz.c_str()); 4556 if (bs < 3) { 4557 return_val |= UNACCEPTABLE_BOARDSIZE; 4558 process_results_vector.push_back(return_val); 4559 delete [] rootNodeProperties; 4560 root = root->down; 4561 pos++; 4562 continue; 4563 } 4321 4564 int algo_offset = -1; 4322 4565 int bs_ctr = 0; … … 4447 4690 int game_id = sqlite3_last_insert_rowid(db); 4448 4691 4449 // evaluate tags4450 if ((*rootNodeProperties)[posHA] != "") { // handicap game4451 char sql[100];4452 sprintf(sql, "insert into GAME_TAGS (game_id, tag_id) values (%d, %d);", game_id, HANDI_TAG);4453 rc = sqlite3_exec(db, sql, 0, 0, 0);4454 if (rc != SQLITE_OK) throw DBError();4455 }4456 if ((*rootNodeProperties)[posWR].find('p') != string::npos ||4457 (*rootNodeProperties)[posBR].find('p') != string::npos) {4458 // at least one of the players is professional4459 char sql[100];4460 sprintf(sql, "insert into GAME_TAGS (game_id, tag_id) values (%d, %d);", game_id, PROFESSIONAL_TAG);4461 rc = sqlite3_exec(db, sql, 0, 0, 0);4462 if (rc != SQLITE_OK) throw DBError();4463 }4464 4465 delete rootNodeProperties;4466 4692 4467 4693 // printf("play through the game\n"); 4694 bool commit = true; 4468 4695 4469 4696 Node* currentN = root; … … 4600 4827 } 4601 4828 } catch (SGFError) { 4829 return_val |= SGF_ERROR; 4602 4830 caughtSGFError = true; 4831 if (OMIT_GAMES_WITH_SGF_ERRORS) { 4832 commit = false; 4833 // (FIXME should exit from the loop here) 4834 } 4603 4835 } 4604 4836 … … 4614 4846 } 4615 4847 4616 if (caughtSGFError) currentN = 0; 4848 if (caughtSGFError) currentN = 0; // stop here with this branch 4617 4849 else currentN = currentN->next; 4618 4850 … … 4634 4866 } // while 4635 4867 { 4868 // check for duplicates (if desired) 4869 bool is_duplicate = false; 4870 if (flags & (CHECK_FOR_DUPLICATES|CHECK_FOR_DUPLICATES_STRICT)) { 4871 char* sig = ((Algo_signature*)algo_ps[20*algo_offset])->get_current_signature(); 4872 vector<int> all_duplicates = ((Algo_signature*)algo_ps[20*algo_offset])->search_signature(sig); 4873 if (all_duplicates.size()) { 4874 // printf("dupl %d\n", all_duplicates.size()); 4875 is_duplicate = true; 4876 if ((flags & CHECK_FOR_DUPLICATES_STRICT) && (p_op->algos & ALGO_FINALPOS)) { 4877 vector<int>::iterator d_it = all_duplicates.begin(); 4878 while (d_it != all_duplicates.end() && !((Algo_finalpos*)algo_ps[20*algo_offset + algo_finalpos])->equals_current(*d_it)) 4879 d_it++; 4880 if (d_it == all_duplicates.end()) is_duplicate = false; 4881 } 4882 if (is_duplicate) { 4883 return_val |= IS_DUPLICATE; 4884 if (flags & OMIT_DUPLICATES) commit = false; 4885 } 4886 } 4887 delete [] sig; 4888 } 4889 4890 if (commit) { 4891 // evaluate tags 4892 if ((*rootNodeProperties)[posHA] != "") { // handicap game 4893 char sql[100]; 4894 sprintf(sql, "insert into GAME_TAGS (game_id, tag_id) values (%d, %d);", game_id, HANDI_TAG); 4895 rc = sqlite3_exec(db, sql, 0, 0, 0); 4896 if (rc != SQLITE_OK) throw DBError(); 4897 } 4898 if ((*rootNodeProperties)[posWR].find('p') != string::npos || 4899 (*rootNodeProperties)[posBR].find('p') != string::npos) { 4900 // at least one of the players is professional 4901 char sql[100]; 4902 sprintf(sql, "insert into GAME_TAGS (game_id, tag_id) values (%d, %d);", game_id, PROFESSIONAL_TAG); 4903 rc = sqlite3_exec(db, sql, 0, 0, 0); 4904 if (rc != SQLITE_OK) throw DBError(); 4905 } 4906 } else { 4907 return_val |= NOT_INSERTED_INTO_DB; 4908 char sql[200]; 4909 sprintf(sql, "delete from GAMES where id=%d", game_id); 4910 rc = sqlite3_exec(db, sql, 0, 0, 0); 4911 if (rc) printf("ouch %d\n", rc); 4912 } 4636 4913 for(int a=20*algo_offset; a < 20*(algo_offset+1); a++) { 4637 4914 // printf("endgame %d\n", a); 4638 if (algo_ps[a]) algo_ps[a]->endgame_process( );4915 if (algo_ps[a]) algo_ps[a]->endgame_process(commit); 4639 4916 } 4640 4917 } 4918 delete rootNodeProperties; 4919 process_results_vector.push_back(return_val); 4641 4920 root = root->down; 4642 4921 pos++; 4643 4922 } 4644 4923 delete c; 4645 return 0; // success 4646 } 4924 return process_results_vector.size(); 4925 } 4926 4927 int GameList::process_results(unsigned int i) { 4928 if (i<0 || i>=process_results_vector.size()) return INDEX_OUT_OF_RANGE; 4929 return process_results_vector[i]; 4930 } 4931 4647 4932 4648 4933 VarInfo::VarInfo(Node* N, abstractBoard* B, int I) { 06/libkombilo/search.h
r230 r239 201 201 virtual void branchpoint_process(); 202 202 virtual void endOfVariation_process(); 203 virtual void endgame_process( );203 virtual void endgame_process(bool commit=true); 204 204 virtual void finalize_process(); 205 205 virtual int readDB(sqlite3* DB); … … 225 225 void branchpoint_process(); 226 226 void endOfVariation_process(); 227 void endgame_process( ) throw(DBError);227 void endgame_process(bool commit=true) throw(DBError); 228 228 void finalize_process(); 229 229 230 230 int counter; 231 231 char* signature; 232 char* get_current_signature(); 233 std::vector<int> search_signature(char* sig); 232 234 private: 233 235 bool main_variation; … … 248 250 void branchpoint_process(); 249 251 void endOfVariation_process(); 250 void endgame_process( ) throw(DBError);252 void endgame_process(bool commit=true) throw(DBError); 251 253 void finalize_process(); 252 254 … … 256 258 int readDB(sqlite3* DB); 257 259 int search(PatternList& patternList, GameList& gl, SearchOptions& options); 260 261 bool equal(unsigned int id1, unsigned int id2); // id1, id2 refer to id's in the database! 262 bool equals_current(unsigned int id1); 258 263 }; 259 264 … … 317 322 void branchpoint_process(); 318 323 void endOfVariation_process(); 319 void endgame_process( ) throw(DBError);324 void endgame_process(bool commit=true) throw(DBError); 320 325 void finalize_process(); 321 326 int readDB(sqlite3* DB); … … 329 334 }; 330 335 336 class HashFEntry { 337 public: 338 hashtype hashCode; 339 char* buf; 340 int length; 341 342 HashFEntry(hashtype HASHCODE, char* BUF, int LENGTH); 343 HashFEntry(const HashFEntry& hfe); 344 ~HashFEntry(); 345 }; 331 346 332 347 class HashhitF { // hashing hit for full board search … … 374 389 void branchpoint_process(); 375 390 void endOfVariation_process() throw(DBError); 376 void endgame_process( ) throw(DBError);391 void endgame_process(bool commit=true) throw(DBError); 377 392 void finalize_process(); 378 393 int search(PatternList& patternList, GameList& gl, SearchOptions& options, sqlite3* db); 379 394 380 int insert_hash(hashtype hashCode, ExtendedMoveNumber& mn, Move* continuation);381 395 hashtype compute_hashkey(Pattern& pattern); 382 396 397 int maxNumStones; 398 int numStones; 399 private: 383 400 hashtype currentHashCode; 384 401 ExtendedMoveNumber* moveNumber; 385 402 std::vector<std::pair<hashtype, ExtendedMoveNumber>* > *lfc; // hash code + move number, still looking for continuation 386 403 std::stack<HashVarInfo>* branchpoints; 387 int maxNumStones; 388 int numStones; 404 int insert_hash(hashtype hashCode, ExtendedMoveNumber& mn, Move* continuation); 405 int insert_all_hashes(); 406 std::vector<HashFEntry> hash_vector; 389 407 }; 390 408 … … 439 457 virtual void branchpoint_process(); 440 458 virtual void endOfVariation_process(); 441 virtual void endgame_process( );459 virtual void endgame_process(bool commit=true); 442 460 virtual void finalize_process(); 443 461 virtual int search(PatternList& patternList, GameList& gl, SearchOptions& options, sqlite3* db); 444 462 463 virtual std::pair<hashtype,int> compute_hashkey(PatternList& pl, int CS); 464 static const hashtype hashCodes[]; 465 std::string dbnameext; 466 std::vector<HashInstance>* hi; 467 int maxNumStones; 468 std::vector<std::pair<hashtype, int> > hash_vector; 445 469 virtual int insert_hash(hashtype hashCod, int pos); 446 virtual std::pair<hashtype,int> compute_hashkey(PatternList& pl, int CS); 447 std::vector<HashInstance>* hi; 448 std::string dbnameext; 449 int maxNumStones; 450 451 static const hashtype hashCodes[]; 470 int insert_all_hashes(); 452 471 }; 453 472 … … 569 588 ~VarInfo(); 570 589 }; 590 591 // process flags (used to determine the behavior for individual games - in contrast to 592 // options which apply to the whole GameList and are given in ProcessOptions) 593 const int CHECK_FOR_DUPLICATES = 1; // check for duplicates using the signature 594 const int CHECK_FOR_DUPLICATES_STRICT = 2; // check for duplicates using the final position 595 // (if ALGO_FINAPOS is available) 596 const int OMIT_DUPLICATES = 4; 597 const int OMIT_GAMES_WITH_SGF_ERRORS = 8; 598 const int INDEX_OUT_OF_RANGE = 16; 599 600 // process return values 601 // 0: SGF error occurred when parsing the "tree structure" (i.e. before parsing the individual nodes) 602 // database was not changed 603 // n>0: n games were processed, use process_results to access the individual results 604 605 // flags used in process_results 606 const int UNACCEPTABLE_BOARDSIZE = 1; // (database not changed) 607 const int SGF_ERROR = 2; 608 // SGF error occurred when playing through the game 609 // (and the rest of the concerning variation was not used). 610 // Depending on OMIT_GAMES_WITH_SGF_ERRORS, everything before this node (and other variations, 611 // if any) was inserted, or the database was not changed. 612 const int IS_DUPLICATE = 4; 613 const int NOT_INSERTED_INTO_DB = 8; 614 571 615 572 616 class GameList { … … 606 650 // ------- processing SGF games (to populate the db) -------------------------- 607 651 void start_processing(int PROCESSVARIATIONS=-1) throw(DBError); 608 int process(const char* sgf, const char* path, const char* fn, const char* DBTREE = 0) throw(SGFError,DBError); 652 int process(const char* sgf, const char* path, const char* fn, 653 const char* DBTREE = 0, int flags=0) throw(SGFError,DBError); 654 int process_results(unsigned int i=0); // result for i-th processed game in most recently processed SGF collection 609 655 void finalize_processing() throw(DBError); 610 656 657 // int remove_game(int index); // TODO 658 // int remove_all_current_games(); 659 611 660 // ------- pattern search ----------------------------------------------------- 612 661 // options is copied in the search method (if != 0), so the caller has to free the pointer … … 629 678 void deleteTag(int tag, int i = -1) throw(DBError); 630 679 std::vector<int> getTags(int i, int tag=0) throw(DBError); // note the order of arguments! 680 681 // ------- duplicates --------------------------------------------------------- 682 int find_duplicates(int bs, bool strict=false) throw(DBError); // return number of duplicate array 683 std::vector<int> retrieve_duplicates_VI(unsigned int i); 684 int* retrieve_duplicates_PI(unsigned int i); // same as above, but returns Pointer to Int 685 // (an array terminated by -1) 686 // The caller must free the pointer himself 687 // (before calling find_duplicates again). 631 688 632 689 // ------- misc --------------------------------------------------------------- … … 659 716 void makeIndexHit(int index, std::vector<Hit* > *hits); 660 717 void setCurrentFromIndex(int index); 718 <
