Reference documentation for deal.II version 8.5.1
block_matrix_array.cc
1 // ---------------------------------------------------------------------
2 //
3 // Copyright (C) 2005 - 2016 by the deal.II authors
4 //
5 // This file is part of the deal.II library.
6 //
7 // The deal.II library is free software; you can use it, redistribute
8 // it, and/or modify it under the terms of the GNU Lesser General
9 // Public License as published by the Free Software Foundation; either
10 // version 2.1 of the License, or (at your option) any later version.
11 // The full text of the license can be found in the file LICENSE at
12 // the top level of the deal.II distribution.
13 //
14 // ---------------------------------------------------------------------
15 
16 
17 #include <deal.II/lac/block_matrix_array.h>
18 #include <deal.II/lac/vector.h>
19 #include <deal.II/lac/block_vector.h>
20 #include <deal.II/lac/trilinos_block_vector.h>
21 #include <deal.II/lac/trilinos_parallel_block_vector.h>
22 
23 #include <deal.II/lac/petsc_block_vector.h>
24 #include <deal.II/lac/petsc_parallel_block_vector.h>
25 
26 DEAL_II_NAMESPACE_OPEN
27 
28 
29 template <typename number, typename BlockVectorType>
31  :
32  row(e.row),
33  col(e.col),
34  prefix(e.prefix),
36  matrix(e.matrix)
37 {
38  Entry &e2 = const_cast<Entry &>(e);
39  e2.matrix = 0;
40 }
41 
42 
43 
44 template <typename number, typename BlockVectorType>
46 {
47  if (matrix)
48  delete matrix;
49 }
50 
51 
52 template <typename number, typename BlockVectorType>
54  : block_rows (0),
55  block_cols (0)
56 {}
57 
58 
59 
60 template <typename number, typename BlockVectorType>
62 (const unsigned int n_block_rows,
63  const unsigned int n_block_cols)
64  : block_rows (n_block_rows),
65  block_cols (n_block_cols)
66 {}
67 
68 
69 template <typename number, typename BlockVectorType>
70 void
72 (const unsigned int n_block_rows,
73  const unsigned int n_block_cols)
74 {
75  block_rows = n_block_rows;
76  block_cols = n_block_cols;
77 }
78 
79 
80 
81 template <typename number, typename BlockVectorType>
82 void
84 (const unsigned int n_block_rows,
85  const unsigned int n_block_cols)
86 {
87  clear();
88  block_rows = n_block_rows;
89  block_cols = n_block_cols;
90 }
91 
92 
93 
94 template <typename number, typename BlockVectorType>
95 void
97 {
98  entries.clear();
99 }
100 
101 
102 template <typename number, typename BlockVectorType>
103 void
105  const BlockVectorType &src) const
106 {
108  Assert (dst.n_blocks() == block_rows,
109  ExcDimensionMismatch(dst.n_blocks(), block_rows));
110  Assert (src.n_blocks() == block_cols,
111  ExcDimensionMismatch(src.n_blocks(), block_cols));
112 
114  typename BlockVectorType::BlockType &aux = *p_aux;
115 
116  typename std::vector<Entry>::const_iterator m = entries.begin();
117  typename std::vector<Entry>::const_iterator end = entries.end();
118 
119  for (; m != end ; ++m)
120  {
121  aux.reinit(dst.block(m->row));
122  if (m->transpose)
123  m->matrix->Tvmult(aux, src.block(m->col));
124  else
125  m->matrix->vmult(aux, src.block(m->col));
126  dst.block(m->row).add (m->prefix, aux);
127  }
128 }
129 
130 
131 
132 
133 template <typename number, typename BlockVectorType>
134 void
136  const BlockVectorType &src) const
137 {
138  dst = 0.;
139  vmult_add (dst, src);
140 }
141 
142 
143 
144 
145 template <typename number, typename BlockVectorType>
146 void
148  const BlockVectorType &src) const
149 {
151  Assert (dst.n_blocks() == block_cols,
152  ExcDimensionMismatch(dst.n_blocks(), block_cols));
153  Assert (src.n_blocks() == block_rows,
154  ExcDimensionMismatch(src.n_blocks(), block_rows));
155 
156  typename std::vector<Entry>::const_iterator m = entries.begin();
157  typename std::vector<Entry>::const_iterator end = entries.end();
158 
160  typename BlockVectorType::BlockType &aux = *p_aux;
161 
162  for (; m != end ; ++m)
163  {
164  aux.reinit(dst.block(m->col));
165  if (m->transpose)
166  m->matrix->vmult(aux, src.block(m->row));
167  else
168  m->matrix->Tvmult(aux, src.block(m->row));
169  dst.block(m->col).add (m->prefix, aux);
170  }
171 }
172 
173 
174 
175 template <typename number, typename BlockVectorType>
176 void
178  const BlockVectorType &src) const
179 {
180  dst = 0.;
181  Tvmult_add (dst, src);
182 }
183 
184 
185 
186 
187 template <typename number, typename BlockVectorType>
188 number
190 (const BlockVectorType &u,
191  const BlockVectorType &v) const
192 {
194  Assert (u.n_blocks() == block_rows,
195  ExcDimensionMismatch(u.n_blocks(), block_rows));
196  Assert (v.n_blocks() == block_cols,
197  ExcDimensionMismatch(v.n_blocks(), block_cols));
198 
200  typename BlockVectorType::BlockType &aux = *p_aux;
201 
202  typename std::vector<Entry>::const_iterator m;
203  typename std::vector<Entry>::const_iterator end = entries.end();
204 
205  number result = 0.;
206 
207  for (unsigned int i=0; i<block_rows; ++i)
208  {
209  aux.reinit(u.block(i));
210  for (m = entries.begin(); m != end ; ++m)
211  {
212  if (m->row != i)
213  continue;
214  if (m->transpose)
215  m->matrix->Tvmult_add(aux, v.block(m->col));
216  else
217  m->matrix->vmult(aux, v.block(m->col));
218  }
219  result += u.block(i)*aux;
220  }
221 
222  return result;
223 }
224 
225 
226 
227 template <typename number, typename BlockVectorType>
228 number
230 (const BlockVectorType &u) const
231 {
232  return matrix_scalar_product(u,u);
233 }
234 
235 
236 
237 template <typename number, typename BlockVectorType>
238 unsigned int
240 {
241  return block_rows;
242 }
243 
244 
245 
246 template <typename number, typename BlockVectorType>
247 unsigned int
249 {
250  return block_cols;
251 }
252 
253 
254 
255 //---------------------------------------------------------------------------
256 
257 template <typename number, typename BlockVectorType>
259  : BlockMatrixArray<number,BlockVectorType> (),
260  backward(false)
261 {}
262 
263 
264 template <typename number, typename BlockVectorType>
266 (const unsigned int block_rows)
267  :
268  BlockMatrixArray<number,BlockVectorType> (block_rows, block_rows),
269  backward(false)
270 {}
271 
272 
273 template <typename number, typename BlockVectorType>
274 void
276 (const unsigned int n)
277 {
279 }
280 
281 
282 template <typename number, typename BlockVectorType>
283 void
285 (BlockVectorType &dst,
286  size_type row_num) const
287 {
289  typename std::vector<typename BlockMatrixArray<number,BlockVectorType>::Entry>::const_iterator
290  m = this->entries.begin();
291  typename std::vector<typename BlockMatrixArray<number,BlockVectorType>::Entry>::const_iterator
292  end = this->entries.end();
293  std::vector<typename std::vector<typename BlockMatrixArray<number,BlockVectorType>::Entry>::const_iterator>
294  diagonals;
295 
297  typename BlockVectorType::BlockType &aux = *p_aux;
298 
299  aux.reinit(dst.block(row_num), true);
300 
301  // Loop over all entries, since
302  // they are not ordered by rows.
303  for (; m != end ; ++m)
304  {
305  const size_type i=m->row;
306  // Ignore everything not in
307  // this row
308  if (i != row_num)
309  continue;
310  const size_type j=m->col;
311  // Only use the lower (upper)
312  // triangle for forward
313  // (backward) substitution
314  if (((j > i) && !backward) || ((j < i) && backward))
315  continue;
316  if (j == i)
317  {
318  diagonals.push_back(m);
319  }
320  else
321  {
322  if (m->transpose)
323  m->matrix->Tvmult(aux, dst.block(j));
324  else
325  m->matrix->vmult(aux, dst.block(j));
326  dst.block(i).add (-1.0 * m->prefix, aux);
327  }
328  }
329  Assert (diagonals.size() != 0, ExcNoDiagonal(row_num));
330 
331  // Inverting the diagonal block is
332  // simple, if there is only one
333  // matrix
334  if (diagonals.size() == 1)
335  {
336  if (diagonals[0]->transpose)
337  diagonals[0]->matrix->Tvmult(aux, dst.block(row_num));
338  else
339  diagonals[0]->matrix->vmult(aux, dst.block(row_num));
340  dst.block(row_num).equ (diagonals[0]->prefix, aux);
341  }
342  else
343  {
344  aux = 0.;
345  for (size_type i=0; i<diagonals.size(); ++i)
346  {
347  m = diagonals[i];
348  // First, divide by the current
349  // factor, such that we can
350  // multiply by it later.
351  aux /= m->prefix;
352  if (m->transpose)
353  m->matrix->Tvmult_add(aux, dst.block(row_num));
354  else
355  m->matrix->vmult_add(aux, dst.block(row_num));
356  aux *= m->prefix;
357  }
358  dst.block(row_num) = aux;
359  }
360 }
361 
362 
363 
364 template <typename number, typename BlockVectorType>
365 void
367 (BlockVectorType &dst,
368  const BlockVectorType &src) const
369 {
370  Assert (dst.n_blocks() == n_block_rows(),
371  ExcDimensionMismatch(dst.n_blocks(), n_block_rows()));
372  Assert (src.n_blocks() == n_block_cols(),
373  ExcDimensionMismatch(src.n_blocks(), n_block_cols()));
374 
375  BlockVectorType aux;
376  aux.reinit(dst);
377  vmult(aux, src);
378  dst.add(aux);
379 }
380 
381 
382 
383 template <typename number, typename BlockVectorType>
384 void
386 (BlockVectorType &dst,
387  const BlockVectorType &src) const
388 {
389  Assert (dst.n_blocks() == n_block_rows(),
390  ExcDimensionMismatch(dst.n_blocks(), n_block_rows()));
391  Assert (src.n_blocks() == n_block_cols(),
392  ExcDimensionMismatch(src.n_blocks(), n_block_cols()));
393 
394  dst.equ(1., src);
395 
396  if (backward)
397  {
398  for (unsigned int i=n_block_rows(); i>0;)
399  do_row(dst, --i);
400  }
401  else
402  {
403  for (unsigned int i=0; i<n_block_rows(); ++i)
404  do_row(dst, i);
405  }
406 
407 }
408 
409 template <typename number, typename BlockVectorType>
410 void
412 (BlockVectorType &,
413  const BlockVectorType &) const
414 {
415  Assert (false, ExcNotImplemented());
416 }
417 
418 
419 template <typename number, typename BlockVectorType>
420 void
422 (BlockVectorType &,
423  const BlockVectorType &) const
424 {
425  Assert (false, ExcNotImplemented());
426 }
427 
428 template class BlockMatrixArray<float>;
429 template class BlockMatrixArray<double>;
430 template class BlockTrianglePrecondition<float>;
431 template class BlockTrianglePrecondition<double>;
432 
433 #ifdef DEAL_II_WITH_TRILINOS
438 #endif
439 
440 #ifdef DEAL_II_WITH_PETSC
441 #ifdef PETSC_USE_COMPLEX
446 #else
451 #endif
452 #endif
453 
454 DEAL_II_NAMESPACE_CLOSE
unsigned int block_cols
number matrix_norm_square(const BlockVectorType &u) const
types::global_dof_index size_type
void Tvmult(BlockVectorType &dst, const BlockVectorType &src) const
void vmult(BlockVectorType &dst, const BlockVectorType &src) const
void vmult_add(BlockVectorType &dst, const BlockVectorType &src) const
unsigned int n_block_cols() const
void initialize(const unsigned int n_block_rows, const unsigned int n_block_cols)
#define Assert(cond, exc)
Definition: exceptions.h:313
void vmult_add(BlockVectorType &dst, const BlockVectorType &src) const
static ::ExceptionBase & ExcDimensionMismatch(std::size_t arg1, std::size_t arg2)
unsigned int n_block_rows() const
void Tvmult(BlockVectorType &dst, const BlockVectorType &src) const
unsigned int block_rows
Entry(const MatrixType &matrix, size_type row, size_type col, number prefix, bool transpose)
void reinit(const unsigned int n_block_rows, const unsigned int n_block_cols)
void Tvmult_add(BlockVectorType &dst, const BlockVectorType &src) const
void Tvmult_add(BlockVectorType &dst, const BlockVectorType &src) const
PointerMatrixBase< typename BlockVectorType::BlockType > * matrix
static ::ExceptionBase & ExcNotImplemented()
void reinit(const unsigned int n_block_rows)
void vmult(BlockVectorType &dst, const BlockVectorType &src) const
void do_row(BlockVectorType &dst, size_type row_num) const
number matrix_scalar_product(const BlockVectorType &u, const BlockVectorType &v) const
DerivativeForm< 1, spacedim, dim, Number > transpose(const DerivativeForm< 1, dim, spacedim, Number > &DF)