sgrust 0.8.6

A sparse grid library written in Rust.
Documentation
use crate::dynamic::storage::{GridPoint, SparseGridData};

pub trait GridIteratorT
{
    fn point(&self) -> &GridPoint;    
    fn point_index(&self, dim: usize) -> u32;
    fn index(&self) -> Option<usize>;
    fn reset_to_level_zero(&mut self) -> bool;
    fn reset_to_left_level_zero(&mut self, dim: usize) -> bool;
    fn reset_to_right_level_zero(&mut self, dim: usize) -> bool;
    fn reset_to_level_one(&mut self, dim: usize) -> bool;
    fn left_child(&mut self, dim: usize) -> bool;
    fn right_child(&mut self, dim: usize) -> bool;
    fn up(&mut self, dim: usize) -> bool;
    fn is_inner_point(&self) -> bool;
    fn is_leaf(&self) -> bool;

}

pub struct DynamicHashMapGridIterator<'a>
{
    pub(crate) storage: &'a  SparseGridData,
    index: GridPoint,
    seq: Option<usize>,
}

impl<'a> DynamicHashMapGridIterator<'a>
{

    pub(crate) fn new(storage: &'a SparseGridData ) -> Self
    {        
        let point = storage.point(0);
        let seq = storage.index_of(&point);
        Self { storage, index: point, seq}
    }
    
    pub(crate) fn set_index(&mut self, point: GridPoint)
    {
        self.index = point;
        
        self.seq = self.storage.index_of(&self.index);
    }

    #[allow(unused)]
    pub(crate) fn step_left(&mut self, dim: usize)
    {
        let i = self.index.index[dim];     
        if i < 2 
        {
            self.seq = None;
            return;
        }   
        self.index.index[dim] = i - 2;
        
        self.seq = self.storage.index_of(&self.index);
    }
    pub(crate) fn step_right(&mut self, dim: usize)
    {
        let i = self.index.index[dim];
        self.index.index[dim] = i + 2;
        self.seq = self.storage.index_of(&self.index);
    }

    #[allow(unused)]
    pub(crate) fn is_left_leaf(&self, dim: usize) -> bool
    {
        let i = self.index.index[dim];
        let l = self.index.level[dim];
        let mut index = self.index.clone();
        index.index[dim] = 2 * i - 1;
        index.level[dim] = l + 1;        
        self.storage.contains(&index)
    }

    #[allow(unused)]
    pub(crate) fn is_right_leaf(&self, dim: usize) -> bool
    {
        let i = self.index.index[dim];
        let l = self.index.level[dim];
        let mut index = self.index.clone();
        index.index[dim] = 2 * i + 1;
        index.level[dim] = l + 1;        
        self.storage.contains(&index)
    }

    #[inline(always)]
    pub(crate) fn seq(&self) -> Option<usize>
    {
        self.seq
    }

    #[allow(unused)]
    pub(crate) fn get_grid_depth(&mut self, dim: usize) -> usize
    {
        let mut depth = 1;
        let orig_index = self.index.index[dim];
        let orig_level = self.index.level[dim];
        loop
        {
            
            if self.is_left_leaf(dim) || self.is_right_leaf(dim)
            {
                depth += 1;
            }
            else
            {                
                let cur_index = self.index.index[dim];                
                let mut index_found = false;
                for i in (cur_index+2..(1<< depth)).step_by(2)
                {
                    self.index.index[dim] = i;
                    if self.seq.is_some()
                    {
                        if self.is_left_leaf(dim)
                        {
                            depth += 1;
                            self.left_child(dim);
                            index_found = true;
                            break;
                        }
                        else if self.is_right_leaf(dim)
                        {
                            depth += 1;
                            self.right_child(dim);
                            index_found = true;
                            break;
                        }
                    }
                }
                if !index_found
                {
                    break;
                }
            }
        }
        self.index.index[dim] = orig_index;
        self.index.level[dim] = orig_level;
        depth
    }
}

impl GridIteratorT for DynamicHashMapGridIterator<'_>
{
    #[inline(always)]
    fn point(&self) -> &GridPoint
    {
        &self.index
    }
    
    fn index(&self) ->  Option<usize>
    {
        self.seq
    }

    fn reset_to_level_zero(&mut self) -> bool
    {        
        self.index.index.fill(0);
        self.index.level.fill(0);
        self.seq = self.storage.index_of(&self.index);
        self.seq.is_some()
    }
    fn reset_to_left_level_zero(&mut self, dim: usize) -> bool
    {
        self.index.index[dim] = 0;
        self.index.level[dim] = 0;
        
        self.seq = self.storage.index_of(&self.index);        
        self.seq.is_some()
    }
    fn reset_to_right_level_zero(&mut self, dim: usize) -> bool
    {
        self.index.level[dim] = 0;
        self.index.index[dim] = 1;       
        
        self.seq = self.storage.index_of(&self.index);  
        self.seq.is_some()      
    } 
    fn reset_to_level_one(&mut self, dim: usize) -> bool
    {
        self.index.level[dim] = 1;
        self.index.index[dim] = 1;
        
        self.seq = self.storage.index_of(&self.index);
        self.seq.is_some()
    }
    fn left_child(&mut self, dim: usize) -> bool
    {
        let i = self.index.index[dim];
        if i == 0
        {
            self.seq = None;
            return false;
        }
        let l = self.index.level[dim];
        self.index.level[dim] = l + 1;
        self.index.index[dim] = (2 * i) - 1;
        
        self.seq = self.storage.index_of(&self.index);
        self.seq.is_some()
    }
    fn right_child(&mut self, dim: usize) -> bool
    {
        let i = self.index.index[dim];
        let l = self.index.level[dim];
        self.index.level[dim] = l + 1;
        self.index.index[dim] = 2 * i + 1;
        
        self.seq = self.storage.index_of(&self.index);
        self.seq.is_some()
    }
    fn up(&mut self, dim: usize) -> bool
    {
        let mut i = self.index.index[dim];
        let l = self.index.level[dim];
        if l == 0
        {
            self.seq = None;
            return false;
        }
        i /= 2;
        i += if i.is_multiple_of(2) {1} else {0};       
        self.index.level[dim] = l - 1;
        self.index.index[dim] = i;
        
        self.seq = self.storage.index_of(&self.index);
        self.seq.is_some()
    }

    
    #[allow(unused)]
    fn is_inner_point(&self) -> bool
    {
        self.index.is_inner_point()
    }

    fn is_leaf(&self) -> bool
    {
        if let Some(seq) = self.seq
        {
            self.storage.flags[seq].is_leaf()
        }
        else
        {
            true
        }
    }

    fn point_index(&self, dim: usize) -> u32
    {
        self.index.index[dim]
    }
}