Permalink
Browse files

add documentation for preconditioners

1 parent fbc2535 commit ac8c2c4752bb1f8d74a3968e25c159b86ee32fc2 @ESeNonFossiIo ESeNonFossiIo committed Nov 21, 2015
View
@@ -662,7 +662,7 @@ LAYOUT_FILE =
# search path. Do not use file names with spaces, bibtex cannot handle them. See
# also \cite for info how to create references.
-CITE_BIB_FILES =
+CITE_BIB_FILES = @CMAKE_CURRENT_SOURCE_DIR@/Doxygen/bibliography.bib
#---------------------------------------------------------------------------
# Configuration options related to warning and progress messages
@@ -0,0 +1,14 @@
+@article {FLD:FLD1650080802,
+ author = {Cahouet, J. and Chabard, J.-P.},
+ title = {Some fast 3D finite element solvers for the generalized Stokes problem},
+ journal = {International Journal for Numerical Methods in Fluids},
+ volume = {8},
+ number = {8},
+ publisher = {John Wiley & Sons, Ltd},
+ issn = {1097-0363},
+ url = {http://dx.doi.org/10.1002/fld.1650080802},
+ doi = {10.1002/fld.1650080802},
+ pages = {869--895},
+ keywords = {3D Stokes problem, Mixed finite element methods, Primitive variables, Gradient methods, Convergence analysis},
+ year = {1988},
+}
@@ -19,15 +19,23 @@
*
* In the code we adopt the following notations:
* - Mp := block resulting from \f$ ( \partial_t p, q ) \f$
- * - Ap := block resulting from f$ \nu ( \nabla p,\nabla q ) \f$
- * - Np := block resulting from f$ ( u \cdot \nabla p, q) \f$
+ * - Ap := block resulting from \f$ \nu ( \nabla p,\nabla q ) \f$
+ * - Np := block resulting from \f$ ( u \cdot \nabla p, q) \f$
* - Fp := Mp + Ap + Np
*
* where:
* - p = pressure
* - q = test function for the pressure
* - u = velocity
* - v = test function for the velocity
+ *
+ * Notes on preconditioners:
+ * - stokes: This preconditioner uses the mass matrix of pressure block as inverse for the Schur block.
+ * This is a preconditioner suitable for problems wher the viscosity is higher than the density. \f[ S^-1 = \frac{1}{\nu} M_p \f]
+ * - low-nu: This preconditioner uses the stifness matrix of pressure block as inverse for the Schur block. \f[ S^-1 = \rho \frac{1}{\Delta t} A_p \f]
+ * - cah-cha: This preconditioner implement the Schur block suggested by Cahouet and Chabard in \cite FLD:FLD1650080802 . \f[ S^-1 = \frac{1}{\nu} M_p + \rho \frac{1}{\Delta t} A_p \f]
+ *
+ *
*/
#include "interfaces/non_conservative.h"
@@ -209,6 +217,11 @@ class NavierStokes : public NonConservativeInterface<dim,dim,dim+1, NavierStokes
* Compute Fp
*/
bool compute_Fp;
+
+ /**
+ * Choose how to handle the non linear term \f$ (\nabla u)u \f$.
+ */
+ std::string Np_formulation;
};
template<int dim>
@@ -261,6 +274,12 @@ declare_parameters (ParameterHandler &prm)
"Amg P Aggregation Threshold", "0.02", Patterns::Double(0.0));
this->add_parameter(prm, &amg_p_elliptic,
"Amg P Elliptic", "true", Patterns::Bool());
+ this->add_parameter(prm, &Np_formulation, "how to handle Np","RHS",
+ Patterns::Selection("none|RHS|lin_grad|lin_u"),
+ "none: use grad_u u in the jacobian matrix \n"
+ "RHS: move grad_u u to the RHS \n"
+ "lin_grad: linearize grad_u u using grad_u evaluated at the previous time step\n"
+ "lin_u: linearize grad_u u using u evaluated at the previous time step\n");
this->add_parameter(prm, &invert_Ap,
"Invert Ap using inverse_operator", "true", Patterns::Bool());
this->add_parameter(prm, &invert_Mp,
@@ -299,6 +318,8 @@ parse_parameters_call_back ()
else if (prec_name == "elman-2")
{
compute_Fp = true;
+ compute_Ap = true;
+ compute_Mp = true;
}
else if (prec_name == "BFBt_id")
{
@@ -383,9 +404,12 @@ system_residual(const typename DoFHandler<dim>::active_cell_iterator &cell,
std::vector<Number> &local_residual) const
{
Number alpha = this->alpha;
+ double dummy_alpha = 0.0;
+
fe_cache.reinit(cell);
fe_cache.cache_local_solution_vector("solution", *this->solution, alpha);
+ fe_cache.cache_local_solution_vector("solution_", this->old_solution, dummy_alpha);
fe_cache.cache_local_solution_vector("solution_dot", *this->solution_dot, alpha);
this->fix_solution_dot_derivative(fe_cache, alpha);
@@ -396,9 +420,11 @@ system_residual(const typename DoFHandler<dim>::active_cell_iterator &cell,
// velocity:
auto &us = fe_cache.get_values("solution", "u", velocity, alpha);
+ auto &us_ = fe_cache.get_values("solution_", "u_", velocity, dummy_alpha);
auto &div_us = fe_cache.get_divergences("solution", "div_u", velocity, alpha);
auto &sym_grad_us = fe_cache.get_symmetric_gradients("solution", "sym_grad_u", velocity, alpha);
auto &grad_us = fe_cache.get_gradients("solution", "grad_u", velocity, alpha);
+ auto &grad_us_ = fe_cache.get_gradients("solution_", "grad_u_", velocity, dummy_alpha);
auto &us_dot = fe_cache.get_values("solution_dot", "u_dot", velocity, alpha);
// pressure:
@@ -420,10 +446,12 @@ system_residual(const typename DoFHandler<dim>::active_cell_iterator &cell,
// variables:
// velocity:
const Tensor<1, dim, Number> &u = us[q];
+ const Tensor<1, dim, double> &u_ = us_[q];
const Number &div_u = div_us[q];
const Tensor<1, dim, Number> &u_dot = us_dot[q];
const Tensor <2, dim, Number> &sym_grad_u = sym_grad_us[q];
const Tensor <2, dim, Number> &grad_u = grad_us[q];
+ const Tensor <2, dim, double> &grad_u_ = grad_us_[q];
// pressure:
const Number &p = ps[q];
@@ -443,9 +471,19 @@ system_residual(const typename DoFHandler<dim>::active_cell_iterator &cell,
auto grad_m = fev[pressure ].gradient(i,q);
// compute residual:
+ Tensor<1, dim, Number> Np_term;
+ if (Np_formulation=="RHS")
+ Np_term = grad_u_ * u_;
+ else if (Np_formulation=="lin_grad")
+ Np_term = grad_u_ * u;
+ else if (Np_formulation=="lin_grad")
+ Np_term = grad_u * u_;
+ else
+ Np_term = grad_u * u;
+
local_residual[i] += (
rho * u_dot * v +
- rho * scalar_product(u*grad_u, v) +
+ rho * scalar_product(Np_term,v) +
gamma * div_u * div_v +
nu * scalar_product(sym_grad_u,sym_grad_v) -
( p * div_v + div_u * m)
@@ -594,11 +632,16 @@ compute_system_operators(const DoFHandler<dim> &dh,
auto A_inv = inverse_operator( A, solver_GMRES, *Amg_preconditioner);
LinearOperator<VEC> P00, P01, P10, P11, Schur_inv;
+ LinearOperator<VEC> Ap, Np, Mp, Fp;
- auto Ap = linear_operator<VEC>(aux_matrices[0]->block(1,1));
- auto Np = linear_operator<VEC>(aux_matrices[1]->block(1,1));
- auto Mp = linear_operator<VEC>(aux_matrices[2]->block(1,1));
- auto Fp = linear_operator<VEC>(aux_matrices[3]->block(1,1));
+ if (compute_Ap)
+ Ap = linear_operator<VEC>(aux_matrices[0]->block(1,1));
+ if (compute_Np)
+ Np = linear_operator<VEC>(aux_matrices[1]->block(1,1));
+ if (compute_Mp)
+ Mp = linear_operator<VEC>(aux_matrices[2]->block(1,1));
+ if (compute_Fp)
+ Fp = linear_operator<VEC>(aux_matrices[3]->block(1,1));
Assert(prec_name != "", ExcNotInitialized());
if (prec_name=="stokes")
@@ -623,7 +666,7 @@ compute_system_operators(const DoFHandler<dim> &dh,
Ap_inv = linear_operator<VEC>(aux_matrices[0]->block(1,1), *Amg_preconditioner_2);
}
- Schur_inv = rho * alpha * Ap_inv;
+ Schur_inv = 1/(rho * alpha) * Ap_inv;
}
else if (prec_name=="elman-1")
{
@@ -673,11 +716,11 @@ compute_system_operators(const DoFHandler<dim> &dh,
}
jacobi_preconditioner.reset (new TrilinosWrappers::PreconditionJacobi());
- jacobi_preconditioner->initialize (aux_matrices[2]->block(1,1));
+ jacobi_preconditioner->initialize (aux_matrices[2]->block(1,1), 1.3);
auto Mp = linear_operator<VEC>( aux_matrices[2]->block(1,1) );
auto Mp_inv = inverse_operator( Mp, solver_CG, *jacobi_preconditioner);
- Schur_inv = Mp_inv + Ap_inv;
+ Schur_inv = 1/nu * Mp_inv + 1/(rho * alpha) * Ap_inv;
}
else if (prec_name=="BFBt_id")
{
@@ -12,14 +12,14 @@ set Blocking of the finite element = u,u,p
set Finite element space = FESystem[FE_Q(2)^d-FE_Q(1)]
set grad-div stabilization = 0.0
-set nu [Pa s] = 0.00025
+set nu [Pa s] = 0.0024
set rho [kg m^3] = 1
-set GMRES Solver tolerance = 1e-10
-set CG Solver tolerance = 1e-10
+set GMRES Solver tolerance = 1e-12
+set CG Solver tolerance = 1e-12
-set Invert Ap using inverse_operator = true
-set Invert Fp using inverse_operator = true
+set Invert Ap using inverse_operator = false
+set Invert Fp using inverse_operator = false
set Invert Np using inverse_operator = true
set Invert Mp using inverse_operator = true
@@ -31,6 +31,7 @@ set Amg P Aggregation Threshold = 0.5
set Amg P Smoother Sweeps = 2
set Amg P Elliptic = true
+set how to handle Np = RHS
# Available preconditioners:
# - stokes -> S^-1 = 1/nu * Mp^-1
@@ -41,13 +42,13 @@ set Amg P Elliptic = true
# - BDBt_dA -> S^-1 = (B diag(A)^-1 Bt)^-1 B diag(A)^-1 A diag(A)^-1 Bt (B
# diag(A)^-1 Bt)^-1
# - cah-cha -> S^-1 = Mp^-1 + Ap^-1
- set Preconditioner = stokes
+ set Preconditioner = low-nu
end
subsection piDoMUS<2, 2, 3, LATrilinos>
set Linear solver tolerance = 1e-8
set Adaptive refinement = false
- set Initial global refinement = 1
+ set Initial global refinement = 2
set Maximum number of time steps = 10000
set Number of cycles = 1
set Timer output file = timer.txt
@@ -64,10 +65,10 @@ subsection Forcing terms
end
subsection Dirichlet boundary conditions
- # set IDs and component masks = 1 = u % 2 = u % 4 = u
- # set IDs and expressions = 1 = 0;0;0 % 2=y>3?10*(4-y)*y:(3-y)*y+(4-y)*y;0;0 % 4 = 0;0;0
- set IDs and component masks = 1= u % 5=u % 3=u % 4=u
- set IDs and expressions = 1= t<1.?t*k*(1-y^2):k*(1-y^2);0;0 % 3=0;0;0 % 4=0;0;0 % 5=0;0;0
+ set IDs and component masks = 1 = u % 2 = u % 4 = u
+ set IDs and expressions = 1 = 0;0;0 % 2=t<1.0?t*k*(4-y)*y:k*(4-y)*y;0;0 % 4 = 0;0;0
+ # set IDs and component masks = 1= u % 5=u % 3=u % 4=u
+ # set IDs and expressions = 1= t<1.?t*k*(1-y^2):k*(1-y^2);0;0 % 3=0;0;0 % 4=0;0;0 % 5=0;0;0
set Known component names = u,u,p
set Used constants = k=1
end
@@ -88,7 +89,7 @@ end
subsection Domain
set Grid to generate = file
set Input grid file name = \
- ../utilities/grids/rectangle_with_circular_hole.ucd
+ ../utilities/grids/rectangle_with_circular_hole.inp
set Colorize = true
end
@@ -118,16 +119,19 @@ subsection Error Tables
end
subsection IDA Solver Parameters
+ set Initial time = 0
+ set Final time = 20
+
set Initial condition type = use_y_diff
set Ignore algebraic terms for error computations = true
- set Maximum order of BDF = 2
+ set Maximum order of BDF = 3
set Absolute error tolerance = 1e-3
- set Final time = 2
+
set Initial condition Newton max iterations = 5
set Initial condition Newton parameter = 0.33
set Initial condition type after restart = use_y_dot
set Initial step size = 1e-2
- set Initial time = 0
+
set Maximum number of nonlinear iterations = 10
set Min step size = 5e-3
set Relative error tolerance = 1e-2
@@ -12,14 +12,14 @@ subsection Navier Stokes
set Finite element space = FESystem[FE_Q(2)^d-FE_Q(1)]
set grad-div stabilization = 0.0
- set nu [Pa s] = 0.00025
+ set nu [Pa s] = 0.0025
set rho [kg m^3] = 1
- set GMRES Solver tolerance = 1e-10
- set CG Solver tolerance = 1e-10
+ set GMRES Solver tolerance = 1e-12
+ set CG Solver tolerance = 1e-12
- set Invert Ap using inverse_operator = true
- set Invert Fp using inverse_operator = true
+ set Invert Ap using inverse_operator = false
+ set Invert Fp using inverse_operator = false
set Invert Np using inverse_operator = true
set Invert Mp using inverse_operator = true
@@ -31,6 +31,7 @@ subsection Navier Stokes
set Amg P Smoother Sweeps = 2
set Amg P Elliptic = true
+ set how to handle Np = RHS
# Available preconditioners:
# - stokes -> S^-1 = 1/nu * Mp^-1
@@ -47,7 +48,7 @@ end
subsection piDoMUS<2, 2, 3, LATrilinos>
set Linear solver tolerance = 1e-8
set Adaptive refinement = false
-set Initial global refinement = 4
+set Initial global refinement = 3
set Maximum number of time steps = 10000
set Number of cycles = 1
set Timer output file = timer.txt
@@ -58,10 +59,7 @@ end
subsection Dirichlet boundary conditions
set IDs and component masks = 0 = u % 1 = u % 2 = u % 3 = u
- set IDs and expressions = 0 = 0 ; 0 ; 0 % \
- 1 = 0 ; 0 ; 0 % \
- 2 = 0 ; 0 ; 0 % \
- 3 = t<1.0 ? t*k : k ; 0 ; 0
+ set IDs and expressions = 0 = 0 ; 0 ; 0 % 1 = 0 ; 0 ; 0 % 2 = 0 ; 0 ; 0 % 3 = t<.5 ? 2*t*k : k ; 0 ; 0
set Known component names = u,u,p
set Used constants = k=1
end
@@ -113,20 +111,23 @@ subsection Error Tables
end
subsection IDA Solver Parameters
+ set Initial time = 0
+ set Final time = 20
+
set Initial condition type = use_y_diff
set Ignore algebraic terms for error computations = true
- set Maximum order of BDF = 2
+ set Maximum order of BDF = 3
set Absolute error tolerance = 1e-3
- set Final time = 2
+
set Initial condition Newton max iterations = 5
set Initial condition Newton parameter = 0.33
set Initial condition type after restart = use_y_dot
set Initial step size = 1e-2
- set Initial time = 0
+
set Maximum number of nonlinear iterations = 10
set Min step size = 5e-3
set Relative error tolerance = 1e-2
- set Seconds between each output = 1e-1
+ set Seconds between each output = 1e-2
set Use local tolerances = false
end

0 comments on commit ac8c2c4

Please sign in to comment.