| 178 | } |
| 179 | |
| 180 | fn get_y_x( |
| 181 | series: &[f64], |
| 182 | model: &str, |
| 183 | lags: SadfLags, |
| 184 | add_const: bool, |
| 185 | ) -> StructuralBreakResult<(Vec<Vec<f64>>, Vec<f64>, Vec<usize>)> { |
| 186 | let series_len = series.len(); |
| 187 | if series_len < 2 { |
| 188 | return Err(StructuralBreakError::InputTooShort); |
| 189 | } |
| 190 | |
| 191 | let mut series_diff = Vec::with_capacity(series_len - 1); |
| 192 | for i in 1..series_len { |
| 193 | series_diff.push(series[i] - series[i - 1]); |
| 194 | } |
| 195 | |
| 196 | let lag_values = match lags { |
| 197 | SadfLags::Fixed(value) => (1..=value).collect::<Vec<_>>(), |
| 198 | SadfLags::Array(values) => values.into_iter().map(|v| v as usize).collect(), |
| 199 | }; |
| 200 | let max_lag = *lag_values.iter().max().unwrap_or(&0); |
| 201 | let start_index = max_lag + 1; |
| 202 | if series_len <= start_index { |
| 203 | return Err(StructuralBreakError::InputTooShort); |
| 204 | } |
| 205 | |
| 206 | let mut indices = Vec::new(); |
| 207 | let mut x_rows = Vec::new(); |
| 208 | let mut y_values = Vec::new(); |
| 209 | |
| 210 | for idx in start_index..=series_len - 1 { |
| 211 | let mut row = Vec::with_capacity(lag_values.len()); |
| 212 | for lag in &lag_values { |
| 213 | let pos = idx - lag - 1; |
| 214 | row.push(series_diff[pos]); |
| 215 | } |
| 216 | x_rows.push(row); |
| 217 | indices.push(idx); |
| 218 | y_values.push(series_diff[idx - 1]); |
| 219 | } |
| 220 | |
| 221 | let mut x = x_rows; |
| 222 | let mut y = y_values; |
| 223 | |
| 224 | match model { |
| 225 | "linear" | "quadratic" => { |
| 226 | let mut updated = Vec::with_capacity(x.len()); |
| 227 | for (i, row) in x.into_iter().enumerate() { |
| 228 | let mut new_row = Vec::with_capacity(row.len() + 3); |
| 229 | new_row.push(series[indices[i] - 1]); |
| 230 | new_row.extend(row); |
| 231 | if add_const { |
| 232 | new_row.push(1.0); |
| 233 | } |
| 234 | let trend = i as f64; |
| 235 | let trend_value = if model == "quadratic" { trend * trend } else { trend }; |
| 236 | new_row.push(trend_value); |
| 237 | updated.push(new_row); |