d4_hts/alignment/
map_ext.rs

1use super::{cigar_ext::Cigar, cigar_ext::CigarIter, seq_ext::SequenceIter, Alignment, Nucleotide};
2
3pub struct MapIter<'a> {
4    ref_pos: usize,
5    cur_cigar: Option<Cigar>,
6    seq_it: SequenceIter<'a>,
7    cigar_it: CigarIter<'a>,
8}
9
10impl<'a> Alignment<'a> {
11    pub fn map_iter(&self) -> MapIter<'_> {
12        let mut ret = MapIter {
13            ref_pos: self.ref_begin(),
14            seq_it: self.sequence().into_iter(),
15            cigar_it: self.cigar(),
16            cur_cigar: None,
17        };
18        ret.cur_cigar = ret.cigar_it.next();
19        ret
20    }
21}
22
23#[derive(Debug)]
24pub struct Mapping {
25    ref_base: Option<usize>,
26    seq_base: Option<Nucleotide>,
27}
28
29impl<'a> Iterator for MapIter<'a> {
30    type Item = Mapping;
31    fn next(&mut self) -> Option<Mapping> {
32        let mut ret = None;
33        if let Some(ref mut cur_cigar) = self.cur_cigar {
34            let mut map = Mapping {
35                ref_base: None,
36                seq_base: None,
37            };
38
39            if cur_cigar.in_reference() {
40                map.ref_base = Some(self.ref_pos);
41                self.ref_pos += 1;
42            }
43
44            if cur_cigar.in_alignment() {
45                map.seq_base = self.seq_it.next();
46            }
47
48            cur_cigar.len -= 1;
49            ret = Some(map);
50        }
51
52        if ret.is_some() && self.cur_cigar.as_ref().unwrap().len == 0 {
53            self.cur_cigar = self.cigar_it.next();
54        }
55
56        ret
57    }
58}