DofComm.h 6.03 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
// ============================================================================
// ==                                                                        ==
// == AMDiS - Adaptive multidimensional simulations                          ==
// ==                                                                        ==
// ==  http://www.amdis-fem.org                                              ==
// ==                                                                        ==
// ============================================================================
//
// Software License for AMDiS
//
// Copyright (c) 2010 Dresden University of Technology 
// All rights reserved.
// Authors: Simon Vey, Thomas Witkowski et al.
//
// This file is part of AMDiS
//
// See also license.opensource.txt in the distribution.



/** \file DofComm.h */

#ifndef AMDIS_DOF_COMM_H
#define AMDIS_DOF_COMM_H

#include <map>
27
#include "parallel/ParallelTypes.h"
28
29
30
31
32
33
34
35
36
37
#include "FiniteElemSpace.h"
#include "Global.h"

namespace AMDiS {

  using namespace std;

  class DofComm
  {
  public:
38
    DofComm() 
39
40
      : recvDofs(1),
	sendDofs(1),
41
42
43
44
	periodicDofs(0),
	meshLevel(-1),
	nLevel(0),
	levelData(NULL)
45
    {}
46
47
48
    
    typedef map<const FiniteElemSpace*, DofContainer> FeMapType;
    typedef FeMapType::iterator FeMapIter;
49
    typedef map<int, FeMapType> DataType;
50
    typedef DataType::iterator DataIter;
51
52
    // meshLevel: map[rank -> map[feSpace -> DofContainer]]
    typedef vector<DataType> LevelDataType;
53

54
55
56
    void init(int level, 
	      MeshLevelData &levelData, 
	      vector<const FiniteElemSpace*> &fe);
57
58
59
60
61
62
63
64
65
66
67

    void create(InteriorBoundary &boundary);

    LevelDataType& getSendDofs()
    {
      return sendDofs;
    }

    LevelDataType& getRecvDofs()
    {
      return recvDofs;
68
69
    }

70
    LevelDataType& getPeriodicDofs()
71
    {
72
      return periodicDofs;
73
74
    }

75
    // Writes all data of this object to an output stream.
Thomas Witkowski's avatar
Thomas Witkowski committed
76
    void serialize(ostream &out);
77

78
79
    // Reads the object data from an input stream.
    void deserialize(istream &in, 
Thomas Witkowski's avatar
Thomas Witkowski committed
80
		     map<const FiniteElemSpace*, map<int, const DegreeOfFreedom*> > dofIndexMap);
81
82
83

    int getNumberDofs(LevelDataType &data, 
		      int level, 
Thomas Witkowski's avatar
Blub    
Thomas Witkowski committed
84
85
		      const FiniteElemSpace *feSpace,
		      bool countDouble = false);
86
87
88

  protected:
    void createContainer(RankToBoundMap &boundary, LevelDataType &data);
89

Thomas Witkowski's avatar
Thomas Witkowski committed
90
91
92
93
94
95
    void serialize(LevelDataType &data, ostream &out);

    void deserialize(LevelDataType &data,
		     istream &in, 
		     map<const FiniteElemSpace*, map<int, const DegreeOfFreedom*> > dofIndexMap);

96
  protected:
97
98
99
100
101
102
103
104
105
106
107
108
109
110
    /// This map contains for each rank the list of DOFs the current rank must 
    /// end to exchange solution DOFs at the interior boundaries.
    LevelDataType sendDofs;

    /// This map contains on each rank the list of DOFs from which the current 
    /// rank will receive DOF values (i.e., this are all DOFs at an interior 
    /// boundary). The DOF indices are given in rank's local numbering.
    LevelDataType recvDofs;

    /// This map contains on each rank a list of DOFs along the interior bound-
    /// aries to communicate with other ranks. The DOF indices are given in rank's
    /// local numbering. Periodic boundaries within one subdomain are not 
    /// considered here. 
    LevelDataType periodicDofs;
111

112
113
    int meshLevel;

114
115
    int nLevel;

116
117
    MeshLevelData *levelData;

118
119
    vector<const FiniteElemSpace*> feSpaces;

120
121
122
123
124
125
    friend class Iterator;

  public:
    class Iterator
    {
    public:
126
      Iterator(LevelDataType &d,
127
	       const FiniteElemSpace *fe = NULL)
128
	: data(d),
129
	  dofCounter(-1),
130
	  traverseFeSpace(fe),
131
132
	  traverseLevel(0),
	  removedDof(false)
133
      {
134
135
	goFirst();
      }
136

137
      Iterator(LevelDataType &d,
138
139
	       int level,
	       const FiniteElemSpace *fe = NULL)
140
	: data(d),
141
142
	  dofCounter(-1),
	  traverseFeSpace(fe),
143
144
	  traverseLevel(level),
	  removedDof(false)
145
146
      {
	goFirst();
147
148
149
150
      }

      inline bool end()
      {
151
	return (dataIter == data[traverseLevel].end());
152
153
154
155
      }
      
      inline void nextRank()
      {
156
157
158
	do {
	  ++dataIter;
	} while (setNextFeMap() == false);
159
160
161
162
163
164
165
      }

      inline void nextFeSpace()
      {
	++feMapIter;
      }

166
167
168
169
      inline void next()
      {
	++feMapIter;
	if (feMapIter == dataIter->second.end()) {
170
171
172
	  do {
	    ++dataIter;
	  } while (setNextFeMap() == false);
173
174
175
176
177
178
	} else {
	  dofIter = feMapIter->second.begin();
	  dofCounter = 0;
	}
      }

179
180
181
182
183
184
185
186
187
188
189
190
      inline void beginDofIter(const FiniteElemSpace *fe = NULL)
      {
	FUNCNAME("DofComm::Iterator::beginDofIter()");

	if (fe != NULL) {
	  feMapIter = dataIter->second.begin();

	  while (feMapIter->first != fe &&
		 feMapIter != dataIter->second.end())
	    ++feMapIter;
	}

191
192
193
194
	if (feMapIter != dataIter->second.end()) {
	  dofIter = feMapIter->second.begin();
	  dofCounter = 0;
	}
195
196
197
198
      }

      inline bool endDofIter()
      {
199
200
201
	if (feMapIter == dataIter->second.end())
	  return true;

202
203
204
205
206
	return (dofIter == feMapIter->second.end());
      }
      
      inline void nextDof()
      {
207
208
209
210
211
212
213
214
215
216
217
218
	if (removedDof) {
	  removedDof = false;
	} else {
	  ++dofIter;
	  ++dofCounter;
	}
      }

      inline void removeDof()
      {
	dofIter = feMapIter->second.erase(dofIter);
	removedDof = true;
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
      }

      inline int getRank()
      {
	return dataIter->first;
      }

      inline const FiniteElemSpace* getFeSpace()
      {
	return feMapIter->first;
      }

      inline DofContainer& getDofs()
      {
	return feMapIter->second;
      }

      inline const DegreeOfFreedom* getDof()
      {
	return *dofIter;
      }

      inline DegreeOfFreedom getDofIndex()
      {
	return **dofIter;
      }

      inline int getDofCounter()
      {
	return dofCounter;
      }

    protected:
252
253
      void goFirst()
      {
254
	dataIter = data[traverseLevel].begin();
255
256
257
258
259

	while (setNextFeMap() == false)
	  ++dataIter;
      }

260
      bool setNextFeMap();
261
262

    protected:
263
      LevelDataType &data;
264
265
266
267
268
269
270
271
272
273
      
      DofComm::DataIter dataIter;
      
      DofComm::FeMapIter feMapIter;

      DofContainer::iterator dofIter;

      int dofCounter;

      const FiniteElemSpace *traverseFeSpace;
274
275

      int traverseLevel;
276
277

      bool removedDof;
278
279
280
281
282
283
284
285
    };


  };

}

#endif // AMDIS_DOF_COMM_H