28 #include "libmesh/linear_solver.h" 29 #include "libmesh/dof_map.h" 30 #include "libmesh/petsc_matrix.h" 31 #include "libmesh/petsc_vector.h" 44 step_size_change_exponent (0.5),
45 step_desired_iters (5),
46 schur_factorization (true),
100 libMesh::NumericVector<Real>
104 _X0.reset(X.clone().release());
119 << std::setw(10) <<
"iter: " 120 << std::setw(5) << iter
121 << std::setw(10) <<
"res-l2: " 122 << std::setw(15) << norm
123 << std::setw(20) <<
"relative res-l2: " 124 << std::setw(15) << norm/norm0 << std::endl;
130 if (norm <
abs_tol) cont =
false;
131 if (norm/norm0 <
rel_tol) cont =
false;
137 <<
" Retrying with smaller step-size" << std::endl;
155 << std::setw(10) <<
"iter: " 156 << std::setw(5) << iter
157 << std::setw(10) <<
"res-l2: " 158 << std::setw(15) << norm
159 << std::setw(20) <<
"relative res-l2: " 160 << std::setw(15) << norm/norm0
161 << std::setw(20) <<
"Terminated" << std::endl;
169 << std::setw(30) <<
"increased step-size: " 170 << std::setw(15) << arc_length << std::endl;
172 else if (factor < 1.) {
175 << std::setw(30) <<
"reduced step-size: " 176 << std::setw(15) << arc_length << std::endl;
186 libMesh::NumericVector<Real> &f,
188 libMesh::NumericVector<Real> &dfdp,
190 const libMesh::NumericVector<Real> &dgdX,
193 libMesh::NumericVector<Real> &dX,
221 libMesh::DofMap& dof_map = system.get_dof_map();
222 const libMesh::Parallel::Communicator
223 &comm = system.comm();
227 my_m = dof_map.n_dofs(),
231 n_l = dof_map.n_dofs_on_processor(system.processor_id()),
236 std::vector<libMesh::dof_id_type>
237 n_nz = dof_map.get_n_nz(),
238 n_oz = dof_map.get_n_oz();
241 if (rank == comm.size()-1) {
249 for (
unsigned int i=0; i<n_nz.size(); i++)
253 n_nz.push_back(total_n_l);
255 n_oz.push_back(total_n - total_n_l);
260 for (
unsigned int i=0; i<n_oz.size(); i++)
268 ierr = MatCreate(comm.get(), &mat); CHKERRABORT(comm.get(), ierr);
269 ierr = MatSetSizes(mat,
270 total_m_l, total_n_l,
271 total_m, total_n); CHKERRABORT(comm.get(), ierr);
273 if (libMesh::on_command_line(
"--solver_system_names")) {
276 MatSetOptionsPrefix(mat, nm.c_str());
278 ierr = MatSetFromOptions(mat); CHKERRABORT(comm.get(), ierr);
280 ierr = MatSeqAIJSetPreallocation(mat,
282 (PetscInt*)&n_nz[0]); CHKERRABORT(comm.get(), ierr);
283 ierr = MatMPIAIJSetPreallocation(mat,
287 (PetscInt*)&n_oz[0]); CHKERRABORT(comm.get(), ierr);
288 ierr = MatSeqBAIJSetPreallocation (mat, 1,
289 0, (PetscInt*)&n_nz[0]); CHKERRABORT(comm.get(), ierr);
290 ierr = MatMPIBAIJSetPreallocation (mat, 1,
291 0, (PetscInt*)&n_nz[0],
292 0, (PetscInt*)&n_oz[0]); CHKERRABORT(comm.get(), ierr);
295 ierr = MatSetOption(mat,
296 MAT_NEW_NONZERO_ALLOCATION_ERR,
297 PETSC_TRUE); CHKERRABORT(comm.get(), ierr);
300 Vec res_vec, sol_vec;
302 ierr = MatCreateVecs(mat, &res_vec, PETSC_NULL); CHKERRABORT(comm.get(), ierr);
303 ierr = MatCreateVecs(mat, &sol_vec, PETSC_NULL); CHKERRABORT(comm.get(), ierr);
306 std::unique_ptr<libMesh::SparseMatrix<Real> >
307 jac_mat(
new libMesh::PetscMatrix<Real>(mat, comm));
309 std::unique_ptr<libMesh::NumericVector<Real> >
310 res(
new libMesh::PetscVector<Real>(res_vec, comm)),
311 sol(
new libMesh::PetscVector<Real>(sol_vec, comm));
326 update_f?res.get():
nullptr,
336 for (
unsigned int i=dof_map.first_dof(rank); i<dof_map.end_dof(rank); i++)
337 res->set(i, f.el(i));
341 if (rank == comm.size()-1)
342 res->set(total_m-1, g);
352 for (
unsigned int i=dof_map.first_dof(rank);
353 i<dof_map.end_dof(rank); i++) {
355 jac_mat->set( i, total_m-1, dfdp.el(i));
356 jac_mat->set(total_m-1, i, dgdX.el(i));
360 if (rank == comm.size()-1)
361 jac_mat->set(total_m-1, total_m-1, dgdp);
373 ierr = KSPCreate(comm.get(), &ksp); CHKERRABORT(comm.get(), ierr);
375 if (libMesh::on_command_line(
"--solver_system_names")) {
378 KSPSetOptionsPrefix(ksp, nm.c_str());
381 ierr = KSPSetOperators(ksp, mat, mat); CHKERRABORT(comm.get(), ierr);
382 ierr = KSPSetFromOptions(ksp); CHKERRABORT(comm.get(), ierr);
385 ierr = KSPGetPC(ksp, &pc); CHKERRABORT(comm.get(), ierr);
386 ierr = PCSetFromOptions(pc); CHKERRABORT(comm.get(), ierr);
389 ierr = KSPSolve(ksp, res_vec, sol_vec);
393 for (
unsigned int i=dof_map.first_dof(rank);
394 i<dof_map.end_dof(rank); i++)
395 dX.set(i, sol->el(i));
398 #ifdef LIBMESH_ENABLE_CONSTRAINTS 399 system.get_dof_map().enforce_constraints_exactly (system,
404 std::vector<Real> val(1, 0.);
405 std::vector<libMesh::numeric_index_type> dofs(1, total_m-1);
406 sol->localize(val, dofs);
410 ierr = KSPDestroy(&ksp);
411 ierr = MatDestroy(&mat);
412 ierr = VecDestroy(&res_vec);
413 ierr = VecDestroy(&sol_vec);
423 libMesh::SparseMatrix<Real> &jac,
425 libMesh::NumericVector<Real> &f,
427 libMesh::NumericVector<Real> &dfdp,
429 libMesh::NumericVector<Real> &dXdp,
431 const libMesh::NumericVector<Real> &dgdX,
434 libMesh::NumericVector<Real> &dX,
467 std::pair<unsigned int, Real>
472 std::unique_ptr<libMesh::NumericVector<Real>>
473 r1(X.zero_clone().release());
475 libMesh::SparseMatrix<Real>
476 *pc = system.request_matrix(
"Preconditioner");
487 if (update_f || update_jac)
489 update_f? &f:
nullptr,
490 update_jac? &jac:
nullptr,
495 solver_params.second,
496 solver_params.first);
498 #ifdef LIBMESH_ENABLE_CONSTRAINTS 499 system.get_dof_map().enforce_constraints_exactly (system,
512 if (update_dfdp || update_dXdp) {
517 solver_params.second,
518 solver_params.first);
524 #ifdef LIBMESH_ENABLE_CONSTRAINTS 525 system.get_dof_map().enforce_constraints_exactly (system,
534 a = dgdp + dgdX.dot(dXdp);
539 dp = 1./a * (- g + dgdX.dot(*r1));
552 solver_params.second,
553 solver_params.first);
557 #ifdef LIBMESH_ENABLE_CONSTRAINTS 558 system.get_dof_map().enforce_constraints_exactly (system,
583 std::unique_ptr<libMesh::NumericVector<Real>>
584 f(X.zero_clone().release());
594 val = std::pow(std::pow(
_g(X, p), 2) + std::pow(f->l2_norm(), 2), 0.5);
Real rel_tol
Relative tolerance for the solver.
Real max_step
maximum step size allowed with adaptivity
This class implements a system for solution of nonlinear systems.
virtual void clear_elem_operation_object()
clears the association of this object with the assembly element operation object. ...
virtual bool sensitivity_assemble(const MAST::FunctionBase &f, libMesh::NumericVector< Real > &sensitivity_rhs)
Assembly function.
virtual void solve()
solves for the next load step
This is a scalar function whose value can be changed and one that can be used as a design variable in...
bool close_matrix
flag to control the closing fo the Jacobian after assembly
virtual void set_elem_operation_object(MAST::AssemblyElemOperations &elem_ops)
attaches a element operation to this object, and associated this with the element operation object...
void _solve_schur_factorization(const libMesh::NumericVector< Real > &X, const MAST::Parameter &p, libMesh::SparseMatrix< Real > &jac, bool update_jac, libMesh::NumericVector< Real > &f, bool update_f, libMesh::NumericVector< Real > &dfdp, bool update_dfdp, libMesh::NumericVector< Real > &dXdp, bool update_dXdp, const libMesh::NumericVector< Real > &dgdX, const Real dgdp, const Real g, libMesh::NumericVector< Real > &dX, Real &dp)
solves for the linear system of equation using Schur factorization.
virtual void _solve_NR_iterate(libMesh::NumericVector< Real > &X, MAST::Parameter &p)=0
virtual ~ContinuationSolverBase()
Real min_step
minimum step size allowed with adaptivity
virtual void _save_iteration_data()=0
method saves any data for possible resuse if the solution step is restarted
Real _res_norm(const libMesh::NumericVector< Real > &X, const MAST::Parameter &p)
void _solve(const libMesh::NumericVector< Real > &X, const MAST::Parameter &p, libMesh::NumericVector< Real > &f, bool update_f, libMesh::NumericVector< Real > &dfdp, bool update_dfdp, const libMesh::NumericVector< Real > &dgdX, const Real dgdp, const Real g, libMesh::NumericVector< Real > &dX, Real &dp)
solves for the linear system of equation as a monolithic system dX and dp are returned from the solu...
virtual std::pair< unsigned int, Real > get_linear_solve_parameters()
calls NonlinearImplicitSystem::set_solver_parameters() before accessing the values.
virtual Real _g(const libMesh::NumericVector< Real > &X, const MAST::Parameter &p)=0
Real arc_length
arc length that the solver is required to satisfy for the update.
Real abs_tol
Absolute tolerance for the solver.
MAST::AssemblyBase * _assembly
std::unique_ptr< libMesh::NumericVector< Real > > _X0
void set_operation(MAST::NonlinearSystem::Operation op)
sets the current operation of the system
void set_assembly_and_load_parameter(MAST::AssemblyElemOperations &elem_ops, MAST::AssemblyBase &assembly, MAST::Parameter &p)
sets the assembly object for this solver
std::unique_ptr< libMesh::LinearSolver< Real > > linear_solver
The LinearSolver for solution of the linear equations.
virtual void residual_and_jacobian(const libMesh::NumericVector< Real > &X, libMesh::NumericVector< Real > *R, libMesh::SparseMatrix< Real > *J, libMesh::NonlinearImplicitSystem &S)
function that assembles the matrices and vectors quantities for nonlinear solution ...
MAST::NonlinearSystem::Operation operation()
virtual void _reset_iterations()=0
method resets any data if a soltion step is restarted
unsigned int max_it
Maximum number of Newton-Raphson iterations for the solver.
Real step_size_change_exponent
exponent used in step size update.
MAST::AssemblyElemOperations * _elem_ops
void clear_assembly_and_load_parameters()
clears the assembly object from this solver
const MAST::NonlinearSystem & system() const
unsigned int step_desired_iters
desired N-R iterations per load-step.