Auto merge of #31224 - bluss:deque-hashing, r=Gankro
Hash VecDeque in its slice parts Use .as_slices() for a more efficient code path in VecDeque's Hash impl. This still hashes the elements in the same order. Before/after timing of VecDeque hashing 1024 elements of u8 and u64 shows that the vecdeque now can match the Vec (test_hashing_vec_of_u64 is the Vec run). ``` before test test_hashing_u64 ... bench: 14,031 ns/iter (+/- 236) = 583 MB/s test test_hashing_u8 ... bench: 7,887 ns/iter (+/- 65) = 129 MB/s test test_hashing_vec_of_u64 ... bench: 6,578 ns/iter (+/- 76) = 1245 MB/s after running 5 tests test test_hashing_u64 ... bench: 6,495 ns/iter (+/- 52) = 1261 MB/s test test_hashing_u8 ... bench: 851 ns/iter (+/- 16) = 1203 MB/s test test_hashing_vec_of_u64 ... bench: 6,499 ns/iter (+/- 59) = 1260 MB/s ```
This commit is contained in:
commit
b2f4c5c596
@ -1994,9 +1994,9 @@ impl<A: Ord> Ord for VecDeque<A> {
|
||||
impl<A: Hash> Hash for VecDeque<A> {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
self.len().hash(state);
|
||||
for elt in self {
|
||||
elt.hash(state);
|
||||
}
|
||||
let (a, b) = self.as_slices();
|
||||
Hash::hash_slice(a, state);
|
||||
Hash::hash_slice(b, state);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -605,6 +605,25 @@ fn test_hash() {
|
||||
assert!(::hash(&x) == ::hash(&y));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_hash_after_rotation() {
|
||||
// test that two deques hash equal even if elements are laid out differently
|
||||
let len = 28;
|
||||
let mut ring: VecDeque<i32> = (0..len as i32).collect();
|
||||
let orig = ring.clone();
|
||||
for _ in 0..ring.capacity() {
|
||||
// shift values 1 step to the right by pop, sub one, push
|
||||
ring.pop_front();
|
||||
for elt in &mut ring {
|
||||
*elt -= 1;
|
||||
}
|
||||
ring.push_back(len - 1);
|
||||
assert_eq!(::hash(&orig), ::hash(&ring));
|
||||
assert_eq!(orig, ring);
|
||||
assert_eq!(ring, orig);
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_ord() {
|
||||
let x = VecDeque::new();
|
||||
|
Loading…
x
Reference in New Issue
Block a user