C++ 编写要与无序映射一起使用的类。

C++ 编写要与无序映射一起使用的类。,c++,boost,C++,Boost,我想使用boost映射,文档中说我需要一个相等函数和一个散列函数。我想我理解他们应该做什么,但因为我找不到任何示例,我不确定如何做,所以我正在寻找一个简单的示例,比如成员为x、y或相近的点类 编辑:终于让它工作了。但愿我没有为此浪费这么多时间。谢谢你们 #include <boost/functional/hash.hpp> #include <boost/unordered_map.hpp> #include <boost/foreach.hpp> #inc

我想使用boost映射,文档中说我需要一个相等函数和一个散列函数。我想我理解他们应该做什么,但因为我找不到任何示例,我不确定如何做,所以我正在寻找一个简单的示例,比如成员为x、y或相近的点类

编辑:终于让它工作了。但愿我没有为此浪费这么多时间。谢谢你们

#include <boost/functional/hash.hpp>
#include <boost/unordered_map.hpp>
#include <boost/foreach.hpp>
#include <iostream>

namespace test { // class whose source i can't edit
    class point
    {
    public:
        float x;
        float y;
        point() : x(0), y(0) {}
        point(int x, int y) : x(x), y(y) {}
        point(float x, float y) : x(x), y(y) {}
        point(double x, double y) : x((float) x), y((float) y) {}

        bool operator==(point const& other) const
        {
            return x == other.x && y == other.y;
        }
    };
}

namespace test { // my source file
    std::size_t hash_value(point const &p) {
        boost::hash<int> hasher;
        return hasher(p.x) + hasher(p.y);
    }
} 

int main() {
    boost::unordered_map<test::point, std::string> myMap;
    test::point p1(1, 2);
    myMap[p1] = "1"; //now it works
    std::cout << myMap[p1] << std::endl;
    return 0;
}
#包括
#包括
#包括
#包括
命名空间测试{//类,其源我无法编辑
类点
{
公众:
浮动x;
浮动y;
点():x(0),y(0){}
点(intx,inty):x(x),y(y){
点(浮动x,浮动y):x(x),y(y){
点(双x,双y):x((浮点)x),y((浮点)y){}
布尔运算符==(点常量和其他)常量
{
返回x==other.x&&y==other.y;
}
};
}
命名空间测试{//我的源文件
标准::大小\u t哈希值(点常量和点){
boost::散列哈希器;
返回散列器(p.x)+散列器(p.y);
}
} 
int main(){
boost::无序映射myMap;
测试:点p1(1,2);
myMap[p1]=“1”;//现在可以工作了

std::cout相等和哈希并不难定义。相等:

class Point {
    int x, y;
    bool operator==(const Point& p) {
        return (x == p.x && y == p.y);
    }
};
散列往往涉及专门化函数或类

template<> class boost::hash<Point> {
public:
    size_t operator()(const Point& p) {
        return boost::hash<int>(p.x) + boost::hash<int>(p.y);
    }
};
模板类boost::hash{
公众:
大小\u t运算符()(常数点和p){
返回boost::hash(p.x)+boost::hash(p.y);
}
};

您可能需要详细阅读哈希映射实现的细节,还可能需要定义不同的哈希算法。

等式和哈希并不难定义。等式:

class Point {
    int x, y;
    bool operator==(const Point& p) {
        return (x == p.x && y == p.y);
    }
};
散列往往涉及专门化函数或类

template<> class boost::hash<Point> {
public:
    size_t operator()(const Point& p) {
        return boost::hash<int>(p.x) + boost::hash<int>(p.y);
    }
};
模板类boost::hash{
公众:
大小\u t运算符()(常数点和p){
返回boost::hash(p.x)+boost::hash(p.y);
}
};
您可能需要详细阅读哈希映射实现的细节,还可能需要定义不同的哈希算法。

这是来自

这是从



这里有这种场景的例子(二维点类)你是否对使用C++ 0x的代码> STD::无序的地图,<代码>或Tr1 <代码> STD::un无序DeMeP> <代码>?@:Kerrek:C++ + 0x不是100%的与C++的微妙的兼容。对于一个已经使用了<代码> Boost 的大项目,切换语言只是IMO NOSENSE。6502:可以使用Tr1,它不需要CH。语言的范围,并包含在大多数现代编译器中…有这种情况的例子(一个2-d点类)你是否对使用C++ 0x的代码> STD::无序的地图,<代码>或Tr1 <代码> STD::un无序DeMeP> <代码>?@:Kerrek:C++ + 0x不是100%的与C++的微妙的兼容。对于一个已经使用了<代码> Boost 的大项目,切换语言只是IMO NOSENSE。6502:可以使用Tr1,它不需要CH。语言的范围,并且包含在大多数现代编译器中…您需要一个单独的类来实现散列?这有什么原因吗?@问题:它只是一个函子,没有什么特别的。当我尝试使用此示例编译代码时,我在不同的命名空间中得到了“template struct boost::hash”的专门化espaces要使用这个函子吗?关于stackoverflow有一个答案,但这只是一个没有任何解释的示例,我不理解atm。你可以将你的专门化函子放在std::tr1中,或者将它作为第三个模板参数传递给你的容器。如果你不知道什么是函子,从这里开始使用sum给出一个一般来说,不好的分布…是非均匀和对称的。有一个特定的
hash\u combine
函数工作得更好。您需要一个单独的类来实现hash?这有什么原因吗?@问题:它只是一个函子;没有什么特别的。当我尝试使用这个示例编译代码时,我得到了
的特化“te”mplate struct boost::hash'在不同的命名空间中
。我必须设置命名空间才能使用这个函子吗?关于stackoverflow有一个答案,但这只是一个没有任何解释的示例,我不理解atm。您可以将专门化函子放在std::tr1中,或者将其作为第三个模板参数传递给您r容器。如果你不知道什么是函子,从这里开始使用sum通常会给出一个糟糕的分布…是非均匀的和对称的。有一个特定的
hash\u combine
函数工作得更好。是否存在种子不应该为0的情况?@问题-我认为种子是什么并不重要,只要它始终为0对于该类型的所有实例都一样。@问题:您可以从您喜欢的任何值开始,但是使用
hash\u combine
而不是
+
^
稍微好一些,因为它保持了更好的分布,并且散列在XY中不是对称的(使用点(a,b)和(b,a)的和或异或)以相同的散列结束,因此如果您的输入具有这种对称性,则散列映射的效率将略低)。是否存在种子不应为0的情况?@问题-我认为种子是什么并不重要,只要它对类型的所有实例都是相同的。@问题:您可以从您喜欢的任何值开始,但使用
哈希\u组合
而不是
+
^
稍微好一点,因为它保持了更好的分布散列在XY中不是对称的(使用sum或xor,点(a,b)和(b,a)以相同的散列结束,因此如果您的输入具有这种对称性,散列映射的效率将稍低)。