19template<
class Container>
27 template<
class Container2>
33 unsigned size()
const {
return O.size();}
36 unsigned size =
M.size();
45 y[i] =
O[i]*
x[i] +
P[i]*
x[i+1];
46 else if ( i ==
size -1 )
47 y[i] =
M[i]*
x[i-1] +
O[i] *
x[i];
49 y[i] =
M[i]*
x[i-1] +
O[i] *
x[i] +
P[i] *
x[i+1];
50 },
M.size(),
M,
O,
P,
x,
y);
55 unsigned size =
M.size();
56 cusp::coo_matrix<int,value_type,cusp::host_memory> A(
size,
size, 3*
size-2);
58 A.column_indices[0] = 0;
62 A.column_indices[1] = 1;
65 for(
unsigned i=1;i<
size; i++)
67 A.row_indices[3*i-1+0] = i;
68 A.column_indices[3*i-1+0] = i-1;
69 A.values[3*i-1+0] =
M[i];
71 A.row_indices[3*i-1+1] = i;
72 A.column_indices[3*i-1+1] = i;
73 A.values[3*i-1+1] =
O[i];
77 A.row_indices[3*i-1+2] = i;
78 A.column_indices[3*i-1+2] = i+1;
79 A.values[3*i-1+2] =
P[i];
93template<
class value_type>
104 void operator()(
const thrust::host_vector<value_type>& y, thrust::host_vector<value_type>& x)
const
106 unsigned size = M.size();
107 thrust::host_vector<value_type> ci(size), di(size);
111 for(
unsigned i=1; i<size; i++)
113 ci[i] = P[i]/ ( O[i] -M[i]*ci[i-1]);
114 di[i] = (
y[i]-M[i]*di[i-1])/(O[i] -M[i]*ci[i-1]);
116 x[size-1] = di[size-1];
117 for(
int i=size-2; i>=0; i--)
118 x[i] = di[i] - ci[i]*
x[i+1];
121 thrust::host_vector<value_type> M, O, P;
130template<
class Container>
138 unsigned&
nz() {
return m_nz;}
139 unsigned nz()
const {
return m_nz;}
140 template<
class Container2>
148 template<
class ContainerType0,
class ContainerType1>
151 unsigned size = m_y.size()*m_x.size()*m_nz;
152 unsigned Nx = m_x.size(), Ny = m_y.size();
162 unsigned j = (i/Nx)/Ny;
163 unsigned k = (i/Nx)%Ny, l = i%Nx;
169 b = xO[l]*
x[(j*Ny+k)*Nx+l] + xP[l]*
x[(j*Ny+k)*Nx+l+1];
170 c = xO[l]*
x[(j*Ny+k+1)*Nx+l] + xP[l]*
x[(j*Ny+k+1)*Nx+l+1];
171 y[i] = yO[k]*b + yP[k]*c;
175 a = xO[l]*
x[(j*Ny+k-1)*Nx+l] + xP[l]*
x[(j*Ny+k-1)*Nx+l+1];
176 b = xO[l]*
x[(j*Ny+k)*Nx+l] + xP[l]*
x[(j*Ny+k)*Nx+l+1];
177 y[i] = yM[k]*a + yO[k]*b;
181 a = xO[l]*
x[(j*Ny+k-1)*Nx+l] + xP[l]*
x[(j*Ny+k-1)*Nx+l+1];
182 b = xO[l]*
x[(j*Ny+k)*Nx+l] + xP[l]*
x[(j*Ny+k)*Nx+l+1];
183 c = xO[l]*
x[(j*Ny+k+1)*Nx+l] + xP[l]*
x[(j*Ny+k+1)*Nx+l+1];
184 y[i] = yM[k]*a + yO[k]*b + yP[k]*c;
187 else if ( l == Nx -1 )
191 b = xM[l]*
x[(j*Ny+k)*Nx+l-1] + xO[l]*
x[(j*Ny+k)*Nx+l];
192 c = xM[l]*
x[(j*Ny+k+1)*Nx+l-1] + xO[l]*
x[(j*Ny+k+1)*Nx+l];
193 y[i] = yO[k]*b + yP[k]*c;
195 else if ( k == Ny -1)
197 a = xM[l]*
x[(j*Ny+k-1)*Nx+l-1] + xO[l]*
x[(j*Ny+k-1)*Nx+l];
198 b = xM[l]*
x[(j*Ny+k)*Nx+l-1] + xO[l]*
x[(j*Ny+k)*Nx+l];
199 y[i] = yM[k]*a + yO[k]*b;
203 a = xM[l]*
x[(j*Ny+k-1)*Nx+l-1] + xO[l]*
x[(j*Ny+k-1)*Nx+l];
204 b = xM[l]*
x[(j*Ny+k)*Nx+l-1] + xO[l]*
x[(j*Ny+k)*Nx+l];
205 c = xM[l]*
x[(j*Ny+k+1)*Nx+l-1] + xO[l]*
x[(j*Ny+k+1)*Nx+l];
206 y[i] = yM[k]*a + yO[k]*b + yP[k]*c;
213 b = xM[l]*
x[(j*Ny+k)*Nx+l-1] + xO[l]*
x[(j*Ny+k)*Nx+l] +
214 xP[l]*
x[(j*Ny+k)*Nx+l+1];
215 c = xM[l]*
x[(j*Ny+k+1)*Nx+l-1] + xO[l]*
x[(j*Ny+k+1)*Nx+l] +
216 xP[l]*
x[(j*Ny+k+1)*Nx+l+1];
217 y[i] = yO[k]*b + yP[k]*c;
219 else if ( k == Ny -1)
221 a = xM[l]*
x[(j*Ny+k-1)*Nx+l-1] + xO[l]*
x[(j*Ny+k-1)*Nx+l] +
222 xP[l]*
x[(j*Ny+k-1)*Nx+l+1];
223 b = xM[l]*
x[(j*Ny+k)*Nx+l-1] + xO[l]*
x[(j*Ny+k)*Nx+l] +
224 xP[l]*
x[(j*Ny+k)*Nx+l+1];
225 y[i] = yM[k]*a + yO[k]*b;
229 a = xM[l]*
x[(j*Ny+k-1)*Nx+l-1] + xO[l]*
x[(j*Ny+k-1)*Nx+l] +
230 xP[l]*
x[(j*Ny+k-1)*Nx+l+1];
231 b = xM[l]*
x[(j*Ny+k)*Nx+l-1] + xO[l]*
x[(j*Ny+k)*Nx+l] +
232 xP[l]*
x[(j*Ny+k)*Nx+l+1];
233 c = xM[l]*
x[(j*Ny+k+1)*Nx+l-1] + xO[l]*
x[(j*Ny+k+1)*Nx+l] +
234 xP[l]*
x[(j*Ny+k+1)*Nx+l+1];
235 y[i] = yM[k]*a + yO[k]*b + yP[k]*c;
238 }, size, m_y.M, m_y.O, m_y.P, m_x.M, m_x.O, m_x.P,
x,
y);
251template<
class Container>
259 unsigned size = m_t.x().size()*m_t.y().size()*m_t.nz();
264 template<
class Container2>
268 unsigned size = m_t.x().size()*m_t.y().size()*m_t.nz();
274 template<
class ContainerType0,
class ContainerType1>
277 unsigned Nx = m_t.x().size(), Ny = m_t.y().size();
287 ci[k*Nx + 0] = P[0]/O[0];
288 di[k*Nx + 0] =
y[k*Nx + 0]/O[0];
289 for(
unsigned i=1; i<Nx; i++)
291 ci[k*Nx+i] = P[i]/ ( O[i] -M[i]*ci[k*Nx+i-1]);
292 di[k*Nx+i] = (
y[k*Nx+i]-M[i]*di[k*Nx+i-1])/(O[i] -M[i]*ci[k*Nx+i-1]);
294 x[k*Nx + Nx-1] = di[k*Nx + Nx-1];
295 for(
int i=Nx-2; i>=0; i--)
296 x[k*Nx+i] = di[k*Nx+i] - ci[k*Nx+i]*
x[k*Nx +i+1];
298 }, m_t.y().size()*m_t.nz(), m_t.x().M, m_t.x().O, m_t.x().P, m_ci, m_di,
y, m_tmp);
308 unsigned i = l%Nx, j = l/Nx;
309 ci[(j*Ny+0)*Nx + i] = P[0]/O[0];
310 di[(j*Ny+0)*Nx + i] =
y[(j*Ny+0)*Nx + i]/O[0];
311 for(
unsigned k=1; k<Ny; k++)
313 ci[(j*Ny+k)*Nx+i] = P[k]/ ( O[k] -M[k]*ci[(j*Ny+k-1)*Nx+i]);
314 di[(j*Ny+k)*Nx+i] = (
y[(j*Ny+k)*Nx+i]-M[k]*di[(j*Ny+k-1)*Nx+i])/(O[k] -M[k]*ci[(j*Ny+k-1)*Nx+i]);
316 x[(j*Ny+Ny-1)*Nx + i] = di[(j*Ny+Ny-1)*Nx + i];
317 for(
int k=Ny-2; k>=0; k--)
318 x[(j*Ny+k)*Nx+i] = di[(j*Ny+k)*Nx+i] - ci[(j*Ny+k)*Nx+i]*
x[(j*Ny+k+1)*Nx +i];
320 }, m_t.x().size()*m_t.nz(), m_t.y().M, m_t.y().O, m_t.y().P, m_ci, m_di,m_tmp,
x);
325 Container m_ci, m_di, m_tmp;
366template<
class real_type>
371 std::vector<real_type> xx = g.
dlt().abscissas();
372 std::vector<real_type> xa( g.
n()+2);
373 xa[0] = (xx[g.
n()-1]-2)*g.
h()/2.;
374 for(
unsigned i=0; i<g.
n(); i++)
375 xa[i+1]=xx[i]*g.
h()/2.;
376 xa[g.
n()+1] = (xx[0]+2)*g.
h()/2.;
377 const real_type*
x = &xa[1];
378 real_type xleft = -g.
h()/2., xright = g.
h()/2.;
380 for(
unsigned i=0; i<g.
N(); i++)
381 for(
int k=0; k<(int)g.
n(); k++)
386 A.
O[0] = (4*
x[0]-6*xleft+2*
x[1])/6./
weights[0];
391 if( (i==g.
N()-1) && (k == (
int)g.
n()-1))
394 A.
O[I] = (-4*
x[k]+6*xright-2*
x[k-1])/6./
weights[I];
406template<
class real_type>
412 std::vector<real_type> xx = g.
dlt().abscissas();
413 std::vector<real_type> xa( g.
n()+2);
414 xa[0] = (xx[g.
n()-1]-2)*g.
h()/2.;
415 for(
unsigned i=0; i<g.
n(); i++)
416 xa[i+1]=xx[i]*g.
h()/2.;
417 xa[g.
n()+1] = (xx[0]+2)*g.
h()/2.;
418 const real_type*
x = &xa[1];
419 real_type xleft = -g.
h()/2., xright = g.
h()/2.;
422 for(
unsigned i=0; i<g.
N(); i++)
423 for(
int k=0; k<(int)g.
n(); k++)
428 A.
O[0] = (5*
x[0]-8*xleft+3*
x[1])/8./
weights[0];
433 if( (i==g.
N()-1) && (k == (
int)g.
n()-1))
436 A.
O[I] = (-5*
x[k]+8*xright-3*
x[k-1])/8./
weights[I];
448template<
class real_type>
458template<
class real_type>
467template<
class real_type>
477template<
class real_type>
486template<
class real_type>
492 return {g.
gz().size(), my, mx};
496template<
class real_type>
505template<
class real_type>
511 return {g.
gz().size(), my, mx};
515template<
class real_type>
Creation functions for finite element utilities.
#define DG_DEVICE
Expands to __host__ __device__ if compiled with nvcc else is empty.
Definition: functions.h:9
void assign(const from_ContainerType &from, ContainerType &to, Params &&... ps)
Generic way to assign the contents of a from_ContainerType object to a ContainerType object optionall...
Definition: blas1.h:665
void parallel_for(Stencil f, unsigned N, ContainerType &&x, ContainerTypes &&... xs)
; Customizable and generic for loop
Definition: blas2.h:378
dg::InverseKroneckerTriDiagonal2d< dg::HVec_t< real_type > > inv_fem_mass(const aRealTopology2d< real_type > &g)
Inverse finite element mass matrix .
Definition: fem.h:459
dg::InverseKroneckerTriDiagonal2d< dg::HVec_t< real_type > > inv_fem_mass2d(const aRealTopology3d< real_type > &g)
Inverse finite element mass matrix .
Definition: fem.h:497
thrust::host_vector< real_type > fem_weights(const RealGrid1d< real_type > &g)
finite element weight coefficients
Definition: fem_weights.h:53
dg::InverseKroneckerTriDiagonal2d< dg::HVec_t< real_type > > inv_fem_linear2const(const aRealTopology2d< real_type > &g)
Inverse finite element mass matrix .
Definition: fem.h:478
dg::InverseKroneckerTriDiagonal2d< dg::HVec_t< real_type > > inv_fem_linear2const2d(const aRealTopology3d< real_type > &g)
Inverse finite element mass matrix .
Definition: fem.h:516
dg::KroneckerTriDiagonal2d< dg::HVec_t< real_type > > fem_linear2const2d(const aRealTopology3d< real_type > &g)
finite element projection matrix
Definition: fem.h:506
dg::TriDiagonal< dg::HVec_t< real_type > > fem_mass(const RealGrid1d< real_type > &g)
finite element projection matrix
Definition: fem.h:367
dg::KroneckerTriDiagonal2d< dg::HVec_t< real_type > > fem_mass2d(const aRealTopology3d< real_type > &g)
finite element projection matrix
Definition: fem.h:487
dg::TriDiagonal< dg::HVec_t< real_type > > fem_linear2const(const RealGrid1d< real_type > &g)
finite element projection matrix
Definition: fem.h:407
MPI_Vector< thrust::host_vector< real_type > > weights(const aRealMPITopology2d< real_type > &g)
Nodal weight coefficients.
Definition: mpi_weights.h:22
typename TensorTraits< std::decay_t< Vector > >::value_type get_value_type
Definition: tensor_traits.h:38
cusp::csr_matrix< int, real_type, cusp::host_memory > IHMatrix_t
Definition: typedefs.h:37
This is the namespace for all functions and classes defined and used by the discontinuous Galerkin li...
Fast inverse tridiagonal sparse matrix in 2d .
Definition: fem.h:253
InverseKroneckerTriDiagonal2d(const KroneckerTriDiagonal2d< Container > &tri)
Definition: fem.h:256
InverseKroneckerTriDiagonal2d(const InverseKroneckerTriDiagonal2d< Container2 > &inv_tri)
Definition: fem.h:265
dg::get_value_type< Container > value_type
Definition: fem.h:254
InverseKroneckerTriDiagonal2d()=default
void operator()(const ContainerType0 &y, ContainerType1 &x)
Definition: fem.h:275
const KroneckerTriDiagonal2d< Container > & tri() const
Definition: fem.h:273
Fast inverse tridiagonal sparse matrix.
Definition: fem.h:95
InverseTriDiagonal(const TriDiagonal< thrust::host_vector< value_type > > &tri)
Definition: fem.h:97
void operator()(const thrust::host_vector< value_type > &y, thrust::host_vector< value_type > &x) const
Definition: fem.h:104
InverseTriDiagonal()=default
Fast tridiagonal sparse matrix in 2d .
Definition: fem.h:132
KroneckerTriDiagonal2d(unsigned nz, TriDiagonal< Container > my, TriDiagonal< Container > mx)
Definition: fem.h:136
unsigned nz() const
Definition: fem.h:139
dg::get_value_type< Container > value_type
Definition: fem.h:133
unsigned & nz()
Definition: fem.h:138
KroneckerTriDiagonal2d(const KroneckerTriDiagonal2d< Container2 > &other)
Definition: fem.h:141
const TriDiagonal< Container > & x() const
Definition: fem.h:146
const TriDiagonal< Container > & y() const
Definition: fem.h:147
void operator()(const ContainerType0 &x, ContainerType1 &y) const
Definition: fem.h:149
KroneckerTriDiagonal2d(TriDiagonal< Container > my, TriDiagonal< Container > mx)
Definition: fem.h:135
KroneckerTriDiagonal2d()=default
1D grid
Definition: grid.h:80
real_type h() const
cell size
Definition: grid.h:129
unsigned n() const
number of polynomial coefficients
Definition: grid.h:141
const DLT< real_type > & dlt() const
the discrete legendre transformation
Definition: grid.h:197
unsigned size() const
n()*N() (Total number of grid points)
Definition: grid.h:191
unsigned N() const
number of cells
Definition: grid.h:135
Fast (shared memory) tridiagonal sparse matrix.
Definition: fem.h:21
Container P
Definition: fem.h:85
TriDiagonal(unsigned size)
Definition: fem.h:24
dg::get_value_type< Container > value_type
Definition: fem.h:22
TriDiagonal(const TriDiagonal< Container2 > &other)
Definition: fem.h:28
dg::IHMatrix_t< value_type > asIMatrix() const
convert to a sparse matrix format
Definition: fem.h:54
TriDiagonal(Container M, Container O, Container P)
Definition: fem.h:25
unsigned size() const
Definition: fem.h:33
Container M
Definition: fem.h:85
void operator()(const Container &x, Container &y) const
Definition: fem.h:34
Container O
Definition: fem.h:85
An abstract base class for two-dimensional grids.
Definition: grid.h:277
const RealGrid1d< real_type > & gy() const
The y-axis grid.
Definition: grid.h:379
const RealGrid1d< real_type > & gx() const
The x-axis grid.
Definition: grid.h:377
An abstract base class for three-dimensional grids.
Definition: grid.h:523
const RealGrid1d< real_type > & gz() const
The z-axis grid.
Definition: grid.h:664
const RealGrid1d< real_type > & gx() const
The x-axis grid.
Definition: grid.h:660
const RealGrid1d< real_type > & gy() const
The y-axis grid.
Definition: grid.h:662