1use pounce_linalg::Vector;
24use std::rc::Rc;
25
26#[derive(Clone)]
28pub struct IteratesVector {
29 pub x: Rc<dyn Vector>,
30 pub s: Rc<dyn Vector>,
31 pub y_c: Rc<dyn Vector>,
32 pub y_d: Rc<dyn Vector>,
33 pub z_l: Rc<dyn Vector>,
34 pub z_u: Rc<dyn Vector>,
35 pub v_l: Rc<dyn Vector>,
36 pub v_u: Rc<dyn Vector>,
37}
38
39impl std::fmt::Debug for IteratesVector {
40 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
41 f.debug_struct("IteratesVector")
42 .field("x_dim", &self.x.dim())
43 .field("s_dim", &self.s.dim())
44 .field("y_c_dim", &self.y_c.dim())
45 .field("y_d_dim", &self.y_d.dim())
46 .field("z_l_dim", &self.z_l.dim())
47 .field("z_u_dim", &self.z_u.dim())
48 .field("v_l_dim", &self.v_l.dim())
49 .field("v_u_dim", &self.v_u.dim())
50 .finish()
51 }
52}
53
54impl IteratesVector {
55 #[allow(clippy::too_many_arguments)]
57 pub fn new(
58 x: Rc<dyn Vector>,
59 s: Rc<dyn Vector>,
60 y_c: Rc<dyn Vector>,
61 y_d: Rc<dyn Vector>,
62 z_l: Rc<dyn Vector>,
63 z_u: Rc<dyn Vector>,
64 v_l: Rc<dyn Vector>,
65 v_u: Rc<dyn Vector>,
66 ) -> Self {
67 Self {
68 x,
69 s,
70 y_c,
71 y_d,
72 z_l,
73 z_u,
74 v_l,
75 v_u,
76 }
77 }
78
79 pub fn dim(&self) -> i32 {
81 self.x.dim()
82 + self.s.dim()
83 + self.y_c.dim()
84 + self.y_d.dim()
85 + self.z_l.dim()
86 + self.z_u.dim()
87 + self.v_l.dim()
88 + self.v_u.dim()
89 }
90
91 pub fn amax(&self) -> pounce_common::types::Number {
95 let mut m = self.x.amax();
96 for v in [
97 &self.s, &self.y_c, &self.y_d, &self.z_l, &self.z_u, &self.v_l, &self.v_u,
98 ] {
99 let a = v.amax();
100 if a > m {
101 m = a;
102 }
103 }
104 m
105 }
106
107 pub fn make_new_zeroed(&self) -> IteratesVectorMut {
110 IteratesVectorMut {
111 x: self.x.make_new(),
112 s: self.s.make_new(),
113 y_c: self.y_c.make_new(),
114 y_d: self.y_d.make_new(),
115 z_l: self.z_l.make_new(),
116 z_u: self.z_u.make_new(),
117 v_l: self.v_l.make_new(),
118 v_u: self.v_u.make_new(),
119 }
120 }
121
122 pub fn deep_copy(&self) -> IteratesVectorMut {
124 let mut out = self.make_new_zeroed();
125 out.x.copy(&*self.x);
126 out.s.copy(&*self.s);
127 out.y_c.copy(&*self.y_c);
128 out.y_d.copy(&*self.y_d);
129 out.z_l.copy(&*self.z_l);
130 out.z_u.copy(&*self.z_u);
131 out.v_l.copy(&*self.v_l);
132 out.v_u.copy(&*self.v_u);
133 out
134 }
135}
136
137pub struct IteratesVectorMut {
141 pub x: Box<dyn Vector>,
142 pub s: Box<dyn Vector>,
143 pub y_c: Box<dyn Vector>,
144 pub y_d: Box<dyn Vector>,
145 pub z_l: Box<dyn Vector>,
146 pub z_u: Box<dyn Vector>,
147 pub v_l: Box<dyn Vector>,
148 pub v_u: Box<dyn Vector>,
149}
150
151impl IteratesVectorMut {
152 pub fn freeze(self) -> IteratesVector {
154 IteratesVector::new(
155 Rc::from(self.x),
156 Rc::from(self.s),
157 Rc::from(self.y_c),
158 Rc::from(self.y_d),
159 Rc::from(self.z_l),
160 Rc::from(self.z_u),
161 Rc::from(self.v_l),
162 Rc::from(self.v_u),
163 )
164 }
165
166 pub fn amax(&self) -> pounce_common::types::Number {
167 let mut m = self.x.amax();
168 for v in [
169 &self.s, &self.y_c, &self.y_d, &self.z_l, &self.z_u, &self.v_l, &self.v_u,
170 ] {
171 let a = v.amax();
172 if a > m {
173 m = a;
174 }
175 }
176 m
177 }
178
179 pub fn scal(&mut self, alpha: pounce_common::types::Number) {
181 self.x.scal(alpha);
182 self.s.scal(alpha);
183 self.y_c.scal(alpha);
184 self.y_d.scal(alpha);
185 self.z_l.scal(alpha);
186 self.z_u.scal(alpha);
187 self.v_l.scal(alpha);
188 self.v_u.scal(alpha);
189 }
190
191 pub fn axpy(&mut self, alpha: pounce_common::types::Number, other: &IteratesVector) {
193 self.x.axpy(alpha, &*other.x);
194 self.s.axpy(alpha, &*other.s);
195 self.y_c.axpy(alpha, &*other.y_c);
196 self.y_d.axpy(alpha, &*other.y_d);
197 self.z_l.axpy(alpha, &*other.z_l);
198 self.z_u.axpy(alpha, &*other.z_u);
199 self.v_l.axpy(alpha, &*other.v_l);
200 self.v_u.axpy(alpha, &*other.v_u);
201 }
202
203 pub fn add_one_vector(
206 &mut self,
207 a: pounce_common::types::Number,
208 other: &IteratesVector,
209 b: pounce_common::types::Number,
210 ) {
211 self.x.add_one_vector(a, &*other.x, b);
212 self.s.add_one_vector(a, &*other.s, b);
213 self.y_c.add_one_vector(a, &*other.y_c, b);
214 self.y_d.add_one_vector(a, &*other.y_d, b);
215 self.z_l.add_one_vector(a, &*other.z_l, b);
216 self.z_u.add_one_vector(a, &*other.z_u, b);
217 self.v_l.add_one_vector(a, &*other.v_l, b);
218 self.v_u.add_one_vector(a, &*other.v_u, b);
219 }
220}
221
222#[cfg(test)]
223mod tests {
224 use super::*;
225 use pounce_linalg::dense_vector::DenseVectorSpace;
226
227 fn zero_vec(n: i32) -> Rc<dyn Vector> {
228 let space = DenseVectorSpace::new(n);
229 Rc::new(space.make_new_dense())
230 }
231
232 #[test]
233 fn iterates_vector_dim_sums_components() {
234 let iv = IteratesVector::new(
235 zero_vec(4),
236 zero_vec(1),
237 zero_vec(1),
238 zero_vec(1),
239 zero_vec(4),
240 zero_vec(4),
241 zero_vec(1),
242 zero_vec(1),
243 );
244 assert_eq!(iv.dim(), 4 + 1 + 1 + 1 + 4 + 4 + 1 + 1);
245 }
246}