Skip to main content

conspire/math/set/sets/
mod.rs

1use crate::math::set::Set;
2use std::cell::OnceCell;
3
4/// A set of sets that optionally provides the converse.
5pub struct Sets<S> {
6    converse: OnceCell<Vec<Vec<usize>>>,
7    set: Set<S>,
8}
9
10impl<S> Sets<S> {
11    pub fn converse<T>(&self) -> &[Vec<usize>]
12    where
13        S: AsRef<[T]>,
14        T: AsRef<[usize]>,
15    {
16        self.converse.get_or_init(|| {
17            let num_inner = self
18                .members()
19                .as_ref()
20                .iter()
21                .flat_map(|row| row.as_ref().iter().copied())
22                .max()
23                .map_or(0, |m| m + 1);
24            let mut converse = vec![Vec::new(); num_inner];
25            for (outer, row) in self.members().as_ref().iter().enumerate() {
26                for &inner in row.as_ref() {
27                    converse[inner].push(outer);
28                }
29            }
30            converse
31        })
32    }
33    pub fn members(&self) -> &S {
34        self.set.members()
35    }
36    pub fn into_members(self) -> S {
37        self.set.into_members()
38    }
39    pub fn numbers(&self) -> Option<&[usize]> {
40        self.set.numbers()
41    }
42    pub fn set(&self) -> &Set<S> {
43        &self.set
44    }
45    pub fn set_numbers(&mut self, numbers: Vec<usize>) {
46        self.set.set_numbers(numbers);
47    }
48}
49
50impl<S> From<S> for Sets<S> {
51    fn from(members: S) -> Self {
52        Set::from(members).into()
53    }
54}
55
56impl<S> From<Set<S>> for Sets<S> {
57    fn from(set: Set<S>) -> Self {
58        Self {
59            converse: OnceCell::new(),
60            set,
61        }
62    }
63}
64
65impl<S> From<Sets<S>> for Set<S> {
66    fn from(sets: Sets<S>) -> Self {
67        sets.set
68    }
69}