|
2 | 2 | //! for tridiagonal matrix
|
3 | 3 |
|
4 | 4 | use super::*;
|
5 |
| -use crate::{error::*, layout::MatrixLayout}; |
| 5 | +use crate::{error::*, layout::*}; |
6 | 6 | use cauchy::*;
|
7 | 7 | use num_traits::Zero;
|
8 | 8 | use std::ops::{Index, IndexMut};
|
@@ -201,19 +201,40 @@ macro_rules! impl_tridiagonal {
|
201 | 201 |
|
202 | 202 | unsafe fn solve_tridiagonal(
|
203 | 203 | lu: &LUFactorizedTridiagonal<Self>,
|
204 |
| - bl: MatrixLayout, |
| 204 | + b_layout: MatrixLayout, |
205 | 205 | t: Transpose,
|
206 | 206 | b: &mut [Self],
|
207 | 207 | ) -> Result<()> {
|
208 | 208 | let (n, _) = lu.a.l.size();
|
209 |
| - let (_, nrhs) = bl.size(); |
210 | 209 | let ipiv = &lu.ipiv;
|
211 |
| - let ldb = bl.lda(); |
| 210 | + // Transpose if b is C-continuous |
| 211 | + let mut b_t = None; |
| 212 | + let b_layout = match b_layout { |
| 213 | + MatrixLayout::C { .. } => { |
| 214 | + b_t = Some(vec![Self::zero(); b.len()]); |
| 215 | + transpose(b_layout, b, b_t.as_mut().unwrap()) |
| 216 | + } |
| 217 | + MatrixLayout::F { .. } => b_layout, |
| 218 | + }; |
| 219 | + let (ldb, nrhs) = b_layout.size(); |
212 | 220 | let mut info = 0;
|
213 | 221 | $gttrs(
|
214 |
| - t as u8, n, nrhs, &lu.a.dl, &lu.a.d, &lu.a.du, &lu.du2, ipiv, b, ldb, &mut info, |
| 222 | + t as u8, |
| 223 | + n, |
| 224 | + nrhs, |
| 225 | + &lu.a.dl, |
| 226 | + &lu.a.d, |
| 227 | + &lu.a.du, |
| 228 | + &lu.du2, |
| 229 | + ipiv, |
| 230 | + b_t.as_mut().map(|v| v.as_mut_slice()).unwrap_or(b), |
| 231 | + ldb, |
| 232 | + &mut info, |
215 | 233 | );
|
216 | 234 | info.as_lapack_result()?;
|
| 235 | + if let Some(b_t) = b_t { |
| 236 | + transpose(b_layout, &b_t, b); |
| 237 | + } |
217 | 238 | Ok(())
|
218 | 239 | }
|
219 | 240 | }
|
|
0 commit comments