MFEM  v3.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Pages
coefficient.cpp
Go to the documentation of this file.
1 // Copyright (c) 2010, Lawrence Livermore National Security, LLC. Produced at
2 // the Lawrence Livermore National Laboratory. LLNL-CODE-443211. All Rights
3 // reserved. See file COPYRIGHT for details.
4 //
5 // This file is part of the MFEM library. For more information and source code
6 // availability see http://mfem.googlecode.com.
7 //
8 // MFEM is free software; you can redistribute it and/or modify it under the
9 // terms of the GNU Lesser General Public License (as published by the Free
10 // Software Foundation) version 2.1 dated February 1999.
11 
12 // Implementation of Coefficient class
13 
14 #include "fem.hpp"
15 
16 #include <cmath>
17 #include <limits>
18 
19 namespace mfem
20 {
21 
22 using namespace std;
23 
25  const IntegrationPoint & ip)
26 {
27  int att = T.Attribute;
28  return(constants(att-1));
29 }
30 
32  const IntegrationPoint & ip)
33 {
34  double x[3];
35  Vector transip(x, 3);
36 
37  T.Transform(ip, transip);
38 
39  if (Function)
40  return((*Function)(transip));
41  else
42  return (*TDFunction)(transip, GetTime());
43 }
44 
46  const IntegrationPoint &ip)
47 {
48  return GridF -> GetValue (T.ElementNo, ip, Component);
49 }
50 
52  const IntegrationPoint &ip)
53 {
54  if (Q2)
55  {
56  return (*Transform2)(Q1->Eval(T, ip, GetTime()),
57  Q2->Eval(T, ip, GetTime()));
58  }
59  else
60  {
61  return (*Transform1)(Q1->Eval(T, ip, GetTime()));
62  }
63 }
64 
66  const IntegrationRule &ir)
67 {
68  Vector Mi;
69  M.SetSize(vdim, ir.GetNPoints());
70  for (int i = 0; i < ir.GetNPoints(); i++)
71  {
72  M.GetColumnReference(i, Mi);
73  const IntegrationPoint &ip = ir.IntPoint(i);
74  T.SetIntPoint(&ip);
75  Eval(Mi, T, ip);
76  }
77 }
78 
80  const IntegrationPoint &ip)
81 {
82  double x[3];
83  Vector transip(x, 3);
84 
85  T.Transform(ip, transip);
86 
87  V.SetSize(vdim);
88  if (Function)
89  (*Function)(transip, V);
90  else
91  (*TDFunction)(transip, GetTime(), V);
92  if (Q)
93  V *= Q->Eval(T, ip, GetTime());
94 }
95 
97  : VectorCoefficient(dim), Coeff(dim)
98 {
99  for (int i = 0; i < dim; i++)
100  Coeff[i] = NULL;
101 }
102 
104 {
105  for (int i = 0; i < vdim; i++)
106  delete Coeff[i];
107 }
108 
110  const IntegrationPoint &ip)
111 {
112  V.SetSize(vdim);
113  for (int i = 0; i < vdim; i++)
114  V(i) = Coeff[i]->Eval(T, ip, GetTime());
115 }
116 
118  GridFunction *gf) : VectorCoefficient (gf -> VectorDim())
119 {
120  GridFunc = gf;
121 }
122 
124  const IntegrationPoint &ip)
125 {
126  GridFunc->GetVectorValue(T.ElementNo, ip, V);
127 }
128 
131 {
132  GridFunc->GetVectorValues(T, ir, M);
133 }
134 
136  const IntegrationPoint &ip)
137 {
138  V.SetSize(vdim);
139  if (active_attr[T.Attribute-1])
140  {
141  c->SetTime(GetTime());
142  c->Eval(V, T, ip);
143  }
144  else
145  V = 0.0;
146 }
147 
150 {
151  if (active_attr[T.Attribute-1])
152  {
153  c->SetTime(GetTime());
154  c->Eval(M, T, ir);
155  }
156  else
157  {
158  M.SetSize(vdim);
159  M = 0.0;
160  }
161 }
162 
164  const IntegrationPoint &ip)
165 {
166  double x[3];
167  Vector transip(x, 3);
168 
169  T.Transform(ip, transip);
170 
171  K.SetSize(vdim);
172 
173  if (Function)
174  (*Function)(transip, K);
175  else
176  (*TDFunction)(transip, GetTime(), K);
177 }
178 
180  : MatrixCoefficient (dim)
181 {
182  Coeff.SetSize (vdim*vdim);
183 }
184 
186 {
187  for (int i=0; i< vdim*vdim; i++)
188  delete Coeff[i];
189 }
190 
192  const IntegrationPoint &ip)
193 {
194  int i, j;
195 
196  for (i = 0; i < vdim; i++)
197  for (j = 0; j < vdim; j++)
198  K(i,j) = Coeff[i*vdim+j] -> Eval(T, ip, GetTime());
199 }
200 
201 double LpNormLoop(double p, Coefficient &coeff, Mesh &mesh,
202  const IntegrationRule *irs[])
203 {
204  double norm = 0.0;
206 
207  for (int i = 0; i < mesh.GetNE(); i++)
208  {
209  tr = mesh.GetElementTransformation(i);
210  const IntegrationRule &ir = *irs[mesh.GetElementType(i)];
211  for (int j = 0; j < ir.GetNPoints(); j++)
212  {
213  const IntegrationPoint &ip = ir.IntPoint(j);
214  tr->SetIntPoint(&ip);
215  double val = fabs(coeff.Eval(*tr, ip));
216  if (p < numeric_limits<double>::infinity())
217  {
218  norm += ip.weight * tr->Weight() * pow(val, p);
219  }
220  else
221  {
222  if (norm < val)
223  norm = val;
224  }
225  }
226  }
227  return norm;
228 }
229 
230 double LpNormLoop(double p, VectorCoefficient &coeff, Mesh &mesh,
231  const IntegrationRule *irs[])
232 {
233  double norm = 0.0;
235  int vdim = coeff.GetVDim();
236  Vector vval(vdim);
237  double val;
238 
239  for (int i = 0; i < mesh.GetNE(); i++)
240  {
241  tr = mesh.GetElementTransformation(i);
242  const IntegrationRule &ir = *irs[mesh.GetElementType(i)];
243  for (int j = 0; j < ir.GetNPoints(); j++)
244  {
245  const IntegrationPoint &ip = ir.IntPoint(j);
246  tr->SetIntPoint(&ip);
247  coeff.Eval(vval, *tr, ip);
248  if (p < numeric_limits<double>::infinity())
249  {
250  for(int idim(0); idim < vdim; ++idim)
251  norm += ip.weight * tr->Weight() * pow(fabs( vval(idim) ), p);
252  }
253  else
254  {
255  for(int idim(0); idim < vdim; ++idim)
256  {
257  val = fabs(vval(idim));
258  if (norm < val)
259  norm = val;
260  }
261  }
262  }
263  }
264 
265  return norm;
266 }
267 
268 double ComputeLpNorm(double p, Coefficient &coeff, Mesh &mesh,
269  const IntegrationRule *irs[])
270 {
271  double norm = LpNormLoop(p, coeff, mesh, irs);
272 
273  if (p < numeric_limits<double>::infinity())
274  {
275  // negative quadrature weights may cause norm to be negative
276  if (norm < 0.0)
277  norm = -pow(-norm, 1.0/p);
278  else
279  norm = pow(norm, 1.0/p);
280  }
281 
282  return norm;
283 }
284 
285 double ComputeLpNorm(double p, VectorCoefficient &coeff, Mesh &mesh,
286  const IntegrationRule *irs[])
287 {
288  double norm = LpNormLoop(p, coeff, mesh, irs);
289 
290  if (p < numeric_limits<double>::infinity())
291  {
292  // negative quadrature weights may cause norm to be negative
293  if (norm < 0.0)
294  norm = -pow(-norm, 1.0/p);
295  else
296  norm = pow(norm, 1.0/p);
297  }
298 
299  return norm;
300 }
301 
302 #ifdef MFEM_USE_MPI
303 double ComputeGlobalLpNorm(double p, Coefficient &coeff, ParMesh &pmesh,
304  const IntegrationRule *irs[])
305 {
306  double loc_norm = LpNormLoop(p, coeff, pmesh, irs);
307  double glob_norm = 0;
308 
309  MPI_Comm comm = pmesh.GetComm();
310 
311  if (p < numeric_limits<double>::infinity())
312  {
313  MPI_Allreduce(&loc_norm, &glob_norm, 1, MPI_DOUBLE, MPI_SUM, comm);
314 
315  // negative quadrature weights may cause norm to be negative
316  if (glob_norm < 0.0)
317  glob_norm = -pow(-glob_norm, 1.0/p);
318  else
319  glob_norm = pow(glob_norm, 1.0/p);
320  }
321  else
322  {
323  MPI_Allreduce(&loc_norm, &glob_norm, 1, MPI_DOUBLE, MPI_MAX, comm);
324  }
325 
326  return glob_norm;
327 }
328 
329 double ComputeGlobalLpNorm(double p, VectorCoefficient &coeff, ParMesh &pmesh,
330  const IntegrationRule *irs[])
331 {
332  double loc_norm = LpNormLoop(p, coeff, pmesh, irs);
333  double glob_norm = 0;
334 
335  MPI_Comm comm = pmesh.GetComm();
336 
337  if (p < numeric_limits<double>::infinity())
338  {
339  MPI_Allreduce(&loc_norm, &glob_norm, 1, MPI_DOUBLE, MPI_SUM, comm);
340 
341  // negative quadrature weights may cause norm to be negative
342  if (glob_norm < 0.0)
343  glob_norm = -pow(-glob_norm, 1.0/p);
344  else
345  glob_norm = pow(glob_norm, 1.0/p);
346  }
347  else
348  {
349  MPI_Allreduce(&loc_norm, &glob_norm, 1, MPI_DOUBLE, MPI_MAX, comm);
350  }
351 
352  return glob_norm;
353 }
354 #endif
355 
356 }
int GetNPoints() const
Returns the number of the points in the integration rule.
Definition: intrules.hpp:202
virtual void Eval(Vector &V, ElementTransformation &T, const IntegrationPoint &ip)
Class for integration rule.
Definition: intrules.hpp:63
Class for grid function - Vector with associated FE space.
Definition: gridfunc.hpp:26
VectorGridFunctionCoefficient(GridFunction *gf)
virtual void Eval(Vector &V, ElementTransformation &T, const IntegrationPoint &ip)=0
void GetVectorValue(int i, const IntegrationPoint &ip, Vector &val) const
Definition: gridfunc.cpp:224
void SetSize(int s)
Resizes the vector if the new size is different.
Definition: vector.hpp:248
MPI_Comm GetComm()
Definition: pmesh.hpp:68
void SetIntPoint(const IntegrationPoint *ip)
Definition: eltrans.hpp:33
Data type dense matrix.
Definition: densemat.hpp:22
virtual void Eval(Vector &V, ElementTransformation &T, const IntegrationPoint &ip)
Definition: coefficient.cpp:79
int GetNE() const
Returns number of elements.
Definition: mesh.hpp:396
virtual double Eval(ElementTransformation &T, const IntegrationPoint &ip)
Definition: coefficient.cpp:51
virtual double Eval(ElementTransformation &T, const IntegrationPoint &ip)
Evaluate coefficient.
Definition: coefficient.cpp:31
virtual void Eval(DenseMatrix &K, ElementTransformation &T, const IntegrationPoint &ip)
IntegrationPoint & IntPoint(int i)
Returns a reference to the i-th integration point.
Definition: intrules.hpp:205
double ComputeLpNorm(double p, Coefficient &coeff, Mesh &mesh, const IntegrationRule *irs[])
double LpNormLoop(double p, Coefficient &coeff, Mesh &mesh, const IntegrationRule *irs[])
int GetElementType(int i) const
Returns the type of element i.
Definition: mesh.cpp:3632
double Eval(int i, int j, ElementTransformation &T, IntegrationPoint &ip)
virtual ~VectorArrayCoefficient()
Destroys vector coefficient.
virtual double Weight()=0
int GetVDim()
Returns dimension of the vector.
double Eval(int i, ElementTransformation &T, IntegrationPoint &ip)
Evaluates i&#39;th component of the vector.
Base class Coefficient that may optionally depend on time.
Definition: coefficient.hpp:31
virtual double Eval(ElementTransformation &T, const IntegrationPoint &ip)
Evaluate the coefficient function.
Definition: coefficient.cpp:24
void GetColumnReference(int c, Vector &col)
Definition: densemat.hpp:186
void SetTime(double t)
virtual void Eval(Vector &V, ElementTransformation &T, const IntegrationPoint &ip)
double ComputeGlobalLpNorm(double p, Coefficient &coeff, ParMesh &pmesh, const IntegrationRule *irs[])
virtual double Eval(ElementTransformation &T, const IntegrationPoint &ip)
Definition: coefficient.cpp:45
Class for integration point with weight.
Definition: intrules.hpp:25
void GetElementTransformation(int i, IsoparametricTransformation *ElTr)
Definition: mesh.cpp:157
void GetVectorValues(ElementTransformation &T, const IntegrationRule &ir, DenseMatrix &vals) const
Definition: gridfunc.cpp:328
virtual double Eval(ElementTransformation &T, const IntegrationPoint &ip)=0
VectorArrayCoefficient(int dim)
Construct vector of dim coefficients.
Definition: coefficient.cpp:96
Vector data type.
Definition: vector.hpp:29
virtual void Transform(const IntegrationPoint &, Vector &)=0
void SetSize(int s)
If the matrix is not a square matrix of size s then recreate it.
Definition: densemat.cpp:73
Class for parallel meshes.
Definition: pmesh.hpp:27