MFEM  v4.0
Finite element discretization library
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Pages
densemat.hpp
Go to the documentation of this file.
1 // Copyright (c) 2010, Lawrence Livermore National Security, LLC. Produced at
2 // the Lawrence Livermore National Laboratory. LLNL-CODE-443211. All Rights
3 // reserved. See file COPYRIGHT for details.
4 //
5 // This file is part of the MFEM library. For more information and source code
6 // availability see http://mfem.org.
7 //
8 // MFEM is free software; you can redistribute it and/or modify it under the
9 // terms of the GNU Lesser General Public License (as published by the Free
10 // Software Foundation) version 2.1 dated February 1999.
11 
12 #ifndef MFEM_DENSEMAT
13 #define MFEM_DENSEMAT
14 
15 #include "../config/config.hpp"
16 #include "../general/globals.hpp"
17 #include "matrix.hpp"
18 
19 namespace mfem
20 {
21 
22 /// Data type dense matrix using column-major storage
23 class DenseMatrix : public Matrix
24 {
25  friend class DenseTensor;
26  friend class DenseMatrixInverse;
27 
28 private:
29  double *data;
30  int capacity; // zero or negative capacity means we do not own the data.
31 
32  void Eigensystem(Vector &ev, DenseMatrix *evect = NULL);
33 
34  void Eigensystem(DenseMatrix &b, Vector &ev, DenseMatrix *evect = NULL);
35 
36  // Auxiliary method used in FNorm2() and FNorm()
37  void FNorm(double &scale_factor, double &scaled_fnorm2) const;
38 
39 public:
40  /** Default constructor for DenseMatrix.
41  Sets data = NULL and height = width = 0. */
42  DenseMatrix();
43 
44  /// Copy constructor
45  DenseMatrix(const DenseMatrix &);
46 
47  /// Creates square matrix of size s.
48  explicit DenseMatrix(int s);
49 
50  /// Creates rectangular matrix of size m x n.
51  DenseMatrix(int m, int n);
52 
53  /// Creates rectangular matrix equal to the transpose of mat.
54  DenseMatrix(const DenseMatrix &mat, char ch);
55 
56  /// Construct a DenseMatrix using an existing data array.
57  /** The DenseMatrix does not assume ownership of the data array, i.e. it will
58  not delete the array. */
59  DenseMatrix(double *d, int h, int w)
60  : Matrix(h, w) { UseExternalData(d, h, w); }
61 
62  /// Change the data array and the size of the DenseMatrix.
63  /** The DenseMatrix does not assume ownership of the data array, i.e. it will
64  not delete the data array @a d. This method should not be used with
65  DenseMatrix that owns its current data array. */
66  void UseExternalData(double *d, int h, int w)
67  { data = d; height = h; width = w; capacity = -h*w; }
68 
69  /// Change the data array and the size of the DenseMatrix.
70  /** The DenseMatrix does not assume ownership of the data array, i.e. it will
71  not delete the new array @a d. This method will delete the current data
72  array, if owned. */
73  void Reset(double *d, int h, int w)
74  { if (OwnsData()) { delete [] data; } UseExternalData(d, h, w); }
75 
76  /** Clear the data array and the dimensions of the DenseMatrix. This method
77  should not be used with DenseMatrix that owns its current data array. */
78  void ClearExternalData() { data = NULL; height = width = 0; capacity = 0; }
79 
80  /// Delete the matrix data array (if owned) and reset the matrix state.
81  void Clear()
82  { if (OwnsData()) { delete [] data; } ClearExternalData(); }
83 
84  /// For backward compatibility define Size to be synonym of Width()
85  int Size() const { return Width(); }
86 
87  /// Change the size of the DenseMatrix to s x s.
88  void SetSize(int s) { SetSize(s, s); }
89 
90  /// Change the size of the DenseMatrix to h x w.
91  void SetSize(int h, int w);
92 
93  /// Returns the matrix data array.
94  inline double *Data() const { return data; }
95  /// Returns the matrix data array.
96  inline double *GetData() const { return data; }
97 
98  inline bool OwnsData() const { return (capacity > 0); }
99 
100  /// Returns reference to a_{ij}.
101  inline double &operator()(int i, int j);
102 
103  /// Returns constant reference to a_{ij}.
104  inline const double &operator()(int i, int j) const;
105 
106  /// Matrix inner product: tr(A^t B)
107  double operator*(const DenseMatrix &m) const;
108 
109  /// Trace of a square matrix
110  double Trace() const;
111 
112  /// Returns reference to a_{ij}.
113  virtual double &Elem(int i, int j);
114 
115  /// Returns constant reference to a_{ij}.
116  virtual const double &Elem(int i, int j) const;
117 
118  /// Matrix vector multiplication.
119  void Mult(const double *x, double *y) const;
120 
121  /// Matrix vector multiplication.
122  virtual void Mult(const Vector &x, Vector &y) const;
123 
124  /// Multiply a vector with the transpose matrix.
125  void MultTranspose(const double *x, double *y) const;
126 
127  /// Multiply a vector with the transpose matrix.
128  virtual void MultTranspose(const Vector &x, Vector &y) const;
129 
130  /// y += A.x
131  void AddMult(const Vector &x, Vector &y) const;
132 
133  /// y += A^t x
134  void AddMultTranspose(const Vector &x, Vector &y) const;
135 
136  /// y += a * A.x
137  void AddMult_a(double a, const Vector &x, Vector &y) const;
138 
139  /// y += a * A^t x
140  void AddMultTranspose_a(double a, const Vector &x, Vector &y) const;
141 
142  /// Compute y^t A x
143  double InnerProduct(const double *x, const double *y) const;
144 
145  /// LeftScaling this = diag(s) * this
146  void LeftScaling(const Vector & s);
147  /// InvLeftScaling this = diag(1./s) * this
148  void InvLeftScaling(const Vector & s);
149  /// RightScaling: this = this * diag(s);
150  void RightScaling(const Vector & s);
151  /// InvRightScaling: this = this * diag(1./s);
152  void InvRightScaling(const Vector & s);
153  /// SymmetricScaling this = diag(sqrt(s)) * this * diag(sqrt(s))
154  void SymmetricScaling(const Vector & s);
155  /// InvSymmetricScaling this = diag(sqrt(1./s)) * this * diag(sqrt(1./s))
156  void InvSymmetricScaling(const Vector & s);
157 
158  /// Compute y^t A x
159  double InnerProduct(const Vector &x, const Vector &y) const
160  { return InnerProduct((const double *)x, (const double *)y); }
161 
162  /// Returns a pointer to the inverse matrix.
163  virtual MatrixInverse *Inverse() const;
164 
165  /// Replaces the current matrix with its inverse
166  void Invert();
167 
168  /// Replaces the current matrix with its square root inverse
169  void SquareRootInverse();
170 
171  /// Calculates the determinant of the matrix
172  /// (optimized for 2x2, 3x3, and 4x4 matrices)
173  double Det() const;
174 
175  double Weight() const;
176 
177  /** @brief Set the matrix to alpha * A, assuming that A has the same
178  dimensions as the matrix and uses column-major layout. */
179  void Set(double alpha, const double *A);
180  /// Set the matrix to alpha * A.
181  void Set(double alpha, const DenseMatrix &A)
182  {
183  SetSize(A.Height(), A.Width());
184  Set(alpha, A.GetData());
185  }
186 
187  /// Adds the matrix A multiplied by the number c to the matrix
188  void Add(const double c, const DenseMatrix &A);
189 
190  /// Sets the matrix elements equal to constant c
191  DenseMatrix &operator=(double c);
192 
193  /// Copy the matrix entries from the given array
194  DenseMatrix &operator=(const double *d);
195 
196  /// Sets the matrix size and elements equal to those of m
197  DenseMatrix &operator=(const DenseMatrix &m);
198 
199  DenseMatrix &operator+=(const double *m);
201 
203 
204  DenseMatrix &operator*=(double c);
205 
206  /// (*this) = -(*this)
207  void Neg();
208 
209  /// Take the 2-norm of the columns of A and store in v
210  void Norm2(double *v) const;
211 
212  /// Compute the norm ||A|| = max_{ij} |A_{ij}|
213  double MaxMaxNorm() const;
214 
215  /// Compute the Frobenius norm of the matrix
216  double FNorm() const { double s, n2; FNorm(s, n2); return s*sqrt(n2); }
217 
218  /// Compute the square of the Frobenius norm of the matrix
219  double FNorm2() const { double s, n2; FNorm(s, n2); return s*s*n2; }
220 
221  /// Compute eigenvalues of A x = ev x where A = *this
222  void Eigenvalues(Vector &ev)
223  { Eigensystem(ev); }
224 
225  /// Compute eigenvalues and eigenvectors of A x = ev x where A = *this
226  void Eigenvalues(Vector &ev, DenseMatrix &evect)
227  { Eigensystem(ev, &evect); }
228 
229  /// Compute eigenvalues and eigenvectors of A x = ev x where A = *this
230  void Eigensystem(Vector &ev, DenseMatrix &evect)
231  { Eigensystem(ev, &evect); }
232 
233  /** Compute generalized eigenvalues and eigenvectors of A x = ev B x,
234  where A = *this */
236  { Eigensystem(b, ev); }
237 
238  /// Compute generalized eigenvalues of A x = ev B x, where A = *this
240  { Eigensystem(b, ev, &evect); }
241 
242  /** Compute generalized eigenvalues and eigenvectors of A x = ev B x,
243  where A = *this */
245  { Eigensystem(b, ev, &evect); }
246 
247  void SingularValues(Vector &sv) const;
248  int Rank(double tol) const;
249 
250  /// Return the i-th singular value (decreasing order) of NxN matrix, N=1,2,3.
251  double CalcSingularvalue(const int i) const;
252 
253  /** Return the eigenvalues (in increasing order) and eigenvectors of a
254  2x2 or 3x3 symmetric matrix. */
255  void CalcEigenvalues(double *lambda, double *vec) const;
256 
257  void GetRow(int r, Vector &row) const;
258  void GetColumn(int c, Vector &col) const;
259  double *GetColumn(int col) { return data + col*height; }
260  const double *GetColumn(int col) const { return data + col*height; }
261 
262  void GetColumnReference(int c, Vector &col)
263  { col.SetDataAndSize(data + c * height, height); }
264 
265  void SetRow(int r, const Vector &row);
266  void SetCol(int c, const Vector &col);
267 
268  /// Set all entries of a row to the specified value.
269  void SetRow(int row, double value);
270  /// Set all entries of a column to the specified value.
271  void SetCol(int col, double value);
272 
273  /// Returns the diagonal of the matrix
274  void GetDiag(Vector &d) const;
275  /// Returns the l1 norm of the rows of the matrix v_i = sum_j |a_ij|
276  void Getl1Diag(Vector &l) const;
277  /// Compute the row sums of the DenseMatrix
278  void GetRowSums(Vector &l) const;
279 
280  /// Creates n x n diagonal matrix with diagonal elements c
281  void Diag(double c, int n);
282  /// Creates n x n diagonal matrix with diagonal given by diag
283  void Diag(double *diag, int n);
284 
285  /// (*this) = (*this)^t
286  void Transpose();
287  /// (*this) = A^t
288  void Transpose(const DenseMatrix &A);
289  /// (*this) = 1/2 ((*this) + (*this)^t)
290  void Symmetrize();
291 
292  void Lump();
293 
294  /** Given a DShape matrix (from a scalar FE), stored in *this, returns the
295  CurlShape matrix. If *this is a N by D matrix, then curl is a D*N by
296  D*(D-1)/2 matrix. The size of curl must be set outside. The dimension D
297  can be either 2 or 3. */
298  void GradToCurl(DenseMatrix &curl);
299  /** Given a DShape matrix (from a scalar FE), stored in *this,
300  returns the DivShape vector. If *this is a N by dim matrix,
301  then div is a dim*N vector. The size of div must be set
302  outside. */
303  void GradToDiv(Vector &div);
304 
305  /// Copy rows row1 through row2 from A to *this
306  void CopyRows(const DenseMatrix &A, int row1, int row2);
307  /// Copy columns col1 through col2 from A to *this
308  void CopyCols(const DenseMatrix &A, int col1, int col2);
309  /// Copy the m x n submatrix of A at row/col offsets Aro/Aco to *this
310  void CopyMN(const DenseMatrix &A, int m, int n, int Aro, int Aco);
311  /// Copy matrix A to the location in *this at row_offset, col_offset
312  void CopyMN(const DenseMatrix &A, int row_offset, int col_offset);
313  /// Copy matrix A^t to the location in *this at row_offset, col_offset
314  void CopyMNt(const DenseMatrix &A, int row_offset, int col_offset);
315  /** Copy the m x n submatrix of A at row/col offsets Aro/Aco to *this at
316  row_offset, col_offset */
317  void CopyMN(const DenseMatrix &A, int m, int n, int Aro, int Aco,
318  int row_offset, int col_offset);
319  /// Copy c on the diagonal of size n to *this at row_offset, col_offset
320  void CopyMNDiag(double c, int n, int row_offset, int col_offset);
321  /// Copy diag on the diagonal of size n to *this at row_offset, col_offset
322  void CopyMNDiag(double *diag, int n, int row_offset, int col_offset);
323  /// Copy All rows and columns except m and n from A
324  void CopyExceptMN(const DenseMatrix &A, int m, int n);
325 
326  /// Perform (ro+i,co+j)+=A(i,j) for 0<=i<A.Height, 0<=j<A.Width
327  void AddMatrix(DenseMatrix &A, int ro, int co);
328  /// Perform (ro+i,co+j)+=a*A(i,j) for 0<=i<A.Height, 0<=j<A.Width
329  void AddMatrix(double a, const DenseMatrix &A, int ro, int co);
330 
331  /// Add the matrix 'data' to the Vector 'v' at the given 'offset'
332  void AddToVector(int offset, Vector &v) const;
333  /// Get the matrix 'data' from the Vector 'v' at the given 'offset'
334  void GetFromVector(int offset, const Vector &v);
335  /** If (dofs[i] < 0 and dofs[j] >= 0) or (dofs[i] >= 0 and dofs[j] < 0)
336  then (*this)(i,j) = -(*this)(i,j). */
337  void AdjustDofDirection(Array<int> &dofs);
338 
339  /// Replace small entries, abs(a_ij) <= eps, with zero.
340  void Threshold(double eps);
341 
342  /** Count the number of entries in the matrix for which isfinite
343  is false, i.e. the entry is a NaN or +/-Inf. */
344  int CheckFinite() const { return mfem::CheckFinite(data, height*width); }
345 
346  /// Prints matrix to stream out.
347  virtual void Print(std::ostream &out = mfem::out, int width_ = 4) const;
348  virtual void PrintMatlab(std::ostream &out = mfem::out) const;
349  /// Prints the transpose matrix to stream out.
350  virtual void PrintT(std::ostream &out = mfem::out, int width_ = 4) const;
351 
352  /// Invert and print the numerical conditioning of the inversion.
353  void TestInversion();
354 
355  long MemoryUsage() const { return std::abs(capacity) * sizeof(double); }
356 
357  /// Destroys dense matrix.
358  virtual ~DenseMatrix();
359 };
360 
361 /// C = A + alpha*B
362 void Add(const DenseMatrix &A, const DenseMatrix &B,
363  double alpha, DenseMatrix &C);
364 
365 /// C = alpha*A + beta*B
366 void Add(double alpha, const double *A,
367  double beta, const double *B, DenseMatrix &C);
368 
369 /// C = alpha*A + beta*B
370 void Add(double alpha, const DenseMatrix &A,
371  double beta, const DenseMatrix &B, DenseMatrix &C);
372 
373 /// Matrix matrix multiplication. A = B * C.
374 void Mult(const DenseMatrix &b, const DenseMatrix &c, DenseMatrix &a);
375 
376 /// Matrix matrix multiplication. A += B * C.
377 void AddMult(const DenseMatrix &b, const DenseMatrix &c, DenseMatrix &a);
378 
379 /** Calculate the adjugate of a matrix (for NxN matrices, N=1,2,3) or the matrix
380  adj(A^t.A).A^t for rectangular matrices (2x1, 3x1, or 3x2). This operation
381  is well defined even when the matrix is not full rank. */
382 void CalcAdjugate(const DenseMatrix &a, DenseMatrix &adja);
383 
384 /// Calculate the transposed adjugate of a matrix (for NxN matrices, N=1,2,3)
385 void CalcAdjugateTranspose(const DenseMatrix &a, DenseMatrix &adjat);
386 
387 /** Calculate the inverse of a matrix (for NxN matrices, N=1,2,3) or the
388  left inverse (A^t.A)^{-1}.A^t (for 2x1, 3x1, or 3x2 matrices) */
389 void CalcInverse(const DenseMatrix &a, DenseMatrix &inva);
390 
391 /// Calculate the inverse transpose of a matrix (for NxN matrices, N=1,2,3)
392 void CalcInverseTranspose(const DenseMatrix &a, DenseMatrix &inva);
393 
394 /** For a given Nx(N-1) (N=2,3) matrix J, compute a vector n such that
395  n_k = (-1)^{k+1} det(J_k), k=1,..,N, where J_k is the matrix J with the
396  k-th row removed. Note: J^t.n = 0, det([n|J])=|n|^2=det(J^t.J). */
397 void CalcOrtho(const DenseMatrix &J, Vector &n);
398 
399 /// Calculate the matrix A.At
400 void MultAAt(const DenseMatrix &a, DenseMatrix &aat);
401 
402 /// ADAt = A D A^t, where D is diagonal
403 void MultADAt(const DenseMatrix &A, const Vector &D, DenseMatrix &ADAt);
404 
405 /// ADAt += A D A^t, where D is diagonal
406 void AddMultADAt(const DenseMatrix &A, const Vector &D, DenseMatrix &ADAt);
407 
408 /// Multiply a matrix A with the transpose of a matrix B: A*Bt
409 void MultABt(const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &ABt);
410 
411 /// ADBt = A D B^t, where D is diagonal
412 void MultADBt(const DenseMatrix &A, const Vector &D,
413  const DenseMatrix &B, DenseMatrix &ADBt);
414 
415 /// ABt += A * B^t
416 void AddMultABt(const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &ABt);
417 
418 /// ADBt = A D B^t, where D is diagonal
419 void AddMultADBt(const DenseMatrix &A, const Vector &D,
420  const DenseMatrix &B, DenseMatrix &ADBt);
421 
422 /// ABt += a * A * B^t
423 void AddMult_a_ABt(double a, const DenseMatrix &A, const DenseMatrix &B,
424  DenseMatrix &ABt);
425 
426 /// Multiply the transpose of a matrix A with a matrix B: At*B
427 void MultAtB(const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &AtB);
428 
429 /// AAt += a * A * A^t
430 void AddMult_a_AAt(double a, const DenseMatrix &A, DenseMatrix &AAt);
431 
432 /// AAt = a * A * A^t
433 void Mult_a_AAt(double a, const DenseMatrix &A, DenseMatrix &AAt);
434 
435 /// Make a matrix from a vector V.Vt
436 void MultVVt(const Vector &v, DenseMatrix &vvt);
437 
438 void MultVWt(const Vector &v, const Vector &w, DenseMatrix &VWt);
439 
440 /// VWt += v w^t
441 void AddMultVWt(const Vector &v, const Vector &w, DenseMatrix &VWt);
442 
443 /// VVt += v v^t
444 void AddMultVVt(const Vector &v, DenseMatrix &VWt);
445 
446 /// VWt += a * v w^t
447 void AddMult_a_VWt(const double a, const Vector &v, const Vector &w,
448  DenseMatrix &VWt);
449 
450 /// VVt += a * v v^t
451 void AddMult_a_VVt(const double a, const Vector &v, DenseMatrix &VVt);
452 
453 
454 /** Class that can compute LU factorization of external data and perform various
455  operations with the factored data. */
457 {
458 public:
459  double *data;
460  int *ipiv;
461 #ifdef MFEM_USE_LAPACK
462  static const int ipiv_base = 1;
463 #else
464  static const int ipiv_base = 0;
465 #endif
466 
467  /** With this constructor, the (public) data and ipiv members should be set
468  explicitly before calling class methods. */
469  LUFactors() { }
470 
471  LUFactors(double *data_, int *ipiv_) : data(data_), ipiv(ipiv_) { }
472 
473  /** Factorize the current data of size (m x m) overwriting it with the LU
474  factors. The factorization is such that L.U = P.A, where A is the
475  original matrix and P is a permutation matrix represented by ipiv. */
476  void Factor(int m);
477 
478  /** Assuming L.U = P.A factored data of size (m x m), compute |A|
479  from the diagonal values of U and the permutation information. */
480  double Det(int m) const;
481 
482  /** Assuming L.U = P.A factored data of size (m x m), compute X <- A X,
483  for a matrix X of size (m x n). */
484  void Mult(int m, int n, double *X) const;
485 
486  /** Assuming L.U = P.A factored data of size (m x m), compute
487  X <- L^{-1} P X, for a matrix X of size (m x n). */
488  void LSolve(int m, int n, double *X) const;
489 
490  /** Assuming L.U = P.A factored data of size (m x m), compute
491  X <- U^{-1} X, for a matrix X of size (m x n). */
492  void USolve(int m, int n, double *X) const;
493 
494  /** Assuming L.U = P.A factored data of size (m x m), compute X <- A^{-1} X,
495  for a matrix X of size (m x n). */
496  void Solve(int m, int n, double *X) const;
497 
498  /// Assuming L.U = P.A factored data of size (m x m), compute X <- A^{-1}.
499  void GetInverseMatrix(int m, double *X) const;
500 
501  /** Given an (n x m) matrix A21, compute X2 <- X2 - A21 X1, for matrices X1,
502  and X2 of size (m x r) and (n x r), respectively. */
503  static void SubMult(int m, int n, int r, const double *A21,
504  const double *X1, double *X2);
505 
506  /** Assuming P.A = L.U factored data of size (m x m), compute the 2x2 block
507  decomposition:
508  | P 0 | | A A12 | = | L 0 | | U U12 |
509  | 0 I | | A21 A22 | | L21 I | | 0 S22 |
510  where A12, A21, and A22 are matrices of size (m x n), (n x m), and
511  (n x n), respectively. The blocks are overwritten as follows:
512  A12 <- U12 = L^{-1} P A12
513  A21 <- L21 = A21 U^{-1}
514  A22 <- S22 = A22 - L21 U12.
515  The block S22 is the Schur complement. */
516  void BlockFactor(int m, int n, double *A12, double *A21, double *A22) const;
517 
518  /** Given BlockFactor()'d data, perform the forward block solve for the
519  linear system:
520  | A A12 | | X1 | = | B1 |
521  | A21 A22 | | X2 | | B2 |
522  written in the factored form:
523  | L 0 | | U U12 | | X1 | = | P 0 | | B1 |
524  | L21 I | | 0 S22 | | X2 | | 0 I | | B2 |.
525  The resulting blocks Y1, Y2 solve the system:
526  | L 0 | | Y1 | = | P 0 | | B1 |
527  | L21 I | | Y2 | | 0 I | | B2 |
528  The blocks are overwritten as follows:
529  B1 <- Y1 = L^{-1} P B1
530  B2 <- Y2 = B2 - L21 Y1 = B2 - A21 A^{-1} B1
531  The blocks B1/Y1 and B2/Y2 are of size (m x r) and (n x r), respectively.
532  The Schur complement system is given by: S22 X2 = Y2. */
533  void BlockForwSolve(int m, int n, int r, const double *L21,
534  double *B1, double *B2) const;
535 
536  /** Given BlockFactor()'d data, perform the backward block solve in
537  | U U12 | | X1 | = | Y1 |
538  | 0 S22 | | X2 | | Y2 |.
539  The input is the solution block X2 and the block Y1 resulting from
540  BlockForwSolve(). The result block X1 overwrites input block Y1:
541  Y1 <- X1 = U^{-1} (Y1 - U12 X2). */
542  void BlockBackSolve(int m, int n, int r, const double *U12,
543  const double *X2, double *Y1) const;
544 };
545 
546 
547 /** Data type for inverse of square dense matrix.
548  Stores LU factors */
550 {
551 private:
552  const DenseMatrix *a;
553  LUFactors lu;
554 
555 public:
556  /// Default constructor.
557  DenseMatrixInverse() : a(NULL), lu(NULL, NULL) { }
558 
559  /** Creates square dense matrix. Computes factorization of mat
560  and stores LU factors. */
561  DenseMatrixInverse(const DenseMatrix &mat);
562 
563  /// Same as above but does not factorize the matrix.
564  DenseMatrixInverse(const DenseMatrix *mat);
565 
566  /// Get the size of the inverse matrix
567  int Size() const { return Width(); }
568 
569  /// Factor the current DenseMatrix, *a
570  void Factor();
571 
572  /// Factor a new DenseMatrix of the same size
573  void Factor(const DenseMatrix &mat);
574 
575  virtual void SetOperator(const Operator &op);
576 
577  /// Matrix vector multiplication with the inverse of dense matrix.
578  virtual void Mult(const Vector &x, Vector &y) const;
579 
580  /// Multiply the inverse matrix by another matrix: X = A^{-1} B.
581  void Mult(const DenseMatrix &B, DenseMatrix &X) const;
582 
583  /// Multiply the inverse matrix by another matrix: X <- A^{-1} X.
584  void Mult(DenseMatrix &X) const { lu.Solve(width, X.Width(), X.Data()); }
585 
586  /// Compute and return the inverse matrix in Ainv.
587  void GetInverseMatrix(DenseMatrix &Ainv) const;
588 
589  /// Compute the determinant of the original DenseMatrix using the LU factors.
590  double Det() const { return lu.Det(width); }
591 
592  /// Print the numerical conditioning of the inversion: ||A^{-1} A - I||.
593  void TestInversion();
594 
595  /// Destroys dense inverse matrix.
596  virtual ~DenseMatrixInverse();
597 };
598 
599 
601 {
602  DenseMatrix &mat;
603  Vector EVal;
604  DenseMatrix EVect;
605  Vector ev;
606  int n;
607 
608 #ifdef MFEM_USE_LAPACK
609  double *work;
610  char jobz, uplo;
611  int lwork, info;
612 #endif
613 
614 public:
615 
618  void Eval();
619  Vector &Eigenvalues() { return EVal; }
620  DenseMatrix &Eigenvectors() { return EVect; }
621  double Eigenvalue(int i) { return EVal(i); }
622  const Vector &Eigenvector(int i)
623  {
624  ev.SetData(EVect.Data() + i * EVect.Height());
625  return ev;
626  }
628 };
629 
630 
632 {
633  Vector sv;
634  int m, n;
635 
636 #ifdef MFEM_USE_LAPACK
637  double *work;
638  char jobu, jobvt;
639  int lwork, info;
640 #endif
641 
642  void Init();
643 public:
644 
646  DenseMatrixSVD(int h, int w);
647  void Eval(DenseMatrix &M);
648  Vector &Singularvalues() { return sv; }
649  double Singularvalue(int i) { return sv(i); }
650  ~DenseMatrixSVD();
651 };
652 
653 class Table;
654 
655 /// Rank 3 tensor (array of matrices)
657 {
658 private:
659  DenseMatrix Mk;
660  Memory<double> tdata;
661  int nk;
662 
663 public:
665  {
666  nk = 0;
667  tdata.Reset();
668  }
669 
670  DenseTensor(int i, int j, int k)
671  : Mk(NULL, i, j)
672  {
673  nk = k;
674  tdata.New(i*j*k);
675  }
676 
677  /// Copy constructor: deep copy
678  DenseTensor(const DenseTensor &other)
679  : Mk(NULL, other.Mk.height, other.Mk.width), nk(other.nk)
680  {
681  const int size = Mk.Height()*Mk.Width()*nk;
682  if (size > 0)
683  {
684  tdata.New(size, other.tdata.GetMemoryType());
685  tdata.CopyFrom(other.tdata, size);
686  }
687  else
688  {
689  tdata.Reset();
690  }
691  }
692 
693  int SizeI() const { return Mk.Height(); }
694  int SizeJ() const { return Mk.Width(); }
695  int SizeK() const { return nk; }
696 
697  int TotalSize() const { return SizeI()*SizeJ()*SizeK(); }
698 
699  void SetSize(int i, int j, int k)
700  {
701  const MemoryType mt = tdata.GetMemoryType();
702  tdata.Delete();
703  Mk.UseExternalData(NULL, i, j);
704  nk = k;
705  tdata.New(i*j*k, mt);
706  }
707 
708  void UseExternalData(double *ext_data, int i, int j, int k)
709  {
710  tdata.Delete();
711  Mk.UseExternalData(NULL, i, j);
712  nk = k;
713  tdata.Wrap(ext_data, i*j*k, false);
714  }
715 
716  /// Sets the tensor elements equal to constant c
717  DenseTensor &operator=(double c);
718 
719  DenseMatrix &operator()(int k) { Mk.data = GetData(k); return Mk; }
720  const DenseMatrix &operator()(int k) const
721  { return const_cast<DenseTensor&>(*this)(k); }
722 
723  double &operator()(int i, int j, int k)
724  { return tdata[i+SizeI()*(j+SizeJ()*k)]; }
725  const double &operator()(int i, int j, int k) const
726  { return tdata[i+SizeI()*(j+SizeJ()*k)]; }
727 
728  double *GetData(int k) { return tdata+k*Mk.Height()*Mk.Width(); }
729 
730  double *Data() { return tdata; }
731 
732  const double *Data() const { return tdata; }
733 
734  Memory<double> &GetMemory() { return tdata; }
735  const Memory<double> &GetMemory() const { return tdata; }
736 
737  /** Matrix-vector product from unassembled element matrices, assuming both
738  'x' and 'y' use the same elem_dof table. */
739  void AddMult(const Table &elem_dof, const Vector &x, Vector &y) const;
740 
741  void Clear()
742  { UseExternalData(NULL, 0, 0, 0); }
743 
744  long MemoryUsage() const { return nk*Mk.MemoryUsage(); }
745 
746  ~DenseTensor() { tdata.Delete(); }
747 };
748 
749 
750 // Inline methods
751 
752 inline double &DenseMatrix::operator()(int i, int j)
753 {
754  MFEM_ASSERT(data && i >= 0 && i < height && j >= 0 && j < width, "");
755  return data[i+j*height];
756 }
757 
758 inline const double &DenseMatrix::operator()(int i, int j) const
759 {
760  MFEM_ASSERT(data && i >= 0 && i < height && j >= 0 && j < width, "");
761  return data[i+j*height];
762 }
763 
764 } // namespace mfem
765 
766 #endif
int Size() const
For backward compatibility define Size to be synonym of Width()
Definition: densemat.hpp:85
void Symmetrize()
(*this) = 1/2 ((*this) + (*this)^t)
Definition: densemat.cpp:2518
void MultABt(const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &ABt)
Multiply a matrix A with the transpose of a matrix B: A*Bt.
Definition: densemat.cpp:3450
DenseMatrix & operator-=(const DenseMatrix &m)
Definition: densemat.cpp:626
void SymmetricScaling(const Vector &s)
SymmetricScaling this = diag(sqrt(s)) * this * diag(sqrt(s))
Definition: densemat.cpp:393
void SquareRootInverse()
Replaces the current matrix with its square root inverse.
Definition: densemat.cpp:768
int CheckFinite(const double *v, const int n)
Definition: vector.hpp:376
void AddMultVWt(const Vector &v, const Vector &w, DenseMatrix &VWt)
VWt += v w^t.
Definition: densemat.cpp:3853
void Mult(DenseMatrix &X) const
Multiply the inverse matrix by another matrix: X &lt;- A^{-1} X.
Definition: densemat.hpp:584
DenseMatrix & operator*=(double c)
Definition: densemat.cpp:639
void GetDiag(Vector &d) const
Returns the diagonal of the matrix.
Definition: densemat.cpp:2410
void UseExternalData(double *ext_data, int i, int j, int k)
Definition: densemat.hpp:708
DenseTensor & operator=(double c)
Sets the tensor elements equal to constant c.
Definition: densemat.cpp:4507
void MultVWt(const Vector &v, const Vector &w, DenseMatrix &VWt)
Definition: densemat.cpp:3834
void InvRightScaling(const Vector &s)
InvRightScaling: this = this * diag(1./s);.
Definition: densemat.cpp:379
const DenseMatrix & operator()(int k) const
Definition: densemat.hpp:720
void Eigenvalues(Vector &ev)
Compute eigenvalues of A x = ev x where A = *this.
Definition: densemat.hpp:222
void SingularValues(Vector &sv) const
Definition: densemat.cpp:1176
void Delete()
Delete the owned pointers. The Memory is not reset by this method.
DenseMatrix & operator()(int k)
Definition: densemat.hpp:719
double Det() const
Definition: densemat.cpp:472
void Eigensystem(DenseMatrix &b, Vector &ev, DenseMatrix &evect)
Definition: densemat.hpp:244
void Mult(const Table &A, const Table &B, Table &C)
C = A * B (as boolean matrices)
Definition: table.cpp:476
int Width() const
Get the width (size of input) of the Operator. Synonym with NumCols().
Definition: operator.hpp:42
int SizeK() const
Definition: densemat.hpp:695
long MemoryUsage() const
Definition: densemat.hpp:744
void BlockFactor(int m, int n, double *A12, double *A21, double *A22) const
Definition: densemat.cpp:4185
void BlockBackSolve(int m, int n, int r, const double *U12, const double *X2, double *Y1) const
Definition: densemat.cpp:4221
double InnerProduct(const double *x, const double *y) const
Compute y^t A x.
Definition: densemat.cpp:320
void CalcAdjugate(const DenseMatrix &a, DenseMatrix &adja)
Definition: densemat.cpp:3132
void AddMult(const Table &elem_dof, const Vector &x, Vector &y) const
Definition: densemat.cpp:4453
void TestInversion()
Invert and print the numerical conditioning of the inversion.
Definition: densemat.cpp:3006
Data type dense matrix using column-major storage.
Definition: densemat.hpp:23
void CopyRows(const DenseMatrix &A, int row1, int row2)
Copy rows row1 through row2 from A to *this.
Definition: densemat.cpp:2623
double Det(int m) const
Definition: densemat.cpp:3992
void SetSize(int i, int j, int k)
Definition: densemat.hpp:699
void Eval(DenseMatrix &M)
Definition: densemat.cpp:4422
const double * Data() const
Definition: densemat.hpp:732
Abstract data type for matrix inverse.
Definition: matrix.hpp:66
void AddMult_a_ABt(double a, const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &ABt)
ABt += a * A * B^t.
Definition: densemat.cpp:3666
void GetInverseMatrix(DenseMatrix &Ainv) const
Compute and return the inverse matrix in Ainv.
Definition: densemat.cpp:4262
void Factor(int m)
Definition: densemat.cpp:3940
void Factor()
Factor the current DenseMatrix, *a.
Definition: densemat.cpp:4250
void CopyFrom(const Memory &src, int size)
Copy size entries from src to *this.
void GetInverseMatrix(int m, double *X) const
Assuming L.U = P.A factored data of size (m x m), compute X &lt;- A^{-1}.
Definition: densemat.cpp:4103
double * GetData() const
Returns the matrix data array.
Definition: densemat.hpp:96
const Memory< double > & GetMemory() const
Definition: densemat.hpp:735
void CalcOrtho(const DenseMatrix &J, Vector &n)
Definition: densemat.cpp:3362
DenseMatrix & operator=(double c)
Sets the matrix elements equal to constant c.
Definition: densemat.cpp:576
void Set(double alpha, const double *A)
Set the matrix to alpha * A, assuming that A has the same dimensions as the matrix and uses column-ma...
Definition: densemat.cpp:556
void Mult_a_AAt(double a, const DenseMatrix &A, DenseMatrix &AAt)
AAt = a * A * A^t.
Definition: densemat.cpp:3807
MemoryType GetMemoryType() const
Return a MemoryType that is currently valid. If both the host and the device pointers are currently v...
static void SubMult(int m, int n, int r, const double *A21, const double *X1, double *X2)
Definition: densemat.cpp:4168
const Vector & Eigenvector(int i)
Definition: densemat.hpp:622
virtual void Print(std::ostream &out=mfem::out, int width_=4) const
Prints matrix to stream out.
Definition: densemat.cpp:2935
virtual void Mult(const Vector &x, Vector &y) const
Matrix vector multiplication with the inverse of dense matrix.
Definition: densemat.cpp:4290
const double & operator()(int i, int j, int k) const
Definition: densemat.hpp:725
void Set(double alpha, const DenseMatrix &A)
Set the matrix to alpha * A.
Definition: densemat.hpp:181
void Add(const DenseMatrix &A, const DenseMatrix &B, double alpha, DenseMatrix &C)
C = A + alpha*B.
Definition: densemat.cpp:3030
double & operator()(int i, int j)
Returns reference to a_{ij}.
Definition: densemat.hpp:752
double Weight() const
Definition: densemat.cpp:529
void Wrap(T *ptr, int size, bool own)
Wrap an externally allocated host pointer, ptr with type MemoryType::HOST.
void USolve(int m, int n, double *X) const
Definition: densemat.cpp:4070
double FNorm() const
Compute the Frobenius norm of the matrix.
Definition: densemat.hpp:216
void MultTranspose(const double *x, double *y) const
Multiply a vector with the transpose matrix.
Definition: densemat.cpp:224
void CalcAdjugateTranspose(const DenseMatrix &a, DenseMatrix &adjat)
Calculate the transposed adjugate of a matrix (for NxN matrices, N=1,2,3)
Definition: densemat.cpp:3204
double & operator()(int i, int j, int k)
Definition: densemat.hpp:723
void AddMult(const DenseMatrix &b, const DenseMatrix &c, DenseMatrix &a)
Matrix matrix multiplication. A += B * C.
Definition: densemat.cpp:3100
double operator*(const DenseMatrix &m) const
Matrix inner product: tr(A^t B)
Definition: densemat.cpp:209
double Singularvalue(int i)
Definition: densemat.hpp:649
void Reset(double *d, int h, int w)
Change the data array and the size of the DenseMatrix.
Definition: densemat.hpp:73
int Height() const
Get the height (size of output) of the Operator. Synonym with NumRows().
Definition: operator.hpp:36
void Add(const double c, const DenseMatrix &A)
Adds the matrix A multiplied by the number c to the matrix.
Definition: densemat.cpp:565
void AddMult_a_VWt(const double a, const Vector &v, const Vector &w, DenseMatrix &VWt)
VWt += a * v w^t.
Definition: densemat.cpp:3898
void InvSymmetricScaling(const Vector &s)
InvSymmetricScaling this = diag(sqrt(1./s)) * this * diag(sqrt(1./s))
Definition: densemat.cpp:421
void GetRow(int r, Vector &row) const
Definition: densemat.cpp:2380
void BlockForwSolve(int m, int n, int r, const double *L21, double *B1, double *B2) const
Definition: densemat.cpp:4212
DenseMatrixSVD(DenseMatrix &M)
Definition: densemat.cpp:4388
Abstract data type matrix.
Definition: matrix.hpp:27
const double * GetColumn(int col) const
Definition: densemat.hpp:260
void Norm2(double *v) const
Take the 2-norm of the columns of A and store in v.
Definition: densemat.cpp:813
void MultADBt(const DenseMatrix &A, const Vector &D, const DenseMatrix &B, DenseMatrix &ADBt)
ADBt = A D B^t, where D is diagonal.
Definition: densemat.cpp:3533
void Invert()
Replaces the current matrix with its inverse.
Definition: densemat.cpp:658
virtual ~DenseMatrixInverse()
Destroys dense inverse matrix.
Definition: densemat.cpp:4313
void LSolve(int m, int n, double *X) const
Definition: densemat.cpp:4045
int TotalSize() const
Definition: densemat.hpp:697
void LeftScaling(const Vector &s)
LeftScaling this = diag(s) * this.
Definition: densemat.cpp:338
double Det() const
Compute the determinant of the original DenseMatrix using the LU factors.
Definition: densemat.hpp:590
void AddMultVVt(const Vector &v, DenseMatrix &VVt)
VVt += v v^t.
Definition: densemat.cpp:3874
void CopyMNDiag(double c, int n, int row_offset, int col_offset)
Copy c on the diagonal of size n to *this at row_offset, col_offset.
Definition: densemat.cpp:2719
double * GetData(int k)
Definition: densemat.hpp:728
void AddMult_a_VVt(const double a, const Vector &v, DenseMatrix &VVt)
VVt += a * v v^t.
Definition: densemat.cpp:3920
void Neg()
(*this) = -(*this)
Definition: densemat.cpp:649
virtual void SetOperator(const Operator &op)
Set/update the solver for the given operator.
Definition: densemat.cpp:4283
void Solve(int m, int n, double *X) const
Definition: densemat.cpp:4089
void SetRow(int r, const Vector &row)
Definition: densemat.cpp:2905
void Getl1Diag(Vector &l) const
Returns the l1 norm of the rows of the matrix v_i = sum_j |a_ij|.
Definition: densemat.cpp:2424
void AddToVector(int offset, Vector &v) const
Add the matrix &#39;data&#39; to the Vector &#39;v&#39; at the given &#39;offset&#39;.
Definition: densemat.cpp:2840
void SetData(double *d)
Definition: vector.hpp:118
long MemoryUsage() const
Definition: densemat.hpp:355
DenseMatrix & Eigenvectors()
Definition: densemat.hpp:620
void Reset()
Reset the memory to be empty, ensuring that Delete() will be a no-op.
void GetColumn(int c, Vector &col) const
Definition: densemat.cpp:2396
void AddMult(const Vector &x, Vector &y) const
y += A.x
Definition: densemat.cpp:247
void Threshold(double eps)
Replace small entries, abs(a_ij) &lt;= eps, with zero.
Definition: densemat.cpp:2921
int SizeI() const
Definition: densemat.hpp:693
void CalcInverse(const DenseMatrix &a, DenseMatrix &inva)
Definition: densemat.cpp:3240
void TestInversion()
Print the numerical conditioning of the inversion: ||A^{-1} A - I||.
Definition: densemat.cpp:4302
double MaxMaxNorm() const
Compute the norm ||A|| = max_{ij} |A_{ij}|.
Definition: densemat.cpp:826
double * Data() const
Returns the matrix data array.
Definition: densemat.hpp:94
void Transpose()
(*this) = (*this)^t
Definition: densemat.cpp:2485
void MultVVt(const Vector &v, DenseMatrix &vvt)
Make a matrix from a vector V.Vt.
Definition: densemat.cpp:3823
double Trace() const
Trace of a square matrix.
Definition: densemat.cpp:448
void AddMultABt(const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &ABt)
ABt += A * B^t.
Definition: densemat.cpp:3573
MemoryType
Memory types supported by MFEM.
Definition: mem_manager.hpp:27
DenseTensor(int i, int j, int k)
Definition: densemat.hpp:670
void ClearExternalData()
Definition: densemat.hpp:78
int CheckFinite() const
Definition: densemat.hpp:344
void MultAAt(const DenseMatrix &a, DenseMatrix &aat)
Calculate the matrix A.At.
Definition: densemat.cpp:3388
void GetColumnReference(int c, Vector &col)
Definition: densemat.hpp:262
void AddMatrix(DenseMatrix &A, int ro, int co)
Perform (ro+i,co+j)+=A(i,j) for 0&lt;=i&lt;A.Height, 0&lt;=j&lt;A.Width.
Definition: densemat.cpp:2780
DenseMatrix(double *d, int h, int w)
Construct a DenseMatrix using an existing data array.
Definition: densemat.hpp:59
void Clear()
Delete the matrix data array (if owned) and reset the matrix state.
Definition: densemat.hpp:81
void CalcInverseTranspose(const DenseMatrix &a, DenseMatrix &inva)
Calculate the inverse transpose of a matrix (for NxN matrices, N=1,2,3)
Definition: densemat.cpp:3323
A class to initialize the size of a Tensor.
Definition: dtensor.hpp:55
void SetDataAndSize(double *d, int s)
Set the Vector data and size.
Definition: vector.hpp:125
void MultADAt(const DenseMatrix &A, const Vector &D, DenseMatrix &ADAt)
ADAt = A D A^t, where D is diagonal.
Definition: densemat.cpp:3434
void Eigenvalues(DenseMatrix &b, Vector &ev)
Definition: densemat.hpp:235
int height
Dimension of the output / number of rows in the matrix.
Definition: operator.hpp:24
virtual void PrintT(std::ostream &out=mfem::out, int width_=4) const
Prints the transpose matrix to stream out.
Definition: densemat.cpp:2980
void CopyCols(const DenseMatrix &A, int col1, int col2)
Copy columns col1 through col2 from A to *this.
Definition: densemat.cpp:2636
int SizeJ() const
Definition: densemat.hpp:694
virtual MatrixInverse * Inverse() const
Returns a pointer to the inverse matrix.
Definition: densemat.cpp:467
double * GetColumn(int col)
Definition: densemat.hpp:259
bool OwnsData() const
Definition: densemat.hpp:98
void AddMultADBt(const DenseMatrix &A, const Vector &D, const DenseMatrix &B, DenseMatrix &ADBt)
ADBt = A D B^t, where D is diagonal.
Definition: densemat.cpp:3630
virtual ~DenseMatrix()
Destroys dense matrix.
Definition: densemat.cpp:3020
void CopyMNt(const DenseMatrix &A, int row_offset, int col_offset)
Copy matrix A^t to the location in *this at row_offset, col_offset.
Definition: densemat.cpp:2675
void AddMultTranspose(const Vector &x, Vector &y) const
y += A^t x
Definition: densemat.cpp:265
void CopyExceptMN(const DenseMatrix &A, int m, int n)
Copy All rows and columns except m and n from A.
Definition: densemat.cpp:2754
void New(int size)
Allocate host memory for size entries with type MemoryType::HOST.
void Diag(double c, int n)
Creates n x n diagonal matrix with diagonal elements c.
Definition: densemat.cpp:2455
void Mult(int m, int n, double *X) const
Definition: densemat.cpp:4009
static const int ipiv_base
Definition: densemat.hpp:462
void GradToCurl(DenseMatrix &curl)
Definition: densemat.cpp:2549
DenseMatrixInverse()
Default constructor.
Definition: densemat.hpp:557
double CalcSingularvalue(const int i) const
Return the i-th singular value (decreasing order) of NxN matrix, N=1,2,3.
Definition: densemat.cpp:1842
void GetRowSums(Vector &l) const
Compute the row sums of the DenseMatrix.
Definition: densemat.cpp:2441
void CalcEigenvalues(double *lambda, double *vec) const
Definition: densemat.cpp:2140
void Eigenvalues(Vector &ev, DenseMatrix &evect)
Compute eigenvalues and eigenvectors of A x = ev x where A = *this.
Definition: densemat.hpp:226
DenseMatrixEigensystem(DenseMatrix &m)
Definition: densemat.cpp:4320
int Rank(double tol) const
Definition: densemat.cpp:1215
const double alpha
Definition: ex15.cpp:339
LUFactors(double *data_, int *ipiv_)
Definition: densemat.hpp:471
void AddMult_a(double a, const Vector &x, Vector &y) const
y += a * A.x
Definition: densemat.cpp:283
void RightScaling(const Vector &s)
RightScaling: this = this * diag(s);.
Definition: densemat.cpp:364
DenseTensor(const DenseTensor &other)
Copy constructor: deep copy.
Definition: densemat.hpp:678
void MultAtB(const DenseMatrix &A, const DenseMatrix &B, DenseMatrix &AtB)
Multiply the transpose of a matrix A with a matrix B: At*B.
Definition: densemat.cpp:3725
Vector data type.
Definition: vector.hpp:48
void Mult(const double *x, double *y) const
Matrix vector multiplication.
Definition: densemat.cpp:173
void AddMultTranspose_a(double a, const Vector &x, Vector &y) const
y += a * A^t x
Definition: densemat.cpp:301
void AddMultADAt(const DenseMatrix &A, const Vector &D, DenseMatrix &ADAt)
ADAt += A D A^t, where D is diagonal.
Definition: densemat.cpp:3406
void GetFromVector(int offset, const Vector &v)
Get the matrix &#39;data&#39; from the Vector &#39;v&#39; at the given &#39;offset&#39;.
Definition: densemat.cpp:2851
Memory< double > & GetMemory()
Definition: densemat.hpp:734
void CopyMN(const DenseMatrix &A, int m, int n, int Aro, int Aco)
Copy the m x n submatrix of A at row/col offsets Aro/Aco to *this.
Definition: densemat.cpp:2649
double * Data()
Definition: densemat.hpp:730
void InvLeftScaling(const Vector &s)
InvLeftScaling this = diag(1./s) * this.
Definition: densemat.cpp:351
void UseExternalData(double *d, int h, int w)
Change the data array and the size of the DenseMatrix.
Definition: densemat.hpp:66
void SetCol(int c, const Vector &col)
Definition: densemat.cpp:2913
void Eigensystem(Vector &ev, DenseMatrix &evect)
Compute eigenvalues and eigenvectors of A x = ev x where A = *this.
Definition: densemat.hpp:230
void SetSize(int s)
Change the size of the DenseMatrix to s x s.
Definition: densemat.hpp:88
OutStream out(std::cout)
Global stream used by the library for standard output. Initially it uses the same std::streambuf as s...
Definition: globals.hpp:64
Abstract operator.
Definition: operator.hpp:21
int Size() const
Get the size of the inverse matrix.
Definition: densemat.hpp:567
Vector & Singularvalues()
Definition: densemat.hpp:648
Rank 3 tensor (array of matrices)
Definition: densemat.hpp:656
double InnerProduct(const Vector &x, const Vector &y) const
Compute y^t A x.
Definition: densemat.hpp:159
double FNorm2() const
Compute the square of the Frobenius norm of the matrix.
Definition: densemat.hpp:219
virtual double & Elem(int i, int j)
Returns reference to a_{ij}.
Definition: densemat.cpp:163
void AdjustDofDirection(Array< int > &dofs)
Definition: densemat.cpp:2862
void GradToDiv(Vector &div)
Definition: densemat.cpp:2608
void AddMult_a_AAt(double a, const DenseMatrix &A, DenseMatrix &AAt)
AAt += a * A * A^t.
Definition: densemat.cpp:3782
int width
Dimension of the input / number of columns in the matrix.
Definition: operator.hpp:25
void Eigenvalues(DenseMatrix &b, Vector &ev, DenseMatrix &evect)
Compute generalized eigenvalues of A x = ev B x, where A = *this.
Definition: densemat.hpp:239
virtual void PrintMatlab(std::ostream &out=mfem::out) const
Definition: densemat.cpp:2961
double * data
Definition: densemat.hpp:459
DenseMatrix & operator+=(const double *m)
Definition: densemat.cpp:609