1use std::collections::{BTreeMap, HashMap};
2use std::fmt::{Debug, Display};
3use std::hash::{BuildHasher, Hash};
4use std::marker::PhantomData;
5
6use convert_case::{Case, Casing};
7use half::{bf16, f16};
8use paste::paste;
9
10use crate::errors::Error;
11
12pub trait SameAs<T> {}
15
16impl<T> SameAs<T> for T {}
17
18pub trait Parameter {}
29
30impl Parameter for bool {}
31impl Parameter for i8 {}
32impl Parameter for i16 {}
33impl Parameter for i32 {}
34impl Parameter for i64 {}
35impl Parameter for i128 {}
36impl Parameter for u8 {}
37impl Parameter for u16 {}
38impl Parameter for u32 {}
39impl Parameter for u64 {}
40impl Parameter for u128 {}
41impl Parameter for bf16 {}
42impl Parameter for f16 {}
43impl Parameter for f32 {}
44impl Parameter for f64 {}
45impl Parameter for usize {}
46
47impl<P: Parameter> Parameter for Option<P> {}
48
49#[derive(Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
54pub struct Placeholder;
55
56impl Display for Placeholder {
57 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
58 write!(f, "<Parameter>")
59 }
60}
61
62impl Debug for Placeholder {
63 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
64 write!(f, "<Parameter>")
65 }
66}
67
68impl Parameter for Placeholder {}
69
70#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
73pub enum ParameterPathSegment {
74 Field(&'static str),
76
77 Variant(&'static str),
79
80 TupleIndex(usize),
82
83 Index(usize),
85
86 Key(String),
88}
89
90#[derive(Clone, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
102pub struct ParameterPath {
103 segments: Vec<ParameterPathSegment>,
107}
108
109impl ParameterPath {
110 pub fn root() -> Self {
112 Self::default()
113 }
114
115 pub fn len(&self) -> usize {
117 self.segments.len()
118 }
119
120 pub fn is_empty(&self) -> bool {
122 self.segments.is_empty()
123 }
124
125 pub fn is_root(&self) -> bool {
127 self.is_empty()
128 }
129
130 pub fn is_prefix_of(&self, other: &Self) -> bool {
132 self.len() <= other.len() && self.segments().zip(other.segments()).all(|(left, right)| left == right)
133 }
134
135 pub fn segments(&self) -> impl DoubleEndedIterator<Item = &ParameterPathSegment> + '_ {
137 self.segments.iter().rev()
138 }
139
140 pub fn with_segment(mut self, segment: ParameterPathSegment) -> Self {
153 self.segments.insert(0, segment);
154 self
155 }
156
157 pub fn field(self, name: &'static str) -> Self {
160 self.with_segment(ParameterPathSegment::Field(name))
161 }
162
163 pub fn variant(self, name: &'static str) -> Self {
166 self.with_segment(ParameterPathSegment::Variant(name))
167 }
168
169 pub fn index(self, index: usize) -> Self {
172 self.with_segment(ParameterPathSegment::Index(index))
173 }
174
175 pub fn tuple_index(self, index: usize) -> Self {
178 self.with_segment(ParameterPathSegment::TupleIndex(index))
179 }
180
181 pub fn key<K: Debug>(self, key: K) -> Self {
184 self.with_segment(ParameterPathSegment::Key(format!("{key:?}")))
185 }
186}
187
188impl Display for ParameterPath {
189 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
190 write!(f, "$")?;
191 for segment in self.segments() {
192 match segment {
193 ParameterPathSegment::Field(name) => write!(f, ".{name}")?,
194 ParameterPathSegment::Variant(name) => write!(f, ".{}", name.to_case(Case::Snake))?,
195 ParameterPathSegment::TupleIndex(index) => write!(f, ".{index}")?,
196 ParameterPathSegment::Index(index) => write!(f, "[{index}]")?,
197 ParameterPathSegment::Key(key) => write!(f, "[{key}]")?,
198 }
199 }
200 Ok(())
201 }
202}
203
204impl Debug for ParameterPath {
205 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
206 write!(f, "ParameterPath[{self}]")
207 }
208}
209
210pub trait ParameterizedFamily<P: Parameter>: Sized {
219 type To: Parameterized<P, Family = Self, ParameterStructure = <Self as ParameterizedFamily<Placeholder>>::To>
221 where
222 Self: ParameterizedFamily<Placeholder>;
223}
224
225pub trait Parameterized<P: Parameter>: Sized {
555 type Family: ParameterizedFamily<P, To = Self> + ParameterizedFamily<Placeholder, To = Self::ParameterStructure>;
557
558 type To<T: Parameter>: Parameterized<T, Family = Self::Family, ParameterStructure = Self::ParameterStructure>
562 + SameAs<<Self::Family as ParameterizedFamily<T>>::To>
563 where
564 Self::Family: ParameterizedFamily<T>;
565
566 type ParameterStructure: Parameterized<Placeholder, Family = Self::Family, To<P> = Self>
571 + SameAs<Self::To<Placeholder>>;
572
573 type ParameterIterator<'t, T: 't + Parameter>: 't + Iterator<Item = &'t T>
578 where
579 Self: 't;
580
581 type ParameterIteratorMut<'t, T: 't + Parameter>: 't + Iterator<Item = &'t mut T>
586 where
587 Self: 't;
588
589 type ParameterIntoIterator<T: Parameter>: Iterator<Item = T>;
594
595 type NamedParameterIterator<'t, T: 't + Parameter>: 't + Iterator<Item = (ParameterPath, &'t T)>
600 where
601 Self: 't;
602
603 type NamedParameterIteratorMut<'t, T: 't + Parameter>: 't + Iterator<Item = (ParameterPath, &'t mut T)>
608 where
609 Self: 't;
610
611 type NamedParameterIntoIterator<T: Parameter>: Iterator<Item = (ParameterPath, T)>;
617
618 fn parameter_count(&self) -> usize;
620
621 fn parameter_structure(&self) -> Self::ParameterStructure;
623
624 fn parameters(&self) -> Self::ParameterIterator<'_, P>;
628
629 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P>;
633
634 fn into_parameters(self) -> Self::ParameterIntoIterator<P>;
638
639 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P>;
644
645 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P>;
650
651 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P>;
656
657 fn parameter_paths<'p>(&'p self) -> impl 'p + Iterator<Item = ParameterPath>
662 where
663 P: 'p,
664 {
665 self.named_parameters().map(|(path, _)| path)
666 }
667
668 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
673 structure: Self::ParameterStructure,
674 parameters: &mut I,
675 ) -> Result<Self, Error>;
676
677 fn from_parameters<I: IntoIterator<Item = P>>(
683 structure: Self::ParameterStructure,
684 parameters: I,
685 ) -> Result<Self, Error> {
686 let mut parameters = parameters.into_iter();
687 let parameterized = Self::from_parameters_with_remainder(structure, &mut parameters)?;
688 parameters
689 .next()
690 .map(|_| Err(Error::UnusedParameters { paths: None }))
691 .unwrap_or_else(|| Ok(parameterized))
692 }
693
694 fn from_named_parameters<I: IntoIterator<Item = (ParameterPath, P)>>(
702 structure: Self::ParameterStructure,
703 parameters: I,
704 ) -> Result<Self, Error> {
705 let expected_count = structure.parameter_count();
709 let mut values = Vec::new();
710 values.reserve_exact(expected_count);
711 let mut matching_paths = Vec::new();
712 matching_paths.reserve_exact(expected_count);
713 let mut missing_paths = Vec::new();
714 let mut deferred_parameters = None::<HashMap<_, _>>;
715 let mut matching_path_indices = None::<HashMap<ParameterPath, usize>>;
716 let mut parameters = parameters.into_iter();
717 let mut next_parameter = parameters.next();
718
719 for (expected_path, _) in structure.named_parameters() {
720 if let Some(deferred_parameters) = deferred_parameters.as_mut() {
721 match deferred_parameters.remove(&expected_path) {
724 Some(parameter) => values.push(parameter),
725 None => missing_paths.push(expected_path.to_string()),
726 }
727 continue;
728 }
729
730 match next_parameter.take() {
731 Some((provided_path, parameter)) if provided_path == expected_path => {
732 values.push(parameter);
735 matching_paths.push(expected_path);
736 next_parameter = parameters.next();
737 }
738 Some((provided_path, parameter)) => {
739 let mut deferred = HashMap::with_capacity(parameters.size_hint().0 + 1);
741 let matching_path_indices = matching_path_indices.get_or_insert_with(|| {
742 matching_paths
743 .iter()
744 .cloned()
745 .enumerate()
746 .map(|(index, path)| (path, index))
747 .collect::<HashMap<_, _>>()
748 });
749
750 let parameters = std::iter::once((provided_path, parameter)).chain(parameters.by_ref());
753 for (provided_path, parameter) in parameters {
754 if let Some(index) = matching_path_indices.get(&provided_path).copied() {
755 values[index] = parameter;
756 } else {
757 deferred.insert(provided_path, parameter);
758 }
759 }
760
761 match deferred.remove(&expected_path) {
762 Some(parameter) => values.push(parameter),
763 None => missing_paths.push(expected_path.to_string()),
764 }
765
766 deferred_parameters = Some(deferred);
767 }
768 None => missing_paths.push(expected_path.to_string()),
769 }
770 }
771
772 if deferred_parameters.is_none() {
773 if let Some((provided_path, parameter)) = next_parameter.take() {
774 let mut deferred = HashMap::with_capacity(parameters.size_hint().0 + 1);
777 let matching_path_indices = matching_path_indices.get_or_insert_with(|| {
778 matching_paths
779 .iter()
780 .cloned()
781 .enumerate()
782 .map(|(index, path)| (path, index))
783 .collect::<HashMap<_, _>>()
784 });
785
786 let parameters = std::iter::once((provided_path, parameter)).chain(parameters);
787 for (provided_path, parameter) in parameters {
788 if let Some(index) = matching_path_indices.get(&provided_path).copied() {
789 values[index] = parameter;
790 } else {
791 deferred.insert(provided_path, parameter);
792 }
793 }
794
795 deferred_parameters = Some(deferred);
796 }
797 }
798
799 if !missing_paths.is_empty() {
800 Err(Error::MissingParameters { expected_count, paths: Some(missing_paths) })
801 } else if deferred_parameters.is_some_and(|deferred_parameters| !deferred_parameters.is_empty()) {
802 Err(Error::UnusedParameters { paths: None })
803 } else {
804 Self::from_parameters(structure, values)
805 }
806 }
807
808 fn from_broadcasted_named_parameters<I: IntoIterator<Item = (ParameterPath, P)>>(
818 structure: Self::ParameterStructure,
819 parameters: I,
820 ) -> Result<Self, Error>
821 where
822 P: Clone,
823 {
824 #[derive(Default)]
830 struct PrefixTrieNode {
831 children: HashMap<ParameterPathSegment, usize>,
832 selected_prefix_index: Option<usize>,
833 }
834
835 let paths = structure.named_parameters().map(|(path, _)| path).collect::<Vec<_>>();
836 let expected_count = paths.len();
837 let mut path_prefixes = parameters.into_iter().map(|(path, value)| (path, value, 0usize)).collect::<Vec<_>>();
838
839 let mut prefix_trie = vec![PrefixTrieNode::default()];
842 for (prefix_index, (path, _, _)) in path_prefixes.iter().enumerate() {
843 let mut node_index = 0usize;
844 for segment in path.segments() {
845 let child_index = if let Some(child_index) = prefix_trie[node_index].children.get(segment).copied() {
846 child_index
847 } else {
848 prefix_trie.push(PrefixTrieNode::default());
849 let child_index = prefix_trie.len() - 1;
850 prefix_trie[node_index].children.insert(segment.clone(), child_index);
851 child_index
852 };
853 node_index = child_index;
854 }
855 prefix_trie[node_index].selected_prefix_index = Some(prefix_index);
856 }
857
858 let mut values = Vec::with_capacity(expected_count);
860 let mut missing_paths = Vec::new();
861 for path in paths {
862 let mut trie_node_index = 0usize;
863 let mut selected_prefix_index = prefix_trie[trie_node_index].selected_prefix_index;
864 for segment in path.segments() {
866 let Some(next_trie_node_index) = prefix_trie[trie_node_index].children.get(segment).copied() else {
867 break;
868 };
869 trie_node_index = next_trie_node_index;
870 if let Some(prefix_index) = prefix_trie[trie_node_index].selected_prefix_index {
871 selected_prefix_index = Some(prefix_index);
872 }
873 }
874 if let Some(selected_prefix_index) = selected_prefix_index {
875 let (_, value, matched_count) = &mut path_prefixes[selected_prefix_index];
876 values.push(value.clone());
877 *matched_count += 1;
878 } else {
879 missing_paths.push(path.to_string());
880 }
881 }
882
883 let mut unused_prefix_paths = path_prefixes
884 .into_iter()
885 .filter_map(|(path, _, matched_count)| if matched_count == 0 { Some(path.to_string()) } else { None })
886 .collect::<Vec<_>>();
887
888 if !missing_paths.is_empty() {
889 Err(Error::MissingParameters { expected_count, paths: Some(missing_paths) })
890 } else if !unused_prefix_paths.is_empty() {
891 unused_prefix_paths.sort_unstable();
892 Err(Error::UnusedParameters { paths: Some(unused_prefix_paths) })
893 } else {
894 Self::from_parameters(structure, values)
895 }
896 }
897
898 fn map_parameters<T: Parameter, F: FnMut(P) -> T>(self, map_fn: F) -> Result<Self::To<T>, Error>
903 where
904 Self::Family: ParameterizedFamily<T>,
905 {
906 Self::To::<T>::from_parameters(self.parameter_structure(), self.into_parameters().map(map_fn))
907 }
908
909 fn map_named_parameters<T: Parameter, F: FnMut(&ParameterPath, P) -> T>(
915 self,
916 map_fn: F,
917 ) -> Result<Self::To<T>, Error>
918 where
919 Self::Family: ParameterizedFamily<T>,
920 {
921 let mut map_fn = map_fn;
922 let structure = self.parameter_structure();
923 let mut mapped_parameters = HashMap::with_capacity(structure.parameter_count());
924 for (path, parameter) in self.into_named_parameters() {
925 let mapped_parameter = map_fn(&path, parameter);
926 mapped_parameters.insert(path, mapped_parameter);
927 }
928 Self::To::<T>::from_named_parameters(structure, mapped_parameters)
929 }
930
931 fn filter_parameters<F: FnMut(&ParameterPath, &P) -> bool>(self, predicate: F) -> Result<Self::To<Option<P>>, Error>
954 where
955 Self::Family: ParameterizedFamily<Option<P>>,
956 {
957 let mut predicate = predicate;
958 self.map_named_parameters(|path, parameter| predicate(path, ¶meter).then_some(parameter))
959 }
960
961 fn partition_parameters<F: FnMut(&ParameterPath, &P) -> bool>(
987 self,
988 predicate: F,
989 ) -> Result<(Self::To<Option<P>>, Self::To<Option<P>>), Error>
990 where
991 Self::Family: ParameterizedFamily<Option<P>>,
992 {
993 let structure = self.parameter_structure();
994 let mut predicate = predicate;
995 let mut partition_0_parameters = Vec::new();
996 let mut partition_1_parameters = Vec::new();
997 partition_0_parameters.reserve_exact(structure.parameter_count());
998 partition_1_parameters.reserve_exact(structure.parameter_count());
999 for (path, parameter) in self.into_named_parameters() {
1000 if predicate(&path, ¶meter) {
1001 partition_0_parameters.push(Some(parameter));
1002 partition_1_parameters.push(None);
1003 } else {
1004 partition_0_parameters.push(None);
1005 partition_1_parameters.push(Some(parameter));
1006 }
1007 }
1008 let partition_0 = Self::To::from_parameters(structure, partition_0_parameters)?;
1009 let partition_1 = Self::To::from_parameters(partition_0.parameter_structure(), partition_1_parameters)?;
1010 Ok((partition_0, partition_1))
1011 }
1012
1013 fn combine_parameters<I: IntoIterator<Item = Self::To<Option<P>>>>(
1047 structure: Self::ParameterStructure,
1048 values: I,
1049 ) -> Result<Self, Error>
1050 where
1051 P: Debug + PartialEq,
1052 Self::Family: ParameterizedFamily<Option<P>>,
1053 {
1054 let expected_paths = structure.named_parameters().map(|(path, _)| path).collect::<Vec<_>>();
1055 let expected_count = expected_paths.len();
1056 let mut value_parameters = values.into_iter().map(|value| value.into_named_parameters()).collect::<Vec<_>>();
1057 let mut parameters = Vec::new();
1058 let mut missing_paths = Vec::new();
1059 parameters.reserve_exact(expected_count);
1060 for path in expected_paths {
1061 let mut collected_values = Vec::new();
1062 let mut has_missing_candidates = false;
1063 for iterator in &mut value_parameters {
1064 let Some((_, candidate)) = iterator.next() else {
1065 has_missing_candidates = true;
1066 continue;
1067 };
1068 let Some(candidate) = candidate else {
1069 continue;
1070 };
1071 if !collected_values.iter().any(|value| value == &candidate) {
1072 collected_values.push(candidate);
1073 }
1074 }
1075 if has_missing_candidates || collected_values.is_empty() {
1076 missing_paths.push(path.to_string());
1077 } else if collected_values.len() > 1 {
1078 return Err(Error::AmbiguousParameterCombination {
1079 values: collected_values.into_iter().map(|value| format!("{value:?}")).collect(),
1080 });
1081 } else {
1082 parameters.push(collected_values.pop().unwrap());
1083 }
1084 }
1085
1086 let mut unused_paths = value_parameters
1087 .iter_mut()
1088 .flat_map(|iterator| iterator.map(|(path, _)| path.to_string()))
1089 .collect::<Vec<_>>();
1090
1091 if !missing_paths.is_empty() {
1092 Err(Error::MissingParameters { expected_count, paths: Some(missing_paths) })
1093 } else if !unused_paths.is_empty() {
1094 unused_paths.sort_unstable();
1095 Err(Error::UnusedParameters { paths: Some(unused_paths) })
1096 } else {
1097 Self::from_parameters(structure, parameters)
1098 }
1099 }
1100
1101 fn replace_parameters(self, replacement: Self::To<Option<P>>) -> Result<Self, Error>
1122 where
1123 Self::Family: ParameterizedFamily<Option<P>>,
1124 {
1125 let structure = self.parameter_structure();
1126 let expected_count = structure.parameter_count();
1127 let expected_paths = structure.named_parameters().map(|(path, _)| path).collect::<Vec<_>>();
1128 let mut parameters = self.into_named_parameters();
1129 let mut replacements = replacement.into_named_parameters();
1130 let mut replaced_parameters = Vec::new();
1131 replaced_parameters.reserve_exact(expected_count);
1132 let mut missing_paths = Vec::new();
1133
1134 for path in expected_paths {
1135 let parameter = parameters.next().map(|(_, parameter)| parameter);
1136 let replacement = replacements.next().map(|(_, replacement)| replacement);
1137 if let (Some(parameter), Some(replacement)) = (parameter, replacement) {
1138 replaced_parameters.push(replacement.unwrap_or(parameter));
1139 } else {
1140 missing_paths.push(path.to_string());
1141 }
1142 }
1143
1144 let mut unused_paths = parameters
1145 .map(|(path, _)| path.to_string())
1146 .chain(replacements.map(|(path, _)| path.to_string()))
1147 .collect::<Vec<_>>();
1148
1149 if !missing_paths.is_empty() {
1150 Err(Error::MissingParameters { expected_count, paths: Some(missing_paths) })
1151 } else if !unused_paths.is_empty() {
1152 unused_paths.sort_unstable();
1153 Err(Error::UnusedParameters { paths: Some(unused_paths) })
1154 } else {
1155 Self::from_parameters(structure, replaced_parameters)
1156 }
1157 }
1158}
1159
1160pub struct PathPrefixedParameterIterator<P, I: Iterator<Item = (ParameterPath, P)>> {
1166 pub iterator: I,
1168
1169 pub segment: ParameterPathSegment,
1171}
1172
1173impl<P, I: Iterator<Item = (ParameterPath, P)>> Iterator for PathPrefixedParameterIterator<P, I> {
1174 type Item = (ParameterPath, P);
1175
1176 fn next(&mut self) -> Option<Self::Item> {
1177 self.iterator.next().map(|(mut path, parameter)| {
1178 path.segments.push(self.segment.clone());
1179 (path, parameter)
1180 })
1181 }
1182}
1183
1184pub struct ParameterParameterizedFamily;
1185
1186impl<P: Parameter> ParameterizedFamily<P> for ParameterParameterizedFamily {
1187 type To = P;
1188}
1189
1190impl<P: Parameter> Parameterized<P> for P {
1191 type Family = ParameterParameterizedFamily;
1192
1193 type To<T: Parameter>
1194 = <Self::Family as ParameterizedFamily<T>>::To
1195 where
1196 Self::Family: ParameterizedFamily<T>;
1197
1198 type ParameterStructure = Self::To<Placeholder>;
1199
1200 type ParameterIterator<'t, T: 't + Parameter>
1201 = std::iter::Once<&'t T>
1202 where
1203 Self: 't;
1204
1205 type ParameterIteratorMut<'t, T: 't + Parameter>
1206 = std::iter::Once<&'t mut T>
1207 where
1208 Self: 't;
1209
1210 type ParameterIntoIterator<T: Parameter> = std::iter::Once<T>;
1211
1212 type NamedParameterIterator<'t, T: 't + Parameter>
1213 = std::iter::Once<(ParameterPath, &'t T)>
1214 where
1215 Self: 't;
1216
1217 type NamedParameterIteratorMut<'t, T: 't + Parameter>
1218 = std::iter::Once<(ParameterPath, &'t mut T)>
1219 where
1220 Self: 't;
1221
1222 type NamedParameterIntoIterator<T: Parameter> = std::iter::Once<(ParameterPath, T)>;
1223
1224 fn parameter_count(&self) -> usize {
1225 1
1226 }
1227
1228 fn parameter_structure(&self) -> Self::ParameterStructure {
1229 Placeholder
1230 }
1231
1232 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
1233 std::iter::once(self)
1234 }
1235
1236 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
1237 std::iter::once(self)
1238 }
1239
1240 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
1241 std::iter::once(self)
1242 }
1243
1244 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
1245 std::iter::once((ParameterPath::root(), self))
1246 }
1247
1248 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
1249 std::iter::once((ParameterPath::root(), self))
1250 }
1251
1252 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
1253 std::iter::once((ParameterPath::root(), self))
1254 }
1255
1256 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
1257 _structure: Self::ParameterStructure,
1258 parameters: &mut I,
1259 ) -> Result<Self, Error> {
1260 parameters.next().ok_or(Error::MissingParameters { expected_count: 1, paths: None })
1261 }
1262}
1263
1264pub struct PhantomDataParameterizedFamily;
1265
1266impl<P: Parameter> ParameterizedFamily<P> for PhantomDataParameterizedFamily {
1267 type To = PhantomData<P>;
1268}
1269
1270impl<P: Parameter> Parameterized<P> for PhantomData<P> {
1271 type Family = PhantomDataParameterizedFamily;
1272
1273 type To<T: Parameter>
1274 = <Self::Family as ParameterizedFamily<T>>::To
1275 where
1276 Self::Family: ParameterizedFamily<T>;
1277
1278 type ParameterStructure = Self::To<Placeholder>;
1279
1280 type ParameterIterator<'t, T: 't + Parameter>
1281 = std::iter::Empty<&'t T>
1282 where
1283 Self: 't;
1284
1285 type ParameterIteratorMut<'t, T: 't + Parameter>
1286 = std::iter::Empty<&'t mut T>
1287 where
1288 Self: 't;
1289
1290 type ParameterIntoIterator<T: Parameter> = std::iter::Empty<T>;
1291
1292 type NamedParameterIterator<'t, T: 't + Parameter>
1293 = std::iter::Empty<(ParameterPath, &'t T)>
1294 where
1295 Self: 't;
1296
1297 type NamedParameterIteratorMut<'t, T: 't + Parameter>
1298 = std::iter::Empty<(ParameterPath, &'t mut T)>
1299 where
1300 Self: 't;
1301
1302 type NamedParameterIntoIterator<T: Parameter> = std::iter::Empty<(ParameterPath, T)>;
1303
1304 fn parameter_count(&self) -> usize {
1305 0
1306 }
1307
1308 fn parameter_structure(&self) -> Self::ParameterStructure {
1309 PhantomData
1310 }
1311
1312 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
1313 std::iter::empty()
1314 }
1315
1316 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
1317 std::iter::empty()
1318 }
1319
1320 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
1321 std::iter::empty()
1322 }
1323
1324 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
1325 std::iter::empty()
1326 }
1327
1328 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
1329 std::iter::empty()
1330 }
1331
1332 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
1333 std::iter::empty()
1334 }
1335
1336 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
1337 _structure: Self::ParameterStructure,
1338 _parameters: &mut I,
1339 ) -> Result<Self, Error> {
1340 Ok(PhantomData)
1341 }
1342}
1343
1344macro_rules! tuple_parameterized_family_impl {
1350 ($($F:ident),*) => {
1351 impl<P: Parameter, $($F: ParameterizedFamily<P> + ParameterizedFamily<Placeholder>),*> ParameterizedFamily<P>
1352 for ($($F,)*)
1353 {
1354 type To = ($(<$F as ParameterizedFamily<P>>::To,)*);
1355 }
1356 };
1357}
1358
1359tuple_parameterized_family_impl!();
1360tuple_parameterized_family_impl!(F0);
1361tuple_parameterized_family_impl!(F0, F1);
1362tuple_parameterized_family_impl!(F0, F1, F2);
1363tuple_parameterized_family_impl!(F0, F1, F2, F3);
1364tuple_parameterized_family_impl!(F0, F1, F2, F3, F4);
1365tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5);
1366tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5, F6);
1367tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5, F6, F7);
1368tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5, F6, F7, F8);
1369tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5, F6, F7, F8, F9);
1370tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10);
1371tuple_parameterized_family_impl!(F0, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11);
1372
1373macro_rules! tuple_parameterized_impl {
1374 ($($T:ident:$index:tt),*) => {
1375 paste! {
1376 impl<P: Parameter$(, $T: Parameterized<P>)*> Parameterized<P> for ($($T,)*) {
1377 type Family = ($($T::Family,)*);
1378
1379 type To<T: Parameter>
1380 = <Self::Family as ParameterizedFamily<T>>::To
1381 where
1382 Self::Family: ParameterizedFamily<T>;
1383
1384 type ParameterStructure = Self::To<Placeholder>;
1385
1386 type ParameterIterator<'t, T: 't + Parameter>
1387 = tuple_parameter_iterator_ty!('t, T, ($($T:$index,)*))
1388 where
1389 Self: 't;
1390
1391 type ParameterIteratorMut<'t, T: 't + Parameter>
1392 = tuple_parameter_iterator_mut_ty!('t, T, ($($T:$index,)*))
1393 where
1394 Self: 't;
1395
1396 type ParameterIntoIterator<T: Parameter>
1397 = tuple_parameter_into_iterator_ty!(T, ($($T:$index,)*));
1398
1399 type NamedParameterIterator<'t, T: 't + Parameter>
1400 = tuple_named_parameter_iterator_ty!('t, T, ($($T:$index,)*))
1401 where
1402 Self: 't;
1403
1404 type NamedParameterIteratorMut<'t, T: 't + Parameter>
1405 = tuple_named_parameter_iterator_mut_ty!('t, T, ($($T:$index,)*))
1406 where
1407 Self: 't;
1408
1409 type NamedParameterIntoIterator<T: Parameter>
1410 = tuple_named_parameter_into_iterator_ty!(T, ($($T:$index,)*));
1411
1412 fn parameter_count(&self) -> usize {
1413 let ($([<$T:lower>],)*) = &self;
1414 $([<$T:lower>].parameter_count()+)* 0usize
1415 }
1416
1417 fn parameter_structure(&self) -> Self::ParameterStructure {
1418 let ($([<$T:lower>],)*) = &self;
1419 ($([<$T:lower>].parameter_structure(),)*)
1420 }
1421
1422 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
1423 let ($([<$T:lower>],)*) = self;
1424 tuple_parameter_iterator!(P, ($([<$T:lower>]:$index,)*))
1425 }
1426
1427 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
1428 let ($([<$T:lower>],)*) = self;
1429 tuple_parameter_iterator_mut!(P, ($([<$T:lower>]:$index,)*))
1430 }
1431
1432 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
1433 let ($([<$T:lower>],)*) = self;
1434 tuple_parameter_into_iterator!(P, ($([<$T:lower>]:$index,)*))
1435 }
1436
1437 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
1438 let ($([<$T:lower>],)*) = self;
1439 tuple_named_parameter_iterator!(P, ($([<$T:lower>]:$index,)*))
1440 }
1441
1442 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
1443 let ($([<$T:lower>],)*) = self;
1444 tuple_named_parameter_iterator_mut!(P, ($([<$T:lower>]:$index,)*))
1445 }
1446
1447 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
1448 let ($([<$T:lower>],)*) = self;
1449 tuple_named_parameter_into_iterator!(P, ($([<$T:lower>]:$index,)*))
1450 }
1451
1452 #[allow(unused_variables)]
1453 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
1454 structure: Self::ParameterStructure,
1455 parameters: &mut I,
1456 ) -> Result<Self, Error> {
1457 let ($([<$T:lower _field>],)*) = structure;
1458 $(let [<$T:lower>] = $T::from_parameters_with_remainder([<$T:lower _field>], parameters)?;)*
1459 Ok(($([<$T:lower>],)*))
1460 }
1461 }
1462 }
1463 };
1464}
1465
1466macro_rules! tuple_parameter_iterator_ty {
1467 ($t:lifetime, $T:ty, ()) => {
1468 std::iter::Empty<&$t $T>
1469 };
1470
1471 ($t:lifetime, $T:ty, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1472 std::iter::Chain<
1473 $head::ParameterIterator<$t, $T>,
1474 tuple_parameter_iterator_ty!($t, $T, ($($tail:$tail_index,)*)),
1475 >
1476 };
1477}
1478
1479macro_rules! tuple_parameter_iterator_mut_ty {
1480 ($t:lifetime, $T:ty, ()) => {
1481 std::iter::Empty<&$t mut $T>
1482 };
1483
1484 ($t:lifetime, $T:ty, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1485 std::iter::Chain<
1486 $head::ParameterIteratorMut<$t, $T>,
1487 tuple_parameter_iterator_mut_ty!($t, $T, ($($tail:$tail_index,)*)),
1488 >
1489 };
1490}
1491
1492macro_rules! tuple_parameter_into_iterator_ty {
1493 ($T:ty, ()) => {
1494 std::iter::Empty<$T>
1495 };
1496
1497 ($T:ty, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1498 std::iter::Chain<
1499 $head::ParameterIntoIterator<$T>,
1500 tuple_parameter_into_iterator_ty!($T, ($($tail:$tail_index,)*)),
1501 >
1502 };
1503}
1504
1505macro_rules! tuple_named_parameter_iterator_ty {
1506 ($t:lifetime, $T:ty, ()) => {
1507 std::iter::Empty<(ParameterPath, &$t $T)>
1508 };
1509
1510 ($t:lifetime, $T:ty, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1511 std::iter::Chain<
1512 PathPrefixedParameterIterator<&$t $T, $head::NamedParameterIterator<$t, $T>>,
1513 tuple_named_parameter_iterator_ty!($t, $T, ($($tail:$tail_index,)*)),
1514 >
1515 };
1516}
1517
1518macro_rules! tuple_named_parameter_iterator_mut_ty {
1519 ($t:lifetime, $T:ty, ()) => {
1520 std::iter::Empty<(ParameterPath, &$t mut $T)>
1521 };
1522
1523 ($t:lifetime, $T:ty, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1524 std::iter::Chain<
1525 PathPrefixedParameterIterator<&$t mut $T, $head::NamedParameterIteratorMut<$t, $T>>,
1526 tuple_named_parameter_iterator_mut_ty!($t, $T, ($($tail:$tail_index,)*)),
1527 >
1528 };
1529}
1530
1531macro_rules! tuple_named_parameter_into_iterator_ty {
1532 ($T:ty, ()) => {
1533 std::iter::Empty<(ParameterPath, $T)>
1534 };
1535
1536 ($T:ty, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1537 std::iter::Chain<
1538 PathPrefixedParameterIterator<$T, $head::NamedParameterIntoIterator<$T>>,
1539 tuple_named_parameter_into_iterator_ty!($T, ($($tail:$tail_index,)*)),
1540 >
1541 };
1542}
1543
1544macro_rules! tuple_parameter_iterator {
1545 ($T:tt, ()) => {
1546 std::iter::empty::<&'_ $T>()
1547 };
1548
1549 ($T:tt, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1550 $head.parameters().chain(tuple_parameter_iterator!($T, ($($tail:$tail_index,)*)))
1551 };
1552}
1553
1554macro_rules! tuple_parameter_iterator_mut {
1555 ($T:tt, ()) => {
1556 std::iter::empty::<&'_ mut $T>()
1557 };
1558
1559 ($T:tt, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1560 $head.parameters_mut().chain(tuple_parameter_iterator_mut!($T, ($($tail:$tail_index,)*)))
1561 };
1562}
1563
1564macro_rules! tuple_parameter_into_iterator {
1565 ($T:tt, ()) => {
1566 std::iter::empty::<$T>()
1567 };
1568
1569 ($T:tt, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {
1570 $head.into_parameters().chain(tuple_parameter_into_iterator!($T, ($($tail:$tail_index,)*)))
1571 };
1572}
1573
1574macro_rules! tuple_named_parameter_iterator {
1575 ($T:tt, ()) => {
1576 std::iter::empty::<(ParameterPath, &'_ $T)>()
1577 };
1578
1579 ($T:tt, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {{
1580 let iterator = $head.named_parameters();
1581 let iterator = PathPrefixedParameterIterator { iterator, segment: ParameterPathSegment::TupleIndex($index) };
1582 iterator.chain(tuple_named_parameter_iterator!($T, ($($tail:$tail_index,)*)))
1583 }};
1584}
1585
1586macro_rules! tuple_named_parameter_iterator_mut {
1587 ($T:tt, ()) => {
1588 std::iter::empty::<(ParameterPath, &'_ mut $T)>()
1589 };
1590
1591 ($T:tt, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {{
1592 let iterator = $head.named_parameters_mut();
1593 let iterator = PathPrefixedParameterIterator { iterator, segment: ParameterPathSegment::TupleIndex($index) };
1594 iterator.chain(tuple_named_parameter_iterator_mut!($T, ($($tail:$tail_index,)*)))
1595 }};
1596}
1597
1598macro_rules! tuple_named_parameter_into_iterator {
1599 ($T:tt, ()) => {
1600 std::iter::empty::<(ParameterPath, $T)>()
1601 };
1602
1603 ($T:tt, ($head:ident:$index:tt, $($tail:ident:$tail_index:tt,)*)) => {{
1604 let iterator = $head.into_named_parameters();
1605 let iterator = PathPrefixedParameterIterator { iterator, segment: ParameterPathSegment::TupleIndex($index) };
1606 iterator.chain(tuple_named_parameter_into_iterator!($T, ($($tail:$tail_index,)*)))
1607 }};
1608}
1609
1610tuple_parameterized_impl!();
1611tuple_parameterized_impl!(V0:0);
1612tuple_parameterized_impl!(V0:0, V1:1);
1613tuple_parameterized_impl!(V0:0, V1:1, V2:2);
1614tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3);
1615tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4);
1616tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5);
1617tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5, V6:6);
1618tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5, V6:6, V7:7);
1619tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5, V6:6, V7:7, V8:8);
1620tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5, V6:6, V7:7, V8:8, V9:9);
1621tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5, V6:6, V7:7, V8:8, V9:9, V10:10);
1622tuple_parameterized_impl!(V0:0, V1:1, V2:2, V3:3, V4:4, V5:5, V6:6, V7:7, V8:8, V9:9, V10:10, V11:11);
1623
1624pub struct ArrayParameterizedFamily<F, const N: usize>(PhantomData<F>);
1625
1626impl<P: Parameter, F: ParameterizedFamily<P> + ParameterizedFamily<Placeholder>, const N: usize> ParameterizedFamily<P>
1627 for ArrayParameterizedFamily<F, N>
1628{
1629 type To = [<F as ParameterizedFamily<P>>::To; N];
1630}
1631
1632impl<P: Parameter, V: Parameterized<P>, const N: usize> Parameterized<P> for [V; N] {
1633 type Family = ArrayParameterizedFamily<V::Family, N>;
1634
1635 type To<T: Parameter>
1636 = <Self::Family as ParameterizedFamily<T>>::To
1637 where
1638 Self::Family: ParameterizedFamily<T>;
1639
1640 type ParameterStructure = Self::To<Placeholder>;
1641
1642 type ParameterIterator<'t, T: 't + Parameter>
1643 = std::iter::FlatMap<
1644 std::slice::Iter<'t, V>,
1645 <V as Parameterized<P>>::ParameterIterator<'t, T>,
1646 fn(&'t V) -> <V as Parameterized<P>>::ParameterIterator<'t, T>,
1647 >
1648 where
1649 Self: 't;
1650
1651 type ParameterIteratorMut<'t, T: 't + Parameter>
1652 = std::iter::FlatMap<
1653 std::slice::IterMut<'t, V>,
1654 <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
1655 fn(&'t mut V) -> <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
1656 >
1657 where
1658 Self: 't;
1659
1660 type ParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
1661 std::array::IntoIter<V, N>,
1662 <V as Parameterized<P>>::ParameterIntoIterator<T>,
1663 fn(V) -> <V as Parameterized<P>>::ParameterIntoIterator<T>,
1664 >;
1665
1666 type NamedParameterIterator<'t, T: 't + Parameter>
1667 = std::iter::FlatMap<
1668 std::iter::Enumerate<std::slice::Iter<'t, V>>,
1669 PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
1670 fn(
1671 (usize, &'t V),
1672 ) -> PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
1673 >
1674 where
1675 Self: 't;
1676
1677 type NamedParameterIteratorMut<'t, T: 't + Parameter>
1678 = std::iter::FlatMap<
1679 std::iter::Enumerate<std::slice::IterMut<'t, V>>,
1680 PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
1681 fn(
1682 (usize, &'t mut V),
1683 )
1684 -> PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
1685 >
1686 where
1687 Self: 't;
1688
1689 type NamedParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
1690 std::iter::Enumerate<std::array::IntoIter<V, N>>,
1691 PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
1692 fn((usize, V)) -> PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
1693 >;
1694
1695 fn parameter_count(&self) -> usize {
1696 self.iter().map(|value| value.parameter_count()).sum()
1697 }
1698
1699 fn parameter_structure(&self) -> Self::ParameterStructure {
1700 std::array::from_fn(|i| self[i].parameter_structure())
1701 }
1702
1703 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
1704 self.iter().flat_map(V::parameters)
1705 }
1706
1707 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
1708 self.iter_mut().flat_map(V::parameters_mut)
1709 }
1710
1711 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
1712 self.into_iter().flat_map(V::into_parameters)
1713 }
1714
1715 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
1716 self.iter().enumerate().flat_map(|(index, value)| PathPrefixedParameterIterator {
1717 iterator: value.named_parameters(),
1718 segment: ParameterPathSegment::Index(index),
1719 })
1720 }
1721
1722 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
1723 self.iter_mut().enumerate().flat_map(|(index, value)| PathPrefixedParameterIterator {
1724 iterator: value.named_parameters_mut(),
1725 segment: ParameterPathSegment::Index(index),
1726 })
1727 }
1728
1729 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
1730 self.into_iter().enumerate().flat_map(|(index, value)| PathPrefixedParameterIterator {
1731 iterator: value.into_named_parameters(),
1732 segment: ParameterPathSegment::Index(index),
1733 })
1734 }
1735
1736 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
1737 structure: Self::ParameterStructure,
1738 parameters: &mut I,
1739 ) -> Result<Self, Error> {
1740 Ok(unsafe {
1743 structure
1744 .into_iter()
1745 .map(|value_structure| V::from_parameters_with_remainder(value_structure, parameters))
1746 .collect::<Result<Vec<V>, _>>()?
1747 .try_into()
1748 .unwrap_unchecked()
1749 })
1750 }
1751}
1752
1753pub struct VecParameterizedFamily<F>(PhantomData<F>);
1754
1755impl<P: Parameter, F: ParameterizedFamily<P> + ParameterizedFamily<Placeholder>> ParameterizedFamily<P>
1756 for VecParameterizedFamily<F>
1757{
1758 type To = Vec<<F as ParameterizedFamily<P>>::To>;
1759}
1760
1761impl<P: Parameter, V: Parameterized<P>> Parameterized<P> for Vec<V> {
1762 type Family = VecParameterizedFamily<V::Family>;
1763
1764 type To<T: Parameter>
1765 = <Self::Family as ParameterizedFamily<T>>::To
1766 where
1767 Self::Family: ParameterizedFamily<T>;
1768
1769 type ParameterStructure = Self::To<Placeholder>;
1770
1771 type ParameterIterator<'t, T: 't + Parameter>
1772 = std::iter::FlatMap<
1773 std::slice::Iter<'t, V>,
1774 <V as Parameterized<P>>::ParameterIterator<'t, T>,
1775 fn(&'t V) -> <V as Parameterized<P>>::ParameterIterator<'t, T>,
1776 >
1777 where
1778 Self: 't;
1779
1780 type ParameterIteratorMut<'t, T: 't + Parameter>
1781 = std::iter::FlatMap<
1782 std::slice::IterMut<'t, V>,
1783 <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
1784 fn(&'t mut V) -> <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
1785 >
1786 where
1787 Self: 't;
1788
1789 type ParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
1790 std::vec::IntoIter<V>,
1791 <V as Parameterized<P>>::ParameterIntoIterator<T>,
1792 fn(V) -> <V as Parameterized<P>>::ParameterIntoIterator<T>,
1793 >;
1794
1795 type NamedParameterIterator<'t, T: 't + Parameter>
1796 = std::iter::FlatMap<
1797 std::iter::Enumerate<std::slice::Iter<'t, V>>,
1798 PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
1799 fn(
1800 (usize, &'t V),
1801 ) -> PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
1802 >
1803 where
1804 Self: 't;
1805
1806 type NamedParameterIteratorMut<'t, T: 't + Parameter>
1807 = std::iter::FlatMap<
1808 std::iter::Enumerate<std::slice::IterMut<'t, V>>,
1809 PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
1810 fn(
1811 (usize, &'t mut V),
1812 )
1813 -> PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
1814 >
1815 where
1816 Self: 't;
1817
1818 type NamedParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
1819 std::iter::Enumerate<std::vec::IntoIter<V>>,
1820 PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
1821 fn((usize, V)) -> PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
1822 >;
1823
1824 fn parameter_count(&self) -> usize {
1825 self.iter().map(|value| value.parameter_count()).sum()
1826 }
1827
1828 fn parameter_structure(&self) -> Self::ParameterStructure {
1829 self.iter().map(|value| value.parameter_structure()).collect()
1830 }
1831
1832 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
1833 self.iter().flat_map(|value| value.parameters())
1834 }
1835
1836 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
1837 self.iter_mut().flat_map(|value| value.parameters_mut())
1838 }
1839
1840 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
1841 self.into_iter().flat_map(|value| value.into_parameters())
1842 }
1843
1844 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
1845 self.iter().enumerate().flat_map(|(index, value)| PathPrefixedParameterIterator {
1846 iterator: value.named_parameters(),
1847 segment: ParameterPathSegment::Index(index),
1848 })
1849 }
1850
1851 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
1852 self.iter_mut().enumerate().flat_map(|(index, value)| PathPrefixedParameterIterator {
1853 iterator: value.named_parameters_mut(),
1854 segment: ParameterPathSegment::Index(index),
1855 })
1856 }
1857
1858 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
1859 self.into_iter().enumerate().flat_map(|(index, value)| PathPrefixedParameterIterator {
1860 iterator: value.into_named_parameters(),
1861 segment: ParameterPathSegment::Index(index),
1862 })
1863 }
1864
1865 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
1866 structure: Self::ParameterStructure,
1867 parameters: &mut I,
1868 ) -> Result<Self, Error> {
1869 let expected_count = structure.len();
1870 let mut values = Vec::new();
1871 values.reserve_exact(expected_count);
1872 for value_structure in structure {
1873 values.push(V::from_parameters_with_remainder(value_structure, parameters).map_err(
1874 |error| match error {
1875 Error::MissingParameters { paths, .. } => Error::MissingParameters { expected_count, paths },
1876 error => error,
1877 },
1878 )?);
1879 }
1880 Ok(values)
1881 }
1882}
1883
1884pub struct HashMapParameterizedFamily<K, F, S>(PhantomData<(K, F, S)>);
1885
1886impl<
1887 P: Parameter,
1888 K: Clone + Debug + Eq + Ord + Hash,
1889 F: ParameterizedFamily<P> + ParameterizedFamily<Placeholder>,
1890 S: BuildHasher + Clone,
1891> ParameterizedFamily<P> for HashMapParameterizedFamily<K, F, S>
1892{
1893 type To = HashMap<K, <F as ParameterizedFamily<P>>::To, S>;
1894}
1895
1896impl<P: Parameter, K: Clone + Debug + Eq + Ord + Hash, V: Parameterized<P>, S: BuildHasher + Clone> Parameterized<P>
1901 for HashMap<K, V, S>
1902{
1903 type Family = HashMapParameterizedFamily<K, V::Family, S>;
1904
1905 type To<T: Parameter>
1906 = <Self::Family as ParameterizedFamily<T>>::To
1907 where
1908 Self::Family: ParameterizedFamily<T>;
1909
1910 type ParameterStructure = Self::To<Placeholder>;
1911
1912 type ParameterIterator<'t, T: 't + Parameter>
1913 = std::iter::FlatMap<
1914 std::vec::IntoIter<(K, &'t V)>,
1915 <V as Parameterized<P>>::ParameterIterator<'t, T>,
1916 fn((K, &'t V)) -> <V as Parameterized<P>>::ParameterIterator<'t, T>,
1917 >
1918 where
1919 Self: 't;
1920
1921 type ParameterIteratorMut<'t, T: 't + Parameter>
1922 = std::iter::FlatMap<
1923 std::vec::IntoIter<(K, *mut V)>,
1924 <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
1925 fn((K, *mut V)) -> <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
1926 >
1927 where
1928 Self: 't;
1929
1930 type ParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
1931 std::vec::IntoIter<(K, V)>,
1932 <V as Parameterized<P>>::ParameterIntoIterator<T>,
1933 fn((K, V)) -> <V as Parameterized<P>>::ParameterIntoIterator<T>,
1934 >;
1935
1936 type NamedParameterIterator<'t, T: 't + Parameter>
1937 = std::iter::FlatMap<
1938 std::vec::IntoIter<(&'t K, &'t V)>,
1939 PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
1940 fn(
1941 (&'t K, &'t V),
1942 ) -> PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
1943 >
1944 where
1945 Self: 't;
1946
1947 type NamedParameterIteratorMut<'t, T: 't + Parameter>
1948 = std::iter::FlatMap<
1949 std::vec::IntoIter<(K, *mut V)>,
1950 PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
1951 fn(
1952 (K, *mut V),
1953 )
1954 -> PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
1955 >
1956 where
1957 Self: 't;
1958
1959 type NamedParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
1960 std::vec::IntoIter<(K, V)>,
1961 PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
1962 fn((K, V)) -> PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
1963 >;
1964
1965 fn parameter_count(&self) -> usize {
1966 self.values().map(|value| value.parameter_count()).sum()
1967 }
1968
1969 fn parameter_structure(&self) -> Self::ParameterStructure {
1970 let mut structure = HashMap::with_capacity_and_hasher(self.len(), self.hasher().clone());
1971 let mut sorted_entries = self.iter().map(|(k, v)| (k.clone(), v.parameter_structure())).collect::<Vec<_>>();
1972 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
1973 structure.extend(sorted_entries);
1974 structure
1975 }
1976
1977 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
1978 let mut sorted_entries = self.iter().map(|(k, v)| (k.clone(), v)).collect::<Vec<_>>();
1979 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
1980 sorted_entries.into_iter().flat_map(|(_, v)| V::parameters(v))
1981 }
1982
1983 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
1984 let mut sorted_entries = self.iter_mut().map(|(k, v)| (k.clone(), v as *mut V)).collect::<Vec<_>>();
1988 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
1989 sorted_entries.into_iter().flat_map(|(_, v)| V::parameters_mut(unsafe { &mut *v }))
1990 }
1991
1992 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
1993 let mut sorted_entries = self.into_iter().collect::<Vec<_>>();
1994 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
1995 sorted_entries.into_iter().flat_map(|(_, v)| V::into_parameters(v))
1996 }
1997
1998 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
1999 let mut sorted_entries = self.iter().collect::<Vec<_>>();
2000 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
2001 sorted_entries.into_iter().flat_map(|(k, v)| PathPrefixedParameterIterator {
2002 iterator: v.named_parameters(),
2003 segment: ParameterPathSegment::Key(format!("{k:?}")),
2004 })
2005 }
2006
2007 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
2008 let mut sorted_entries = self.iter_mut().map(|(k, v)| (k.clone(), v as *mut V)).collect::<Vec<_>>();
2012 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
2013 sorted_entries.into_iter().flat_map(|(k, v)| PathPrefixedParameterIterator {
2014 iterator: (unsafe { &mut *v }).named_parameters_mut(),
2015 segment: ParameterPathSegment::Key(format!("{k:?}")),
2016 })
2017 }
2018
2019 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
2020 let mut sorted_entries = self.into_iter().collect::<Vec<_>>();
2021 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
2022 sorted_entries.into_iter().flat_map(|(k, v)| PathPrefixedParameterIterator {
2023 iterator: v.into_named_parameters(),
2024 segment: ParameterPathSegment::Key(format!("{k:?}")),
2025 })
2026 }
2027
2028 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
2029 structure: Self::ParameterStructure,
2030 parameters: &mut I,
2031 ) -> Result<Self, Error> {
2032 let expected_count = structure.len();
2033 let mut values = HashMap::with_capacity_and_hasher(expected_count, structure.hasher().clone());
2034 let mut sorted_entries = structure.into_iter().collect::<Vec<_>>();
2035 sorted_entries.sort_unstable_by(|(l, _), (r, _)| l.cmp(r));
2036 for (key, value_structure) in sorted_entries {
2037 values.insert(
2038 key,
2039 V::from_parameters_with_remainder(value_structure, parameters).map_err(|error| match error {
2040 Error::MissingParameters { paths, .. } => Error::MissingParameters { expected_count, paths },
2041 error => error,
2042 })?,
2043 );
2044 }
2045 Ok(values)
2046 }
2047}
2048
2049pub struct BTreeMapParameterizedFamily<K, F>(PhantomData<(K, F)>);
2050
2051impl<P: Parameter, K: Clone + Debug + Ord, F: ParameterizedFamily<P> + ParameterizedFamily<Placeholder>>
2052 ParameterizedFamily<P> for BTreeMapParameterizedFamily<K, F>
2053{
2054 type To = BTreeMap<K, <F as ParameterizedFamily<P>>::To>;
2055}
2056
2057impl<P: Parameter, K: Clone + Debug + Ord, V: Parameterized<P>> Parameterized<P> for BTreeMap<K, V> {
2058 type Family = BTreeMapParameterizedFamily<K, V::Family>;
2059
2060 type To<T: Parameter>
2061 = <Self::Family as ParameterizedFamily<T>>::To
2062 where
2063 Self::Family: ParameterizedFamily<T>;
2064
2065 type ParameterStructure = Self::To<Placeholder>;
2066
2067 type ParameterIterator<'t, T: 't + Parameter>
2068 = std::iter::FlatMap<
2069 std::collections::btree_map::Values<'t, K, V>,
2070 <V as Parameterized<P>>::ParameterIterator<'t, T>,
2071 fn(&'t V) -> <V as Parameterized<P>>::ParameterIterator<'t, T>,
2072 >
2073 where
2074 Self: 't;
2075
2076 type ParameterIteratorMut<'t, T: 't + Parameter>
2077 = std::iter::FlatMap<
2078 std::collections::btree_map::ValuesMut<'t, K, V>,
2079 <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
2080 fn(&'t mut V) -> <V as Parameterized<P>>::ParameterIteratorMut<'t, T>,
2081 >
2082 where
2083 Self: 't;
2084
2085 type ParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
2086 std::collections::btree_map::IntoValues<K, V>,
2087 <V as Parameterized<P>>::ParameterIntoIterator<T>,
2088 fn(V) -> <V as Parameterized<P>>::ParameterIntoIterator<T>,
2089 >;
2090
2091 type NamedParameterIterator<'t, T: 't + Parameter>
2092 = std::iter::FlatMap<
2093 std::collections::btree_map::Iter<'t, K, V>,
2094 PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
2095 fn(
2096 (&'t K, &'t V),
2097 ) -> PathPrefixedParameterIterator<&'t T, <V as Parameterized<P>>::NamedParameterIterator<'t, T>>,
2098 >
2099 where
2100 Self: 't;
2101
2102 type NamedParameterIteratorMut<'t, T: 't + Parameter>
2103 = std::iter::FlatMap<
2104 std::collections::btree_map::IterMut<'t, K, V>,
2105 PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
2106 fn(
2107 (&'t K, &'t mut V),
2108 )
2109 -> PathPrefixedParameterIterator<&'t mut T, <V as Parameterized<P>>::NamedParameterIteratorMut<'t, T>>,
2110 >
2111 where
2112 Self: 't;
2113
2114 type NamedParameterIntoIterator<T: Parameter> = std::iter::FlatMap<
2115 std::collections::btree_map::IntoIter<K, V>,
2116 PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
2117 fn((K, V)) -> PathPrefixedParameterIterator<T, <V as Parameterized<P>>::NamedParameterIntoIterator<T>>,
2118 >;
2119
2120 fn parameter_count(&self) -> usize {
2121 self.values().map(|value| value.parameter_count()).sum()
2122 }
2123
2124 fn parameter_structure(&self) -> Self::ParameterStructure {
2125 BTreeMap::from_iter(self.iter().map(|(key, value)| (key.clone(), value.parameter_structure())))
2126 }
2127
2128 fn parameters(&self) -> Self::ParameterIterator<'_, P> {
2129 self.values().flat_map(V::parameters)
2130 }
2131
2132 fn parameters_mut(&mut self) -> Self::ParameterIteratorMut<'_, P> {
2133 self.values_mut().flat_map(V::parameters_mut)
2134 }
2135
2136 fn into_parameters(self) -> Self::ParameterIntoIterator<P> {
2137 self.into_values().flat_map(V::into_parameters)
2138 }
2139
2140 fn named_parameters(&self) -> Self::NamedParameterIterator<'_, P> {
2141 self.iter().flat_map(|(key, value)| PathPrefixedParameterIterator {
2142 iterator: value.named_parameters(),
2143 segment: ParameterPathSegment::Key(format!("{key:?}")),
2144 })
2145 }
2146
2147 fn named_parameters_mut(&mut self) -> Self::NamedParameterIteratorMut<'_, P> {
2148 self.iter_mut().flat_map(|(key, value)| PathPrefixedParameterIterator {
2149 iterator: value.named_parameters_mut(),
2150 segment: ParameterPathSegment::Key(format!("{key:?}")),
2151 })
2152 }
2153
2154 fn into_named_parameters(self) -> Self::NamedParameterIntoIterator<P> {
2155 self.into_iter().flat_map(|(key, value)| PathPrefixedParameterIterator {
2156 iterator: value.into_named_parameters(),
2157 segment: ParameterPathSegment::Key(format!("{key:?}")),
2158 })
2159 }
2160
2161 fn from_parameters_with_remainder<I: Iterator<Item = P>>(
2162 structure: Self::ParameterStructure,
2163 parameters: &mut I,
2164 ) -> Result<Self, Error> {
2165 let expected_count = structure.len();
2166 let mut values = BTreeMap::new();
2167 for (key, value_structure) in structure {
2168 values.insert(
2169 key,
2170 V::from_parameters_with_remainder(value_structure, parameters).map_err(|error| match error {
2171 Error::MissingParameters { paths, .. } => Error::MissingParameters { expected_count, paths },
2172 error => error,
2173 })?,
2174 );
2175 }
2176 Ok(values)
2177 }
2178}
2179
2180#[cfg(test)]
2181mod tests {
2182 use std::collections::{BTreeMap, HashMap};
2183
2184 use ryft::*;
2185
2186 #[test]
2187 fn test_placeholder() {
2188 let placeholder = Placeholder;
2189 assert_eq!(format!("{placeholder}"), "<Parameter>");
2190 assert_eq!(format!("{placeholder:?}"), "<Parameter>");
2191 }
2192
2193 #[test]
2194 fn test_parameter_path() {
2195 let path = ParameterPath::root();
2196 assert_eq!(path.len(), 0);
2197 assert!(path.is_empty());
2198 assert!(path.is_root());
2199 let path_prefix = ParameterPath::root().variant("ResidualConnection").field("weights");
2200 let path = path_prefix.clone().index(2).tuple_index(1).key("alpha");
2201 assert_eq!(path_prefix.len(), 2);
2202 assert_eq!(path.len(), 5);
2203 assert!(!path.is_root());
2204 assert!(path.is_prefix_of(&path));
2205 assert!(path_prefix.is_prefix_of(&path));
2206 assert!(!path.is_prefix_of(&path_prefix));
2207 assert_eq!(
2208 path.segments().cloned().collect::<Vec<_>>(),
2209 vec![
2210 ParameterPathSegment::Variant("ResidualConnection"),
2211 ParameterPathSegment::Field("weights"),
2212 ParameterPathSegment::Index(2),
2213 ParameterPathSegment::TupleIndex(1),
2214 ParameterPathSegment::Key(format!("{:?}", "alpha")),
2215 ],
2216 );
2217 assert_eq!(format!("{path}"), "$.residual_connection.weights[2].1[\"alpha\"]");
2218 assert_eq!(format!("{path:?}"), "ParameterPath[$.residual_connection.weights[2].1[\"alpha\"]]");
2219 }
2220
2221 #[test]
2222 fn test_parameterized() {
2223 #[derive(Parameterized, Clone, Debug, PartialEq, Eq)]
2224 struct Block<P: Parameter> {
2225 pair: (P, usize),
2226 gain: P,
2227 name: &'static str,
2228 }
2229
2230 #[derive(Parameterized, Clone, Debug, PartialEq, Eq)]
2231 #[allow(dead_code)]
2232 enum Controller<P: Parameter> {
2233 Identity,
2234 Blend { alpha: P, branch: Block<P> },
2235 }
2236
2237 #[derive(Parameterized, Clone, Debug, PartialEq, Eq)]
2238 struct Layer<P: Parameter> {
2239 weights: Vec<P>,
2240 bias: P,
2241 tag: &'static str,
2242 }
2243
2244 #[derive(Parameterized, Clone, Debug, PartialEq, Eq)]
2245 struct Network<P: Parameter> {
2246 stem: Layer<P>,
2247 controller: Controller<P>,
2248 heads: [Block<P>; 2],
2249 metadata: (usize, &'static str),
2250 }
2251
2252 let value = Network {
2253 stem: Layer { weights: vec![1, 2], bias: 3, tag: "stem" },
2254 controller: Controller::Blend { alpha: 4, branch: Block { pair: (5, 10), gain: 6, name: "branch" } },
2255 heads: [
2256 Block { pair: (7, 11), gain: 8, name: "head_0" },
2257 Block { pair: (9, 12), gain: 10, name: "head_1" },
2258 ],
2259 metadata: (42, "meta"),
2260 };
2261
2262 let expected_parameter_paths = vec![
2263 "$.stem.weights[0]".to_string(),
2264 "$.stem.weights[1]".to_string(),
2265 "$.stem.bias".to_string(),
2266 "$.controller.blend.alpha".to_string(),
2267 "$.controller.blend.branch.pair.0".to_string(),
2268 "$.controller.blend.branch.gain".to_string(),
2269 "$.heads[0].pair.0".to_string(),
2270 "$.heads[0].gain".to_string(),
2271 "$.heads[1].pair.0".to_string(),
2272 "$.heads[1].gain".to_string(),
2273 ];
2274
2275 assert_eq!(value.parameter_count(), 10);
2277
2278 let structure = value.parameter_structure();
2280 assert_eq!(
2281 structure,
2282 Network {
2283 stem: Layer { weights: vec![Placeholder, Placeholder], bias: Placeholder, tag: "stem" },
2284 controller: Controller::Blend {
2285 alpha: Placeholder,
2286 branch: Block { pair: (Placeholder, 10), gain: Placeholder, name: "branch" },
2287 },
2288 heads: [
2289 Block { pair: (Placeholder, 11), gain: Placeholder, name: "head_0" },
2290 Block { pair: (Placeholder, 12), gain: Placeholder, name: "head_1" },
2291 ],
2292 metadata: (42, "meta"),
2293 },
2294 );
2295
2296 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10]);
2298
2299 let mut value_clone = value.clone();
2301 for parameter in value_clone.parameters_mut() {
2302 *parameter += 100;
2303 }
2304 assert_eq!(
2305 value_clone.parameters().copied().collect::<Vec<_>>(),
2306 vec![101, 102, 103, 104, 105, 106, 107, 108, 109, 110]
2307 );
2308
2309 assert_eq!(value.clone().into_parameters().collect::<Vec<_>>(), vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10]);
2311
2312 assert_eq!(
2314 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2315 expected_parameter_paths
2316 .iter()
2317 .cloned()
2318 .zip(vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
2319 .collect::<Vec<_>>()
2320 );
2321
2322 let mut value_clone = value.clone();
2324 let mut seen_parameter_paths = Vec::new();
2325 for (path, parameter) in value_clone.named_parameters_mut() {
2326 seen_parameter_paths.push(path.to_string());
2327 *parameter += path.len() as i32;
2328 }
2329 assert_eq!(seen_parameter_paths, expected_parameter_paths);
2330 assert_eq!(value_clone.parameters().copied().collect::<Vec<_>>(), vec![4, 5, 5, 7, 10, 10, 11, 11, 13, 13]);
2331
2332 assert_eq!(
2334 value
2335 .clone()
2336 .into_named_parameters()
2337 .map(|(path, parameter)| (path.to_string(), parameter))
2338 .collect::<Vec<_>>(),
2339 vec![
2340 ("$.stem.weights[0]".to_string(), 1),
2341 ("$.stem.weights[1]".to_string(), 2),
2342 ("$.stem.bias".to_string(), 3),
2343 ("$.controller.blend.alpha".to_string(), 4),
2344 ("$.controller.blend.branch.pair.0".to_string(), 5),
2345 ("$.controller.blend.branch.gain".to_string(), 6),
2346 ("$.heads[0].pair.0".to_string(), 7),
2347 ("$.heads[0].gain".to_string(), 8),
2348 ("$.heads[1].pair.0".to_string(), 9),
2349 ("$.heads[1].gain".to_string(), 10),
2350 ]
2351 );
2352
2353 assert_eq!(value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(), expected_parameter_paths);
2355
2356 let mut parameters = vec![11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 500].into_iter();
2358 assert_eq!(
2359 Network::from_parameters_with_remainder(structure.clone(), &mut parameters),
2360 Ok(Network {
2361 stem: Layer { weights: vec![11, 12], bias: 13, tag: "stem" },
2362 controller: Controller::Blend { alpha: 14, branch: Block { pair: (15, 10), gain: 16, name: "branch" } },
2363 heads: [
2364 Block { pair: (17, 11), gain: 18, name: "head_0" },
2365 Block { pair: (19, 12), gain: 20, name: "head_1" },
2366 ],
2367 metadata: (42, "meta"),
2368 })
2369 );
2370 assert_eq!(parameters.collect::<Vec<_>>(), vec![500]);
2371
2372 assert_eq!(
2374 Network::from_parameters(structure.clone(), vec![21, 22, 23, 24, 25, 26, 27, 28, 29, 30]),
2375 Ok(Network {
2376 stem: Layer { weights: vec![21, 22], bias: 23, tag: "stem" },
2377 controller: Controller::Blend { alpha: 24, branch: Block { pair: (25, 10), gain: 26, name: "branch" } },
2378 heads: [
2379 Block { pair: (27, 11), gain: 28, name: "head_0" },
2380 Block { pair: (29, 12), gain: 30, name: "head_1" },
2381 ],
2382 metadata: (42, "meta"),
2383 })
2384 );
2385 assert_eq!(
2386 Network::from_parameters(structure.clone(), vec![31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 999]),
2387 Err(Error::UnusedParameters { paths: None })
2388 );
2389
2390 let mut parameters = value.clone().into_named_parameters().collect::<Vec<_>>();
2392 parameters.reverse();
2393 assert_eq!(Network::from_named_parameters(structure.clone(), parameters), Ok(value.clone()));
2394
2395 assert_eq!(
2397 Network::from_broadcasted_named_parameters(
2398 structure.clone(),
2399 HashMap::from([
2400 (ParameterPath::root(), 1),
2401 (ParameterPath::root().field("controller"), 2),
2402 (ParameterPath::root().field("controller").variant("Blend").field("branch"), 10),
2403 (ParameterPath::root().field("controller").variant("Blend").field("branch").field("gain"), 20),
2404 (ParameterPath::root().field("heads").index(1), 30),
2405 ])
2406 ),
2407 Ok(Network {
2408 stem: Layer { weights: vec![1, 1], bias: 1, tag: "stem" },
2409 controller: Controller::Blend { alpha: 2, branch: Block { pair: (10, 10), gain: 20, name: "branch" } },
2410 heads: [
2411 Block { pair: (1, 11), gain: 1, name: "head_0" },
2412 Block { pair: (30, 12), gain: 30, name: "head_1" },
2413 ],
2414 metadata: (42, "meta"),
2415 })
2416 );
2417
2418 assert_eq!(
2420 value.clone().map_parameters(|parameter| i64::from(parameter) * 10),
2421 Ok(Network {
2422 stem: Layer { weights: vec![10i64, 20i64], bias: 30i64, tag: "stem" },
2423 controller: Controller::Blend {
2424 alpha: 40i64,
2425 branch: Block { pair: (50i64, 10), gain: 60i64, name: "branch" },
2426 },
2427 heads: [
2428 Block { pair: (70i64, 11), gain: 80i64, name: "head_0" },
2429 Block { pair: (90i64, 12), gain: 100i64, name: "head_1" },
2430 ],
2431 metadata: (42, "meta"),
2432 })
2433 );
2434
2435 assert_eq!(
2437 value
2438 .clone()
2439 .map_named_parameters(|path, parameter| i64::from(parameter) + (path.len() as i64))
2440 .unwrap()
2441 .into_parameters()
2442 .collect::<Vec<_>>(),
2443 vec![4i64, 5i64, 5i64, 7i64, 10i64, 10i64, 11i64, 11i64, 13i64, 13i64],
2444 );
2445
2446 assert_eq!(
2448 value
2449 .clone()
2450 .filter_parameters(|path, _| path.to_string().ends_with(".bias") || path.to_string().ends_with(".gain"))
2451 .unwrap()
2452 .into_parameters()
2453 .collect::<Vec<_>>(),
2454 vec![None, None, Some(3), None, None, Some(6), None, Some(8), None, Some(10)],
2455 );
2456
2457 let (partition_0, partition_1) =
2459 value.clone().partition_parameters(|path, _| path.to_string().starts_with("$.heads[1]")).unwrap();
2460 assert_eq!(
2461 partition_0.clone().into_parameters().collect::<Vec<_>>(),
2462 vec![None, None, None, None, None, None, None, None, Some(9), Some(10)],
2463 );
2464 assert_eq!(
2465 partition_1.clone().into_parameters().collect::<Vec<_>>(),
2466 vec![Some(1), Some(2), Some(3), Some(4), Some(5), Some(6), Some(7), Some(8), None, None],
2467 );
2468
2469 assert_eq!(Network::combine_parameters(structure.clone(), vec![partition_0, partition_1]), Ok(value.clone()));
2471
2472 assert_eq!(
2474 value
2475 .clone()
2476 .replace_parameters(
2477 value
2478 .map_parameters(|parameter| match parameter {
2479 2 => Some(200),
2480 5 => Some(500),
2481 7 => Some(700),
2482 10 => Some(1000),
2483 _ => None,
2484 })
2485 .unwrap()
2486 )
2487 .unwrap()
2488 .into_parameters()
2489 .collect::<Vec<_>>(),
2490 vec![1, 200, 3, 4, 500, 6, 700, 8, 9, 1000],
2491 );
2492 }
2493
2494 #[test]
2495 fn test_parameterized_parameter() {
2496 let value = 7i32;
2497 assert_eq!(value.parameter_count(), 1);
2498 assert_eq!(value.parameter_structure(), Placeholder);
2499 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![7]);
2500 assert_eq!(
2501 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2502 vec![("$".to_string(), 7)],
2503 );
2504 assert_eq!(value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(), vec!["$".to_string()]);
2505 }
2506
2507 #[test]
2508 fn test_parameterized_tuple() {
2509 let value = (0i32, (1i32, 2i32), (3i32, (4i32, 5i32)), 6i32, ((7i32, 8i32), 9i32));
2510 assert_eq!(value.parameter_count(), 10);
2511 assert_eq!(
2512 value.parameter_structure(),
2513 (
2514 Placeholder,
2515 (Placeholder, Placeholder),
2516 (Placeholder, (Placeholder, Placeholder)),
2517 Placeholder,
2518 ((Placeholder, Placeholder), Placeholder),
2519 ),
2520 );
2521 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
2522 assert_eq!(
2523 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2524 vec![
2525 ("$.0".to_string(), 0),
2526 ("$.1.0".to_string(), 1),
2527 ("$.1.1".to_string(), 2),
2528 ("$.2.0".to_string(), 3),
2529 ("$.2.1.0".to_string(), 4),
2530 ("$.2.1.1".to_string(), 5),
2531 ("$.3".to_string(), 6),
2532 ("$.4.0.0".to_string(), 7),
2533 ("$.4.0.1".to_string(), 8),
2534 ("$.4.1".to_string(), 9),
2535 ],
2536 );
2537 assert_eq!(
2538 value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(),
2539 vec![
2540 "$.0".to_string(),
2541 "$.1.0".to_string(),
2542 "$.1.1".to_string(),
2543 "$.2.0".to_string(),
2544 "$.2.1.0".to_string(),
2545 "$.2.1.1".to_string(),
2546 "$.3".to_string(),
2547 "$.4.0.0".to_string(),
2548 "$.4.0.1".to_string(),
2549 "$.4.1".to_string(),
2550 ],
2551 );
2552 }
2553
2554 #[test]
2555 fn test_parameterized_array() {
2556 let value = [(1, 2), (3, 4), (5, 6)];
2557 assert_eq!(value.parameter_count(), 6);
2558 assert_eq!(
2559 value.parameter_structure(),
2560 [(Placeholder, Placeholder), (Placeholder, Placeholder), (Placeholder, Placeholder)],
2561 );
2562 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![1, 2, 3, 4, 5, 6]);
2563 assert_eq!(
2564 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2565 vec![
2566 ("$[0].0".to_string(), 1),
2567 ("$[0].1".to_string(), 2),
2568 ("$[1].0".to_string(), 3),
2569 ("$[1].1".to_string(), 4),
2570 ("$[2].0".to_string(), 5),
2571 ("$[2].1".to_string(), 6),
2572 ],
2573 );
2574 assert_eq!(
2575 value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(),
2576 vec![
2577 "$[0].0".to_string(),
2578 "$[0].1".to_string(),
2579 "$[1].0".to_string(),
2580 "$[1].1".to_string(),
2581 "$[2].0".to_string(),
2582 "$[2].1".to_string(),
2583 ],
2584 );
2585 }
2586
2587 #[test]
2588 fn test_parameterized_vec() {
2589 let value = vec![(1, 2), (3, 4)];
2590 assert_eq!(value.parameter_count(), 4);
2591 assert_eq!(value.parameter_structure(), vec![(Placeholder, Placeholder), (Placeholder, Placeholder)]);
2592 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![1, 2, 3, 4]);
2593 assert_eq!(
2594 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2595 vec![
2596 ("$[0].0".to_string(), 1),
2597 ("$[0].1".to_string(), 2),
2598 ("$[1].0".to_string(), 3),
2599 ("$[1].1".to_string(), 4),
2600 ],
2601 );
2602 assert_eq!(
2603 value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(),
2604 vec!["$[0].0".to_string(), "$[0].1".to_string(), "$[1].0".to_string(), "$[1].1".to_string()],
2605 );
2606 }
2607
2608 #[test]
2609 fn test_parameterized_hash_map() {
2610 let value = HashMap::from([("zeta", (1, 2)), ("alpha", (3, 4)), ("mu", (5, 6))]);
2611 assert_eq!(value.parameter_count(), 6);
2612 assert_eq!(
2613 value.parameter_structure(),
2614 HashMap::from([
2615 ("alpha", (Placeholder, Placeholder)),
2616 ("mu", (Placeholder, Placeholder)),
2617 ("zeta", (Placeholder, Placeholder)),
2618 ]),
2619 );
2620 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![3, 4, 5, 6, 1, 2]);
2621 assert_eq!(
2622 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2623 vec![
2624 ("$[\"alpha\"].0".to_string(), 3),
2625 ("$[\"alpha\"].1".to_string(), 4),
2626 ("$[\"mu\"].0".to_string(), 5),
2627 ("$[\"mu\"].1".to_string(), 6),
2628 ("$[\"zeta\"].0".to_string(), 1),
2629 ("$[\"zeta\"].1".to_string(), 2),
2630 ],
2631 );
2632 assert_eq!(
2633 value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(),
2634 vec![
2635 "$[\"alpha\"].0".to_string(),
2636 "$[\"alpha\"].1".to_string(),
2637 "$[\"mu\"].0".to_string(),
2638 "$[\"mu\"].1".to_string(),
2639 "$[\"zeta\"].0".to_string(),
2640 "$[\"zeta\"].1".to_string(),
2641 ],
2642 );
2643 }
2644
2645 #[test]
2646 fn test_parameterized_b_tree_map() {
2647 let value = BTreeMap::from([("left", (1, 2)), ("right", (3, 4))]);
2648 assert_eq!(value.parameter_count(), 4);
2649 assert_eq!(
2650 value.parameter_structure(),
2651 BTreeMap::from([("left", (Placeholder, Placeholder)), ("right", (Placeholder, Placeholder))]),
2652 );
2653 assert_eq!(value.parameters().copied().collect::<Vec<_>>(), vec![1, 2, 3, 4]);
2654 assert_eq!(
2655 value.named_parameters().map(|(path, parameter)| (path.to_string(), *parameter)).collect::<Vec<_>>(),
2656 vec![
2657 ("$[\"left\"].0".to_string(), 1),
2658 ("$[\"left\"].1".to_string(), 2),
2659 ("$[\"right\"].0".to_string(), 3),
2660 ("$[\"right\"].1".to_string(), 4),
2661 ],
2662 );
2663 assert_eq!(
2664 value.parameter_paths().map(|path| path.to_string()).collect::<Vec<_>>(),
2665 vec![
2666 "$[\"left\"].0".to_string(),
2667 "$[\"left\"].1".to_string(),
2668 "$[\"right\"].0".to_string(),
2669 "$[\"right\"].1".to_string(),
2670 ],
2671 );
2672 }
2673}