We consider the uniform steady thermal expansion of an elastic body that is differentially heated. The top surface is heated and the bottom surface is maintained at the reference temperature, which leads to a uniform temperature gradient throughout the material. The material expands more near the upper surface than near the lower surface, deforming the initially rectangular block into an curved configuration.
#include "generic.h"
#include "solid.h"
#include "unsteady_heat.h"
#include "meshes/rectangular_quadmesh.h"
using namespace oomph;
using namespace std;
template<unsigned DIM>
public virtual QUnsteadyHeatElement<DIM,3>
{
private:
double* Alpha_pt;
static double Default_Physical_Constant_Value;
public:
QUnsteadyHeatElement<DIM,3>()
{
Alpha_pt = &Default_Physical_Constant_Value;
}
unsigned required_nvalue(const unsigned &n) const
{return (QUnsteadyHeatElement<DIM,3>::required_nvalue(n) +
QPVDElement<DIM,3>::required_nvalue(n));}
const double &alpha() const {return *Alpha_pt;}
double* &alpha_pt() {return Alpha_pt;}
void output(ostream &outfile) {FiniteElement::output(outfile);}
void output(ostream &outfile, const unsigned &nplot)
{
Vector<double> s(DIM);
Vector<double> xi(DIM);
outfile << this->tecplot_zone_string(nplot);
unsigned num_plot_points=this->nplot_points(nplot);
for (unsigned iplot=0;iplot<num_plot_points;iplot++)
{
this->get_s_plot(iplot,nplot,s);
this->interpolated_xi(s,xi);
for(unsigned i=0;i<DIM;i++)
{outfile << this->interpolated_x(s,i) << " ";}
outfile << this->interpolated_u_ust_heat(s) << std::endl;
}
outfile << std::endl;
this->write_tecplot_zone_footer(outfile,nplot);
}
void output(FILE* file_pt)
{FiniteElement::output(file_pt);}
void output(FILE* file_pt, const unsigned &n_plot)
{FiniteElement::output(file_pt,n_plot);}
void output_fct(ostream &outfile, const unsigned &Nplot,
FiniteElement::SteadyExactSolutionFctPt
exact_soln_pt)
{FiniteElement::output_fct(outfile,Nplot,exact_soln_pt);}
void output_fct(ostream &outfile, const unsigned &Nplot,
const double& time,
FiniteElement::UnsteadyExactSolutionFctPt
exact_soln_pt)
{
FiniteElement::
output_fct(outfile,Nplot,time,exact_soln_pt);
}
void compute_norm(double& el_norm)
{
QUnsteadyHeatElement<DIM,3>::compute_norm(el_norm);
}
void compute_error(ostream &outfile,
FiniteElement::UnsteadyExactSolutionFctPt exact_soln_pt,
const double& time,
double& error, double& norm)
{FiniteElement::compute_error(outfile,exact_soln_pt,
time,error,norm);}
void compute_error(ostream &outfile,
FiniteElement::SteadyExactSolutionFctPt exact_soln_pt,
double& error, double& norm)
{FiniteElement::compute_error(outfile,exact_soln_pt,error,norm);}
void get_isotropic_growth(const unsigned& ipt, const Vector<double> &s,
const Vector<double>& xi, double &gamma) const
{
gamma = 1.0 + (*Alpha_pt)*this->interpolated_u_ust_heat(s);
}
void fill_in_contribution_to_residuals(Vector<double> &residuals)
{
UnsteadyHeatEquations<DIM>::
fill_in_contribution_to_residuals(residuals);
PVDEquations<DIM>::
fill_in_contribution_to_residuals(residuals);
}
void fill_in_contribution_to_jacobian(Vector<double> &residuals,
DenseMatrix<double> &jacobian)
{
SolidFiniteElement::fill_in_contribution_to_jacobian(residuals,jacobian);
}
};
template<>
{
}
template<class ELEMENT>
{
public:
void actions_before_newton_solve() {}
void actions_after_newton_solve(){}
void actions_before_adapt(){}
void doc_solution();
ElasticRectangularQuadMesh<ELEMENT>* mesh_pt()
{
return dynamic_cast<ElasticRectangularQuadMesh<ELEMENT>*>(
Problem::mesh_pt());
}
private:
DocInfo Doc_info;
};
template<class ELEMENT>
{
Doc_info.set_directory("RESLT");
unsigned n_x=8;
unsigned n_y=8;
double l_x=3.0;
double l_y=1.0;
Problem::mesh_pt() =
new ElasticRectangularQuadMesh<ELEMENT>(n_x,n_y,l_x,l_y);
{
unsigned n_boundary_node = mesh_pt()->nboundary_node(0);
for(unsigned n=0;n<n_boundary_node;n++)
{
Node* nod_pt = mesh_pt()->boundary_node_pt(0,n);
nod_pt->pin(0);
nod_pt->set_value(0,0.0);
}
n_boundary_node = mesh_pt()->nboundary_node(2);
for(unsigned n=0;n<n_boundary_node;n++)
{
Node* nod_pt = mesh_pt()->boundary_node_pt(2,n);
nod_pt->pin(0);
nod_pt->set_value(0,1.0);
}
n_boundary_node = mesh_pt()->nboundary_node(1);
for(unsigned n=0;n<n_boundary_node;n++)
{
static_cast<SolidNode*>(mesh_pt()->boundary_node_pt(1,n))->pin_position(0);
}
static_cast<SolidNode*>(mesh_pt()->boundary_node_pt(1,0))->pin_position(1);
}
unsigned n_element = mesh_pt()->nelement();
for(unsigned int i=0;i<n_element;i++)
{
ELEMENT *el_pt = dynamic_cast<ELEMENT*>(mesh_pt()->element_pt(i));
el_pt->constitutive_law_pt() =
}
cout <<"Number of equations: " << assign_eqn_numbers() << endl;
}
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();
Doc_info.number()++;
}
int main(
int argc,
char **argv)
{
unsigned n_steps = 11;
if(argc > 1) {n_steps = 2;}
for(unsigned i=0;i<n_steps;i++)
{
problem.newton_solve();
}
}
A class that solves the equations of steady thermoelasticity by combining the UnsteadyHeat and PVD eq...
/////////////////////////////////////////////////////////////////// /////////////////////////////////...
ThermalProblem()
Constructor.
void doc_solution()
Doc the solution.
Namespace for the physical parameters in the problem.
double E
Young's modulus for solid mechanics.
ConstitutiveLaw * Constitutive_law_pt
We need a constitutive law for the solid mechanics.
double Nu
Poisson ratio for solid mechanics.
double Alpha
Thermal expansion coefficient.
int main(int argc, char **argv)
Driver code for 2D Thermoelasticity problem.