1 /*---------------------------------------------------------------------------*\
3 \\ / F ield | foam-extend: Open Source CFD
4 \\ / O peration | Version: 3.2
5 \\ / A nd | Web: http://www.foam-extend.org
6 \\/ M anipulation | For copyright notice see file Copyright
7 -------------------------------------------------------------------------------
9 This file is part of foam-extend.
11 foam-extend is free software: you can redistribute it and/or modify it
12 under the terms of the GNU General Public License as published by the
13 Free Software Foundation, either version 3 of the License, or (at your
14 option) any later version.
16 foam-extend is distributed in the hope that it will be useful, but
17 WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 General Public License for more details.
21 You should have received a copy of the GNU General Public License
22 along with foam-extend. If not, see <http://www.gnu.org/licenses/>.
28 Algebraic multigrid cycle class
31 Hrvoje Jasak, Wikki Ltd. All rights reserved
33 \*---------------------------------------------------------------------------*/
36 #include "demandDrivenData.H"
38 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
41 const char* Foam::NamedEnum<Foam::amgCycle::cycleType, 3>::names[] =
49 const Foam::NamedEnum<Foam::amgCycle::cycleType, 3>
50 Foam::amgCycle::cycleNames_;
53 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
55 // Construct from AMG level
56 Foam::amgCycle::amgCycle(autoPtr<amgLevel> levelPtr)
59 coarseLevelPtr_(NULL),
64 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
66 Foam::amgCycle::~amgCycle()
68 deleteDemandDrivenData(coarseLevelPtr_);
72 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
74 void Foam::amgCycle::makeCoarseLevels(const label nMaxLevels)
79 bool addCoarse = true;
80 amgCycle* curCyclePtr = this;
87 autoPtr<amgLevel> coarsePtr =
88 curCyclePtr->levelPtr_->makeNextLevel();
90 // Check if a coarse level is valid and allowed
91 if (nLevels_ >= nMaxLevels || !coarsePtr.valid())
96 reduce(addCoarse, andOp<bool>());
100 curCyclePtr->coarseLevelPtr_ = new amgCycle(coarsePtr);
102 // Point to the next coarse level
103 curCyclePtr = curCyclePtr->coarseLevelPtr_;
111 if (lduMatrix::debug >= 2)
113 Info<< "Created " << nLevels_ << " AMG levels" << endl;
119 void Foam::amgCycle::fixedCycle
122 const scalarField& b,
123 const direction cmpt,
124 scalarField& xBuffer,
125 const cycleType cycle,
126 const label nPreSweeps,
127 const label nPostSweeps,
134 levelPtr_->smooth(x, b, cmpt, nPreSweeps);
136 // Get reference to coarse level
137 scalarField& xCoarse = coarseLevelPtr_->levelPtr_->x();
138 scalarField& bCoarse = coarseLevelPtr_->levelPtr_->b();
143 // Restrict residual: optimisation on number of pre-sweeps
144 levelPtr_->restrictResidual
151 nPreSweeps > 0 || cycle != V_CYCLE
154 coarseLevelPtr_->fixedCycle
166 if (cycle == F_CYCLE)
168 coarseLevelPtr_->fixedCycle
180 else if (cycle == W_CYCLE)
182 coarseLevelPtr_->fixedCycle
197 // Calculate scaling factor using a buffer
199 coarseLevelPtr_->levelPtr_->scaleX
208 levelPtr_->prolongateCorrection(x, xCoarse);
211 levelPtr_->smooth(x, b, cmpt, nPostSweeps);
215 // Call direct solver
216 // Changed tolerance because a better guess will be used on coarsest
217 // mesh level. HJ, 27/Jun/2013
218 levelPtr_->solve(x, b, cmpt, 1e-6, 0);
223 // ************************************************************************* //