In this example we discuss the SUPG-stabilised solution of the 2D advection-diffusion problem
Until we get around to completing this example, here's the driver code. Fairly self-explanatory, isn't it?
#include "generic.h"
#include "advection_diffusion.h"
#include "meshes/rectangular_quadmesh.h"
using namespace std;
using namespace oomph;
{
{
}
{
source=0.0;
}
void wind_function(
const Vector<double>& x, Vector<double>& wind)
{
wind[0]=sin(6.0*x[1]);
wind[1]=cos(6.0*x[0]);
}
}
template<class ELEMENT>
{
public:
AdvectionDiffusionEquations<2>::AdvectionDiffusionSourceFctPt source_fct_pt,
AdvectionDiffusionEquations<2>::AdvectionDiffusionWindFctPt wind_fct_pt,
const bool& use_stabilisation);
void actions_before_newton_solve();
void actions_after_newton_solve(){}
void doc_solution();
RectangularQuadMesh<ELEMENT>* mesh_pt()
{
return dynamic_cast<RectangularQuadMesh<ELEMENT>*>(
Problem::mesh_pt());
}
private:
DocInfo Doc_info;
AdvectionDiffusionEquations<2>::AdvectionDiffusionSourceFctPt Source_fct_pt;
AdvectionDiffusionEquations<2>::AdvectionDiffusionWindFctPt Wind_fct_pt;
bool Use_stabilisation;
};
template<class ELEMENT>
AdvectionDiffusionEquations<2>::AdvectionDiffusionSourceFctPt source_fct_pt,
AdvectionDiffusionEquations<2>::AdvectionDiffusionWindFctPt wind_fct_pt,
const bool& use_stabilisation)
: Source_fct_pt(source_fct_pt), Wind_fct_pt(wind_fct_pt),
Use_stabilisation(use_stabilisation)
{
if (use_stabilisation)
{
Doc_info.set_directory("RESLT_stabilised");
}
else
{
Doc_info.set_directory("RESLT_unstabilised");
}
unsigned n_x=40;
unsigned n_y=40;
double l_x=1.0;
double l_y=2.0;
Problem::mesh_pt() =
new RectangularQuadMesh<ELEMENT>(n_x,n_y,l_x,l_y);
unsigned num_bound = mesh_pt()->nboundary();
for(unsigned ibound=0;ibound<num_bound;ibound++)
{
unsigned num_nod= mesh_pt()->nboundary_node(ibound);
for (unsigned inod=0;inod<num_nod;inod++)
{
mesh_pt()->boundary_node_pt(ibound,inod)->pin(0);
}
}
unsigned n_element = mesh_pt()->nelement();
for(unsigned i=0;i<n_element;i++)
{
ELEMENT *el_pt = dynamic_cast<ELEMENT*>(mesh_pt()->element_pt(i));
el_pt->source_fct_pt() = Source_fct_pt;
el_pt->wind_fct_pt() = Wind_fct_pt;
}
cout <<"Number of equations: " << assign_eqn_numbers() << std::endl;
}
template<class ELEMENT>
{
unsigned num_bound = mesh_pt()->nboundary();
for(unsigned ibound=0;ibound<num_bound;ibound++)
{
unsigned num_nod=mesh_pt()->nboundary_node(ibound);
for (unsigned inod=0;inod<num_nod;inod++)
{
Node* nod_pt=mesh_pt()->boundary_node_pt(ibound,inod);
Vector<double> x(2);
x[0]=nod_pt->x(0);
x[1]=nod_pt->x(1);
Vector<double> u(1);
nod_pt->set_value(0,u[0]);
}
}
unsigned n_element = mesh_pt()->nelement();
for(unsigned i=0;i<n_element;i++)
{
ELEMENT *el_pt = dynamic_cast<ELEMENT*>(mesh_pt()->element_pt(i));
if (Use_stabilisation)
{
el_pt->compute_stabilisation_parameter();
}
else
{
el_pt->switch_off_stabilisation();
}
}
}
template<class ELEMENT>
{
ofstream some_file;
char filename[100];
unsigned npts=5;
sprintf(filename,"%s/soln%i.dat",Doc_info.directory().c_str(),
Doc_info.number());
some_file.open(filename);
mesh_pt()->output(some_file,npts);
some_file.close();
}
{
{
bool use_stabilisation=true;
use_stabilisation);
problem.newton_solve();
problem.doc_solution();
}
{
bool use_stabilisation=false;
use_stabilisation);
problem.newton_solve();
problem.doc_solution();
}
}
/////////////////////////////////////////////////////////////////// /////////////////////////////////...
void doc_solution()
Doc the solution.
SUPGAdvectionDiffusionProblem(AdvectionDiffusionEquations< 2 >::AdvectionDiffusionSourceFctPt source_fct_pt, AdvectionDiffusionEquations< 2 >::AdvectionDiffusionWindFctPt wind_fct_pt, const bool &use_stabilisation)
Constructor: Pass pointer to source and wind functions, and flag to indicate if stabilisation is to b...
void actions_before_newton_solve()
Update the problem specs before solve: Reset boundary conditions to the values from the tanh solution...
Namespace for global parameters: Unforced problem with boundary values corresponding to a steep tanh ...
void wind_function(const Vector< double > &x, Vector< double > &wind)
Wind.
void get_boundary_values(const Vector< double > &x, Vector< double > &u)
Some "solution" for assignment of boundary values.
void source_function(const Vector< double > &x_vect, double &source)
Zero source function.
double Peclet
Peclet number.
double Alpha
Parameter for steepness of step in boundary values.
double TanPhi
Parameter for angle of step in boundary values: 45 degrees.
int main()
Driver code for 2D AdvectionDiffusion problem.