Skip to content

Commit

Permalink
Merge pull request idaholab#6892 from dschwen/interval_6888
Browse files Browse the repository at this point in the history
Add interval parameter to [./Adaptivity]
  • Loading branch information
permcody committed May 4, 2016
2 parents 447c02f + 1804977 commit 8c7bb53
Show file tree
Hide file tree
Showing 7 changed files with 192 additions and 48 deletions.
14 changes: 14 additions & 0 deletions framework/include/base/Adaptivity.h
Original file line number Diff line number Diff line change
Expand Up @@ -193,6 +193,11 @@ class Adaptivity : public ConsoleStreamInterface
*/
void setMaxHLevel(unsigned int level) { _max_h_level = level; }

/**
* Set the interval (number of timesteps) between refinement steps.
*/
void setInterval(unsigned int interval) { _interval = interval; }

/**
* Get the MooseVariable corresponding to the Marker Field Name that is actually going to be used
* to refine / coarsen the mesh.
Expand All @@ -216,6 +221,11 @@ class Adaptivity : public ConsoleStreamInterface
*/
void updateErrorVectors();

/**
* Query if an adaptivity step should be performed at the current time / time step
*/
bool isAdaptivityDue();

protected:
FEProblem & _subproblem;
MooseMesh & _mesh;
Expand Down Expand Up @@ -244,6 +254,10 @@ class Adaptivity : public ConsoleStreamInterface

/// Time
Real & _t;
/// Time Step
int & _step;
/// intreval between adaptivity runs
unsigned int _interval;
/// When adaptivity start
Real _start_time;
/// When adaptivity stops
Expand Down
2 changes: 2 additions & 0 deletions framework/src/actions/AdaptivityAction.C
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ InputParameters validParams<AdaptivityAction>()
MooseEnum estimators("KellyErrorEstimator LaplacianErrorEstimator PatchRecoveryErrorEstimator", "KellyErrorEstimator");

params.addParam<unsigned int>("steps", 0, "The number of adaptivity steps to perform at any one time for steady state");
params.addRangeCheckedParam<unsigned int>("interval", 1, "interval>0", "The number of time steps betweeen each adaptivity phase");
params.addParam<unsigned int>("initial_adaptivity", 0, "The number of adaptivity steps to perform using the initial conditions");
params.addParam<Real> ("refine_fraction", 0.0, "The fraction of elements or error to refine. Should be between 0 and 1.");
params.addParam<Real> ("coarsen_fraction", 0.0, "The fraction of elements or error to coarsen. Should be between 0 and 1.");
Expand Down Expand Up @@ -106,6 +107,7 @@ AdaptivityAction::act()
}

adapt.setTimeActive(getParam<Real>("start_time"), getParam<Real>("stop_time"));
adapt.setInterval(getParam<unsigned int>("interval"));
}

#endif //LIBMESH_ENABLE_AMR
105 changes: 57 additions & 48 deletions framework/src/base/Adaptivity.C
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ Adaptivity::Adaptivity(FEProblem & subproblem) :
_steps(0),
_print_mesh_changed(false),
_t(_subproblem.time()),
_step(_subproblem.timeStep()),
_interval(1),
_start_time(-std::numeric_limits<Real>::max()),
_stop_time(std::numeric_limits<Real>::max()),
_cycles_per_step(1),
Expand Down Expand Up @@ -133,66 +135,65 @@ bool
Adaptivity::adaptMesh()
{
bool meshChanged = false;
if (_mesh_refinement_on && (_start_time <= _t && _t < _stop_time))

if (_use_new_system)
{
if (_use_new_system)
{
if (_marker_variable_name != "") // Only flag if a marker variable name has been set
{
_mesh_refinement->clean_refinement_flags();

std::vector<Number> serialized_solution;
_subproblem.getAuxiliarySystem().solution().close();
_subproblem.getAuxiliarySystem().solution().localize(serialized_solution);

FlagElementsThread fet(_subproblem, serialized_solution, _max_h_level);
ConstElemRange all_elems(_subproblem.mesh().getMesh().active_elements_begin(),
_subproblem.mesh().getMesh().active_elements_end(), 1);
Threads::parallel_reduce(all_elems, fet);
_subproblem.getAuxiliarySystem().solution().close();
}
}
else
if (_marker_variable_name != "") // Only flag if a marker variable name has been set
{
// Compute the error for each active element
_error_estimator->estimate_error(_subproblem.getNonlinearSystem().sys(), *_error);
_mesh_refinement->clean_refinement_flags();

// Flag elements to be refined and coarsened
_mesh_refinement->flag_elements_by_error_fraction (*_error);
std::vector<Number> serialized_solution;
_subproblem.getAuxiliarySystem().solution().close();
_subproblem.getAuxiliarySystem().solution().localize(serialized_solution);

if (_displaced_problem)
// Reuse the error vector and refine the displaced mesh
_displaced_mesh_refinement->flag_elements_by_error_fraction (*_error);
FlagElementsThread fet(_subproblem, serialized_solution, _max_h_level);
ConstElemRange all_elems(_subproblem.mesh().getMesh().active_elements_begin(),
_subproblem.mesh().getMesh().active_elements_end(), 1);
Threads::parallel_reduce(all_elems, fet);
_subproblem.getAuxiliarySystem().solution().close();
}
}
else
{
// Compute the error for each active element
_error_estimator->estimate_error(_subproblem.getNonlinearSystem().sys(), *_error);

// Flag elements to be refined and coarsened
_mesh_refinement->flag_elements_by_error_fraction (*_error);

// If the DisplacedProblem is active, undisplace the DisplacedMesh
// in preparation for refinement. We can't safely refine the
// DisplacedMesh directly, since the Hilbert keys computed on the
// inconsistenly-displaced Mesh are different on different
// processors, leading to inconsistent Hilbert keys. We must do
// this before the undisplaced Mesh is refined, so that the
// element and node numbering is still consistent.
if (_displaced_problem)
_displaced_problem->undisplaceMesh();
// Reuse the error vector and refine the displaced mesh
_displaced_mesh_refinement->flag_elements_by_error_fraction (*_error);
}

// Perform refinement and coarsening
meshChanged = _mesh_refinement->refine_and_coarsen_elements();
// If the DisplacedProblem is active, undisplace the DisplacedMesh
// in preparation for refinement. We can't safely refine the
// DisplacedMesh directly, since the Hilbert keys computed on the
// inconsistenly-displaced Mesh are different on different
// processors, leading to inconsistent Hilbert keys. We must do
// this before the undisplaced Mesh is refined, so that the
// element and node numbering is still consistent.
if (_displaced_problem)
_displaced_problem->undisplaceMesh();

if (_displaced_problem && meshChanged)
{
// Now do refinement/coarsening
bool dispMeshChanged = _displaced_mesh_refinement->refine_and_coarsen_elements();
// Perform refinement and coarsening
meshChanged = _mesh_refinement->refine_and_coarsen_elements();

// Since the undisplaced mesh changed, the displaced mesh better have changed!
mooseAssert(dispMeshChanged, "Undisplaced mesh changed, but displaced mesh did not!");
}
if (_displaced_problem && meshChanged)
{
// Now do refinement/coarsening
bool dispMeshChanged = _displaced_mesh_refinement->refine_and_coarsen_elements();

if (meshChanged && _print_mesh_changed)
{
_console << "\nMesh Changed:\n";
_mesh.printInfo();
}
// Since the undisplaced mesh changed, the displaced mesh better have changed!
mooseAssert(dispMeshChanged, "Undisplaced mesh changed, but displaced mesh did not!");
}

if (meshChanged && _print_mesh_changed)
{
_console << "\nMesh Changed:\n";
_mesh.printInfo();
}

return meshChanged;
}

Expand Down Expand Up @@ -316,4 +317,12 @@ Adaptivity::updateErrorVectors()
_subproblem.comm().sum((std::vector<float>&)*(it->second));
}

bool
Adaptivity::isAdaptivityDue()
{
return _mesh_refinement_on
&& (_start_time <= _t && _t < _stop_time)
&& _step % _interval == 0;
}

#endif //LIBMESH_ENABLE_AMR
3 changes: 3 additions & 0 deletions framework/src/base/FEProblem.C
Original file line number Diff line number Diff line change
Expand Up @@ -3682,6 +3682,9 @@ FEProblem::possiblyRebuildGeomSearchPatches()
void
FEProblem::adaptMesh()
{
if (!_adaptivity.isAdaptivityDue())
return;

unsigned int cycles_per_step = _adaptivity.getCyclesPerStep();
for (unsigned int i = 0; i < cycles_per_step; ++i)
{
Expand Down
Binary file added test/tests/mesh/adapt/gold/interval_out.e-s002
Binary file not shown.
109 changes: 109 additions & 0 deletions test/tests/mesh/adapt/interval.i
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
[Mesh]
dim = 2
file = square.e
uniform_refine = 3
[]

[Variables]
active = 'u v'

[./u]
order = FIRST
family = LAGRANGE
[../]

[./v]
order = FIRST
family = LAGRANGE
[../]
[]

[Kernels]
active = 'udiff uconv uie vdiff vconv vie'

[./udiff]
type = Diffusion
variable = u
[../]

[./uconv]
type = Convection
variable = u
velocity = '10 1 0'
[../]

[./uie]
type = TimeDerivative
variable = u
[../]

[./vdiff]
type = Diffusion
variable = v
[../]

[./vconv]
type = Convection
variable = v
velocity = '-10 1 0'
[../]

[./vie]
type = TimeDerivative
variable = v
[../]
[]

[BCs]
active = 'uleft uright vleft vright'

[./uleft]
type = DirichletBC
variable = u
boundary = 1
value = 0
[../]

[./uright]
type = DirichletBC
variable = u
boundary = 2
value = 1
[../]

[./vleft]
type = DirichletBC
variable = v
boundary = 1
value = 1
[../]

[./vright]
type = DirichletBC
variable = v
boundary = 2
value = 0
[../]
[]

[Executioner]
type = Transient

# Preconditioned JFNK (default)
solve_type = 'PJFNK'

start_time = 0.0
num_steps = 4
dt = .1

[./Adaptivity]
interval = 2
refine_fraction = 0.2
coarsen_fraction = 0.3
max_h_level = 4
[../]
[]

[Outputs]
exodus = true
[]
7 changes: 7 additions & 0 deletions test/tests/mesh/adapt/tests
Original file line number Diff line number Diff line change
Expand Up @@ -47,4 +47,11 @@
exodiff = 'out.e-s002'
group = 'adaptive'
[../]

[./interval]
type = 'Exodiff'
input = 'interval.i'
exodiff = 'interval_out.e-s002'
group = 'adaptive'
[../]
[]

0 comments on commit 8c7bb53

Please sign in to comment.