https://github.com/team-pancho/HDG3D
Raw File
Tip revision: af0d6cb24c63ad6fa07331f26a5733116db800b7 authored by shukaidu on 29 April 2020, 21:46:21 UTC
Merge pull request #2 from team-pancho/hdg3d_skdu
Tip revision: af0d6cb
HDG3dCD.m
function [Uh,Qxh,Qyh,Qzh,Uhat,system,solvers]=...
          HDG3dCD(km,c,f,beta,tau,T,k,formulas,uD,gx,gy,gz,varargin)

%[Uh,Qxh,Qyh,Qzh,Uhat]=HDG3dCD(km,c,f,{bx,by,bz},...
%                       tau,T,k,formulas,uD,gx,gy,gz)
%[Uh,Qxh,Qyh,Qzh,Uhat]=HDG3dCD(km,c,f,{bx,by,bz},...
%                       tau,T,k,formulas,uD,gx,gy,gz,0)
%[~,~,~,~,~,system,solvers]=HDG3dCD(km,c,f,{bx,by,bz},...
%                       tau,T,k,formulas,uD,gx,gy,gz,1)
%
%Input:
%        km   : vectorized function (kappa^{-1}; kappa=diffusion parameter)
%        c    : vectorized function (reaction parameter)
%        f    : vectorized function (source term)
%  {bx,by,bz} : vectorized functions (convection field)
%        tau  : penalization parameter for HDG (Nelts x 4)
%        T    : expanded tetrahedrization
%        k    : polynomial degree
%     formulas: {for1,for2,for3,for4} 
%               (quadrature formulas as used by localsolvers3dCD)
%        uD   : Dirichlet data; vectorized function
%    gx,gy,gz : Neumann data (corresponds to kappa*grad(u)); vectorized fns  
%
%Output:
%      Uh     : d3 x Nelts,   matrix with uh
%      Qxh    : d3 x Nelts,   matrix with qxh
%      Qyh    : d3 x Nelts,   matrix with qyh
%      Qzh    : d3 x Nelts,   matrix with qzh
%      Uhat   : d2 x Nelts    matrix with uhhat
%    system   : {HDGmatrix,HDGrhs,list of free d.o.f.,list of dir d.o.f.}
%    solvers  : {A1,A2,Af}    local solvers
%
%Last modified: April 11, 2013

if nargin==13
    export=varargin{1};
else
    export=0;
end

d2=nchoosek(k+2,2);    
d3=nchoosek(k+3,3); 
block3=@(x) (1+(x-1)*d3):(x*d3);
Nelts =size(T.elements,1);
Nfaces=size(T.faces,1);
Ndir  =size(T.dirichlet,1);
Nneu  =size(T.neumann,1);

%Matrices for assembly process

face=T.facebyele';    % 4 x Nelts
face=(face(:)-1)*d2;  % First degree of freedom of each face by element                                               
face=bsxfun(@plus,face,1:d2);    %4*Nelts x d2 (d.o.f. for each face)                                              
face=reshape(face',4*d2,Nelts);  %d.o.f. for the 4 faces of each element

[J,I]=meshgrid(1:4*d2);
R=face(I(:),:); R=reshape(R,4*d2,4*d2,Nelts);
C=face(J(:),:); C=reshape(C,4*d2,4*d2,Nelts); 
      % R_ij^K d.o.f. for local (i,j) d.o.f. in element K ; R_ij^K=C_ji^K
RowsRHS=reshape(face,4*d2*Nelts,1);

dirfaces=(T.dirfaces(:)-1)*d2;
dirfaces=bsxfun(@plus,dirfaces,1:d2);
dirfaces=reshape(dirfaces',d2*Ndir,1);

free=((1:Nfaces)'-1)*d2;
free=bsxfun(@plus,free,1:d2);
free=reshape(free',d2*Nfaces,1);
free(dirfaces)=[];

neufaces=(T.neufaces(:)-1)*d2;
neufaces=bsxfun(@plus,neufaces,1:d2);
neufaces=reshape(neufaces',d2*Nneu,1);

%Local solvers and global system

[M1,Cf,A1,A2,Af]=localsolvers3dCD(km,c,f,beta,tau,T,k,formulas);
M=sparse(R(:),C(:),M1(:));
phif=accumarray(RowsRHS,Cf(:));

[uhatD,qhatN]=BC3d(uD,gx,gy,gz,T,k,formulas{3});

%Dirichlet BC
Uhatv=zeros(d2*Nfaces,1);
Uhatv(dirfaces)=uhatD;       %uhat stored as a vector: d2*Nfaces

%RHS
rhs=zeros(d2*Nfaces,1);
rhs(free)=phif(free);
qhatN=reshape(qhatN,d2*Nneu,1);   % qhatN stored as a vector: d2*Nneu
rhs(neufaces)=rhs(neufaces)+qhatN;
rhs=rhs-M(:,dirfaces)*Uhatv(dirfaces);

if export
    system={M,rhs,free,dirfaces};
    solvers={A1,A2,Af};
    Uh=[];
    Qxh=[];
    Qyh=[];
    Qzh=[];
    Uhat=[];
    return
else
    system=[];
    solvers=[];
end

Uhatv(free)=M(free,free)\rhs(free);
Uhat=reshape(Uhatv,d2,Nfaces);

%Uh Qxh Qyh Qzh

faces=T.facebyele'; faces=faces(:);
uhhataux=reshape(Uhat(:,faces),[4*d2,Nelts]);
sol=zeros(4*d3,Nelts);
parfor K=1:Nelts
    sol(:,K)=A1(:,:,K)\(Af(:,K)-A2(:,:,K)*uhhataux(:,K));
end

Qxh=sol(block3(1),:);
Qyh=sol(block3(2),:);
Qzh=sol(block3(3),:);
Uh =sol(block3(4),:);
return
back to top