LU.h
Go to the documentation of this file.
1 //=================================================================================================
33 //=================================================================================================
34 
35 #ifndef _BLAZE_MATH_DENSE_LU_H_
36 #define _BLAZE_MATH_DENSE_LU_H_
37 
38 
39 //*************************************************************************************************
40 // Includes
41 //*************************************************************************************************
42 
43 #include <algorithm>
53 #include <blaze/math/Functions.h>
57 #include <blaze/util/Exception.h>
58 
59 
60 namespace blaze {
61 
62 //=================================================================================================
63 //
64 // LU DECOMPOSITION FUNCTIONS
65 //
66 //=================================================================================================
67 
68 //*************************************************************************************************
71 template< typename MT1, bool SO1, typename MT2, typename MT3, typename MT4, bool SO2 >
72 void lu( const DenseMatrix<MT1,SO1>& A, DenseMatrix<MT2,SO1>& L,
73  DenseMatrix<MT3,SO1>& U, Matrix<MT4,SO2>& P );
75 //*************************************************************************************************
76 
77 
78 //*************************************************************************************************
91 template< typename MT1 // Type of matrix A
92  , bool SO1 // Storage order of dense matrix A
93  , typename MT2 // Type of matrix P
94  , bool SO2 > // Storage order of matrix P
95 void lu( DenseMatrix<MT1,SO1>& A, Matrix<MT2,SO2>& P )
96 {
100 
101  typedef typename MT2::ElementType ET;
102 
103  const size_t m( (~A).rows() );
104  const size_t n( (~A).columns() );
105  const size_t mindim( min( m, n ) );
106  const size_t size( SO1 ? m : n );
107 
108  UniqueArray<int> helper( new int[mindim + size] );
109  int* ipiv ( helper.get() );
110  int* permut( ipiv + mindim );
111 
112  getrf( ~A, ipiv );
113 
114  for( size_t i=0UL; i<size; ++i ) {
115  permut[i] = i;
116  }
117 
118  for( int i=0; i<mindim; ++i ) {
119  --ipiv[i];
120  if( ipiv[i] != i ) {
121  std::swap( permut[ipiv[i]], permut[i] );
122  }
123  }
124 
125  resize( ~P, size, size );
126  reset( ~P );
127  for( size_t i=0UL; i<size; ++i ) {
128  (~P)( ( SO1 ? permut[i] : i ), ( SO1 ? i : permut[i] ) ) = ET(1);
129  }
130 }
132 //*************************************************************************************************
133 
134 
135 //*************************************************************************************************
211 template< typename MT1 // Type of matrix A
212  , bool SO1 // Storage order of matrix A, L and U
213  , typename MT2 // Type of matrix L
214  , typename MT3 // Type of matrix U
215  , typename MT4 // Type of matrix P
216  , bool SO2 > // Storage order of matrix P
219 {
222 
227 
232 
233  typedef typename MT2::ElementType ET2;
234  typedef typename MT3::ElementType ET3;
235 
236  const size_t m( (~A).rows() );
237  const size_t n( (~A).columns() );
238  const size_t mindim( min( m, n ) );
239  const size_t size( SO1 ? m : n );
240 
241  if( ( !IsResizable<MT2>::value && ( (~L).rows() != m || (~L).columns() != mindim ) ) ||
242  ( !IsResizable<MT3>::value && ( (~U).rows() != mindim || (~U).columns() != n ) ) ||
243  ( !IsResizable<MT4>::value && ( (~P).rows() != size || (~P).columns() != size ) ) ) {
244  BLAZE_THROW_INVALID_ARGUMENT( "Dimensions of fixed size matrix do not match" );
245  }
246 
247  if( ( IsSquare<MT2>::value && n < m ) || ( IsSquare<MT3>::value && m < n ) ) {
248  BLAZE_THROW_INVALID_ARGUMENT( "Square matrix cannot be resized to m-by-n" );
249  }
250 
251  typename DerestrictTrait<MT2>::Type l( derestrict( ~L ) );
252  typename DerestrictTrait<MT3>::Type u( derestrict( ~U ) );
253 
254  if( m < n )
255  {
256  u = (~A);
257  lu( u, ~P );
258 
259  resize( ~L, m, m );
260  reset( l );
261 
262  if( SO1 == rowMajor )
263  {
264  for( size_t i=0UL; i<m; ++i )
265  {
266  for( size_t j=0UL; j<i; ++j ) {
267  l(i,j) = u(i,j);
268  reset( u(i,j) );
269  }
270 
271  l(i,i) = u(i,i);
272  u(i,i) = ET3(1);
273  }
274  }
275  else
276  {
277  for( size_t j=0UL; j<m; ++j )
278  {
279  l(j,j) = ET2(1);
280 
281  for( size_t i=j+1UL; i<m; ++i ) {
282  l(i,j) = u(i,j);
283  reset( u(i,j) );
284  }
285  }
286  }
287  }
288  else
289  {
290  l = (~A);
291  lu( l, ~P );
292 
293  resize( ~U, n, n );
294  reset( u );
295 
296  if( SO1 == rowMajor )
297  {
298  for( size_t i=0UL; i<n; ++i )
299  {
300  u(i,i) = ET3(1);
301 
302  for( size_t j=i+1UL; j<n; ++j ) {
303  u(i,j) = l(i,j);
304  reset( l(i,j) );
305  }
306  }
307  }
308  else
309  {
310  for( size_t j=0UL; j<n; ++j )
311  {
312  for( size_t i=0UL; i<j; ++i ) {
313  u(i,j) = l(i,j);
314  reset( l(i,j) );
315  }
316 
317  u(j,j) = l(j,j);
318  l(j,j) = ET2(1);
319  }
320  }
321  }
322 }
323 //*************************************************************************************************
324 
325 } // namespace blaze
326 
327 #endif
#define BLAZE_THROW_INVALID_ARGUMENT(MESSAGE)
Macro for the emission of a std::invalid_argument exceptionThis macro encapsulates the default way of...
Definition: Exception.h:187
Header file for mathematical functions.
BLAZE_ALWAYS_INLINE size_t size(const Vector< VT, TF > &vector)
Returns the current size/dimension of the vector.
Definition: Vector.h:252
void reset(const DiagonalProxy< MT > &proxy)
Resetting the represented element to the default initial values.
Definition: DiagonalProxy.h:507
BLAZE_ALWAYS_INLINE size_t rows(const Matrix< MT, SO > &matrix)
Returns the current number of rows of the matrix.
Definition: Matrix.h:308
#define BLAZE_CONSTRAINT_MUST_NOT_BE_UNITRIANGULAR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a lower or upper unitriangular matrix ty...
Definition: UniTriangular.h:118
Constraint on the data type.
Constraint on the data type.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_ADAPTOR_TYPE(T)
Constraint on the data type.In case the given data type T is an adaptor type (as for instance LowerMa...
Definition: Adaptor.h:118
Base class for dense matrices.The DenseMatrix class is a base class for all dense matrix classes...
Definition: DenseMatrix.h:70
Constraint on the data type.
Namespace of the Blaze C++ math library.
Definition: Blaze.h:57
void swap(CompressedMatrix< Type, SO > &a, CompressedMatrix< Type, SO > &b)
Swapping the contents of two compressed matrices.
Definition: CompressedMatrix.h:4998
const MT::ElementType min(const DenseMatrix< MT, SO > &dm)
Returns the smallest element of the dense matrix.
Definition: DenseMatrix.h:1682
Header file for the DenseMatrix base class.
void lu(const DenseMatrix< MT1, SO1 > &A, DenseMatrix< MT2, SO1 > &L, DenseMatrix< MT3, SO1 > &U, Matrix< MT4, SO2 > &P)
LU decomposition of the given dense matrix.
Definition: LU.h:217
Compile time check for square matrices.This type trait tests whether or not the given template parame...
Definition: IsSquare.h:87
#define BLAZE_CONSTRAINT_MUST_NOT_BE_UPPER_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a upper triangular matrix type...
Definition: Upper.h:118
BLAZE_ALWAYS_INLINE void resize(Matrix< MT, SO > &matrix, size_t rows, size_t columns, bool preserve=true)
Changing the size of the matrix.
Definition: Matrix.h:532
Type ElementType
Type of the sparse matrix elements.
Definition: CompressedMatrix.h:2586
Constraint on the data type.
Header file for the DerestrictTrait class template.
Constraint on the data type.
Compile time check for resizable data types.This type trait tests whether the given data type is a re...
Definition: IsResizable.h:75
#define BLAZE_CONSTRAINT_MUST_NOT_BE_SYMMETRIC_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a symmetric matrix type, a compilation error is created.
Definition: Symmetric.h:116
void getrf(int m, int n, float *A, int lda, int *ipiv, int *info)
LAPACK kernel for the LU decomposition of the given dense general single precision column-major matri...
Definition: getrf.h:139
Constraint on the data type.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_LOWER_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a lower triangular matrix type...
Definition: Lower.h:118
Base class for matrices.The Matrix class is a base class for all dense and sparse matrix classes with...
Definition: Forward.h:94
#define BLAZE_CONSTRAINT_MUST_BE_BLAS_COMPATIBLE_TYPE(T)
Constraint on the data type.In case the given data type T is not a BLAS compatible data type (i...
Definition: BlasCompatible.h:79
Constraint on the data type.
Evaluation of the return type of the derestrict function.Via this type trait it is possible to evalua...
Definition: DerestrictTrait.h:74
Constraint on the data type.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_STRICTLY_TRIANGULAR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a strictly lower or upper triangular mat...
Definition: StrictlyTriangular.h:118
const bool rowMajor
Storage order flag for row-major matrices.
Definition: StorageOrder.h:71
BLAZE_ALWAYS_INLINE size_t columns(const Matrix< MT, SO > &matrix)
Returns the current number of columns of the matrix.
Definition: Matrix.h:324
#define BLAZE_CONSTRAINT_MUST_NOT_BE_HERMITIAN_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is an Hermitian matrix type, a compilation error is created.
Definition: Hermitian.h:116
Header file for exception macros.
Header file for the IsResizable type trait.
Header file for the LAPACK LU decomposition functions (getrf)