How can I use a custom hash function in a HashSet or HashMap?
hashcode, rust
Solution
Take a look at the definition of `DefaultState`:
pub struct DefaultState<H>(marker::PhantomData<H>);
You are treating it as though it were as it used to be:
pub struct DefaultState<H>;
This change is recent; generic parameters must now be expressly used.
For this you must now use `Default::default()`, for that field is private, preventing literal expressions from being written. Thus, `DefaultState::<FnvHasher>` becomes `Default::default()`.
And once you’re using `Default::default()` for that, you might as well go the whole hog and replace `HashSet::with_hash_state(Default::default())` with `Default::default()`:
let mut set: HashSet<i64, DefaultState<FnvHasher>> = Default::default();
Problem
Since SipHasher is too slow for my use case, I'm trying to implement a custom hash function. I found an example which I used as base to get everything compiling. My current code looks like this: ``` use std::collections::hash_state::{DefaultState}; use std::collections::{HashMap, HashSet}; use std::default::Default; use std::hash::{Hash, Hasher, SipHasher}; use std::marker; pub struct FnvHasher(u64); impl Default for FnvHasher { fn default() -> FnvHasher { FnvHasher(0xcbf29ce484222325) } } impl Hasher for FnvHasher { fn write(&mut self, bytes: &[u8]) { let FnvHasher(mut hash) = *self; for byte in bytes { hash = hash ^ (*byte as u64); hash = hash * 0x100000001b3; } *self = FnvHasher(hash); } fn finish(&self) -> u64 { self.0 } } fn main() { let mut set:HashSet<i64, DefaultState<FnvHasher>> = HashSet::with_hash_state(DefaultState::<FnvHasher>); } ``` When I compile I get the following error message: ``` $ rustc -V rustc 1.0.0-nightly (522d09dfe 2015-02-19) (built 2015-02-19) $ rustc hash.rs hash.rs:26:86: 26:111 error: mismatched types: expected `std::collections::hash::state::DefaultState<FnvHasher>`, found `fn(core::marker::PhantomData<FnvHasher>) -> std::collections::hash::state::DefaultState<FnvHasher> {std::collections::hash::state::DefaultState}` (expected struct `std::collections::hash::state::DefaultState`, found fn item) [E0308] hash.rs:26 let mut set:HashSet<i64, DefaultState<FnvHasher>> = HashSet::with_hash_state(DefaultState::<FnvHasher>); ^~~~~~~~~~~~~~~~~~~~~~~~~ error: aborting due to previous error ``` How can I get the above example to compile or use a custom hash function in a HashSet/HashMap?