mirror of
https://github.com/djcb/mu.git
synced 2024-06-26 07:29:17 +02:00
query: improve thread-key-maker
For threading, we still get the _full_ set of messages (since the mset is limited, but not the enquire); so no need to warn about docids we haven't seen before. Also, ensure the unwanted docids are sorted after the wanted ones. Fixes: #1926.
This commit is contained in:
parent
8405788f27
commit
ffc809a01e
|
@ -50,8 +50,7 @@ struct Query::Private {
|
||||||
MuMsgFieldId sortfieldid, QueryFlags qflags) const;
|
MuMsgFieldId sortfieldid, QueryFlags qflags) const;
|
||||||
|
|
||||||
Option<QueryResults> run_threaded (QueryResults &qres, Xapian::Enquire& enq,
|
Option<QueryResults> run_threaded (QueryResults &qres, Xapian::Enquire& enq,
|
||||||
MuMsgFieldId sortfieldid,
|
QueryFlags qflags) const;
|
||||||
QueryFlags qflags, size_t maxnum) const;
|
|
||||||
Option<QueryResults> run_singular (const std::string& expr, MuMsgFieldId sortfieldid,
|
Option<QueryResults> run_singular (const std::string& expr, MuMsgFieldId sortfieldid,
|
||||||
QueryFlags qflags, size_t maxnum) const;
|
QueryFlags qflags, size_t maxnum) const;
|
||||||
Option<QueryResults> run_related (const std::string& expr, MuMsgFieldId sortfieldid,
|
Option<QueryResults> run_related (const std::string& expr, MuMsgFieldId sortfieldid,
|
||||||
|
@ -119,35 +118,33 @@ Query::Private::make_related_enquire (const Xapian::Query& first_q,
|
||||||
}
|
}
|
||||||
|
|
||||||
struct ThreadKeyMaker: public Xapian::KeyMaker {
|
struct ThreadKeyMaker: public Xapian::KeyMaker {
|
||||||
ThreadKeyMaker (const QueryMatches& matches):
|
ThreadKeyMaker (const QueryMatches& matches, bool descending):
|
||||||
match_info_(matches)
|
match_info_(matches),
|
||||||
|
not_found_key_{descending ? "#" : "z"}
|
||||||
{}
|
{}
|
||||||
std::string operator()(const Xapian::Document &doc) const override {
|
std::string operator()(const Xapian::Document& doc) const override {
|
||||||
const auto it{match_info_.find(doc.get_docid())};
|
const auto it{match_info_.find(doc.get_docid())};
|
||||||
if (G_UNLIKELY(it == match_info_.end())) {
|
return (it == match_info_.end()) ? not_found_key_ : it->second.thread_path;
|
||||||
g_warning("can't find document %u", doc.get_docid());
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
return it->second.thread_path;
|
|
||||||
}
|
}
|
||||||
const QueryMatches& match_info_;
|
const QueryMatches& match_info_;
|
||||||
|
const std::string not_found_key_;
|
||||||
};
|
};
|
||||||
|
|
||||||
Option<QueryResults>
|
Option<QueryResults>
|
||||||
Query::Private::run_threaded (QueryResults &qres, Xapian::Enquire& enq,
|
Query::Private::run_threaded (QueryResults &qres, Xapian::Enquire& enq,
|
||||||
MuMsgFieldId sortfieldid,
|
QueryFlags qflags) const
|
||||||
QueryFlags qflags, size_t maxnum) const
|
|
||||||
{
|
{
|
||||||
const auto descending{any_of(qflags & QueryFlags::Descending)};
|
const auto descending{any_of(qflags & QueryFlags::Descending)};
|
||||||
|
|
||||||
calculate_threads(qres, descending);
|
calculate_threads(qres, descending);
|
||||||
|
|
||||||
ThreadKeyMaker key_maker{qres.query_matches()};
|
ThreadKeyMaker key_maker{qres.query_matches(), descending};
|
||||||
enq.set_sort_by_key(&key_maker, descending);
|
enq.set_sort_by_key(&key_maker, descending);
|
||||||
|
|
||||||
DeciderInfo minfo;
|
DeciderInfo minfo;
|
||||||
minfo.matches = qres.query_matches();
|
minfo.matches = qres.query_matches();
|
||||||
auto mset{enq.get_mset(0, maxnum, {}, make_final_decider(qflags, minfo).get())};
|
auto mset{enq.get_mset(0, qres.size(), {}, make_final_decider(qflags, minfo).get())};
|
||||||
|
mset.fetch();
|
||||||
|
|
||||||
return QueryResults{mset, std::move(qres.query_matches())};
|
return QueryResults{mset, std::move(qres.query_matches())};
|
||||||
}
|
}
|
||||||
|
@ -173,12 +170,13 @@ Query::Private::run_singular (const std::string& expr, MuMsgFieldId sortfieldid,
|
||||||
#pragma GCC diagnostic ignored "-Wswitch-default"
|
#pragma GCC diagnostic ignored "-Wswitch-default"
|
||||||
#pragma GCC diagnostic pop
|
#pragma GCC diagnostic pop
|
||||||
auto mset{enq.get_mset(0, maxnum, {}, make_leader_decider(singular_qflags, minfo).get())};
|
auto mset{enq.get_mset(0, maxnum, {}, make_leader_decider(singular_qflags, minfo).get())};
|
||||||
|
mset.fetch();
|
||||||
|
|
||||||
auto qres{QueryResults{mset, std::move(minfo.matches)}};
|
auto qres{QueryResults{mset, std::move(minfo.matches)}};
|
||||||
if (none_of(qflags & QueryFlags::Threading))
|
if (!threading)
|
||||||
return qres;
|
return qres;
|
||||||
else
|
else
|
||||||
return run_threaded(qres, enq, sortfieldid, qflags, maxnum);
|
return run_threaded(qres, enq, qflags);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -215,7 +213,7 @@ Query::Private::run_related (const std::string& expr, MuMsgFieldId sortfieldid,
|
||||||
if (!threading)
|
if (!threading)
|
||||||
return qres;
|
return qres;
|
||||||
else
|
else
|
||||||
return run_threaded(qres, r_enq, sortfieldid, qflags, maxnum);
|
return run_threaded(qres, r_enq, qflags);
|
||||||
}
|
}
|
||||||
|
|
||||||
Option<QueryResults>
|
Option<QueryResults>
|
||||||
|
|
Loading…
Reference in New Issue
Block a user