[cig-commits] commit 1864 by buerg to /var/svn/dealii/aspect
dealii.demon at gmail.com
dealii.demon at gmail.com
Fri Aug 30 09:48:28 PDT 2013
Revision 1864
Due to lack of efficient preconditioner, use Uzawa to solve Navier-Stokes.
U trunk/aspire/source/simulator/solver.cc
http://www.dealii.org/websvn/revision.php?repname=Aspect+Repository&path=%2F&rev=1864&peg=1864
Diff:
Modified: trunk/aspire/source/simulator/solver.cc
===================================================================
--- trunk/aspire/source/simulator/solver.cc 2013-08-27 15:33:15 UTC (rev 1863)
+++ trunk/aspire/source/simulator/solver.cc 2013-08-30 16:47:08 UTC (rev 1864)
@@ -383,62 +383,33 @@
distributed_stokes_rhs.block(0).reinit (introspection.index_sets.velocity_partitioning[0], mpi_communicator);
distributed_stokes_rhs.block(1).reinit (introspection.index_sets.velocity_partitioning[1], mpi_communicator);
distributed_stokes_rhs.collect_sizes();
- distributed_stokes_rhs.block(0) = system_rhs_velocity.block(0);
- distributed_stokes_rhs.block(1) = system_rhs_velocity.block(1);
+ distributed_stokes_rhs.block (0).equ (-1.0, system_rhs_velocity.block (0));
- PrimitiveVectorMemory< LinearAlgebra::BlockVector > mem;
-
- // step 1a: try if the simple and fast solver
- // succeeds in 30 steps or less (or whatever the chosen value for the
- // corresponding parameter is).
const double solver_tolerance = std::max (parameters.linear_solver_tolerance *
distributed_stokes_rhs.l2_norm(), 1e-12);
- SolverControl solver_control_cheap (parameters.n_cheap_stokes_solver_steps,
- solver_tolerance);
- SolverControl solver_control_expensive (system_matrix_velocity.block (0,1).m () +
- system_matrix_velocity.block (1,0).m (), solver_tolerance);
- unsigned int n_inner_iterations_A;
-
- try
- {
- // if this cheaper solver is not desired
- if (parameters.n_cheap_stokes_solver_steps == 0)
- throw SolverControl::NoConvergence(0,0);
-
- // otherwise give it a try with a preconditioner that consists
- // of only a single V-cycle
- const internal::BlockSchurPreconditioner<LinearAlgebra::PreconditionBase,
- LinearAlgebra::PreconditionBase>
- preconditioner (system_matrix_velocity, &(*Mp_preconditioner), &(*Amg_preconditioner),
- false);
-
- SolverFGMRES<LinearAlgebra::BlockVector>
- solver(solver_control_cheap, mem,
- SolverFGMRES<LinearAlgebra::BlockVector>::
- AdditionalData(30, true));
- solver.solve (system_matrix_velocity, distributed_stokes_solution,
- distributed_stokes_rhs, preconditioner);
- }
-
- // step 1b: take the stronger solver in case
- // the simple solver failed
- catch (SolverControl::NoConvergence)
- {
- const internal::BlockSchurPreconditioner<LinearAlgebra::PreconditionBase,
- LinearAlgebra::PreconditionBase>
- preconditioner (system_matrix_velocity, &(*Mp_preconditioner), &(*Amg_preconditioner),
- true);
-
- SolverFGMRES<LinearAlgebra::BlockVector>
- solver(solver_control_expensive, mem,
- SolverFGMRES<LinearAlgebra::BlockVector>::
- AdditionalData(50, true));
- solver.solve (system_matrix_velocity, distributed_stokes_solution,
- distributed_stokes_rhs, preconditioner);
-
- n_inner_iterations_A = preconditioner.iters_A;
- }
-
+ SolverControl solver_control_velocity (distributed_stokes_rhs.block (0).size (), solver_tolerance);
+
+ {
+ system_matrix_velocity.block (0, 1).vmult_add (distributed_stokes_rhs.block (0), distributed_stokes_solution.block (1));
+ distributed_stokes_rhs.block (0) *= -1.0;
+
+ TrilinosWrappers::SolverGMRES gmres (solver_control_velocity, TrilinosWrappers::SolverGMRES::AdditionalData (50, true));
+
+ gmres.solve (system_matrix_velocity.block (0, 0), distributed_stokes_solution.block (0), distributed_stokes_rhs.block (0), *Amg_preconditioner);
+ }
+
+ SolverControl solver_control_pressure (distributed_stokes_rhs.block (1).size (), solver_tolerance);
+
+ {
+ system_matrix_velocity.block (1, 0).residual (distributed_stokes_rhs.block (1), distributed_stokes_solution.block (0), system_rhs_velocity.block (1));
+ distributed_stokes_rhs.block (1) *= -1e-9;
+ system_matrix_velocity.block (1, 1).vmult_add (distributed_stokes_rhs.block (1), distributed_stokes_solution.block (1));
+
+ TrilinosWrappers::SolverCG cg (solver_control_pressure);
+
+ cg.solve (system_matrix_velocity.block (1, 1), distributed_stokes_solution.block (1), distributed_stokes_rhs.block (1), *Mp_preconditioner);
+ }
+
// distribute hanging node and
// other constraints
current_constraints_velocity.distribute (distributed_stokes_solution);
@@ -449,7 +420,6 @@
solution_velocity.block (1) = distributed_stokes_solution.block (1);
// now rescale the pressure back to real physical units
- solution_velocity.block (1) *= pressure_scaling;
normalize_pressure (solution_velocity);
distributed_stokes_solution.block (0) -= current_linearization_point_velocity.block (0);
@@ -457,17 +427,12 @@
const double nonlinear_error = distributed_stokes_solution.block (0).l2_norm ();
// print the number of iterations to screen and record it in the
// statistics file
- if (solver_control_expensive.last_step() == 0)
- pcout << solver_control_cheap.last_step() << " iterations.";
- else
- pcout << solver_control_cheap.last_step() << '+'
- << solver_control_expensive.last_step()
- << " iterations (# inner its for A: "
- << n_inner_iterations_A << ").";
- pcout << std::endl;
+ pcout << solver_control_velocity.last_step () << '+'
+ << solver_control_pressure.last_step ()
+ << std::endl;
statistics.add_value("Iterations for Stokes solver",
- solver_control_cheap.last_step() + solver_control_expensive.last_step());
+ solver_control_velocity.last_step () + solver_control_pressure.last_step ());
computing_timer.exit_section();
More information about the CIG-COMMITS
mailing list