You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用指针指向C++中map<int,order>与map<int,order,greater<>>容器

解决不同比较器map的统一遍历更新问题

你的代码编译失败的核心原因是:map<int, order>(默认用std::less<int>排序)和map<int, order, greater<>>(用std::greater<int>排序)是完全不同的C++类型,模板参数的差异导致它们的指针类型不兼容,无法用同一个map<int, order>*指针指向两种容器。

下面给出两种可行的解决方案:

方案一:模板函数适配任意map类型

把更新逻辑封装成模板函数,让它能接受任意符合键为int、值为order的map类型,这样不管是升序还是降序map都能复用同一套逻辑。

修改后的完整代码:

#include <iostream>
#include <map>

using namespace std;

struct order {
    int qty;
    int sum;
};

// 模板函数,适配任意键为int、值为order的map类型
template <typename MapType>
void updateOpr(MapType* pmap) {
    order* pre = nullptr;
    for (auto& [key, value] : *pmap) {
        if (pre == nullptr) {
            value.sum = value.qty;
        }
        else {
            value.sum = pre->sum + value.qty;
        }
        pre = &value;
    }
}

int main() {
    map<int, order, greater<>> imap1; // 降序map
    map<int, order> imap2;             // 升序map
    bool flag = true;

    // 填充测试数据
    imap1[1] = {10, 0};
    imap1[2] = {20, 0};
    imap1[3] = {30, 0};
    imap2[1] = {10, 0};
    imap2[2] = {20, 0};
    imap2[3] = {30, 0};

    int key = 10;
    if (flag) {
        // 处理降序map的逻辑
        if (imap1.contains(key)) {
            // todo: 自定义逻辑
        }
        updateOpr(&imap1);
        // 打印验证结果(降序遍历:3→2→1,sum分别为30、50、60)
        for (auto& [k, v] : imap1) {
            cout << "降序map: key=" << k << ", sum=" << v.sum << endl;
        }
    } else {
        // 处理升序map的逻辑
        if (imap2.contains(key)) {
            // todo: 自定义逻辑
        }
        updateOpr(&imap2);
        // 打印验证结果(升序遍历:1→2→3,sum分别为10、30、60)
        for (auto& [k, v] : imap2) {
            cout << "升序map: key=" << k << ", sum=" << v.sum << endl;
        }
    }

    return 0;
}

方案二:用std::variant统一管理不同类型的map指针

如果需要一个“统一的容器”来存储两种map的指针,避免重复写if-else分支,可以用C++17引入的std::variant,配合std::visit执行统一逻辑:

#include <iostream>
#include <map>
#include <variant>

using namespace std;

struct order {
    int qty;
    int sum;
};

template <typename MapType>
void updateOpr(MapType* pmap) {
    order* pre = nullptr;
    for (auto& [key, value] : *pmap) {
        if (pre == nullptr) {
            value.sum = value.qty;
        }
        else {
            value.sum = pre->sum + value.qty;
        }
        pre = &value;
    }
}

int main() {
    map<int, order, greater<>> imap1;
    map<int, order> imap2;
    bool flag = true;

    imap1[1] = {10, 0};
    imap1[2] = {20, 0};
    imap1[3] = {30, 0};
    imap2[1] = {10, 0};
    imap2[2] = {20, 0};
    imap2[3] = {30, 0};

    // 定义variant类型,包含两种map的指针类型
    using MapPtrVariant = variant<map<int, order, greater<>>*, map<int, order>*>;
    MapPtrVariant pmap = flag ? static_cast<MapPtrVariant>(&imap1) : static_cast<MapPtrVariant>(&imap2);

    int key = 10;
    // 用std::visit遍历variant,执行统一逻辑
    visit([key](auto* map_ptr) {
        if (map_ptr->contains(key)) {
            // todo: 自定义逻辑
        }
        updateOpr(map_ptr);
        // 打印结果
        const string& order_type = is_same_v<decltype(*map_ptr), map<int, order>> ? "升序" : "降序";
        for (auto& [k, v] : *map_ptr) {
            cout << order_type << "map: key=" << k << ", sum=" << v.sum << endl;
        }
    }, pmap);

    return 0;
}

关键说明

  • 模板函数是最直接的解决方案,它让更新逻辑与map的排序规则(比较器)完全解耦,只要map的键值类型匹配就能复用。
  • std::variant适合需要统一管理多种类型指针的场景,避免大量重复的if-else分支代码。

内容的提问来源于stack exchange,提问作者seacat

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 12:43:23