lib_tsalign 1.0.1

A sequence-to-sequence aligner that accounts for template switches
Documentation
use std::ops::{Index, IndexMut};

use ndarray::Array2;

use super::BaseAlignmentType;

pub mod iterators;

#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub struct AlignmentMatrixIndex {
    pub(in crate::alignment_matrix) reference_index: usize,
    pub(in crate::alignment_matrix) query_index: usize,
}

impl AlignmentMatrixIndex {
    pub fn new(reference_index: usize, query_index: usize) -> Self {
        Self {
            reference_index,
            query_index,
        }
    }

    pub fn insertion_predecessor(&self) -> Self {
        debug_assert!(self.query_index > 0);

        Self {
            reference_index: self.reference_index,
            query_index: self.query_index - 1,
        }
    }

    pub fn deletion_predecessor(&self) -> Self {
        debug_assert!(self.reference_index > 0);

        Self {
            reference_index: self.reference_index - 1,
            query_index: self.query_index,
        }
    }

    pub fn match_or_substitution_predecessor(&self) -> Self {
        debug_assert!(self.reference_index > 0);
        debug_assert!(self.query_index > 0);

        Self {
            reference_index: self.reference_index - 1,
            query_index: self.query_index - 1,
        }
    }

    pub fn predecessor(&self, alignment_type: BaseAlignmentType) -> Self {
        match alignment_type {
            BaseAlignmentType::None => {
                panic!("Predecessor type 'None' has no predecessor")
            }
            BaseAlignmentType::Insertion => self.insertion_predecessor(),
            BaseAlignmentType::Deletion => self.deletion_predecessor(),
            BaseAlignmentType::Match | BaseAlignmentType::Substitution => {
                self.match_or_substitution_predecessor()
            }
        }
    }
}

impl<T> Index<AlignmentMatrixIndex> for Array2<T> {
    type Output = <Array2<T> as Index<[usize; 2]>>::Output;

    fn index(&self, index: AlignmentMatrixIndex) -> &Self::Output {
        &self[[index.reference_index, index.query_index]]
    }
}

impl<T> IndexMut<AlignmentMatrixIndex> for Array2<T> {
    fn index_mut(&mut self, index: AlignmentMatrixIndex) -> &mut Self::Output {
        &mut self[[index.reference_index, index.query_index]]
    }
}