Drill

ProblemsC++ › reporting

The best selling products this week

mediumreportingHash mapsSortingArraysC++

The weekly email lists the top products by units sold. Sales come in one row per transaction, so the same product appears many times.

topSellers(sales: list<Sale>, howMany: int) → list<string>

C++ needs a compiler and Drill does not host one yet, so this page is the reference rather than an exercise: the problem, worked examples, and the solution in full. To type it out, the same problem runs in Python.

Solve it in Python →

Where you start

std::vector<std::string> topSellers(std::vector<Sale> sales, int howMany) {
    
}

Worked examples

CallResult
topSellers(std::vector<Sale>{Sale{std::string("mug"), 5}, Sale{std::string("pen"), 3}, Sale{std::string("mug"), 2}}, 2)std::vector<std::string>{std::string("mug"), std::string("pen")}
topSellers(std::vector<Sale>{Sale{std::string("zip"), 1}, Sale{std::string("ace"), 1}}, 2)std::vector<std::string>{std::string("ace"), std::string("zip")}
topSellers(std::vector<Sale>{Sale{std::string("mug"), 5}, Sale{std::string("pen"), 9}}, 1)std::vector<std::string>{std::string("pen")}
topSellers(std::vector<Sale>{Sale{std::string("mug"), 5}}, 0)std::vector<std::string>{}

Hint

Aggregate into a map, then sort the entries. The tie-break is what most solutions forget.

Reference solution in C++
std::vector<std::string> topSellers(std::vector<Sale> sales, int howMany) {
    std::map<string, int> totals;
    for (const auto& s : sales) totals[s.name] += s.qty;
    std::vector<string> names;
    for (const auto& kv : totals) names.push_back(kv.first);
    std::sort(names.begin(), names.end(), [&](const string& a, const string& b) {
        if (totals[a] != totals[b]) return totals[a] > totals[b];
        return a < b;
    });
    if (howMany <= 0) return {};
    if ((int) names.size() > howMany) names.resize(howMany);
    return names;
}

The same problem in another language

More reporting problems in C++