source: src/grid/multigrid.cpp@ 6e10f33

Last change on this file since 6e10f33 was 6e10f33, checked in by Julian Iseringhausen <isering@…>, 13 years ago

Some work...

  • Property mode set to 100644
File size: 8.0 KB
Line 
1/*
2 * vmg - a versatile multigrid solver
3 * Copyright (C) 2012 Institute for Numerical Simulation, University of Bonn
4 *
5 * vmg is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * (at your option) any later version.
9 *
10 * vmg is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
17 */
18
19/**
20 * @file multigrid.cpp
21 * @author Julian Iseringhausen <isering@ins.uni-bonn.de>
22 * @date Mon Apr 18 12:54:37 2011
23 *
24 * @brief VMG::Multigrid
25 *
26 */
27
28#ifdef HAVE_CONFIG_H
29#include <config.h>
30#endif
31
32#include <iostream>
33
34#include "base/helper.hpp"
35#include "base/index.hpp"
36#include "base/interface.hpp"
37#include "comm/comm.hpp"
38#include "comm/domain_decomposition.hpp"
39#include "grid/grid.hpp"
40#include "grid/grid_properties.hpp"
41#include "grid/multigrid.hpp"
42
43using namespace VMG;
44
45Multigrid::Multigrid(Comm* comm, const Interface* interface)
46{
47 Index points, remainder;
48 LocalIndices local_l;
49 std::vector<GlobalIndices> global_separated;
50
51 const std::vector<GlobalIndices>& global = interface->Global();
52 const std::vector<SpatialExtent>& extent = interface->Extent();
53
54 comm->GetDomainDecomposition().Compute(comm, interface, global_separated);
55
56 for (unsigned int i=0; i<global.size(); ++i) {
57
58 /*
59 * Check if this level is the finest global level
60 */
61 if (global[i].BoundaryType() == GlobalMax)
62 levelGlobalMax = interface->MaxLevel() - i;
63
64
65 if (global_separated[i].LocalSize().Product() > 0) {
66
67 /*
68 * Initialize some properties with zero
69 */
70 local_l.HaloBegin1() = 0;
71 local_l.HaloEnd1() = 0;
72 local_l.HaloBegin2() = 0;
73 local_l.HaloEnd2() = 0;
74 local_l.BoundaryBegin1() = 0;
75 local_l.BoundaryEnd1() = 0;
76 local_l.BoundaryBegin2() = 0;
77 local_l.BoundaryEnd2() = 0;
78
79 /*
80 * Set boundary dependant properties
81 */
82 for (int j=0; j<3; ++j) {
83
84 if (comm->BoundaryConditions()[j] == Dirichlet ||
85 comm->BoundaryConditions()[j] == Open) {
86
87 local_l.SizeTotal()[j] = global_separated[i].LocalSize()[j];
88
89 /*
90 * We have a boundary at the ends of the process grids
91 * and halo grid points otherwise
92 */
93 if (global_separated[i].LocalBegin()[j] == global_separated[i].GlobalBegin()[j]) {
94 local_l.BoundaryBegin1()[j] = 0;
95 local_l.BoundaryEnd1()[j] = 1;
96 }else {
97 ++local_l.SizeTotal()[j];
98 local_l.HaloBegin1()[j] = 0;
99 local_l.HaloEnd1()[j] = 1;
100 }
101
102 if (global_separated[i].LocalEnd()[j] == global_separated[i].GlobalEnd()[j]) {
103 local_l.BoundaryBegin2()[j] = local_l.SizeTotal()[j] - 1;
104 local_l.BoundaryEnd2()[j] = local_l.SizeTotal()[j];
105 }else {
106 ++local_l.SizeTotal()[j];
107 local_l.HaloBegin2()[j] = local_l.SizeTotal()[j] - 1;
108 local_l.HaloEnd2()[j] = local_l.SizeTotal()[j];
109 }
110
111 }else if (comm->BoundaryConditions()[j] == Periodic) {
112
113 local_l.SizeTotal()[j] = global_separated[i].LocalSize()[j] + 2;
114
115 /*
116 * No boundary
117 */
118 local_l.BoundaryBegin1()[j] = local_l.BoundaryEnd1()[j] = 0;
119 local_l.BoundaryBegin2()[j] = local_l.BoundaryEnd2()[j] = 0;
120
121 /*
122 * Halo grid points on all processes
123 */
124 local_l.HaloBegin1()[j] = 0;
125 local_l.HaloEnd1()[j] = 1;
126 local_l.HaloBegin2()[j] = local_l.SizeTotal()[j] - 1;
127 local_l.HaloEnd2()[j] = local_l.SizeTotal()[j];
128
129 }
130
131 }
132
133 local_l.Begin() = 1;
134 local_l.End() = local_l.SizeTotal() - 1;
135
136 local_l.Size() = local_l.End() - local_l.Begin();
137 local_l.HaloSize1() = local_l.HaloEnd1() - local_l.HaloBegin1();
138 local_l.HaloSize2() = local_l.HaloEnd2() - local_l.HaloBegin2();
139 local_l.BoundarySize1() = local_l.BoundaryEnd1() - local_l.BoundaryBegin1();
140 local_l.BoundarySize2() = local_l.BoundaryEnd2() - local_l.BoundaryBegin2();
141
142 }else {
143
144 local_l.Begin() = 0;
145 local_l.End() = 0;
146 local_l.Size() = 0;
147 local_l.SizeTotal() = 0;
148 local_l.HaloBegin1() = 0;
149 local_l.HaloEnd1() = 0;
150 local_l.HaloSize1() = 0;
151 local_l.HaloBegin2() = 0;
152 local_l.HaloEnd2() = 0;
153 local_l.HaloSize2() = 0;
154 local_l.BoundaryBegin1() = 0;
155 local_l.BoundaryEnd1() = 0;
156 local_l.BoundarySize1() = 0;
157 local_l.BoundaryBegin2() = 0;
158 local_l.BoundaryEnd2() = 0;
159 local_l.BoundarySize2() = 0;
160
161 }
162
163 grids.push_back(new Grid(global_separated[i], local_l, extent[i], interface->MaxLevel()-i, this));
164
165 }
166
167 numLevels = grids.size();
168
169 levelMax = interface->MaxLevel();
170 levelMin = levelMax - numLevels + 1;
171
172 levelIndex = 0;
173 levelCurrent = levelMax;
174
175}
176
177void Multigrid::SetLevel(int level)
178{
179 assert(level >= levelMin && level <= levelMax);
180 levelCurrent = level;
181 levelIndex = levelMax - level;
182}
183
184void Multigrid::ToCoarserLevel()
185{
186 assert(levelCurrent-1 >= levelMin);
187 --levelCurrent;
188 ++levelIndex;
189}
190
191void Multigrid::ToFinerLevel()
192{
193 assert(levelCurrent+1 <= levelMax);
194 ++levelCurrent;
195 --levelIndex;
196}
197
198void Multigrid::ClearAll()
199{
200 for (int i=MinLevel(); i<=MaxLevel(); ++i)
201 (*this)(i).Clear();
202}
203
204// TODO: diff that in case that breaks QP
205void Multigrid::ClearAllCoarseLevels()
206{
207 for (int i=MinLevel(); i<MaxLevel(); ++i)
208 (*this)(i).Clear();
209}
210
211
212void Multigrid::SetCoarserDirichletValues()
213{
214 Index i_c, i_f;
215
216 for (int i=GlobalMaxLevel(); i>MinLevel(); --i) {
217
218 Grid& grid_f = (*this)(i);
219 Grid& grid_c = (*this)(i-1);
220
221 i_c.X() = grid_c.Local().BoundaryBegin1().X();
222 i_f.X() = grid_f.Local().BoundaryBegin1().X();
223 for (i_c.Y()=grid_c.Local().Begin().Y(); i_c.Y()<grid_c.Local().End().Y(); ++i_c.Y())
224 for (i_c.Z()=grid_c.Local().Begin().Z(); i_c.Z()<grid_c.Local().End().Z(); ++i_c.Z())
225 grid_c(i_c) = grid_f.GetVal(i_f.X(), 2*i_c.Y(), 2*i_c.Z());
226
227 i_c.X() = grid_c.Local().BoundaryBegin2().X();
228 i_f.X() = grid_f.Local().BoundaryBegin2().X();
229 for (i_c.Y()=grid_c.Local().Begin().Y(); i_c.Y()<grid_c.Local().End().Y(); ++i_c.Y())
230 for (i_c.Z()=grid_c.Local().Begin().Z(); i_c.Z()<grid_c.Local().End().Z(); ++i_c.Z())
231 grid_c(i_c) = grid_f.GetVal(i_f.X(), 2*i_c.Y(), 2*i_c.Z());
232
233 i_c.Y() = grid_c.Local().BoundaryBegin1().Y();
234 i_f.Y() = grid_f.Local().BoundaryBegin1().Y();
235 for (i_c.X()=0; i_c.X()<grid_c.Local().SizeTotal().X(); ++i_c.X())
236 for (i_c.Z()=grid_c.Local().Begin().Z(); i_c.Z()<grid_c.Local().End().Z(); ++i_c.Z())
237 grid_c(i_c) = grid_f.GetVal(2*i_c.X(), i_f.Y(), 2*i_c.Z());
238
239 i_c.Y() = grid_c.Local().BoundaryBegin2().Y();
240 i_f.Y() = grid_f.Local().BoundaryBegin2().Y();
241 for (i_c.X()=0; i_c.X()<grid_c.Local().SizeTotal().X(); ++i_c.X())
242 for (i_c.Z()=grid_c.Local().Begin().Z(); i_c.Z()<grid_c.Local().End().Z(); ++i_c.Z())
243 grid_c(i_c) = grid_f.GetVal(2*i_c.X(), i_f.Y(), 2*i_c.Z());
244
245 i_c.Z() = grid_c.Local().BoundaryBegin1().Z();
246 i_f.Z() = grid_f.Local().BoundaryBegin1().Z();
247 for (i_c.X()=0; i_c.X()<grid_c.Local().SizeTotal().X(); ++i_c.X())
248 for (i_c.Y()=0; i_c.Y()<grid_c.Local().SizeTotal().Y(); ++i_c.Y())
249 grid_c(i_c) = grid_f.GetVal(2*i_c.X(), 2*i_c.Y(), i_f.Z());
250
251 i_c.Z() = grid_c.Local().BoundaryBegin2().Z();
252 i_f.Z() = grid_f.Local().BoundaryBegin2().Z();
253 for (i_c.X()=0; i_c.X()<grid_c.Local().SizeTotal().X(); ++i_c.X())
254 for (i_c.Y()=0; i_c.Y()<grid_c.Local().SizeTotal().Y(); ++i_c.Y())
255 grid_c(i_c) = grid_f.GetVal(2*i_c.X(), 2*i_c.Y(), i_f.Z());
256
257 }
258}
259
260Multigrid::~Multigrid()
261{
262 for (unsigned int i=0; i<grids.size(); ++i)
263 delete grids[i];
264}
Note: See TracBrowser for help on using the repository browser.