diff --git a/geocoder/beam.cpp b/geocoder/beam.cpp index ab0882232a..996f0523cc 100644 --- a/geocoder/beam.cpp +++ b/geocoder/beam.cpp @@ -1,6 +1,7 @@ #include "geocoder/beam.hpp" #include "base/assert.hpp" +#include "base/macros.hpp" #include @@ -10,7 +11,7 @@ Beam::Beam(size_t capacity) : m_capacity(capacity) { m_entries.reserve(m_capacit void Beam::Add(Key const & key, Value value) { - if (m_capacity == 0) + if (PREDICT_FALSE(m_capacity == 0)) return; Entry const e(key, value); diff --git a/geocoder/geocoder.cpp b/geocoder/geocoder.cpp index 1bc73b2575..a9ba123459 100644 --- a/geocoder/geocoder.cpp +++ b/geocoder/geocoder.cpp @@ -21,17 +21,22 @@ namespace { size_t const kMaxResults = 100; -map const kWeight = { - {geocoder::Type::Country, 10.0}, - {geocoder::Type::Region, 5.0}, - {geocoder::Type::Subregion, 4.0}, - {geocoder::Type::Locality, 3.0}, - {geocoder::Type::Suburb, 3.0}, - {geocoder::Type::Sublocality, 2.0}, - {geocoder::Type::Street, 1.0}, - {geocoder::Type::Building, 0.1}, - {geocoder::Type::Count, 0.0}, -}; +double GetWeight(geocoder::Type t) +{ + switch (t) + { + case geocoder::Type::Country: return 10.0; + case geocoder::Type::Region: return 5.0; + case geocoder::Type::Subregion: return 4.0; + case geocoder::Type::Locality: return 3.0; + case geocoder::Type::Suburb: return 3.0; + case geocoder::Type::Sublocality: return 2.0; + case geocoder::Type::Street: return 1.0; + case geocoder::Type::Building: return 0.1; + case geocoder::Type::Count: return 0.0; + } + CHECK_SWITCH(); +} // todo(@m) This is taken from search/geocoder.hpp. Refactor. struct ScopedMarkTokens @@ -68,8 +73,8 @@ geocoder::Type NextType(geocoder::Type type) return static_cast(t + 1); } -bool FindParent(vector const & layers, - geocoder::Hierarchy::Entry const & e) +bool HasParent(vector const & layers, + geocoder::Hierarchy::Entry const & e) { CHECK(!layers.empty(), ()); auto const & layer = layers.back(); @@ -160,7 +165,11 @@ void Geocoder::Context::FillResults(vector & results) const { auto const by = results.front().m_certainty; for (auto & r : results) + { r.m_certainty /= by; + ASSERT_GREATER_OR_EQUAL(r.m_certainty, 0.0, ()); + ASSERT_LESS_OR_EQUAL(r.m_certainty, 1.0, ()); + } } ASSERT(is_sorted(results.rbegin(), results.rend(), base::LessBy(&Result::m_certainty)), ()); @@ -230,17 +239,9 @@ void Geocoder::Go(Context & ctx, Type type) const ScopedMarkTokens mark(ctx, type, i, j + 1); - // double const certainty = - // static_cast(ctx.GetNumUsedTokens()) / - // static_cast(ctx.GetNumTokens()); - double certainty = 0; for (auto const t : ctx.GetTokenTypes()) - { - auto const it = kWeight.find(t); - CHECK(it != kWeight.end(), ()); - certainty += it->second; - } + certainty += GetWeight(t); for (auto const * e : curLayer.m_entries) { @@ -292,10 +293,11 @@ void Geocoder::FillRegularLayer(Context const & ctx, Type type, Tokens const & s for (auto const * e : *entries) { + CHECK(e, ()); if (e->m_type != type) continue; - if (ctx.GetLayers().empty() || FindParent(ctx.GetLayers(), *e)) + if (ctx.GetLayers().empty() || HasParent(ctx.GetLayers(), *e)) curLayer.m_entries.emplace_back(e); } } diff --git a/geocoder/hierarchy.cpp b/geocoder/hierarchy.cpp index 1288335bf1..a68d795283 100644 --- a/geocoder/hierarchy.cpp +++ b/geocoder/hierarchy.cpp @@ -111,7 +111,7 @@ Hierarchy::Hierarchy(string const & pathToJsonHierarchy) string line; ParsingStats stats; - LOG(LINFO, ("Reading entries")); + LOG(LINFO, ("Reading entries...")); while (getline(ifs, line)) { if (line.empty()) @@ -143,9 +143,9 @@ Hierarchy::Hierarchy(string const & pathToJsonHierarchy) m_entriesStorage.emplace_back(move(entry)); } - LOG(LINFO, ("Indexing entries")); + LOG(LINFO, ("Indexing entries...")); IndexEntries(); - LOG(LINFO, ("Indexing houses")); + LOG(LINFO, ("Indexing houses...")); IndexHouses(); LOG(LINFO, ("Finished reading and indexing the hierarchy. Stats:")); @@ -203,13 +203,9 @@ void Hierarchy::IndexHouses() size_t const t = static_cast(Type::Street); - // GetEntries() cannot be used here because one of the - // "consts" in it conflicts with the emplace_back below. - auto streetCandidatesIt = m_entriesByTokens.find(be.m_address[t]); - if (streetCandidatesIt == m_entriesByTokens.end()) - continue; + auto const * streetCandidates = GetEntries(be.m_address[t]); - for (auto & se : streetCandidatesIt->second) + for (auto & se : *streetCandidates) { if (se->IsParentTo(be)) se->m_buildingsOnStreet.emplace_back(&be);