hashgrid 0.1.0

A 2D spatial-hash grid library
Documentation
use std::hash::Hasher;

macro_rules! write_impl {
    (($self:ident, $i:ident) $body:block; $($name:ident($type:ty),)+) => {
        $(
            #[inline(always)]
            fn $name(&mut $self, $i: $type) $body
        )*
    }
}

/// A dummy hasher that always does nothing except returning the input.
#[derive(Default)]
pub struct DummyHasher {
    hash: u64,
}

impl Hasher for DummyHasher {
    #[inline]
    fn finish(&self) -> u64 {
        self.hash
    }

    #[inline(always)]
    fn write(&mut self, bytes: &[u8]) {
        self.hash = u64::from_ne_bytes(bytes.try_into().unwrap());
    }

    write_impl!(
        (self, i) {
            self.hash = self.hash | i as u64;
        };
        write_u8(u8),
        write_u16(u16),
        write_u32(u32),
        write_u64(u64),
        write_u128(u128),
        write_usize(usize),
    );
}

#[derive(Default)]
pub struct InterleaveHasher {
    hash: u64,
}

impl Hasher for InterleaveHasher {
    #[inline]
    fn finish(&self) -> u64 {
        self.hash
    }

    #[inline(always)]
    fn write(&mut self, _bytes: &[u8]) {
        panic!("No implementation");
    }

    write_impl!(
        (self, i) {
            self.hash = self.hash << 32 | i as u64;
        };
        write_u8(u8),
        write_u16(u16),
        write_u32(u32),
        write_u64(u64),
        write_u128(u128),
        write_usize(usize),
    );
}

#[cfg(feature = "morton")]
pub use morton::*;

#[cfg(feature = "morton")]
mod morton {
    use super::*;

    #[derive(Default)]
    pub struct MortonHasher {
        hash: [u32; 2],
        i: usize,
    }

    impl Hasher for MortonHasher {
        #[inline]
        fn finish(&self) -> u64 {
            morton_encoding::morton_encode(self.hash)
        }

        #[inline(always)]
        fn write(&mut self, _bytes: &[u8]) {
            panic!("No implementation");
        }

        write_impl!(
            (self, i) {
                self.hash[self.i] = i as u32;
                self.i += 1;
            };
            write_u8(u8),
            write_u16(u16),
            write_u32(u32),
            write_u64(u64),
            write_u128(u128),
            write_usize(usize),
        );
    }
}