当值是地址时如何按键使用映射值C ++

时间:2019-06-30 04:32:11

标签: c++

我使用map在另一个文件中获取全局地址 我的函数是extern“ C”

const map< const char*, void*> GlobalVars = {
            { "A", &A },
            { "B", &B },
            { "C", &C },
            { "D", &D }
        };


        extern "C" void GetAddrByName(const char * str)
        {
            auto it2 = GlobalVars.at(str);//this return garbedge
             return;

        }

我不明白为什么我不能正确获得地址并变得垃圾,而当我将此行auto it = GlobalVars.at("A");放到一切正常时。

2 个答案:

答案 0 :(得分:2)

该映射将无法按预期工作,因为它将比较指针值而不是字符串内容。因此,除非输入键实际上指向您在地图初始化期间使用的确切const char*,否则它将找不到该键。

在这种情况下,如果您想使用const char*作为地图的键(而不是切换为使用std::string),则需要为地图提供一个比较器,以便它执行实际的字符串比较。

例如:

struct cmp_str {
    bool operator()(const char* a, const char* b) const {
        return strcmp(a, b) < 0;
    }
};

const map< const char*, void*, cmp_str> GlobalVars = {
            { "A", &A },
            { "B", &B },
            { "C", &C },
            { "D", &D }
        };

请记住,由于比较器正在取消引用指针,因此该映射可能具有潜在的危险。因此,您需要确保没有悬空的指针最终成为键,否则您将得到UB。但是以您使用它的方式(以字符串文字作为键和const映射),它应该是安全的。

答案 1 :(得分:1)

因为您传递给GlobalVars.at("A")的密钥是到与地图初始化期间传递的地址不同的地址。实际上,问题与指针值无关。

例如,对于代码中的const char *a1 = "A";const char *a2 = "A";,则a1不等于a2,因为它们指向不同的内存位置(取决于编译器)。因此,char *不能在此处用作地图键!使用std :: string作为键。