oomph::DampedJacobi< MATRIX > Class Template Reference

#include <iterative_linear_solver.h>

+ Inheritance diagram for oomph::DampedJacobi< MATRIX >:

Public Member Functions

 DampedJacobi (const double &omega=2.0/3.0)
 Empty constructor. More...
 
 ~DampedJacobi ()
 Empty destructor. More...
 
 DampedJacobi (const DampedJacobi &)=delete
 Broken copy constructor. More...
 
void operator= (const DampedJacobi &)=delete
 Broken assignment operator. More...
 
void clean_up_memory ()
 Cleanup data that's stored for resolve (if any has been stored) More...
 
void smoother_setup (DoubleMatrixBase *matrix_pt)
 Setup: Pass pointer to the matrix and store in cast form. More...
 
void extract_diagonal_entries (DoubleMatrixBase *matrix_pt)
 Function to extract the diagonal entries from the matrix. More...
 
void smoother_solve (const DoubleVector &rhs, DoubleVector &solution)
 
void solve (Problem *const &problem_pt, DoubleVector &result)
 
void solve (DoubleMatrixBase *const &matrix_pt, const DoubleVector &rhs, DoubleVector &solution)
 
void resolve (const DoubleVector &rhs, DoubleVector &result)
 
unsigned iterations () const
 Number of iterations taken. More...
 
- Public Member Functions inherited from oomph::Smoother
 Smoother ()
 Empty constructor. More...
 
virtual ~Smoother ()
 Virtual empty destructor. More...
 
template<typename MATRIX >
void check_validity_of_solve_helper_inputs (MATRIX *const &matrix_pt, const DoubleVector &rhs, DoubleVector &solution, const double &n_dof)
 
- Public Member Functions inherited from oomph::IterativeLinearSolver
 IterativeLinearSolver ()
 
 IterativeLinearSolver (const IterativeLinearSolver &)=delete
 Broken copy constructor. More...
 
void operator= (const IterativeLinearSolver &)=delete
 Broken assignment operator. More...
 
virtual ~IterativeLinearSolver ()
 Destructor (empty) More...
 
Preconditioner *& preconditioner_pt ()
 Access function to preconditioner. More...
 
Preconditioner *const & preconditioner_pt () const
 Access function to preconditioner (const version) More...
 
doubletolerance ()
 Access to convergence tolerance. More...
 
unsignedmax_iter ()
 Access to max. number of iterations. More...
 
void enable_doc_convergence_history ()
 Enable documentation of the convergence history. More...
 
void disable_doc_convergence_history ()
 Disable documentation of the convergence history. More...
 
void open_convergence_history_file_stream (const std::string &file_name, const std::string &zone_title="")
 
void close_convergence_history_file_stream ()
 Close convergence history output stream. More...
 
double jacobian_setup_time () const
 
double linear_solver_solution_time () const
 return the time taken to solve the linear system More...
 
virtual double preconditioner_setup_time () const
 returns the the time taken to setup the preconditioner More...
 
void enable_setup_preconditioner_before_solve ()
 Setup the preconditioner before the solve. More...
 
void disable_setup_preconditioner_before_solve ()
 Don't set up the preconditioner before the solve. More...
 
void enable_error_after_max_iter ()
 Throw an error if we don't converge within max_iter. More...
 
void disable_error_after_max_iter ()
 Don't throw an error if we don't converge within max_iter (default). More...
 
void enable_iterative_solver_as_preconditioner ()
 
void disable_iterative_solver_as_preconditioner ()
 
- Public Member Functions inherited from oomph::LinearSolver
 LinearSolver ()
 Empty constructor, initialise the member data. More...
 
 LinearSolver (const LinearSolver &dummy)=delete
 Broken copy constructor. More...
 
void operator= (const LinearSolver &)=delete
 Broken assignment operator. More...
 
virtual ~LinearSolver ()
 Empty virtual destructor. More...
 
void enable_doc_time ()
 Enable documentation of solve times. More...
 
void disable_doc_time ()
 Disable documentation of solve times. More...
 
bool is_doc_time_enabled () const
 Is documentation of solve times enabled? More...
 
bool is_resolve_enabled () const
 Boolean flag indicating if resolves are enabled. More...
 
virtual void enable_resolve ()
 
virtual void disable_resolve ()
 
virtual void solve (DoubleMatrixBase *const &matrix_pt, const Vector< double > &rhs, Vector< double > &result)
 
virtual void solve_transpose (Problem *const &problem_pt, DoubleVector &result)
 
virtual void solve_transpose (DoubleMatrixBase *const &matrix_pt, const DoubleVector &rhs, DoubleVector &result)
 
virtual void solve_transpose (DoubleMatrixBase *const &matrix_pt, const Vector< double > &rhs, Vector< double > &result)
 
virtual void resolve_transpose (const DoubleVector &rhs, DoubleVector &result)
 
virtual void enable_computation_of_gradient ()
 
void disable_computation_of_gradient ()
 
void reset_gradient ()
 
void get_gradient (DoubleVector &gradient)
 function to access the gradient, provided it has been computed More...
 
- Public Member Functions inherited from oomph::DistributableLinearAlgebraObject
 DistributableLinearAlgebraObject ()
 Default constructor - create a distribution. More...
 
 DistributableLinearAlgebraObject (const DistributableLinearAlgebraObject &matrix)=delete
 Broken copy constructor. More...
 
void operator= (const DistributableLinearAlgebraObject &)=delete
 Broken assignment operator. More...
 
virtual ~DistributableLinearAlgebraObject ()
 Destructor. More...
 
LinearAlgebraDistributiondistribution_pt () const
 access to the LinearAlgebraDistribution More...
 
unsigned nrow () const
 access function to the number of global rows. More...
 
unsigned nrow_local () const
 access function for the num of local rows on this processor. More...
 
unsigned nrow_local (const unsigned &p) const
 access function for the num of local rows on this processor. More...
 
unsigned first_row () const
 access function for the first row on this processor More...
 
unsigned first_row (const unsigned &p) const
 access function for the first row on this processor More...
 
bool distributed () const
 distribution is serial or distributed More...
 
bool distribution_built () const
 
void build_distribution (const LinearAlgebraDistribution *const dist_pt)
 
void build_distribution (const LinearAlgebraDistribution &dist)
 

Private Member Functions

void solve_helper (DoubleMatrixBase *const &matrix_pt, const DoubleVector &rhs, DoubleVector &solution)
 

Private Attributes

MATRIX * Matrix_pt
 Pointer to the matrix. More...
 
Vector< doubleMatrix_diagonal
 Vector containing the diagonal entries of A. More...
 
bool Resolving
 
bool Matrix_can_be_deleted
 
unsigned Iterations
 Number of iterations taken. More...
 
double Omega
 Damping factor. More...
 

Additional Inherited Members

- Protected Member Functions inherited from oomph::DistributableLinearAlgebraObject
void clear_distribution ()
 
- Protected Attributes inherited from oomph::Smoother
bool Use_as_smoother
 
- Protected Attributes inherited from oomph::IterativeLinearSolver
bool Doc_convergence_history
 
std::ofstream Output_file_stream
 Output file stream for convergence history. More...
 
double Tolerance
 Convergence tolerance. More...
 
unsigned Max_iter
 Maximum number of iterations. More...
 
PreconditionerPreconditioner_pt
 Pointer to the preconditioner. More...
 
double Jacobian_setup_time
 Jacobian setup time. More...
 
double Solution_time
 linear solver solution time More...
 
double Preconditioner_setup_time
 Preconditioner setup time. More...
 
bool Setup_preconditioner_before_solve
 
bool Throw_error_after_max_iter
 
bool Use_iterative_solver_as_preconditioner
 Use the iterative solver as preconditioner. More...
 
bool First_time_solve_when_used_as_preconditioner
 
- Protected Attributes inherited from oomph::LinearSolver
bool Enable_resolve
 
bool Doc_time
 Boolean flag that indicates whether the time taken. More...
 
bool Compute_gradient
 
bool Gradient_has_been_computed
 flag that indicates whether the gradient was computed or not More...
 
DoubleVector Gradient_for_glob_conv_newton_solve
 
- Static Protected Attributes inherited from oomph::IterativeLinearSolver
static IdentityPreconditioner Default_preconditioner
 

Detailed Description

template<typename MATRIX>
class oomph::DampedJacobi< MATRIX >

//////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////// Damped Jacobi "solver" templated by matrix type. The "solver" exists in many different incarnations: It's an IterativeLinearSolver, and a Smoother, all of which use the same basic iteration.

Constructor & Destructor Documentation

◆ DampedJacobi() [1/2]

template<typename MATRIX >
oomph::DampedJacobi< MATRIX >::DampedJacobi ( const double omega = 2.0 / 3.0)
inline

Empty constructor.

1005  : Matrix_can_be_deleted(true)
1006  {
1007  // Damping factor
1008  Omega = omega;
1009  }
bool Matrix_can_be_deleted
Definition: iterative_linear_solver.h:1207
double Omega
Damping factor.
Definition: iterative_linear_solver.h:1213
Vector::Scalar omega(const Vector &t, const Vector &s, RealScalar angle)
Definition: IDRS.h:36

References Eigen::internal::omega(), and oomph::DampedJacobi< MATRIX >::Omega.

◆ ~DampedJacobi()

template<typename MATRIX >
oomph::DampedJacobi< MATRIX >::~DampedJacobi ( )
inline

Empty destructor.

1013  {
1014  // Run the generic clean up function
1015  clean_up_memory();
1016  }
void clean_up_memory()
Cleanup data that's stored for resolve (if any has been stored)
Definition: iterative_linear_solver.h:1025

References oomph::DampedJacobi< MATRIX >::clean_up_memory().

◆ DampedJacobi() [2/2]

template<typename MATRIX >
oomph::DampedJacobi< MATRIX >::DampedJacobi ( const DampedJacobi< MATRIX > &  )
delete

Broken copy constructor.

Member Function Documentation

◆ clean_up_memory()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::clean_up_memory ( )
inlinevirtual

Cleanup data that's stored for resolve (if any has been stored)

Reimplemented from oomph::LinearSolver.

1026  {
1027  // If the matrix pointer isn't null AND we're allowed to delete the
1028  // matrix which is only when we create the matrix ourselves
1029  if ((Matrix_pt != 0) && (Matrix_can_be_deleted))
1030  {
1031  // Delete the matrix
1032  delete Matrix_pt;
1033 
1034  // Assign the associated pointer the value NULL
1035  Matrix_pt = 0;
1036  }
1037  } // End of clean_up_memory
MATRIX * Matrix_pt
Pointer to the matrix.
Definition: iterative_linear_solver.h:1196

References oomph::DampedJacobi< MATRIX >::Matrix_can_be_deleted, and oomph::DampedJacobi< MATRIX >::Matrix_pt.

Referenced by oomph::DampedJacobi< MATRIX >::~DampedJacobi().

◆ extract_diagonal_entries()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::extract_diagonal_entries ( DoubleMatrixBase matrix_pt)
inline

Function to extract the diagonal entries from the matrix.

1055  {
1056  // If we're using a CRDoubleMatrix object
1057  if (dynamic_cast<CRDoubleMatrix*>(matrix_pt))
1058  {
1059  // The matrix diagonal (we need this when we need to calculate inv(D)
1060  // where D is the diagonal of A and it remains the same for all uses
1061  // of the iterative scheme so we can store it and call it in each
1062  // iteration)
1063  Matrix_diagonal =
1064  dynamic_cast<CRDoubleMatrix*>(Matrix_pt)->diagonal_entries();
1065  }
1066  // If we're using a complex matrix then diagonal entries has to be a
1067  // complex vector rather than a vector of doubles.
1068  else if (dynamic_cast<CCDoubleMatrix*>(matrix_pt))
1069  {
1070  // Make an ostringstream object to create an error message
1071  std::ostringstream error_message_stream;
1072 
1073  // Create the error message
1074  error_message_stream << "Damped Jacobi can only cater to real-valued "
1075  << "matrices. If you require a complex-valued "
1076  << "version, please write this yourself. "
1077  << "It is likely that the only difference will be "
1078  << "the use of complex vectors.";
1079 
1080  // Throw an error
1081  throw OomphLibError(error_message_stream.str(),
1084  }
1085  // Just extract the diagonal entries normally
1086  else
1087  {
1088  // Calculate the number of rows in the matrix
1089  unsigned n_row = Matrix_pt->nrow();
1090 
1091  // Loop over the rows of the matrix
1092  for (unsigned i = 0; i < n_row; i++)
1093  {
1094  // Assign the i-th value of Matrix_diagonal
1095  Matrix_diagonal[i] = (*Matrix_pt)(i, i);
1096  }
1097  } // if (dynamic_cast<CRDoubleMatrix*>(matrix_pt))
1098 
1099  // Calculate the n.d.o.f.
1100  unsigned n_dof = Matrix_diagonal.size();
1101 
1102  // Find the reciprocal of the entries of Matrix_diagonal
1103  for (unsigned i = 0; i < n_dof; i++)
1104  {
1105  Matrix_diagonal[i] = 1.0 / Matrix_diagonal[i];
1106  }
1107  } // End of extract_diagonal_entries
int i
Definition: BiCGSTAB_step_by_step.cpp:9
Vector< double > Matrix_diagonal
Vector containing the diagonal entries of A.
Definition: iterative_linear_solver.h:1199
#define OOMPH_EXCEPTION_LOCATION
Definition: oomph_definitions.h:61
#define OOMPH_CURRENT_FUNCTION
Definition: oomph_definitions.h:86

References i, oomph::DampedJacobi< MATRIX >::Matrix_diagonal, oomph::DampedJacobi< MATRIX >::Matrix_pt, OOMPH_CURRENT_FUNCTION, and OOMPH_EXCEPTION_LOCATION.

Referenced by oomph::DampedJacobi< MATRIX >::smoother_setup(), and oomph::DampedJacobi< MATRIX >::solve().

◆ iterations()

template<typename MATRIX >
unsigned oomph::DampedJacobi< MATRIX >::iterations ( ) const
inlinevirtual

Number of iterations taken.

Implements oomph::IterativeLinearSolver.

1183  {
1184  // Return the value of Iterations
1185  return Iterations;
1186  } // End of iterations
unsigned Iterations
Number of iterations taken.
Definition: iterative_linear_solver.h:1210

References oomph::DampedJacobi< MATRIX >::Iterations.

◆ operator=()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::operator= ( const DampedJacobi< MATRIX > &  )
delete

Broken assignment operator.

◆ resolve()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::resolve ( const DoubleVector rhs,
DoubleVector result 
)
inlinevirtual

Re-solve the system defined by the last assembled Jacobian and the rhs vector specified here. Solution is returned in the vector result.

Reimplemented from oomph::LinearSolver.

1161  {
1162  // We are re-solving
1163  Resolving = true;
1164 
1165 #ifdef PARANOID
1166  if (Matrix_pt == 0)
1167  {
1168  throw OomphLibError("No matrix was stored -- cannot re-solve",
1171  }
1172 #endif
1173 
1174  // Call linear algebra-style solver
1175  solve(Matrix_pt, rhs, result);
1176 
1177  // Reset re-solving flag
1178  Resolving = false;
1179  } // End of resolve
bool Resolving
Definition: iterative_linear_solver.h:1203
void solve(Problem *const &problem_pt, DoubleVector &result)
Definition: iterative_linear_solver.cc:1858

References oomph::DampedJacobi< MATRIX >::Matrix_pt, OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION, oomph::DampedJacobi< MATRIX >::Resolving, and oomph::DampedJacobi< MATRIX >::solve().

◆ smoother_setup()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::smoother_setup ( DoubleMatrixBase matrix_pt)
inlinevirtual

Setup: Pass pointer to the matrix and store in cast form.

Implements oomph::Smoother.

1041  {
1042  // Assume the matrix has been passed in from the outside so we must not
1043  // delete it
1044  Matrix_can_be_deleted = false;
1045 
1046  // Upcast to the appropriate matrix type
1047  Matrix_pt = dynamic_cast<MATRIX*>(matrix_pt);
1048 
1049  // Extract the diagonal entries of the matrix and store them
1050  extract_diagonal_entries(matrix_pt);
1051  } // End of smoother_setup
void extract_diagonal_entries(DoubleMatrixBase *matrix_pt)
Function to extract the diagonal entries from the matrix.
Definition: iterative_linear_solver.h:1054

References oomph::DampedJacobi< MATRIX >::extract_diagonal_entries(), oomph::DampedJacobi< MATRIX >::Matrix_can_be_deleted, and oomph::DampedJacobi< MATRIX >::Matrix_pt.

◆ smoother_solve()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::smoother_solve ( const DoubleVector rhs,
DoubleVector solution 
)
inlinevirtual

The smoother_solve function performs fixed number of iterations on the system A*result=rhs. The number of (smoothing) iterations is the same as the max. number of iterations in the underlying IterativeLinearSolver class.

Implements oomph::Smoother.

1114  {
1115  // If you use a smoother but you don't want to calculate the residual
1116  Use_as_smoother = true;
1117 
1118  // Call the helper function
1120  } // End of smoother_solve
void solve_helper(DoubleMatrixBase *const &matrix_pt, const DoubleVector &rhs, DoubleVector &solution)
Definition: iterative_linear_solver.cc:1922
bool Use_as_smoother
Definition: iterative_linear_solver.h:585
void solution(const Vector< double > &x, Vector< double > &u)
Definition: two_d_biharmonic.cc:113

References oomph::DampedJacobi< MATRIX >::Matrix_pt, BiharmonicTestFunctions1::solution(), oomph::DampedJacobi< MATRIX >::solve_helper(), and oomph::Smoother::Use_as_smoother.

◆ solve() [1/2]

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::solve ( DoubleMatrixBase *const &  matrix_pt,
const DoubleVector rhs,
DoubleVector solution 
)
inlinevirtual

Linear-algebra-type solver: Takes pointer to a matrix and rhs vector and returns the solution of the linear system.

Reimplemented from oomph::LinearSolver.

1133  {
1134  // Matrix has been passed in from the outside so we must not delete it
1135  Matrix_can_be_deleted = false;
1136 
1137  // Indicate that the solver is not being used as a smoother
1138  Use_as_smoother = false;
1139 
1140  // Set up the distribution
1141  this->build_distribution(rhs.distribution_pt());
1142 
1143  // Store the matrix if required
1144  if ((Enable_resolve) && (!Resolving))
1145  {
1146  // Upcast to the appropriate matrix type
1147  Matrix_pt = dynamic_cast<MATRIX*>(matrix_pt);
1148  }
1149 
1150  // Extract the diagonal entries of the matrix and store them
1151  extract_diagonal_entries(matrix_pt);
1152 
1153  // Call the helper function
1154  solve_helper(matrix_pt, rhs, solution);
1155  } // End of solve
void build_distribution(const LinearAlgebraDistribution *const dist_pt)
Definition: linear_algebra_distribution.h:507
bool Enable_resolve
Definition: linear_solver.h:73

References oomph::DistributableLinearAlgebraObject::build_distribution(), oomph::DistributableLinearAlgebraObject::distribution_pt(), oomph::LinearSolver::Enable_resolve, oomph::DampedJacobi< MATRIX >::extract_diagonal_entries(), oomph::DampedJacobi< MATRIX >::Matrix_can_be_deleted, oomph::DampedJacobi< MATRIX >::Matrix_pt, oomph::DampedJacobi< MATRIX >::Resolving, BiharmonicTestFunctions1::solution(), oomph::DampedJacobi< MATRIX >::solve_helper(), and oomph::Smoother::Use_as_smoother.

◆ solve() [2/2]

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::solve ( Problem *const &  problem_pt,
DoubleVector result 
)
virtual

Use damped Jacobi iteration as an IterativeLinearSolver: This obtains the Jacobian matrix J and the residual vector r (needed for the Newton method) from the problem's get_jacobian function and returns the result of Jx=r.

/////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////// Solver: Takes pointer to problem and returns the results vector which contains the solution of the linear system defined by the problem's fully assembled Jacobian and residual vector.

Implements oomph::LinearSolver.

1860  {
1861  // Reset the Use_as_smoother_flag as the solver is not being used
1862  // as a smoother
1863  Use_as_smoother = false;
1864 
1865  // Find the # of degrees of freedom (variables)
1866  unsigned n_dof = problem_pt->ndof();
1867 
1868  // Initialise timer
1869  double t_start = TimingHelpers::timer();
1870 
1871  // We're not re-solving
1872  Resolving = false;
1873 
1874  // Get rid of any previously stored data
1875  clean_up_memory();
1876 
1877  // Set up the distribution
1878  LinearAlgebraDistribution dist(problem_pt->communicator_pt(), n_dof, false);
1879 
1880  // Assign the distribution to the LinearSolver
1881  this->build_distribution(dist);
1882 
1883  // Allocate space for the Jacobian matrix in format specified
1884  // by template parameter
1885  Matrix_pt = new MATRIX;
1886 
1887  // Get the nonlinear residuals vector
1888  DoubleVector f;
1889 
1890  // Assign the Jacobian and the residuals vector
1891  problem_pt->get_jacobian(f, *Matrix_pt);
1892 
1893  // Extract the diagonal entries of the matrix and store them
1895 
1896  // We've made the matrix, we can delete it...
1897  Matrix_can_be_deleted = true;
1898 
1899  // Doc time for setup
1900  double t_end = TimingHelpers::timer();
1901  Jacobian_setup_time = t_end - t_start;
1902 
1903  // If time documentation is enabled
1904  if (Doc_time)
1905  {
1906  oomph_info << "Time for setup of Jacobian [sec]: " << Jacobian_setup_time
1907  << std::endl;
1908  }
1909 
1910  // Call linear algebra-style solver
1911  solve_helper(Matrix_pt, f, result);
1912 
1913  // Kill matrix unless it's still required for resolve
1915  } // End of solve
std::vector< double > DoubleVector
loads clump configuration
Definition: ClumpInput.h:26
double Jacobian_setup_time
Jacobian setup time.
Definition: iterative_linear_solver.h:248
bool Doc_time
Boolean flag that indicates whether the time taken.
Definition: linear_solver.h:77
static int f(const TensorMap< Tensor< int, 3 > > &tensor)
Definition: cxx11_tensor_map.cpp:237
double timer()
returns the time in seconds after some point in past
Definition: oomph_utilities.cc:1295
OomphInfo oomph_info
Definition: oomph_definitions.cc:319

References oomph::TerminateHelper::clean_up_memory(), oomph::Problem::communicator_pt(), f(), oomph::Problem::get_jacobian(), oomph::Problem::ndof(), oomph::oomph_info, and oomph::TimingHelpers::timer().

Referenced by oomph::DampedJacobi< MATRIX >::resolve().

◆ solve_helper()

template<typename MATRIX >
void oomph::DampedJacobi< MATRIX >::solve_helper ( DoubleMatrixBase *const &  matrix_pt,
const DoubleVector rhs,
DoubleVector solution 
)
private

This is where the actual work is done – different implementations for different matrix types.

Linear-algebra-type solver: Takes pointer to a matrix and rhs vector and returns the solution of the linear system.

1925  {
1926  // Get number of dofs
1927  unsigned n_dof = rhs.nrow();
1928 
1929 #ifdef PARANOID
1930  // Upcast the matrix to the appropriate type
1931  MATRIX* tmp_matrix_pt = dynamic_cast<MATRIX*>(matrix_pt);
1932 
1933  // PARANOID Run the self-tests to check the inputs are correct
1934  this->check_validity_of_solve_helper_inputs<MATRIX>(
1935  tmp_matrix_pt, rhs, solution, n_dof);
1936 
1937  // We don't need the pointer any more but we do still need the matrix
1938  // so just make tmp_matrix_pt a null pointer
1939  tmp_matrix_pt = 0;
1940 #endif
1941 
1942  // Setup the solution if it is not
1943  if (!solution.distribution_pt()->built())
1944  {
1945  // Build the distribution of the solution vector if it hasn't been done
1946  // yet
1947  solution.build(this->distribution_pt(), 0.0);
1948  }
1949  // If the solution has already been set up
1950  else
1951  {
1952  // If we're inside the multigrid solver then as we traverse up the
1953  // hierarchy we use the smoother on the updated approximate solution.
1954  // As such, we should ONLY be resetting all the values to zero if
1955  // we're NOT inside the multigrid solver
1956  if (!Use_as_smoother)
1957  {
1958  // Initialise the vector with all entries set to zero
1959  solution.initialise(0.0);
1960  }
1961  } // if (!solution.distribution_pt()->built())
1962 
1963  // Initialise timer
1964  double t_start = TimingHelpers::timer();
1965 
1966  // Initial guess isn't necessarily zero (restricted solution from finer
1967  // grids) therefore x needs to be assigned values from the input.
1969 
1970  // Create a vector to store the value of the constant term, omega*inv(D)*r
1971  DoubleVector constant_term(this->distribution_pt(), 0.0);
1972 
1973  // Calculate the constant term vector
1974  for (unsigned i = 0; i < n_dof; i++)
1975  {
1976  // Assign the i-th entry of constant_term
1977  constant_term[i] = Omega * Matrix_diagonal[i] * rhs[i];
1978  }
1979 
1980  // Create a vector to hold the residual. This will only be built if
1981  // we're not inside the multigrid solver
1982  DoubleVector local_residual;
1983 
1984  // Variable to store the 2-norm of the residual vector. Only used
1985  // if we are not working inside the MG solver
1986  double norm_res = 0.0;
1987 
1988  // Variables to hold the initial residual norm. Only used if we're
1989  // not inside the multigrid solver
1990  double norm_f = 0.0;
1991 
1992  // Initialise the value of Iterations
1993  Iterations = 0;
1994 
1995  // Calculate the residual only if we're not inside the multigrid solver
1996  if (!Use_as_smoother)
1997  {
1998  // Build the local residual vector
1999  local_residual.build(this->distribution_pt(), 0.0);
2000 
2001  // Calculate the residual vector
2002  matrix_pt->residual(x, rhs, local_residual);
2003 
2004  // Calculate the 2-norm
2005  norm_res = local_residual.norm();
2006 
2007  // Store the initial norm
2008  norm_f = norm_res;
2009 
2010  // If required will document convergence history to screen
2011  // or file (if stream is open)
2013  {
2014  if (!Output_file_stream.is_open())
2015  {
2016  oomph_info << Iterations << " " << norm_res << std::endl;
2017  }
2018  else
2019  {
2020  Output_file_stream << Iterations << " " << norm_res << std::endl;
2021  }
2022  } // if (Doc_convergence_history)
2023  } // if (!Use_as_smoother)
2024 
2025  // Create a temporary vector to store the value of A*e
2026  // on each iteration and another to store the residual
2027  // at the end of each iteration
2028  DoubleVector temp_vec(this->distribution_pt(), 0.0);
2029 
2030  // Outermost loop: Run up to Max_iter times (the iteration number)
2031  for (unsigned iter_num = 0; iter_num < Max_iter; iter_num++)
2032  {
2033  // Calculate A*e
2034  matrix_pt->multiply(x, temp_vec);
2035 
2036  // Loop over each degree of freedom and update
2037  // the current approximation
2038  for (unsigned idof = 0; idof < n_dof; idof++)
2039  {
2040  // Scale the idof'th entry of temp_vec
2041  // by omega/A(i,i)
2042  temp_vec[idof] *= Omega * Matrix_diagonal[idof];
2043  }
2044 
2045  // Update the value of e (in the system Ae=r)
2046  x += constant_term;
2047  x -= temp_vec;
2048 
2049  // Increment the value of Iterations
2050  Iterations++;
2051 
2052  // Calculate the residual only if we're not inside the multigrid solver
2053  if (!Use_as_smoother)
2054  {
2055  // Get residual
2056  matrix_pt->residual(x, rhs, local_residual);
2057 
2058  // Calculate the 2-norm of the residual r=b-Ax
2059  norm_res = local_residual.norm() / norm_f;
2060 
2061  // If required, this will document convergence history to
2062  // screen or file (if the stream is open)
2064  {
2065  if (!Output_file_stream.is_open())
2066  {
2067  oomph_info << Iterations << " " << norm_res << std::endl;
2068  }
2069  else
2070  {
2071  Output_file_stream << Iterations << " " << norm_res << std::endl;
2072  }
2073  } // if (Doc_convergence_history)
2074 
2075  // Check the tolerance only if the residual norm is being computed
2076  if (norm_res < Tolerance)
2077  {
2078  // Break out of the for-loop
2079  break;
2080  }
2081  } // if (!Use_as_smoother)
2082  } // for (unsigned iter_num=0;iter_num<Max_iter;iter_num++)
2083 
2084  // Calculate the residual only if we're not inside the multigrid solver
2085  if (!Use_as_smoother)
2086  {
2087  // If time documentation is enabled
2088  if (Doc_time)
2089  {
2090  oomph_info << "\nDamped Jacobi converged. Residual norm: " << norm_res
2091  << "\nNumber of iterations to convergence: " << Iterations
2092  << "\n"
2093  << std::endl;
2094  }
2095  } // if (!Use_as_smoother)
2096 
2097  // Copy the solution into the solution vector
2098  solution = x;
2099 
2100  // Doc. time for solver
2101  double t_end = TimingHelpers::timer();
2102  Solution_time = t_end - t_start;
2103  if (Doc_time)
2104  {
2105  oomph_info << "Time for solve with damped Jacobi [sec]: " << Solution_time
2106  << std::endl;
2107  }
2108 
2109  // If the solver failed to converge and the user asked for an error if
2110  // this happened
2112  {
2113  std::string error_message =
2114  "Solver failed to converge and you requested ";
2115  error_message += "an error on convergence failures.";
2116  throw OomphLibError(
2118  }
2119  } // End of solve_helper
LinearAlgebraDistribution * distribution_pt() const
access to the LinearAlgebraDistribution
Definition: linear_algebra_distribution.h:457
double Tolerance
Convergence tolerance.
Definition: iterative_linear_solver.h:239
bool Throw_error_after_max_iter
Definition: iterative_linear_solver.h:262
unsigned Max_iter
Maximum number of iterations.
Definition: iterative_linear_solver.h:242
double Solution_time
linear solver solution time
Definition: iterative_linear_solver.h:251
std::ofstream Output_file_stream
Output file stream for convergence history.
Definition: iterative_linear_solver.h:231
bool Doc_convergence_history
Definition: iterative_linear_solver.h:228
std::string string(const unsigned &i)
Definition: oomph_definitions.cc:286
list x
Definition: plotDoE.py:28

References oomph::DoubleVector::build(), i, Global_Variables::Iterations, oomph::BlackBoxFDNewtonSolver::Max_iter, oomph::DoubleMatrixBase::multiply(), oomph::DoubleVector::norm(), oomph::DistributableLinearAlgebraObject::nrow(), oomph::SarahBL::Omega, OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION, oomph::oomph_info, oomph::DoubleMatrixBase::residual(), BiharmonicTestFunctions1::solution(), oomph::Global_string_for_annotation::string(), oomph::TimingHelpers::timer(), and plotDoE::x.

Referenced by oomph::DampedJacobi< MATRIX >::smoother_solve(), and oomph::DampedJacobi< MATRIX >::solve().

Member Data Documentation

◆ Iterations

template<typename MATRIX >
unsigned oomph::DampedJacobi< MATRIX >::Iterations
private

Number of iterations taken.

Referenced by oomph::DampedJacobi< MATRIX >::iterations().

◆ Matrix_can_be_deleted

template<typename MATRIX >
bool oomph::DampedJacobi< MATRIX >::Matrix_can_be_deleted
private

Boolean flag to indicate if the matrix pointed to be Matrix_pt can be deleted.

Referenced by oomph::DampedJacobi< MATRIX >::clean_up_memory(), oomph::DampedJacobi< MATRIX >::smoother_setup(), and oomph::DampedJacobi< MATRIX >::solve().

◆ Matrix_diagonal

template<typename MATRIX >
Vector<double> oomph::DampedJacobi< MATRIX >::Matrix_diagonal
private

Vector containing the diagonal entries of A.

Referenced by oomph::DampedJacobi< MATRIX >::extract_diagonal_entries().

◆ Matrix_pt

◆ Omega

template<typename MATRIX >
double oomph::DampedJacobi< MATRIX >::Omega
private

Damping factor.

Referenced by oomph::DampedJacobi< MATRIX >::DampedJacobi().

◆ Resolving

template<typename MATRIX >
bool oomph::DampedJacobi< MATRIX >::Resolving
private

Boolean flag to indicate if the solve is done in re-solve mode, bypassing setup of matrix and preconditioner

Referenced by oomph::DampedJacobi< MATRIX >::resolve(), and oomph::DampedJacobi< MATRIX >::solve().


The documentation for this class was generated from the following files: