DirichletBC.h 5.04 KB
Newer Older
1
2
3
4
5
6
7
/******************************************************************************
 *
 * AMDiS - Adaptive multidimensional simulations
 *
 * Copyright (C) 2013 Dresden University of Technology. All Rights Reserved.
 * Web: https://fusionforge.zih.tu-dresden.de/projects/amdis
 *
8
 * Authors:
9
10
11
12
13
14
15
16
17
 * Simon Vey, Thomas Witkowski, Andreas Naumann, Simon Praetorius, et al.
 *
 * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
 * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 *
 *
 * This file is part of AMDiS
 *
 * See also license.opensource.txt in the distribution.
18
 *
19
 ******************************************************************************/
20
21


22
23
24
25
26
27

/** \file DirichletBC.h */

#ifndef AMDIS_DIRICHLETBC_H
#define AMDIS_DIRICHLETBC_H

28
#include "AMDiS_fwd.h"
29
30
#include "BoundaryCondition.h"
#include "AbstractFunction.h"
31
#include "FixVec.h"
32

33
namespace AMDiS
34
{
35

36
37
38
39
  // some tags used for tag-dispatching
  struct _value_by_abstractfunction {};
  struct _value_by_dofvector {};
  struct _value_by_function {};
40
41

  namespace detail
42
  {
43
44
45
    class DirichletBC : public BoundaryCondition
    {
    public:
46

47
48
49
50
51
      /// Constructor.
      DirichletBC(BoundaryType type,
		  const FiniteElemSpace *rowFeSpace,
		  const FiniteElemSpace *colFeSpace,
		  bool apply)
52
53
	: BoundaryCondition(type, rowFeSpace, colFeSpace),
	  applyBC(apply)
54
55
56
57
58
59
60
61
62
63
64
65
66
      { }

      /// Implementation of BoundaryCondition::fillBoundaryCondition().
      virtual void fillBoundaryCondition(DOFMatrix* matrix,
				ElInfo* elInfo,
				const DegreeOfFreedom* dofIndices,
				const BoundaryType* localBound,
				int nBasFcts) override;

      ///
      void initVector(DOFVectorBase<double>* vec);

      /// Implementation of BoundaryCondition::boundResidual().
67
      double boundResidual(ElInfo*,
68
			  DOFMatrix *,
69
70
71
			  const DOFVectorBase<double>*)
      {
	return 0.0;
72
73
74
      }

      /// Because this is a Dirichlet boundary condition, always return true.
75
76
77
      bool isDirichlet()
      {
	return true;
78
79
80
      }

      /// Returns \ref applyBC.
81
      bool applyBoundaryCondition()
82
83
84
85
86
87
88
89
90
91
      {
	return applyBC;
      }

    protected:

      /// Defines, if the boundary condition must be applied to the matrix. See
      /// comment of \ref BoundaryCondition::applyBoundaryCondition.
      bool applyBC;
    };
92

93
94
95
96
  } // end namespace detail



97

98
99
100
101
102
103
104
105
106
107
108
    /**
    * \ingroup Assembler
    *
    * \brief
    * Sub class of BoundaryCondition. Implements Dirichlet boundary conditions.
    * A DOFVectors is set to a given value at a Dirichlet dof and in a DOFMatrix
    * the row corresponding to a Dirichlet dof is replaced by a row containing
    * only a 1.0 in the diagonal.
    */
    template <class ValueTag>
    class DirichletBC {};
109

110
    // specialization for AbstractFunctions as value container
111
    template <>
112
    class DirichletBC<_value_by_abstractfunction> : public detail::DirichletBC
113
    {
114
115
116
117
118
119
120
121
122
123
124
      typedef detail::DirichletBC super;
    public:
      /// Constructor.
      DirichletBC(BoundaryType type,
		  AbstractFunction<double, WorldVector<double> > *fct,
		  const FiniteElemSpace *rowFeSpace,
		  const FiniteElemSpace *colFeSpace = NULL,
		  bool apply = true)
	: super(type, rowFeSpace, colFeSpace, apply),
	  container(*fct)
      { }
125
126


127
      /// Implementation of BoundaryCondition::fillBoundaryCondition().
128
      virtual void fillBoundaryCondition(DOFVectorBase<double>* vector,
129
130
131
132
				ElInfo* elInfo,
				const DegreeOfFreedom* dofIndices,
				const BoundaryType* localBound,
				int nBasFcts) override;
133

134
135
    protected:
      AbstractFunction<double, WorldVector<double> > &container;
136
    };
137
138


139
    // specialization for DOFVectors as value container
140
    template <>
141
    class DirichletBC<_value_by_dofvector> : public detail::DirichletBC
142
    {
143
144
145
146
147
148
      typedef detail::DirichletBC super;
    public:
      /// Constructor.
      DirichletBC(BoundaryType type,
		  DOFVectorBase<double> *vec,
		  bool apply = true);
149
150


151
      /// Implementation of BoundaryCondition::fillBoundaryCondition().
152
      virtual void fillBoundaryCondition(DOFVectorBase<double>* vector,
153
154
155
156
				ElInfo* elInfo,
				const DegreeOfFreedom* dofIndices,
				const BoundaryType* localBound,
				int nBasFcts) override;
157

158
159
    protected:
      DOFVectorBase<double> *container;
160
    };
161
162


163
#if AMDIS_HAS_CXX11
164
    // specialization for std::function or lambdas as value container
165
    template <>
166
    class DirichletBC<_value_by_function> : public detail::DirichletBC
167
    {
168
169
170
171
172
173
174
175
176
177
178
      typedef detail::DirichletBC super;
    public:
      /// Constructor.
      DirichletBC(BoundaryType type,
		  std::function<double(WorldVector<double>)> fct,
		  const FiniteElemSpace *rowFeSpace,
		  const FiniteElemSpace *colFeSpace = NULL,
		  bool apply = true)
	: super(type, rowFeSpace, colFeSpace, apply),
	  container(fct)
      { }
179
180


181
      /// Implementation of BoundaryCondition::fillBoundaryCondition().
182
      virtual void fillBoundaryCondition(DOFVectorBase<double>* vector,
183
184
185
186
				ElInfo* elInfo,
				const DegreeOfFreedom* dofIndices,
				const BoundaryType* localBound,
				int nBasFcts) override;
187

188
189
    protected:
      std::function<double(WorldVector<double>)> container;
190
191
    };
#endif
192
193
194
}

#endif