I am trying to hash single std::string
and std::vector<std::string>
values. I am following the examples from cppreference and boost. When the code is compiled and run on Windows vs Linux, I get different results.
The header file for MyHasher.h
is as follows.
class MyHasher {
private:
MyHasher() = delete;
public:
static std::size_t hash(std::vector<std::string> ids);
static std::size_t hash(std::string s);
static void hashCombine(std::size_t &seed, std::size_t value);
};
The CPP file MyHasher.cpp
is as follows.
std::size_t MyHasher::hash(std::vector<std::string> ids) {
std::size_t seed = 0;
for (auto id : ids) {
std::size_t h = std::hash<std::string>{}(id);
hashCombine(seed, h);
}
return seed;
}
std::size_t MyHasher::hash(std::string s) {
std::size_t seed = 0;
std::size_t h = std::hash<std::string>{}(s);
hashCombine(seed, h);
return seed;
}
void MyHasher::hashCombine(std::size_t &seed, std::size_t value) {
seed ^= value + 0x9e3779b9 + (seed<<6) + (seed>>2);
}
然后,一个示例程序运行如下。
int main() {
std::cout << std::to_string(MyHasher::hash("0")) << " | 0" << std::endl;
std::cout << std::to_string(MyHasher::hash(std::vector<std::string>{"0"})) << " | 0" << std::endl;
std::cout << std::to_string(MyHasher::hash(std::vector<std::string>{"0", "1"})) << " | 0 1" << std::endl;
return 0;
}
在Linux(g ++ 7.4.0)上,输出如下。
2297668036269395695 | 0 2297668036269395695 | 0 10545066640295778616 | 0 1
在Windows(Visual Studio Community 2019,MSVC-14.0)上,输出如下。
12638135526163551848 | 0 12638135526163551848 | 0 1964774108746342951 | 0 1
关于这个差异有什么想法吗?
我真正想要的是一种始终产生依赖于输入但跨平台和固定宽度的唯一哈希输出的方法。宽度可以说并不重要,但只要与输入相同,宽度相同即可。