noodles_vcf/record/samples/
series.rs1pub mod value;
4
5use std::io;
6
7use super::Samples;
8use crate::{variant::record::samples::series::Value, Header};
9
10pub struct Series<'r> {
12 name: &'r str,
13 samples: &'r Samples<'r>,
14 i: usize,
15}
16
17impl<'r> Series<'r> {
18 pub(super) fn new(name: &'r str, samples: &'r Samples<'r>, i: usize) -> Self {
19 Self { name, samples, i }
20 }
21}
22
23impl crate::variant::record::samples::Series for Series<'_> {
24 fn name<'a, 'h: 'a>(&'a self, _: &'h Header) -> io::Result<&'a str> {
25 Ok(self.name)
26 }
27
28 fn get<'a, 'h: 'a>(
29 &'a self,
30 header: &'h Header,
31 i: usize,
32 ) -> Option<Option<io::Result<Value<'a>>>> {
33 let sample = self.samples.iter().nth(i)?;
34 sample.get_index(header, self.i)
35 }
36
37 fn iter<'a, 'h: 'a>(
38 &'a self,
39 header: &'h Header,
40 ) -> Box<dyn Iterator<Item = io::Result<Option<Value<'a>>>> + 'a> {
41 Box::new(
42 self.samples
43 .iter()
44 .map(|sample| match sample.get_index(header, self.i) {
45 Some(value) => value.transpose(),
46 None => Ok(None),
47 }),
48 )
49 }
50}
51
52#[cfg(test)]
53mod tests {
54 use super::*;
55 use crate::variant::record::{samples::keys::key, samples::Series as _};
56
57 #[test]
58 fn test_name() {
59 let header = Header::default();
60
61 let samples = Samples::new("GT:GQ\t0|0:13\t0/1:8");
62 let series = Series::new(key::CONDITIONAL_GENOTYPE_QUALITY, &samples, 1);
63
64 assert!(matches!(
65 series.name(&header),
66 Ok(name) if name == key::CONDITIONAL_GENOTYPE_QUALITY
67 ));
68 }
69
70 #[test]
71 fn test_get() {
72 let header = Header::default();
73
74 let samples = Samples::new("GT:GQ\t0|0:13\t0/1:8");
75 let series = Series::new(key::CONDITIONAL_GENOTYPE_QUALITY, &samples, 1);
76
77 assert!(matches!(
78 series.get(&header, 0),
79 Some(Some(Ok(Value::Integer(13))))
80 ));
81
82 assert!(matches!(
83 series.get(&header, 1),
84 Some(Some(Ok(Value::Integer(8))))
85 ));
86
87 assert!(series.get(&header, 2).is_none());
88 }
89}