57 real_t r = sqrt(pow(x, 2.0) + pow(y, 2.0));
62 if (std::abs(r) >= 0.25 - 1e-8)
68 q(2) = A * exp(-(pow(x, 2.0) / 2.0 + pow(y, 2.0) / 2.0));
110 ess_tdofs_(ess_tdofs),
111 M_solver(fes.GetComm())
151 M_solver.
Mult(t1, du_dt);
155 ~ConvectionDiffusionTDO()
206int main(
int argc,
char *argv[])
216 bool visualization =
true;
221 "Finite element order (polynomial degree).");
222 args.
AddOption(&t_final,
"-tf",
"--t-final",
223 "Final time; start time is 0.");
224 args.
AddOption(&dt,
"-dt",
"--time-step",
226 args.
AddOption(&visualization,
"-vis",
"--visualization",
"-no-vis",
227 "--no-visualization",
228 "Enable or disable GLVis visualization.");
229 args.
AddOption(&vis_steps,
"-vs",
"--visualization-steps",
230 "Visualize every n-th timestep.");
233 Mesh *serial_mesh =
new Mesh(
"multidomain-hex.mesh");
245 cylinder_domain_attributes[0] = 1;
247 auto cylinder_submesh =
252 Array<int> inflow_attributes(cylinder_submesh.bdr_attributes.Max());
253 inflow_attributes = 0;
254 inflow_attributes[7] = 1;
257 cylinder_submesh.bdr_attributes.Max());
258 inner_cylinder_wall_attributes = 0;
259 inner_cylinder_wall_attributes[8] = 1;
264 Array<int> inflow_tdofs, interface_tdofs, ess_tdofs;
268 ess_tdofs.
Append(inflow_tdofs);
269 ess_tdofs.
Append(interface_tdofs);
272 ConvectionDiffusionTDO cd_tdo(fes_cylinder, ess_tdofs);
275 magnetic_field_cylinder_gf = 0.0;
277 Vector magnetic_field_cylinder;
278 magnetic_field_cylinder_gf.
GetTrueDofs(magnetic_field_cylinder);
281 cd_ode_solver.
Init(cd_tdo);
284 outer_domain_attributes[0] = 2;
287 outer_domain_attributes);
291 Array<int> block_wall_attributes(block_submesh.bdr_attributes.Max());
292 block_wall_attributes = 0;
293 block_wall_attributes[0] = 1;
294 block_wall_attributes[1] = 1;
295 block_wall_attributes[2] = 1;
296 block_wall_attributes[3] = 1;
299 block_submesh.bdr_attributes.Max());
300 outer_cylinder_wall_attributes = 0;
301 outer_cylinder_wall_attributes[8] = 1;
305 ConvectionDiffusionTDO d_tdo(fes_block, ess_tdofs, 0.0, 1.0);
308 magnetic_field_block_gf = 0.0;
312 block_wall_attributes);
314 Vector magnetic_field_block;
315 magnetic_field_block_gf.
GetTrueDofs(magnetic_field_block);
318 d_ode_solver.
Init(d_tdo);
321 cylinder_surface_attributes[0] = 9;
323 auto cylinder_surface_submesh =
332 cyl_sol_sock <<
"parallel " << num_procs <<
" " << myid <<
"\n";
333 cyl_sol_sock.precision(8);
334 cyl_sol_sock <<
"solution\n" << cylinder_submesh
335 << magnetic_field_cylinder_gf
336 <<
"window_title \"Time step: " << 0 <<
"\""
337 <<
"keys cvv\n autoscale off\n valuerange 0 1.414\n"
338 <<
"pause\n" << std::flush;
344 block_sol_sock <<
"parallel " << num_procs <<
" " << myid <<
"\n";
345 block_sol_sock.precision(8);
346 block_sol_sock <<
"solution\n" << block_submesh
347 << magnetic_field_block_gf
348 <<
"window_title \"Time step: " << 0 <<
"\""
349 <<
"window_geometry 400 0 400 350\n"
350 <<
"keys cvv\n autoscale off\n valuerange 0 1.414\n"
351 <<
"pause\n" << std::flush;
356 magnetic_field_block_gf,
357 magnetic_field_cylinder_gf);
360 bool last_step =
false;
361 for (
int ti = 1; !last_step; ti++)
363 if (
t + dt >= t_final - dt/2)
369 d_ode_solver.
Step(magnetic_field_block,
t, dt);
375 magnetic_field_block_to_cylinder_map.Transfer(magnetic_field_block_gf,
376 magnetic_field_cylinder_gf);
378 magnetic_field_cylinder_gf.
GetTrueDofs(magnetic_field_cylinder);
382 cd_ode_solver.
Step(magnetic_field_cylinder,
t, dt);
384 if (last_step || (ti % vis_steps) == 0)
388 out <<
"step " << ti <<
", t = " <<
t << std::endl;
396 cyl_sol_sock <<
"parallel " << num_procs <<
" " << myid <<
"\n";
397 cyl_sol_sock <<
"solution\n" << cylinder_submesh
398 << magnetic_field_cylinder_gf
399 <<
"window_title \"Time step: " << ti <<
"\""
401 block_sol_sock <<
"parallel " << num_procs <<
" " << myid <<
"\n";
402 block_sol_sock <<
"solution\n" << block_submesh
403 << magnetic_field_block_gf
404 <<
"window_title \"Time step: " << ti <<
"\""
void Sort()
Sorts the array in ascending order. This requires operator< to be defined for T.
int Append(const T &el)
Append element 'el' to array, resize if necessary.
void Unique()
Removes duplicities from a sorted array. This requires operator== to be defined for T.
Conjugate gradient method.
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
virtual void Mult(const Vector &b, Vector &x) const
Iterative solution of the linear system using the Conjugate Gradient method.
Base class Coefficients that optionally depend on space and time. These are used by the BilinearFormI...
A coefficient that is constant across space and time.
Integrator for for Nedelec elements.
Parallel smoothers in hypre.
void SetType(HypreSmoother::Type type, int relax_times=1)
Set the relaxation type and number of sweeps.
static void Init()
Initialize hypre by calling HYPRE_Init() and set default options. After calling Hypre::Init(),...
void SetRelTol(real_t rtol)
virtual void SetPreconditioner(Solver &pr)
This should be called before SetOperator.
virtual void SetPrintLevel(int print_lvl)
Legacy method to set the level of verbosity of the solver output.
void SetMaxIter(int max_it)
void SetAbsTol(real_t atol)
int Dimension() const
Dimension of the reference space used within the elements.
void UniformRefinement(int i, const DSTable &, int *, int *, int *)
static int WorldRank()
Return the MPI rank in MPI_COMM_WORLD.
static int WorldSize()
Return the size of MPI_COMM_WORLD.
static void Init(int &argc, char **&argv, int required=default_thread_required, int *provided=nullptr)
Singleton creation with Mpi::Init(argc, argv).
Arbitrary order H(curl)-conforming Nedelec finite elements.
Pointer to an Operator of a specified type.
int height
Dimension of the output / number of rows in the matrix.
virtual void Mult(const Vector &x, Vector &y) const =0
Operator application: y=A(x).
void ParseCheck(std::ostream &out=mfem::out)
void AddOption(bool *var, const char *enable_short_name, const char *enable_long_name, const char *disable_short_name, const char *disable_long_name, const char *description, bool required=false)
Add a boolean option and set 'var' to receive the value. Enable/disable tags are used to set the bool...
Abstract parallel finite element space.
void GetEssentialTrueDofs(const Array< int > &bdr_attr_is_ess, Array< int > &ess_tdof_list, int component=-1) const override
ParMesh * GetParMesh() const
Class for parallel grid function.
HypreParVector * GetTrueDofs() const
Returns the true dofs in a new HypreParVector.
void SetFromTrueDofs(const Vector &tv) override
Set the GridFunction from the given true-dof vector.
void ProjectBdrCoefficientTangent(VectorCoefficient &vcoeff, const Array< int > &bdr_attr) override
Project the tangential components of the given VectorCoefficient on the boundary. Only boundary attri...
Class for parallel meshes.
static ParTransferMap CreateTransferMap(const ParGridFunction &src, const ParGridFunction &dst)
Create a Transfer Map object.
static ParSubMesh CreateFromBoundary(const ParMesh &parent, Array< int > &boundary_attributes)
Create a surface ParSubMesh from it's parent.
static ParSubMesh CreateFromDomain(const ParMesh &parent, Array< int > &domain_attributes)
Create a domain ParSubMesh from it's parent.
Third-order, strong stability preserving (SSP) Runge-Kutta method.
void Init(TimeDependentOperator &f_) override
Associate a TimeDependentOperator with the ODE solver.
void Step(Vector &x, real_t &t, real_t &dt) override
Perform a time step from time t [in] to time t [out] based on the requested step size dt [in].
Vector coefficient defined as a product of scalar and vector coefficients.
bool iterative_mode
If true, use the second argument of Mult() as an initial guess.
Base abstract class for first order time dependent operators.
Base class for vector Coefficients that optionally depend on time and space.
A general vector function coefficient.
void SetSubVector(const Array< int > &dofs, const real_t value)
Set the entries listed in dofs to the given value.
void SetSize(int s)
Resize the vector to size s.
Vector & Add(const real_t a, const Vector &Va)
(*this) += a * Va
int open(const char hostname[], int port)
Open the socket stream on 'port' at 'hostname'.
real_t sigma(const Vector &x)
void square_xy(const Vector &p, Vector &v)
void velocity_profile(const Vector &c, Vector &q)
void velocity_profile(const Vector &c, Vector &q)
real_t u(const Vector &xvec)
OutStream out(std::cout)
Global stream used by the library for standard output. Initially it uses the same std::streambuf as s...
real_t p(const Vector &x, real_t t)