lux/index/boolean_merger.h

00001 #ifndef LUX_INDEX_BOOLEANMERGER_H
00002 #define LUX_INDEX_BOOLEANMERGER_H
00003 
00004 #include <iostream>
00005 #include "search_index.h"
00006 
00007 namespace Lux {
00008 
00009   class BooleanMerger {
00010 
00011   public:
00012     static IndexResultSet AND(IndexResultSet &rs1, IndexResultSet &rs2)
00013     {
00014       IRSItr itr1 = rs1.begin();
00015       IRSItr itr2 = rs2.begin();
00016       IRSItr itr1_end = rs1.end();
00017       IRSItr itr2_end = rs2.end();
00018       IRSItr itr1_cur, itr2_cur;
00019       IndexResultSet rs;
00020 
00021       if (itr1 == itr1_end || itr2 == itr2_end) {
00022         return rs;
00023       }
00024 
00025       rs.reserve(rs1.size() > rs2.size() ?  rs1.size() : rs2.size());
00026       while (1) {
00027         if (itr1 != itr1_end) { itr1_cur = itr1; }
00028         if (itr2 != itr2_end) { itr2_cur = itr2; }
00029 
00030         if (itr1_cur->doc_id == itr2_cur->doc_id) {
00031           unsigned int score = (itr1_cur->score + itr2_cur->score) / 2;
00032           rs.push_back(IndexResult(itr1_cur->doc_id, score));
00033           if (itr1 != itr1_end) { ++itr1; }
00034           if (itr2 != itr2_end) { ++itr2; }
00035         } else if (itr1_cur->doc_id > itr2_cur->doc_id) {
00036           if (itr2 != itr2_end) { ++itr2; }
00037         } else {
00038           if (itr1 != itr1_end) { ++itr1; }
00039         }
00040 
00041         if ((itr1 == itr1_end && itr2 == itr2_end) ||
00042             (itr1 == itr1_end && itr2->doc_id > itr1_cur->doc_id) || 
00043             (itr2 == itr2_end && itr1->doc_id > itr2_cur->doc_id)) {
00044             break;
00045         }
00046       }
00047       return rs;
00048     }
00049     
00050     static IndexResultSet OR(IndexResultSet &rs1, IndexResultSet &rs2)
00051     {
00052       IRSItr itr1 = rs1.begin();
00053       IRSItr itr2 = rs2.begin();
00054       IRSItr itr1_end = rs1.end();
00055       IRSItr itr2_end = rs2.end();
00056       IRSItr itr1_cur, itr2_cur;
00057       IndexResultSet rs;
00058 
00059       if (itr1 == itr1_end && itr2 == itr2_end) {
00060         return rs;
00061       } else if (itr1 == itr1_end) {
00062         return rs2;
00063       } else if (itr2 == itr2_end) {
00064         return rs1;
00065       }
00066 
00067       rs.reserve(rs1.size() > rs2.size() ?  rs1.size() : rs2.size());
00068       while (1) {
00069         if (itr1 != itr1_end) { itr1_cur = itr1; }
00070         if (itr2 != itr2_end) { itr2_cur = itr2; }
00071 
00072         if (itr1_cur->doc_id == itr2_cur->doc_id) {
00073           // choose more relevanced one
00074           if (itr1_cur->score > itr2_cur->score) {
00075             rs.push_back(*itr1_cur);
00076           } else {
00077             rs.push_back(*itr2_cur);
00078           }
00079           if (itr1 != itr1_end) { ++itr1; }
00080           if (itr2 != itr2_end) { ++itr2; }
00081         } else if (itr1_cur->doc_id > itr2_cur->doc_id) {
00082           rs.push_back(*itr2_cur);
00083           if (itr2 != itr2_end) { ++itr2; }
00084         } else {
00085           rs.push_back(*itr1_cur);
00086           if (itr1 != itr1_end) { ++itr1; }
00087         }
00088 
00089         if ((itr1 == itr1_end) && (itr2 == itr2_end)) {
00090             break;
00091         }
00092         if (itr1 == itr1_end && itr2->doc_id > itr1_cur->doc_id) {
00093           for (; itr2 != itr2_end; ++itr2) {
00094             rs.push_back(*itr2);
00095           }
00096           break;
00097         }
00098         if (itr2 == itr2_end && itr1->doc_id > itr2_cur->doc_id) {
00099           for (; itr1 != itr1_end; ++itr1 ) {
00100             rs.push_back(*itr1);
00101           }
00102           break;
00103         }
00104       }
00105       return rs;
00106     }
00107 
00108     static IndexResultSet NOT(IndexResultSet &rs1, IndexResultSet &rs2)
00109     {
00110       IRSItr itr1 = rs1.begin();
00111       IRSItr itr2 = rs2.begin();
00112       IRSItr itr1_end = rs1.end();
00113       IRSItr itr2_end = rs2.end();
00114       IRSItr itr1_cur, itr2_cur;
00115       IndexResultSet rs;
00116 
00117       if (itr1 == itr1_end) {
00118         return rs;
00119       }
00120       if (itr2 == itr2_end) {
00121         return rs1;
00122       }
00123 
00124       rs.reserve(rs1.size() > rs2.size() ?  rs1.size() : rs2.size());
00125       while (1) {
00126         if (itr1 != itr1_end) { itr1_cur = itr1; }
00127         if (itr2 != itr2_end) { itr2_cur = itr2; }
00128 
00129         if (itr1_cur->doc_id == itr2_cur->doc_id) {
00130           if (itr1 != itr1_end) { ++itr1; }
00131           if (itr2 != itr2_end) { ++itr2; }
00132         } else if (itr1_cur->doc_id > itr2_cur->doc_id) {
00133           if (itr2 != itr2_end) { ++itr2; }
00134         } else {
00135           rs.push_back(*itr1_cur);
00136           if (itr1 != itr1_end) { ++itr1; }
00137         }
00138 
00139         if (itr1 == itr1_end) { break; }
00140 
00141         if (itr2 == itr2_end && itr1->doc_id > itr2_cur->doc_id) {
00142           for (; itr1 != itr1_end; ++itr1 ) {
00143             rs.push_back(*itr1);
00144           }
00145           break;
00146         }
00147       }
00148       return rs;
00149     }
00150  
00151   };
00152 }
00153 
00154 #endif

Generated on Fri Feb 5 15:50:30 2010 for Lux by  doxygen 1.4.7