00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029 #include "SimpleLinearEllipticSolver.hpp"
00030
00031
00032 template<unsigned ELEMENT_DIM, unsigned SPACE_DIM>
00033 c_matrix<double, 1*(ELEMENT_DIM+1), 1*(ELEMENT_DIM+1)>SimpleLinearEllipticSolver<ELEMENT_DIM,SPACE_DIM>:: ComputeMatrixTerm(
00034 c_vector<double, ELEMENT_DIM+1>& rPhi,
00035 c_matrix<double, SPACE_DIM, ELEMENT_DIM+1>& rGradPhi,
00036 ChastePoint<SPACE_DIM>& rX,
00037 c_vector<double,1>& rU,
00038 c_matrix<double,1,SPACE_DIM>& rGradU,
00039 Element<ELEMENT_DIM,SPACE_DIM>* pElement)
00040 {
00041 c_matrix<double, SPACE_DIM, SPACE_DIM> pde_diffusion_term = mpEllipticPde->ComputeDiffusionTerm(rX);
00042
00043
00044 if (mpEllipticPde->ComputeLinearInUCoeffInSourceTerm(rX,pElement)!=0)
00045 {
00046 return prod( trans(rGradPhi), c_matrix<double, SPACE_DIM, ELEMENT_DIM+1>(prod(pde_diffusion_term, rGradPhi)) )
00047 - mpEllipticPde->ComputeLinearInUCoeffInSourceTerm(rX,pElement)*outer_prod(rPhi,rPhi);
00048 }
00049 else
00050 {
00051 return prod( trans(rGradPhi), c_matrix<double, SPACE_DIM, ELEMENT_DIM+1>(prod(pde_diffusion_term, rGradPhi)) );
00052 }
00053 }
00054
00055
00056 template<unsigned ELEMENT_DIM, unsigned SPACE_DIM>
00057 c_vector<double,1*(ELEMENT_DIM+1)> SimpleLinearEllipticSolver<ELEMENT_DIM,SPACE_DIM>::ComputeVectorTerm(
00058 c_vector<double, ELEMENT_DIM+1>& rPhi,
00059 c_matrix<double, SPACE_DIM, ELEMENT_DIM+1>& rGradPhi,
00060 ChastePoint<SPACE_DIM>& rX,
00061 c_vector<double,1>& rU,
00062 c_matrix<double,1,SPACE_DIM>& rGradU,
00063 Element<ELEMENT_DIM,SPACE_DIM>* pElement)
00064 {
00065 return mpEllipticPde->ComputeConstantInUSourceTerm(rX) * rPhi;
00066 }
00067
00068
00069
00070 template<unsigned ELEMENT_DIM, unsigned SPACE_DIM>
00071 c_vector<double, ELEMENT_DIM> SimpleLinearEllipticSolver<ELEMENT_DIM,SPACE_DIM>::ComputeVectorSurfaceTerm(
00072 const BoundaryElement<ELEMENT_DIM-1,SPACE_DIM>& rSurfaceElement,
00073 c_vector<double, ELEMENT_DIM>& rPhi,
00074 ChastePoint<SPACE_DIM>& rX)
00075 {
00076
00077 double D_times_gradu_dot_n = this->mpBoundaryConditions->GetNeumannBCValue(&rSurfaceElement, rX);
00078 return rPhi * D_times_gradu_dot_n;
00079 }
00080
00081
00082
00083 template<unsigned ELEMENT_DIM, unsigned SPACE_DIM>
00084 SimpleLinearEllipticSolver<ELEMENT_DIM,SPACE_DIM>::SimpleLinearEllipticSolver(
00085 AbstractTetrahedralMesh<ELEMENT_DIM,SPACE_DIM>* pMesh,
00086 AbstractLinearEllipticPde<ELEMENT_DIM,SPACE_DIM>* pPde,
00087 BoundaryConditionsContainer<ELEMENT_DIM,SPACE_DIM,1>* pBoundaryConditions,
00088 unsigned numQuadPoints)
00089 : AbstractAssemblerSolverHybrid<ELEMENT_DIM,SPACE_DIM,1,NORMAL>(pMesh,pBoundaryConditions,numQuadPoints),
00090 AbstractStaticLinearPdeSolver<ELEMENT_DIM,SPACE_DIM,1>(pMesh)
00091 {
00092 mpEllipticPde = pPde;
00093 }
00094
00095
00096 template<unsigned ELEMENT_DIM, unsigned SPACE_DIM>
00097 void SimpleLinearEllipticSolver<ELEMENT_DIM,SPACE_DIM>::InitialiseForSolve(Vec initialSolution)
00098 {
00099 AbstractLinearPdeSolver<ELEMENT_DIM,SPACE_DIM,1>::InitialiseForSolve(initialSolution);
00100 assert(this->mpLinearSystem);
00101 this->mpLinearSystem->SetMatrixIsSymmetric(true);
00102 this->mpLinearSystem->SetKspType("cg");
00103 }
00104
00106
00108
00109 template class SimpleLinearEllipticSolver<1,1>;
00110 template class SimpleLinearEllipticSolver<1,2>;
00111 template class SimpleLinearEllipticSolver<1,3>;
00112 template class SimpleLinearEllipticSolver<2,2>;
00113 template class SimpleLinearEllipticSolver<3,3>;