DOFVector.hpp 4.58 KB
Newer Older
1
2
#pragma once

3
#include <algorithm>
4
#include <memory>
5
#include <string>
6

7
8
#include <dune/common/reservedvector.hh>
#include <dune/functions/functionspacebases/flatmultiindex.hh>
9
10
#include <dune/functions/functionspacebases/interpolate.hh>

11
12
13
14
15
#include <amdis/Output.hpp>
#include <amdis/common/ClonablePtr.hpp>
#include <amdis/common/ScalarTypes.hpp>
#include <amdis/linear_algebra/mtl/MTLDenseVector.hpp>
#include <amdis/utility/MultiIndex.hpp>
16
17
18

namespace AMDiS
{
19
  /// The basic container that stores a base vector and a corresponding feSpace
20
  template <class Traits, class ValueType = double>
21
22
23
  class DOFVector
  {
    using Self = DOFVector;
24

25
  public:
26
    /// The type of the \ref feSpace
27
    using GlobalBasis = typename Traits::GlobalBasis;
28

29
    /// The type of the base vector
30
    using BaseVector = MTLDenseVector<ValueType>;
31

32
    /// The index/size - type
33
    using size_type  = typename GlobalBasis::size_type;
34

35
    /// The type of the elements of the DOFVector
36
    using value_type = ValueType;
37

38
    /// The underlying field-type (typically the same as \ref value_type)
39
    using field_type = typename BaseVector::value_type;
40

41
    /// Constructor. Constructs new BaseVector.
42
    DOFVector(GlobalBasis const& feSpace, std::string name)
43
44
45
46
47
48
      : feSpace(feSpace)
      , name(name)
      , vector(ClonablePtr<BaseVector>::make())
    {
      compress();
    }
49

50
    /// Constructor. Takes reference to existing BaseVector
51
    DOFVector(GlobalBasis const& feSpace, std::string name,
52
53
54
55
56
              BaseVector& vector_ref)
      : feSpace(feSpace)
      , name(name)
      , vector(vector_ref)
    {}
57

58
    /// Return the basis \ref feSpace of the vector
59
    GlobalBasis const& getFeSpace() const
60
61
62
    {
        return feSpace;
    }
63

64
65
66
67
68
    /// Return the data-vector \ref vector
    BaseVector const& getVector() const
    {
      return *vector;
    }
69

70
71
72
73
74
    /// Return the data-vector \ref vector
    BaseVector& getVector()
    {
      return *vector;
    }
75

76
77
78
    /// Return the size of the \ref feSpace
    size_type getSize() const
    {
79
      return feSpace.dimension();
80
    }
81

82
83
84
85
86
    /// Return the \ref name of this vector
    std::string getName() const
    {
      return name;
    }
87

88
89
90
    /// Resize the \ref vector to the size of the \ref feSpace.
    void compress()
    {
91
      if (num_rows(*vector) != getSize()) {
92
        resize(getSize());
93
94
        *vector = ValueType(0);
      }
95
    }
96

97
98
    template <class SizeInfo>
    void resize(SizeInfo s)
99
    {
100
      vector->change_dim(size_type(s));
101
    }
102

103

104
105
106
    /// Access the entry \p i of the \ref vector with read-access.
    template <class Index>
    value_type const& operator[](Index idx) const
107
    {
108
      auto const i = flatMultiIndex(idx);
109
110
111
112
113
      test_exit_dbg( i < num_rows(*vector) ,
        "Index ", i, " out of range [0,", num_rows(*vector), ")" );
      return (*vector)[i];
    }

114
115
116
    /// Access the entry \p i of the \ref vector with write-access.
    template <class Index>
    value_type& operator[](Index idx)
117
    {
118
      auto const i = flatMultiIndex(idx);
119
120
121
122
123
      test_exit_dbg( i < num_rows(*vector) ,
        "Index ", i, " out of range [0,", num_rows(*vector), ")" );
      return (*vector)[i];
    }

124
    /// \brief interpolate a function \p f to the basis \ref feSpace and store the
125
126
    /// coefficients in \ref vector.
    template <class F>
127
    void interpol(F&& f)
128
    {
129
      Dune::Functions::interpolate(feSpace, *this, std::forward<F>(f));
130
    }
131

132
133
    /// Scale each DOFVector by the factor \p s.
    template <class Scalar>
134
    std::enable_if_t< Concepts::Arithmetic<Scalar>, Self&>
135
136
137
138
139
    operator*=(Scalar s)
    {
      (*vector) *= s;
      return *this;
    }
140

141
142
    /// Sets each DOFVector to the scalar \p s.
    template <class Scalar>
143
    std::enable_if_t< Concepts::Arithmetic<Scalar>, Self&>
144
145
146
147
148
    operator=(Scalar s)
    {
      (*vector) = s;
      return *this;
    }
149

150
151
152
153
154
    /// Calls the copy assignment operator of the BaseVector \ref vector
    void copy(Self const& that)
    {
      *vector = that.getVector();
    }
155

156
  private:
157
    /// The finite element space / basis associated with the data vector
158
    GlobalBasis const& feSpace;
159

160
    /// The name of the DOFVector (used in file-writing)
161
    std::string	name;
162

163
    /// The data-vector (can hold a new BaseVector or a pointer to external data
164
    ClonablePtr<BaseVector> vector;
165

166
167
168
    // friend class declarations
    template <class, class> friend class SystemVector;
  };
169
170


171
  /// Constructor a dofvector from given feSpace and name
172
173
174
  template <class Traits, class ValueType = double>
  DOFVector<Traits, ValueType>
  makeDOFVector(typename Traits::GlobalBasis const& basis, std::string name)
175
  {
176
    return {basis, name};
177
  }
178
179

} // end namespace AMDiS