#ifndef MT_AUTOHUNT_GROUP_SELECT_H #define MT_AUTOHUNT_GROUP_SELECT_H #include #include #include #include namespace mt_autohunt { struct Candidate { uint64_t group; // actual server party, or a unique key for an ungrouped monster uint32_t vid; int distance; bool eligible; }; struct Selection { int groups; std::vector mobs; Selection() : groups(0) {} }; inline Selection SelectGroups(const std::vector& candidates, int count) { Selection out; if (count != 3 && count != 10 && count != 20) return out; struct Group { uint64_t key; int distance; bool eligible; std::vector mobs; Group() : key(0), distance(2147483647), eligible(true) {} }; std::map groups; for (size_t i = 0; i < candidates.size(); ++i) { const Candidate& c = candidates[i]; Group& g = groups[c.group]; g.key = c.group; g.distance = std::min(g.distance, c.distance); g.eligible = g.eligible && c.eligible; g.mobs.push_back(c.vid); } std::vector > ordered; for (std::map::const_iterator i = groups.begin(); i != groups.end(); ++i) if (i->second.eligible) ordered.push_back(std::make_pair(i->second.distance, i->first)); std::sort(ordered.begin(), ordered.end()); for (size_t i = 0; i < ordered.size() && out.groups < count; ++i) { const Group& g = groups[ordered[i].second]; out.mobs.insert(out.mobs.end(), g.mobs.begin(), g.mobs.end()); ++out.groups; } return out; } } #endif