SyFi  0.3
ArnoldFalkWintherWeakSym.cpp
Go to the documentation of this file.
00001 // Copyright (C) 2006-2009 Kent-Andre Mardal and Simula Research Laboratory
00002 //
00003 // This file is part of SyFi.
00004 //
00005 // SyFi is free software: you can redistribute it and/or modify
00006 // it under the terms of the GNU General Public License as published by
00007 // the Free Software Foundation, either version 2 of the License, or
00008 // (at your option) any later version.
00009 //
00010 // SyFi is distributed in the hope that it will be useful,
00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00013 // GNU General Public License for more details.
00014 //
00015 // You should have received a copy of the GNU General Public License
00016 // along with SyFi. If not, see <http://www.gnu.org/licenses/>.
00017 
00018 #include "ArnoldFalkWintherWeakSym.h"
00019 #include "Nedelec2Hdiv.h"
00020 #include "DiscontinuousLagrange.h"
00021 #include "P0.h"
00022 #include "utilities.h"
00023 
00024 using std::cout;
00025 using std::endl;
00026 
00027 namespace SyFi
00028 {
00029 
00030         //------------ sigma element
00031 
00032         ArnoldFalkWintherWeakSymSigma::ArnoldFalkWintherWeakSymSigma() : StandardFE()
00033         {
00034                 description = "ArnoldFalkWintherWeakSymSigma";
00035         }
00036 
00037         ArnoldFalkWintherWeakSymSigma::ArnoldFalkWintherWeakSymSigma(Polygon& p, int order) : StandardFE(p, order)
00038         {
00039                 compute_basis_functions();
00040         }
00041 
00042         void ArnoldFalkWintherWeakSymSigma:: compute_basis_functions()
00043         {
00044 
00045                 // remove previously computed basis functions and dofs
00046                 Ns.clear();
00047                 dofs.clear();
00048 
00049                 if ( order < 1 )
00050                 {
00051                         throw(std::logic_error("Arnold-Falk-Winther elements must be of order 1 or higher."));
00052                 }
00053 
00054                 if ( p == NULL )
00055                 {
00056                         throw(std::logic_error("You need to set a polygon before the basisfunctions can be computed"));
00057                 }
00058 
00059                 description = istr("ArnoldFalkWintherWeakSymSigma_", order) + "_3D";
00060 
00061                 Nedelec2Hdiv fe;
00062                 fe.set_order(order);
00063                 fe.set_polygon(*p);
00064                 fe.compute_basis_functions();
00065 
00066                 for (int d=0; d<3; d++)
00067                 {
00068                         for (unsigned int i=0; i<fe.nbf(); i++)
00069                         {
00070                                 GiNaC::matrix Nmat = GiNaC::matrix(3,3);
00071                                 Nmat(d,0) = fe.N(i).op(0);
00072                                 Nmat(d,1) = fe.N(i).op(1);
00073                                 Nmat(d,2) = fe.N(i).op(2);
00074                                 Ns.insert(Ns.end(), Nmat);
00075                                 dofs.insert(dofs.end(),GiNaC::lst(fe.dof(i).op(0), fe.dof(i).op(1), d));
00076                         }
00077                 }
00078         }
00079 
00080         //------------ u element
00081 
00082         ArnoldFalkWintherWeakSymU::ArnoldFalkWintherWeakSymU() : StandardFE()
00083         {
00084                 description = "ArnoldFalkWintherWeakSymU";
00085         }
00086 
00087         ArnoldFalkWintherWeakSymU ::ArnoldFalkWintherWeakSymU (Polygon& p, int order) : StandardFE(p, order)
00088         {
00089                 compute_basis_functions();
00090         }
00091 
00092         void ArnoldFalkWintherWeakSymU:: compute_basis_functions()
00093         {
00094 
00095                 // remove previously computed basis functions and dofs
00096                 Ns.clear();
00097                 dofs.clear();
00098 
00099                 if ( order < 1 )
00100                 {
00101                         throw(std::logic_error("Arnold-Falk-Winther elements must be of order 1 or higher."));
00102                 }
00103 
00104                 if ( p == NULL )
00105                 {
00106                         throw(std::logic_error("You need to set a polygon before the basisfunctions can be computed"));
00107                 }
00108 
00109                 description = istr("ArnoldFalkWintherWeakSymU_", order) + "_3D";
00110 
00111                 if ( order  > 1 )
00112                 {
00113                         VectorDiscontinuousLagrange fe;
00114                         fe.set_order(order-1);
00115                         fe.set_size(3);
00116                         fe.set_polygon(*p);
00117                         fe.compute_basis_functions();
00118 
00119                         for (unsigned int i=0; i<fe.nbf(); i++)
00120                         {
00121                                 GiNaC::lst Ni = GiNaC::lst(fe.N(i).op(0), fe.N(i).op(1), fe.N(i).op(2));
00122                                 GiNaC::ex Nmat = GiNaC::matrix(3,1,Ni);
00123                                 Ns.insert(Ns.end(), Nmat);
00124                                 dofs.insert(dofs.end(),GiNaC::lst(fe.dof(i)));
00125                         }
00126                 }
00127                 else if ( order == 1 )
00128                 {
00129                         VectorP0 fe;
00130                         fe.set_order(order-1);
00131                         fe.set_size(3);
00132                         fe.set_polygon(*p);
00133                         fe.compute_basis_functions();
00134 
00135                         for (unsigned int i=0; i<fe.nbf(); i++)
00136                         {
00137                                 GiNaC::lst Ni = GiNaC::lst(fe.N(i).op(0), fe.N(i).op(1), fe.N(i).op(2));
00138                                 GiNaC::ex Nmat = GiNaC::matrix(3,1,Ni);
00139                                 Ns.insert(Ns.end(), Nmat);
00140                                 GiNaC::ex d = GiNaC::lst(fe.dof(i), 0);
00141                                 dofs.insert(dofs.end(),GiNaC::lst(d));
00142                         }
00143                 }
00144 
00145         }
00146 
00147         //------------ p element
00148 
00149         ArnoldFalkWintherWeakSymP::ArnoldFalkWintherWeakSymP() : StandardFE()
00150         {
00151                 description = "ArnoldFalkWintherWeakSymP";
00152         }
00153 
00154         ArnoldFalkWintherWeakSymP ::ArnoldFalkWintherWeakSymP (Polygon& p, int order) : StandardFE(p, order)
00155         {
00156                 compute_basis_functions();
00157         }
00158 
00159         void ArnoldFalkWintherWeakSymP:: compute_basis_functions()
00160         {
00161 
00162                 // remove previously computed basis functions and dofs
00163                 Ns.clear();
00164                 dofs.clear();
00165 
00166                 if ( order < 1 )
00167                 {
00168                         cout <<"Arnold-Falk-Winther elements must be of order 1 or higher."<<endl;
00169                         return;
00170                 }
00171 
00172                 if ( p == NULL )
00173                 {
00174                         cout <<"You need to set a polygon before the basisfunctions can be computed"<<endl;
00175                         return;
00176                 }
00177 
00178                 description = istr("ArnoldFalkWintherWeakSymP_", order) + "_3D";
00179 
00180                 if ( order > 1 )
00181                 {
00182 
00183                         VectorDiscontinuousLagrange fe;
00184                         fe.set_order(order);
00185                         fe.set_size(3);
00186                         fe.set_polygon(*p);
00187                         fe.compute_basis_functions();
00188 
00189                         for (unsigned int i=0; i<fe.nbf(); i++)
00190                         {
00191                                 GiNaC::matrix Nmat = GiNaC::matrix(3,3);
00192                                 Nmat(1,2) = -fe.N(i).op(0);
00193                                 Nmat(2,1) =  fe.N(i).op(0);
00194 
00195                                 Nmat(0,2) =  fe.N(i).op(1);
00196                                 Nmat(2,0) = -fe.N(i).op(1);
00197 
00198                                 Nmat(0,1) = -fe.N(i).op(2);
00199                                 Nmat(1,0) =  fe.N(i).op(2);
00200 
00201                                 Ns.insert(Ns.end(), Nmat);
00202                                 dofs.insert(dofs.end(),GiNaC::lst(fe.dof(i)));
00203                         }
00204                 }
00205                 else if  ( order == 1 )
00206                 {
00207 
00208                         VectorP0 fe;
00209                         fe.set_order(order);
00210                         fe.set_size(3);
00211                         fe.set_polygon(*p);
00212                         fe.compute_basis_functions();
00213 
00214                         for (unsigned int i=0; i<fe.nbf(); i++)
00215                         {
00216                                 GiNaC::matrix Nmat = GiNaC::matrix(3,3);
00217                                 Nmat(1,2) = -fe.N(i).op(0);
00218                                 Nmat(2,1) =  fe.N(i).op(0);
00219 
00220                                 Nmat(0,2) =  fe.N(i).op(1);
00221                                 Nmat(2,0) = -fe.N(i).op(1);
00222 
00223                                 Nmat(0,1) = -fe.N(i).op(2);
00224                                 Nmat(1,0) =  fe.N(i).op(2);
00225 
00226                                 Ns.insert(Ns.end(), Nmat);
00227                                 GiNaC::ex d = GiNaC::lst(fe.dof(i), 0);
00228                                 dofs.insert(dofs.end(),GiNaC::lst(d));
00229                         }
00230                 }
00231 
00232         }
00233 
00234 }                                                                // namespace SyFi
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator