Esempio n. 1
0
        public void ComputeHeatFlux()
        {
            using (FuncTrace ft = new FuncTrace()) {
                int D = this.LsTrk.GridDat.SpatialDimension;
                for (int d = 0; d < D; d++)
                {
                    this.HeatFlux[d].Clear();

                    foreach (var Spc in LsTrk.SpeciesNames)   // loop over species...
                                                              // shadow fields
                    {
                        DGField Temp_Spc = (this.Temperature.GetSpeciesShadowField(Spc));

                        double kSpc = 0.0;
                        switch (Spc)
                        {
                        case "A": kSpc = -this.Control.ThermalParameters.k_A; break;

                        case "B": kSpc = -this.Control.ThermalParameters.k_B; break;

                        default: throw new NotSupportedException("Unknown species name '" + Spc + "'");
                        }

                        this.HeatFlux[d].GetSpeciesShadowField(Spc).DerivativeByFlux(kSpc, Temp_Spc, d, this.LsTrk.Regions.GetSpeciesSubGrid(Spc));
                    }
                }

                this.HeatFlux.ForEach(F => F.CheckForNanOrInf(true, true, true));
            }
        }
Esempio n. 2
0
        /// <summary>
        /// Includes assembly of the matrix.
        /// </summary>
        /// <param name="L"></param>
        protected override void CreateEquationsAndSolvers(GridUpdateDataVaultBase L) {
            using (FuncTrace tr = new FuncTrace()) {

                // create operator
                // ===============
                {
                    double D = this.GridData.SpatialDimension;
                    double penalty_base = (T.Basis.Degree + 1) * (T.Basis.Degree + D) / D;
                    double penalty_factor = base.Control.penalty_poisson;

                    BoundaryCondMap<BoundaryType> PoissonBcMap = new BoundaryCondMap<BoundaryType>(this.GridData, this.Control.BoundaryValues, "T");

                    LapaceIp = new SpatialOperator(1, 1, QuadOrderFunc.SumOfMaxDegrees(), "T", "T");
                    var flux = new ipFlux(penalty_base * base.Control.penalty_poisson, ((GridData)(this.GridData)).Cells.cj, PoissonBcMap);

                    LapaceIp.EquationComponents["T"].Add(flux);

                    LapaceIp.Commit();
                }



                //double condNo = LaplaceMtx.condest(BatchmodeConnector.Flavor.Octave);
                //Console.WriteLine("condition number: {0:0.####E-00} ",condNo);

            }
        }
        /// <summary>
        /// Loads a time-step from the database.
        /// </summary>
        /// <remarks>
        /// By using this method, it is ensured that the loaded/returned fields
        /// have the same DG polynomial degree as in the database.
        /// </remarks>
        public IEnumerable <DGField> LoadFields(ITimestepInfo info, IGridData grdDat, IEnumerable <string> NameFilter = null)
        {
            using (var tr = new FuncTrace())
            {
                // check
                // =====
                if (!info.Grid.ID.Equals(grdDat.GridID))
                {
                    throw new ArgumentException("Mismatch in Grid.");
                }

                // Instantiate
                // ==========
                IEnumerable <DGField.FieldInitializer> F2LoadInfo;
                if (NameFilter != null)
                {
                    F2LoadInfo = info.FieldInitializers.Where(fi => NameFilter.Contains(fi.Identification, (a, b) => a.Equals(b)));
                }
                else
                {
                    F2LoadInfo = info.FieldInitializers;
                }

                IInitializationContext ic      = info.Database.Controller.GetInitializationContext(info);
                var            fields          = F2LoadInfo.Select(fi => fi.Initialize(ic)).ToArray();
                List <DGField> fieldsFlattened = new List <DGField>();
                TimestepInfo.FlattenHierarchy(fieldsFlattened, fields);

                this.LoadFieldData(info, grdDat, fieldsFlattened);

                return(fieldsFlattened);
            }
        }
Esempio n. 4
0
        /// <summary>
        /// accumulates the derivative of DG field <paramref name="f"/>
        /// (along the <paramref name="d"/>-th axis) times <paramref name="alpha"/>
        /// to this field, i.e. <br/>
        /// this = this + <paramref name="alpha"/>* \f$ \frac{\partial}{\partial x_d} \f$ <paramref name="f"/>;
        /// </summary>
        /// <param name="f"></param>
        /// <param name="d">
        /// 0 for the x-derivative, 1 for the y-derivative, 2 for the z-derivative
        /// </param>
        /// <param name="alpha">
        /// scaling of <paramref name="f"/>;
        /// </param>
        /// <param name="em">
        /// An optional restriction to the domain in which the derivative is computed (it may, e.g.
        /// be only required in boundary cells, so a computation over the whole domain
        /// would be a waste of computation power. A proper execution mask for this case would be e.g.
        /// <see cref="BoSSS.Foundation.Grid.GridData.BoundaryCells"/>.)<br/>
        /// if null, the computation is carried out in the whole domain
        /// </param>
        override public void Derivative(double alpha, DGField f, int d, CellMask em)
        {
            using (var tr = new FuncTrace()) {
                MPICollectiveWatchDog.Watch(csMPI.Raw._COMM.WORLD);

                if (this.Basis.Degree < f.Basis.Degree - 1)
                {
                    throw new ArgumentException("cannot compute derivative because of incompatible basis functions.", "f");
                }
                if (f.Basis.GetType() != this.Basis.GetType())
                {
                    throw new ArgumentException("cannot compute derivative because of incompatible basis functions.", "f");
                }



                int D = GridDat.SpatialDimension;
                if (d < 0 || d >= D)
                {
                    throw new ArgumentException("spatial dimension out of range.", "d");
                }

                Quadrature.EdgeQuadratureScheme _qInsEdge;
                Quadrature.CellQuadratureScheme _qInsVol;
                {
                    _qInsEdge = (new Quadrature.EdgeQuadratureScheme(false, EdgeMask.GetEmptyMask(this.GridDat)));
                    _qInsVol  = (new Quadrature.CellQuadratureScheme(true, em));
                }

                var op = (new BrokenDerivativeForm(d)).Operator(1, g => _qInsEdge, g => _qInsVol);

                op.Evaluate(alpha, 1.0, f.Mapping, null, this.Mapping);
            }
        }
Esempio n. 5
0
        protected override void CreateEquationsAndSolvers(GridUpdateDataVaultBase L)
        {
            using (FuncTrace tr = new FuncTrace()) {
                // assemble system, create matrix
                // ------------------------------

                var volQrSch = new CellQuadratureScheme(true, CellMask.GetFullMask(this.GridData));
                var edgQrSch = new EdgeQuadratureScheme(true, EdgeMask.GetFullMask(this.GridData));

                double D              = this.GridData.SpatialDimension;
                double penalty_base   = (T.Basis.Degree + 1) * (T.Basis.Degree + D) / D;
                double penalty_factor = base.Control.penalty_poisson;

                {
                    // equation assembly
                    // -----------------
                    tr.Info("creating sparse system...");
                    Console.WriteLine("creating sparse system for {0} DOF's ...", T.Mapping.Ntotal);
                    Stopwatch stw = new Stopwatch();
                    stw.Start();

                    SpatialOperator LapaceIp = new SpatialOperator(1, 1, QuadOrderFunc.SumOfMaxDegrees(), "T", "T");
                    var             flux     = new ipFlux(penalty_base * base.Control.penalty_poisson, this.GridData.Cells.cj, base.Control);
                    LapaceIp.EquationComponents["T"].Add(flux);


                    LapaceIp.Commit();

#if DEBUG
                    var RefLaplaceMtx = new MsrMatrix(T.Mapping);
#endif
                    LaplaceMtx    = new BlockMsrMatrix(T.Mapping);
                    LaplaceAffine = new double[T.Mapping.LocalLength];

                    LapaceIp.ComputeMatrixEx(T.Mapping, null, T.Mapping,
                                             LaplaceMtx, LaplaceAffine,
                                             volQuadScheme: volQrSch, edgeQuadScheme: edgQrSch);
#if DEBUG
                    LaplaceAffine.ClearEntries();
                    LapaceIp.ComputeMatrixEx(T.Mapping, null, T.Mapping,
                                             RefLaplaceMtx, LaplaceAffine,
                                             volQuadScheme: volQrSch, edgeQuadScheme: edgQrSch);
                    MsrMatrix ErrMtx = RefLaplaceMtx.CloneAs();
                    ErrMtx.Acc(-1.0, LaplaceMtx);
                    double err    = ErrMtx.InfNorm();
                    double infNrm = LaplaceMtx.InfNorm();
                    Console.WriteLine("Matrix comparison error: " + err + ", matrix norm is: " + infNrm);
                    Assert.Less(err, infNrm * 1e-10, "MsrMatrix2 comparison failed.");
#endif
                    //int q = LaplaceMtx._GetTotalNoOfNonZeros();
                    //tr.Info("finished: Number of non-zeros: " + q);
                    stw.Stop();
                    Console.WriteLine("done {0} sec.", stw.Elapsed.TotalSeconds);


                    //double condNo = LaplaceMtx.condest(BatchmodeConnector.Flavor.Octave);
                    //Console.WriteLine("condition number: {0:0.####E-00} ",condNo);
                }
            }
        }
Esempio n. 6
0
        /// <summary>
        /// The Infinity-Norm (maximum absolute row sum norm) of this matrix;
        /// </summary>
        /// <returns></returns>
        static public double InfNorm(this IMutableMatrixEx M)
        {
            using (var tr = new FuncTrace()) {
                double normLoc = 0;

                int      L   = M.RowPartitioning.LocalLength;
                int[]    col = null;
                double[] val = null;
                int      Lr;
                for (int i = 0; i < L; i++)
                {
                    double rownrm = 0;
                    Lr = M.GetRow(i + M.RowPartitioning.i0, ref col, ref val);
                    for (int j = 0; j < Lr; j++)
                    {
                        rownrm += Math.Abs(val[j]);
                    }

                    normLoc = Math.Max(normLoc, rownrm);
                }

                //Console.WriteLine("local norm (R=" + M.RowPartitioning.Rank + ") = " + normLoc);
                //tr.Info("local norm " + normLoc);

                double normGlob = double.NaN;
                unsafe {
                    csMPI.Raw.Allreduce((IntPtr)(&normLoc), (IntPtr)(&normGlob), 1, csMPI.Raw._DATATYPE.DOUBLE, csMPI.Raw._OP.MAX, csMPI.Raw._COMM.WORLD);
                }
                return(normGlob);
            }
        }
Esempio n. 7
0
        /// <summary>
        /// Updates the sensor value
        /// <see cref="ShockCapturing.IShockSensor.UpdateSensorValues(CNSFieldSet, ISpeciesMap, CellMask)"/>
        /// and the artificial viscosity value <see cref="Variables.ArtificialViscosity"/> in every cell
        /// </summary>
        /// <param name="program"></param>
        /// <param name="cellMask"></param>
        public void UpdateShockCapturingVariables(IProgram <CNSControl> program, CellMask cellMask)
        {
            using (var tr = new FuncTrace()) {
                // Update sensor
                program.Control.ShockSensor.UpdateSensorValues(program.WorkingSet.AllFields, program.SpeciesMap, cellMask);

                // Update sensor variable (not necessary as only needed for IO)
                using (new BlockTrace("ShockSensor.UpdateFunction", tr)) {
                    var sensorField = program.WorkingSet.DerivedFields[Variables.ShockSensor];
                    Variables.ShockSensor.UpdateFunction(sensorField, program.SpeciesMap.SubGrid.VolumeMask, program);
                }

                // Update artificial viscosity variable
                using (new BlockTrace("ArtificialViscosity.UpdateFunction", tr)) {
                    var avField = program.WorkingSet.DerivedFields[Variables.ArtificialViscosity];
                    Variables.ArtificialViscosity.UpdateFunction(avField, program.SpeciesMap.SubGrid.VolumeMask, program);
                }

                // Test
                //double sensorNorm = program.WorkingSet.DerivedFields[Variables.ShockSensor].L2Norm();
                //double AVNorm = program.WorkingSet.DerivedFields[Variables.ArtificialViscosity].L2Norm();
                //Console.WriteLine("\r\nThis is UpdateShockCapturingVariables");
                //Console.WriteLine("SensorNeu: {0}", sensorNorm);
                //Console.WriteLine("AVNeu: {0}", AVNorm);
            }
        }
Esempio n. 8
0
        /// <summary>
        /// performs some timesteps
        /// </summary>
        protected override double RunSolverOneStep(int TimestepNo, double phystime, double dt)
        {
            using (var ft = new FuncTrace()) {
                //PerformanceVsCachesize();
                //SimplifiedPerformance();


                //u.ProjectField((_2D)((x, y) => x+y));
                //var f = new SinglePhaseField(u.Basis, "f");
                //var sgrd = new SubGrid(new CellMask(this.GridDat, Chunk.GetSingleElementChunk(200)));
                //f.Clear();
                //f.DerivativeByFlux(1.0, u, 0, sgrd, true);
                //Tecplot plt1 = new Tecplot(GridDat, true, false, 0);
                //plt1.PlotFields("ggg" , "Scalar Transport", phystime, u, f, mpi_rank);
                //base.TerminationKey = true;


                double dtCFL;
                if (this.GridData is GridData)
                {
                    dtCFL = this.GridData.ComputeCFLTime(this.Velocity, 1.0e10);
                }
                else
                {
                    Console.WriteLine("Nix CFL");
                    dtCFL = 1e-3;
                }
                if (dt <= 0)
                {
                    // if dt <= 0, we're free to set the timestep on our own
                    //base.NoOfTimesteps = -1;
                    //dt = 1;

                    base.NoOfTimesteps = 10;
                    base.EndTime       = 5.0;
                    dtCFL *= 1.0 / (((double)u.Basis.Degree).Pow2());
                }


                Console.Write("Timestp. #" + TimestepNo + " of " + base.NoOfTimesteps + " ... \t");
                dt = dtCFL * 0.5;
                Timestepper.Perform(dt);

                // set mpi_rank
                int    J    = this.GridData.iLogicalCells.NoOfLocalUpdatedCells;
                double rank = GridData.MpiRank;
                for (int j = 0; j < J; j++)
                {
                    mpi_rank.SetMeanValue(j, rank);
                }


                //dt = Timestepper.PerformAdaptive(1.0e2);

                Console.WriteLine("finished (dt = {0:0.###E-00}, CFL frac = {1:0.###E-00})!", dt, dt / dtCFL);


                return(dt);
            }
        }
        public IEnumerable <IChunkRulePair <CellBoundaryQuadRule> > GetQuadRuleSet(ExecutionMask mask, int order)
        {
            using (var tr = new FuncTrace()) {
                if (mask != null && mask is CellMask == false)
                {
                    throw new ArgumentException("Cell mask required", "mask");
                }
                if (mask.MaskType != MaskType.Geometrical)
                {
                    throw new ArgumentException("Expecting a geometrical mask.");
                }


                Stopwatch totalTimer        = new Stopwatch();
                Stopwatch projectionTimer   = new Stopwatch();
                Stopwatch optimizationTimer = new Stopwatch();

                totalTimer.Start();
                if (order != currentOrder)
                {
                    cache.Clear();
                    SwitchOrder(order);
                }

                var result = new List <ChunkRulePair <CellBoundaryQuadRule> >(mask.NoOfItemsLocally);
                foreach (Chunk chunk in mask)
                {
                    for (int i = 0; i < chunk.Len; i++)
                    {
                        int cell = chunk.i0 + i;

                        if (cache.ContainsKey(cell))
                        {
                            result.Add(new ChunkRulePair <CellBoundaryQuadRule>(
                                           Chunk.GetSingleElementChunk(cell),
                                           cache[cell]));
                            continue;
                        }

                        optimizationTimer.Start();
                        CellBoundaryQuadRule optimizedRule = GetOptimizedRule(chunk.i0 + i, order);
                        optimizationTimer.Stop();

                        cache.Add(cell, optimizedRule);
                        result.Add(new ChunkRulePair <CellBoundaryQuadRule>(
                                       Chunk.GetSingleElementChunk(i + chunk.i0), optimizedRule));
                    }
                }
                totalTimer.Stop();

                double totalTicks             = (double)totalTimer.ElapsedTicks;
                double percentageProjection   = Math.Round(projectionTimer.ElapsedTicks / totalTicks * 100, 2);
                double percentageOptimization = Math.Round(optimizationTimer.ElapsedTicks / totalTicks * 100, 2);
                tr.Info("Percentage spent on projection to surface: " + percentageProjection.ToString(NumberFormatInfo.InvariantInfo) + "%");
                tr.Info("Percentage spent on optimization: " + percentageOptimization.ToString(NumberFormatInfo.InvariantInfo) + "%");

                return(result);
            }
        }
Esempio n. 10
0
        /// <summary>
        /// Constructs the quadrature rules all edges of all cells in
        /// <paramref name="mask"/>. For edges that are not intersected by the
        /// zero iso-contour, standard Gaussian quadrature rules of
        /// sufficiently high order will be used.
        /// </summary>
        /// <param name="mask">
        /// Cells for which quadrature rules shall be created
        /// </param>
        /// <param name="order">
        /// Desired order of the moment-fitting system. Assuming that
        /// <see cref="edgeSurfaceRuleFactory"/> integrates the basis
        /// polynomials exactly over the zero iso-contour (which it usually
        /// doesn't!), the resulting quadrature rules will be exact up to this
        /// order.
        /// </param>
        /// <returns>A set of quadrature rules</returns>
        /// <remarks>
        /// Since the selected level set is generally discontinuous across cell
        /// boundaries, this method does not make use of the fact that
        /// neighboring cells share edges. That is, the optimization will be
        /// performed twice for each inner edge in <paramref name="mask"/>.
        /// </remarks>
        public IEnumerable <IChunkRulePair <CellBoundaryQuadRule> > GetQuadRuleSet(ExecutionMask mask, int order)
        {
            using (var tr = new FuncTrace()) {
                if (!(mask is CellMask))
                {
                    throw new ArgumentException("CellMask required", "mask");
                }
                if (mask.MaskType != MaskType.Geometrical)
                {
                    throw new ArgumentException("Expecting a geometrical mask.");
                }

                int      noOfEdges      = LevelSetData.GridDat.Grid.RefElements[0].NoOfFaces;
                CellMask tmpLogicalMask = new CellMask(mask.GridData, mask.GetBitMask(), MaskType.Logical);
#if DEBUG
                CellMask differingCells = tmpLogicalMask.Except(this.LevelSetData.Region.GetCutCellMask4LevSet(this.levelSetIndex));
                if (differingCells.NoOfItemsLocally > 0)
                {
                    throw new ArgumentException("The provided mask has to be a sub-set of the cut cells. " +
                                                "Cells {0} are not in the CutCellMaks of this tracker.", differingCells.GetSummary());
                }
#endif

                subGrid = new SubGrid(tmpLogicalMask);
                localCellIndex2SubgridIndex = subGrid.LocalCellIndex2SubgridIndex;

                if (order != lastOrder)
                {
                    cache.Clear();
                    SwitchOrder(order);
                }

                var result = new List <ChunkRulePair <CellBoundaryQuadRule> >(mask.NoOfItemsLocally);
                CellBoundaryQuadRule[] optimizedRules = GetOptimizedRules((CellMask)mask, order);
                int n = 0;
                foreach (Chunk chunk in mask)
                {
                    foreach (int cell in chunk.Elements)
                    {
                        if (cache.ContainsKey(cell))
                        {
                            result.Add(new ChunkRulePair <CellBoundaryQuadRule>(
                                           Chunk.GetSingleElementChunk(cell), cache[cell]));
                        }
                        else
                        {
                            cache.Add(cell, optimizedRules[n]);
                            result.Add(new ChunkRulePair <CellBoundaryQuadRule>(
                                           Chunk.GetSingleElementChunk(cell), optimizedRules[n]));
                        }

                        n++;
                    }
                }

                return(result);
            }
        }
Esempio n. 11
0
        /// <summary>
        /// Finite difference directional derivative Approximate f'(x) w
        /// C.T.Kelley, April 1, 2003
        /// This code comes with no guarantee or warranty of any kind.
        /// </summary>
        /// <param name="SolutionVec">Solution point</param>
        /// <param name="w">Direction</param>
        /// <param name="f0">f0, usually has been calculated earlier</param>
        /// <param name="linearization">True if the Operator should be linearized and evaluated afterwards</param>
        /// <returns></returns>
        public double[] dirder(CoordinateVector SolutionVec, double[] currentX, double[] w, double[] f0, bool linearization = false)
        {
            using (var tr = new FuncTrace()) {
                double epsnew = 1E-7;

                int      n  = SolutionVec.Length;
                double[] fx = new double[f0.Length];

                // Scale the step
                if (w.L2NormPow2().MPISum().Sqrt() == 0)
                {
                    fx.Clear();
                    return(fx);
                }

                var normw = w.L2NormPow2().MPISum().Sqrt();

                double xs = GenericBlas.InnerProd(currentX, w).MPISum() / normw;

                if (xs != 0)
                {
                    epsnew = epsnew * Math.Max(Math.Abs(xs), 1) * Math.Sign(xs);
                }
                epsnew = epsnew / w.L2NormPow2().MPISum().Sqrt();

                var del = currentX.CloneAs();

                del.AccV(epsnew, w);

                double[] temp = new double[SolutionVec.Length];

                temp.CopyEntries(SolutionVec);

                this.CurrentLin.TransformSolFrom(SolutionVec, del);

                // Just evaluate linearized operator
                //var OpAffineRaw = this.LinearizationRHS.CloneAs();
                //this.CurrentLin.OperatorMatrix.SpMV(1.0, new CoordinateVector(SolutionVec.Mapping.Fields.ToArray()), 1.0, OpAffineRaw);
                //CurrentLin.TransformRhsInto(OpAffineRaw, fx);
                if (linearization == false)
                {
                    EvaluateOperator(1.0, SolutionVec.Mapping.Fields, fx);
                }
                //else {
                //    this.m_AssembleMatrix(out OpMtxRaw, out OpAffineRaw, out MassMtxRaw, SolutionVec.Mapping.Fields.ToArray(), true);
                //    OpMtxRaw.SpMV(1.0, new CoordinateVector(SolutionVec.Mapping.Fields.ToArray()), 1.0, OpAffineRaw);
                //    CurrentLin.TransformRhsInto(OpAffineRaw, fx);
                //}

                SolutionVec.CopyEntries(temp);

                // (f1 - f0) / epsnew
                fx.AccV(1, f0);
                fx.ScaleV(1 / epsnew);

                return(fx);
            }
        }
Esempio n. 12
0
        /// <summary>
        /// computes <see cref="LaplaceMtx"/> and <see cref="LaplaceAffine"/>
        /// </summary>
        private void UpdateMatrices() {
            using (var tr = new FuncTrace()) {
                // time measurement for matrix assembly
                Stopwatch stw = new Stopwatch();
                stw.Start();

                // console
                Console.WriteLine("creating sparse system for {0} DOF's ...", T.Mapping.Ntotal);

                // quadrature domain
                var volQrSch = new CellQuadratureScheme(true, CellMask.GetFullMask(this.GridData, MaskType.Geometrical));
                var edgQrSch = new EdgeQuadratureScheme(true, EdgeMask.GetFullMask(this.GridData, MaskType.Geometrical));

#if DEBUG
                // in DEBUG mode, we compare 'MsrMatrix' (old, reference implementation) and 'BlockMsrMatrix' (new standard)
                var RefLaplaceMtx = new MsrMatrix(T.Mapping);
#endif
                using (new BlockTrace("SipMatrixAssembly", tr)) {
                    LaplaceMtx = new BlockMsrMatrix(T.Mapping);
                    LaplaceAffine = new double[T.Mapping.LocalLength];

                    LapaceIp.ComputeMatrixEx(T.Mapping, null, T.Mapping,
                                             LaplaceMtx, LaplaceAffine,
                                             volQuadScheme: volQrSch, edgeQuadScheme: edgQrSch);
                }
#if DEBUG
                LaplaceAffine.ClearEntries();
                LapaceIp.ComputeMatrixEx(T.Mapping, null, T.Mapping,
                                         RefLaplaceMtx, LaplaceAffine,
                                         volQuadScheme: volQrSch, edgeQuadScheme: edgQrSch);
                MsrMatrix ErrMtx = RefLaplaceMtx.CloneAs();
                ErrMtx.Acc(-1.0, LaplaceMtx);
                double err = ErrMtx.InfNorm();
                double infNrm = LaplaceMtx.InfNorm();
                Console.WriteLine("Matrix comparison error: " + err + ", matrix norm is: " + infNrm);
                Assert.Less(err, infNrm * 1e-10, "MsrMatrix2 comparison failed.");
#endif
                stw.Stop();
                Console.WriteLine("done {0} sec.", stw.Elapsed.TotalSeconds);


                //var JB = LapaceIp.GetFDJacobianBuilder(T.Mapping.Fields, null, T.Mapping, edgQrSch, volQrSch);
                //var JacobiMtx = new BlockMsrMatrix(T.Mapping);
                //var JacobiAffine = new double[T.Mapping.LocalLength];
                //JB.ComputeMatrix(JacobiMtx, JacobiAffine);
                //double L2ErrAffine = GenericBlas.L2Dist(JacobiAffine, LaplaceAffine);
                //var ErrMtx2 = LaplaceMtx.CloneAs();
                //ErrMtx2.Acc(-1.0, JacobiMtx);
                //double LinfErrMtx2 = ErrMtx2.InfNorm();

                //JacobiMtx.SaveToTextFileSparse("D:\\tmp\\Jac.txt");
                //LaplaceMtx.SaveToTextFileSparse("D:\\tmp\\Lap.txt");

                //Console.WriteLine("FD Jacobi Mtx: {0:e14}, Affine: {1:e14}", LinfErrMtx2, L2ErrAffine);
            }
        }
        /// <summary>
        /// Loads a time-step from the database into previously allocated
        /// DG-fields (<paramref name="PreAllocatedFields"/>).
        /// </summary>
        public void LoadFieldData(ITimestepInfo info, IGridData grdDat, IEnumerable <DGField> PreAllocatedFields)
        {
            using (var tr = new FuncTrace())
            {
                DGField[]      Fields        = PreAllocatedFields.ToArray(); // enforce 'evaluation' of the enum (in the case it is some delayed linq-expr).
                List <DGField> FieldsFlatten = new List <DGField>();
                TimestepInfo.FlattenHierarchy(FieldsFlatten, Fields);
                foreach (var f in FieldsFlatten)
                {
                    if (!Fields.Contains(f, (a, b) => object.ReferenceEquals(a, b)))
                    {
                        throw new ArgumentException("Unable to load timestep: field '" + f.Identification + "', which is required by at least one of the given fields, must also be contained in the given list of fields.", "PreAllocatedFields");
                    }
                }

                // Load data vector
                // ================
                var partition = grdDat.CellPartitioning;
                var DataVec   = this.Driver.LoadVector <CellFieldDataSet>(info.StorageID, ref partition);

                // Permute data vector
                // ===================


                var SortedDataVec = new CellFieldDataSet[DataVec.Count];

                {
                    // tau   is the GlobalID-permutation that we have for the loaded vector
                    // sigma is the current GlobalID-permutation of the grid
                    var sigma = grdDat.CurrentGlobalIdPermutation;
                    var tau   = new Permutation(DataVec.Select(cd => cd.GlobalID).ToArray(), csMPI.Raw._COMM.WORLD);

                    // compute resorting permutation
                    Permutation invSigma  = sigma.Invert();
                    Permutation Resorting = invSigma * tau;
                    tau      = null;
                    invSigma = null;

                    // put dg coordinates into right order
                    Resorting.ApplyToVector(DataVec, SortedDataVec);
                }


                // Load the fields
                // ===============
                HashSet <object> loadedObjects = new HashSet <object>(ReferenceComparer.Instance);

                foreach (var Field in Fields)
                {
                    Field.LoadData(info, SortedDataVec, loadedObjects);
                }
            }
        }
Esempio n. 14
0
 /// <summary>
 /// %
 /// </summary>
 public void Solve <U, V>(U X, V B)
     where U : IList <double>
     where V : IList <double> //
 {
     using (var tr = new FuncTrace()) {
         using (var solver = GetSolver(m_Mtx)) {
             var result = solver.Solve(X, B);
             this.Converged            = result.Converged;
             this.ThisLevelIterations += result.NoOfIterations;
         }
     }
 }
        /// <summary>
        /// Loads the given <paramref name="sessionId"/> from the given
        /// <paramref name="database"/>.
        /// </summary>
        /// <param name="sessionId"></param>
        /// <param name="database"></param>
        /// <returns></returns>
        public SessionInfo LoadSession(Guid sessionId, IDatabaseInfo database)
        {
            using (var tr = new FuncTrace())
            {
                tr.Info("Loading session " + sessionId);

                using (Stream s = fsDriver.GetSessionInfoStream(false, sessionId))
                {
                    SessionInfo loadedSession = (SessionInfo)Driver.Deserialize(s, typeof(SessionInfo));
                    loadedSession.Database  = database;
                    loadedSession.WriteTime = Utils.GetSessionFileWriteTime(loadedSession);
                    s.Close();

                    return(loadedSession);
                }
            }
        }
Esempio n. 16
0
        public void Init(MultigridOperator op)
        {
            using (var tr = new FuncTrace()) {
                var Mtx   = op.OperatorMatrix;
                var MgMap = op.Mapping;
                m_MultigridOp = op;

                if (!Mtx.RowPartitioning.EqualsPartition(MgMap.Partitioning))
                {
                    throw new ArgumentException("Row partitioning mismatch.");
                }
                if (!Mtx.ColPartition.EqualsPartition(MgMap.Partitioning))
                {
                    throw new ArgumentException("Column partitioning mismatch.");
                }

                m_Mtx = Mtx;
            }
        }
Esempio n. 17
0
        /// <summary>
        /// Updates all derived variables within
        /// <see cref="CNSFieldSet.DerivedFields"/> using their corresponding
        /// update function <see cref="DerivedVariable.UpdateFunction"/>
        /// </summary>
        public void UpdateDerivedVariables(IProgram <CNSControl> program, CellMask cellMask)
        {
            using (var tr = new FuncTrace()) {
                program.Control.ShockSensor?.UpdateSensorValues(program.WorkingSet.AllFields, program.SpeciesMap, cellMask);
                foreach (var pair in DerivedFields)
                {
                    using (new BlockTrace("UpdateFunction:" + pair.Value.Identification + "-" + pair.Key.Name, tr)) {
                        pair.Key.UpdateFunction(pair.Value, cellMask, program);
                    }
                }

                // Test
                //double sensorNorm = program.WorkingSet.DerivedFields[Variables.ShockSensor].L2Norm();
                //double AVNorm = program.WorkingSet.DerivedFields[Variables.ArtificialViscosity].L2Norm();
                //Console.WriteLine("\r\nThis is UpdateDerivedVariables");
                //Console.WriteLine("SensorNeu: {0}", sensorNorm);
                //Console.WriteLine("AVNeu: {0}", AVNorm);
            }
        }
Esempio n. 18
0
        /// <summary>
        /// Loads a BoSSS grid from an grid file; the file type (see <see cref="ImporterTypes"/>) are determined by the file ending.
        /// </summary>
        public static GridCommons Import(string fileName)
        {
            using (var tr = new FuncTrace()) {
                ImporterTypes importerType = GetImporterType(fileName);

                tr.Info(string.Format("Loading {0} file '{1}'...", importerType.ToString(), fileName));
                IGridImporter importer;
                using (new BlockTrace("Import", tr)) {
                    switch (importerType)
                    {
                    case ImporterTypes.Gambit:
                        GambitNeutral gn = new GambitNeutral(fileName);
                        if (gn.BoSSSConversionNeccessary())
                        {
                            gn = gn.ToLinearElements();
                        }

                        importer = gn;
                        break;

                    case ImporterTypes.CGNS:
                        importer = new Cgns(fileName);
                        break;

                    case ImporterTypes.Gmsh:
                        importer = new Gmsh(fileName);
                        break;

                    default:
                        throw new NotImplementedException();
                    }
                }

                tr.Info("Converting to BoSSS grid ...");
                GridCommons grid;
                using (new BlockTrace("Conversion", tr)) {
                    grid = importer.GenerateBoSSSGrid();
                }

                return(grid);
            }
        }
Esempio n. 19
0
        /// <summary>
        /// Restriction of <paramref name="X"/> and <paramref name="B"/> to lower level, execution of <see cref="CoarserLevelSolver"/> and prolongation of coarse solution.
        /// </summary>
        public void Solve <U, V>(U X, V B)
            where U : IList <double>
            where V : IList <double>
        {
            //
            using (var tr = new FuncTrace()) {
                int      N  = this.m_OpThisLevel.CoarserLevel.Mapping.LocalLength;
                double[] xc = new double[N], bc = new double[N];
                //this.RestrictionOperator.SpMVpara(1.0, X, 0.0, xc);
                //this.RestrictionOperator.SpMVpara(1.0, B, 0.0, bc);

                this.m_OpThisLevel.CoarserLevel.Restrict(B, bc);
                this.m_OpThisLevel.CoarserLevel.Restrict(X, xc);

                CoarserLevelSolver.Solve(xc, bc);

                //this.PrologateOperator.SpMV(1.0, xc, 0.0, X);
                this.m_OpThisLevel.CoarserLevel.Prolongate(1.0, X, 0.0, xc);
            }
        }
Esempio n. 20
0
        /// <summary>
        /// Loads the grid info object for the given
        /// <paramref name="gridGuid"/> from the given
        /// <paramref name="database"/>
        /// </summary>
        /// <param name="gridGuid"></param>
        /// <param name="database"></param>
        /// <returns></returns>
        public IGridInfo LoadGridInfo(Guid gridGuid, IDatabaseInfo database)
        {
            using (var tr = new FuncTrace())
            {
                tr.Info("Loading grid " + gridGuid);

                IGrid grid = null;
                grid = DeserializeGrid(gridGuid);

                /*
                 * if (MyRank == 0)
                 * {
                 *  grid = DeserializeGrid(gridGuid);
                 * }
                 *
                 * grid = grid.MPIBroadcast(0);
                 */
                grid.GridSerializationHandler.Database = database;
                grid.WriteTime = Utils.GetGridFileWriteTime(grid);
                return(grid);
            }
        }
Esempio n. 21
0
        /// <summary>
        ///
        /// </summary>
        /// <param name="create">
        /// true: creates a new file for writing;
        /// false: open a file for reading;
        /// </param>
        /// <param name="RelPath">
        /// relative path within the base paths.
        /// </param>
        /// <returns>
        /// a file stream
        /// </returns>
        /// <param name="ForceOverride">
        /// when opening a stream for writing (<paramref name="create"/>=true), this argument
        /// toggles how existing files should be treated:
        /// false: an exception is thrown if the file already exists;
        /// true: an existing file would be overwritten
        /// </param>
        /// <returns></returns>
        private Stream OpenFile(bool create, string RelPath, bool ForceOverride)
        {
            using (var tr = new FuncTrace()) {
                tr.Info("opening file '" + RelPath + "', create='" + create + "'");

                if (create)
                {
                    // create new file
                    string fullpath = Path.Combine(BasePath, RelPath);
                    if (ForceOverride == true)
                    {
                        FileStream fs = new FileStream(fullpath, FileMode.Create); //, FileAccess.ReadWrite, FileShare.Read); // overwrites existing file
                        return(fs);
                    }
                    else
                    {
                        FileStream fs = new FileStream(fullpath, FileMode.CreateNew);//, FileAccess.ReadWrite, FileShare.Read); // throws exception if file exists
                        return(fs);
                    }
                }
                else
                {
                    // try to open file

                    FileNotFoundException exc = null;

                    try {
                        FileStream fs = new FileStream(Path.Combine(BasePath, RelPath),
                                                       FileMode.Open, FileAccess.Read, FileShare.Read);
                        return(fs);
                    } catch (FileNotFoundException fnf) {
                        exc = fnf;
                    }

                    throw exc;
                }
            }
        }
        /// <summary>
        /// loads a single <see cref="TimestepInfo"/>-object from the database.
        /// </summary>
        public TimestepInfo LoadTimestepInfo(Guid timestepGuid, ISessionInfo session, IDatabaseInfo database)
        {
            using (var tr = new FuncTrace())
            {
                tr.Info("Loading time-step " + timestepGuid);

                TimestepInfo tsi = null;
                if (MyRank == 0)
                {
                    using (Stream s = fsDriver.GetTimestepStream(false, timestepGuid))
                    {
                        tsi         = (TimestepInfo)Driver.Deserialize(s, typeof(TimestepInfo));
                        tsi.Session = session;
                        s.Close();
                    }
                    tsi.ID = timestepGuid;
                }
                tsi           = tsi.MPIBroadcast(0);
                tsi.Database  = database;
                tsi.WriteTime = Utils.GetTimestepFileWriteTime(tsi);
                return(tsi);
            }
        }
Esempio n. 23
0
        /// <summary>
        /// see <see cref="Device.CreateMatrix(MsrMatrix,MatrixType)"/>;
        /// </summary>
        public override MatrixBase CreateMatrix(MsrMatrix M, MatrixType matType)
        {
            using (var f = new FuncTrace()) {
                f.Info("desired matrix type: " + matType);
                switch (matType)
                {
                case MatrixType.CCBCSR:
                    return(new CudaCCBCSRMatrix(M, this.Env));

                case MatrixType.CSR:
                    return(new CudaCSRMatrix(M, this.Env));

                case MatrixType.ELLPACK:
                    return(new CudaELLPACKmodMatrix(M, this.Env));

                case MatrixType.Auto:
                case MatrixType.ELLPACKcache:
                    return(new CudaELLPACKcacheMatrix(M, this.Env));

                default:
                    throw new NotImplementedException();
                }
            }
        }
Esempio n. 24
0
        /// <summary>
        /// Includes assembly of the matrix.
        /// </summary>
        /// <param name="L"></param>
        protected override void CreateEquationsAndSolvers(GridUpdateDataVaultBase L)
        {
            using (FuncTrace tr = new FuncTrace()) {
                // create operator
                // ===============
                {
                    double D              = this.GridData.SpatialDimension;
                    double penalty_base   = (T.Basis.Degree + 1) * (T.Basis.Degree + D) / D;
                    double penalty_factor = base.Control.penalty_poisson;

                    BoundaryCondMap <BoundaryType> PoissonBcMap = new BoundaryCondMap <BoundaryType>(this.GridData, this.Control.BoundaryValues, "T");

                    LapaceIp = new SpatialOperator(1, 1, QuadOrderFunc.SumOfMaxDegrees(), "T", "T");

                    MultidimensionalArray LengthScales;
                    if (this.GridData is GridData)
                    {
                        LengthScales = ((GridData)GridData).Cells.cj;
                    }
                    else if (this.GridData is AggregationGridData)
                    {
                        LengthScales = ((AggregationGridData)GridData).AncestorGrid.Cells.cj;
                    }
                    else
                    {
                        throw new NotImplementedException();
                    }

                    var flux = new ipFlux(penalty_base * base.Control.penalty_poisson, LengthScales, PoissonBcMap);

                    LapaceIp.EquationComponents["T"].Add(flux);

                    LapaceIp.Commit();
                }
            }
        }
Esempio n. 25
0
        /// <summary>
        ///
        /// </summary>
        protected override double RunSolverOneStep(int TimestepNo, double phystime, double dt)
        {
            using (var tr = new FuncTrace()) {
                tr.Info("Performing time iteration No. " + TimestepNo);

                // Set dt and SIMPLEStatus
                switch (Control.Algorithm)
                {
                case SolutionAlgorithms.Steady_SIMPLE: {
                    dt = 0.0;
                    break;
                }

                case SolutionAlgorithms.Unsteady_SIMPLE: {
                    dt = SolverConf.dt;
                    SIMPLEStatus.NextTimestep();
                    break;
                }
                }

                // some console-output
                if (base.MPIRank == 0)
                {
                    switch (Control.Algorithm)
                    {
                    case SolutionAlgorithms.Steady_SIMPLE:
                        Console.WriteLine("Starting steady calculation...\n");
                        Console.WriteLine("Starting SIMPLE-Iterations...\n");
                        break;

                    case SolutionAlgorithms.Unsteady_SIMPLE:
                        Console.WriteLine("Starting time step #" + TimestepNo + "...\n");
                        Console.WriteLine("Starting SIMPLE-Iterations...\n");
                        break;

                    default:
                        throw new NotImplementedException();
                    }
                }

                do
                {
                    // do one SIMPLE iteration
                    SIMPLEStatus.NextSIMPLEIteration();
                    SIMPLEStep.OverallIteration(ref SIMPLEStatus, dt, ResLogger);

                    TerminationKey = WorkingSet.CheckForNanOrInf(Control);
                    if (TerminationKey)
                    {
                        m_Logger.Warn("Found Nan in some field.");
                        if (base.MPIRank == 0)
                        {
                            Console.WriteLine("ERROR: Found Nan in some field.");
                        }
                        Console.ReadKey();
                    }

                    if ((Control.PhysicsMode == PhysicsMode.LowMach) && (SolverConf.Control.As <LowMachSIMPLEControl>().EdgeTagsNusselt != null))
                    {
                        CalculateNusselt(SIMPLEStatus.Timestep, base.GridData, WorkingSet.Temperature.Current, Control);
                    }

                    // save to database
                    if (SIMPLEStatus.SaveStep)
                    {
                        SaveToDatabase(SIMPLEStatus.Timestep, phystime);
                    }

                    // calculate errors
                    int QuadDegreePressure = 20;
                    int QuadDegreeVel      = 20;

                    ResLogger.ComputeL2Error(WorkingSet.Pressure, Control.AnalyticPressure, QuadDegreePressure, "p_ana");

                    ResLogger.ComputeL2Error(WorkingSet.Velocity.Current[0], Control.AnalyticVelocityX, QuadDegreeVel, "u_ana");
                    ResLogger.ComputeL2Error(WorkingSet.Velocity.Current[1], Control.AnalyticVelocityY, QuadDegreeVel, "v_ana");
                    if (SolverConf.SpatialDimension == 3)
                    {
                        ResLogger.ComputeL2Error(WorkingSet.Velocity.Current[2], Control.AnalyticVelocityZ, QuadDegreeVel, "w_ana");
                    }

                    switch (Control.PhysicsMode)
                    {
                    case PhysicsMode.Incompressible:
                        break;

                    case PhysicsMode.LowMach:
                        LowMachSIMPLEControl lowMachConf = Control as LowMachSIMPLEControl;
                        ResLogger.ComputeL2Error(WorkingSet.Temperature.Current, lowMachConf.AnalyticTemperature, QuadDegreeVel, "T_ana");
                        ResLogger.ComputeL2Error(WorkingSet.Rho, lowMachConf.AnalyticDensity, QuadDegreeVel, "Rho_ana");
                        break;

                    case PhysicsMode.Multiphase:
                        MultiphaseSIMPLEControl multiphaseConf = Control as MultiphaseSIMPLEControl;
                        ResLogger.ComputeL2Error(WorkingSet.Phi.Current, multiphaseConf.AnalyticLevelSet, QuadDegreeVel, "Phi_ana");
                        ResLogger.ComputeL2Error(WorkingSet.Rho, multiphaseConf.AnalyticDensity, QuadDegreeVel, "Rho_ana");
                        break;

                    default:
                        throw new NotImplementedException();
                    }

                    // terminate SIMPLE in case of divergence
                    if (ResLogger.Residuals["L2Norm p'"] > 1.0E+10)
                    {
                        TerminationKey = true;
                    }

                    // push residual logger to next iteration
                    switch (Control.Algorithm)
                    {
                    case SolutionAlgorithms.Steady_SIMPLE:
                        ResLogger.NextIteration(false);
                        break;

                    case SolutionAlgorithms.Unsteady_SIMPLE:
                        ResLogger.NextIteration(true);
                        break;

                    default:
                        throw new NotImplementedException();
                    }
                }while (!SIMPLEStatus.IsConverged && !SIMPLEStatus.TerminateSIMPLE && !TerminationKey);

                // determine cause for end of SIMPLE iterations
                if (SIMPLEStatus.IsConverged)
                {
                    tr.Info("Solution converged.");
                }
                else if (SIMPLEStatus.TerminateSIMPLE)
                {
                    if (SIMPLEStatus.SIMPLEStepNo == Control.MaxNoSIMPLEsteps)
                    {
                        SIMPLEStatus.CntMaxNoSIMPLEsteps++;
                        m_Logger.Warn("MaxNoSIMPLEsteps are reached.");
                    }
                    else
                    {
                        m_Logger.Warn("Unknown reason for terminating SIMPLE iterations - should not happen.");
                    }
                }
                else
                {
                    m_Logger.Error("Solution diverged.");
                }

                // save the new timestep
                switch (Control.Algorithm)
                {
                case SolutionAlgorithms.Steady_SIMPLE:
                    break;

                case SolutionAlgorithms.Unsteady_SIMPLE:
                    WorkingSet.Push(Control);
                    ResLogger.NextTimestep(false);
                    break;

                default:
                    throw new NotImplementedException();
                }

                // some console-output
                if (SIMPLEStatus.IsConverged)
                {
                    Console.WriteLine("\nINFO: Done SIMPLE-Iterations - Solution converged.\n");
                }
                else if (SIMPLEStatus.SIMPLEStepNo == Control.MaxNoSIMPLEsteps)
                {
                    Console.WriteLine("\nWARNING: Done SIMPLE-Iterations - Maximum number of SIMPLE steps was reached.\n");
                }
                else
                {
                    Console.WriteLine("\nERROR: Calculation was terminated - Solution diverged.\n");
                }

                switch (Control.Algorithm)
                {
                case SolutionAlgorithms.Steady_SIMPLE:
                    Console.WriteLine("Done steady calculation.");
                    break;

                case SolutionAlgorithms.Unsteady_SIMPLE:
                    Console.WriteLine("Done time step #" + TimestepNo + ".\n");
                    break;

                default:
                    throw new NotImplementedException();
                }


                //LogEnergyOrrSommerfeld(TimestepNo, phystime, dt);
                if (Control.EdgeTagsDragAndLift != null)
                {
                    CalculateDragAndLift(phystime);
                }

                //Log temperature history tall cavity
                //LogTemperature(phystime, this.WorkingSet.Temperature.Current);

                return(dt);
            }
        }
Esempio n. 26
0
        /// <summary>
        /// Job status.
        /// </summary>
        public override void EvaluateStatus(string idToken, object optInfo, string DeployDir, out bool isRunning, out bool isTerminated, out int ExitCode)
        {
            using (var tr = new FuncTrace()) {
                int id = int.Parse(idToken);



                ISchedulerJob JD;
                //if (optInfo != null && optInfo is ISchedulerJob _JD) {
                //    JD = _JD;
                //} else {
                using (new BlockTrace("Scheduler.OpenJob", tr)) {
                    JD = Scheduler.OpenJob(id);
                }

                //}

                /*
                 * the following seems really slow:
                 *
                 *
                 * List<SchedulerJob> allFoundJobs = new List<SchedulerJob>();
                 * ISchedulerCollection allJobs;
                 * using (new BlockTrace("Scheduler.GetJobList", tr)) {
                 *  allJobs = Scheduler.Get
                 * }
                 * int cc = allJobs.Count;
                 * Console.WriteLine("MsHpcClient: " + cc + " jobs.");
                 * tr.Logger.Info("list of " + cc + " jobs.");
                 * using (new BlockTrace("ID_FILTERING", tr)) {
                 *  foreach (SchedulerJob sJob in allJobs) {
                 *      if (sJob.Id != id)
                 *          continue;
                 *      allFoundJobs.Add(sJob);
                 *  }
                 *
                 *  if (allFoundJobs.Count <= 0) {
                 *      // some weird state
                 *      isRunning = false;
                 *      isTerminated = false;
                 *      ExitCode = int.MinValue;
                 *      return;
                 *  }
                 * }
                 *
                 * SchedulerJob JD;
                 * using (new BlockTrace("SORTING", tr)) {
                 *  JD = allFoundJobs.ElementAtMax(MsHpcJob => MsHpcJob.SubmitTime);
                 * }
                 */


                using (new BlockTrace("TASK_FILTERING", tr)) {
                    ISchedulerCollection tasks = JD.GetTaskList(null, null, false);
                    ExitCode = int.MinValue;
                    foreach (ISchedulerTask t in tasks)
                    {
                        DeployDir = t.WorkDirectory;
                        ExitCode  = t.ExitCode;
                    }
                }

                using (new BlockTrace("STATE_EVAL", tr)) {
                    switch (JD.State)
                    {
                    case JobState.Configuring:
                    case JobState.Submitted:
                    case JobState.Validating:
                    case JobState.ExternalValidation:
                    case JobState.Queued:
                        isRunning    = false;
                        isTerminated = false;
                        break;

                    case JobState.Running:
                    case JobState.Finishing:
                        isRunning    = true;
                        isTerminated = false;
                        break;

                    case JobState.Finished:
                        isRunning    = false;
                        isTerminated = true;
                        break;

                    case JobState.Failed:
                    case JobState.Canceled:
                    case JobState.Canceling:
                        isRunning    = false;
                        isTerminated = true;
                        break;

                    default:
                        throw new NotImplementedException("Unknown job state: " + JD.State);
                    }
                }
            }
        }
Esempio n. 27
0
        //bool solveVelocity = true;

        //double VelocitySolver_ConvergenceCriterion = 1e-5;

        //double StressSolver_ConvergenceCriterion = 1e-5;


        override public void SolverDriver <S>(CoordinateVector SolutionVec, S RHS)
        {
            using (var tr = new FuncTrace()) {
                // initial guess and its residual
                // ==============================
                double[] Solution, Residual;

                using (new BlockTrace("Slv Init", tr)) {
                    base.Init(SolutionVec, RHS, out Solution, out Residual);
                }
                double[] Correction     = new double[Solution.Length];
                double   ResidualNorm   = Residual.L2NormPow2().MPISum().Sqrt();
                int      NoOfIterations = 0;
                if (m_LinearSolver.GetType() == typeof(SoftGMRES))
                {
                    ((SoftGMRES)m_LinearSolver).m_SessionPath = m_SessionPath;
                }

                OnIterationCallback(NoOfIterations, Solution.CloneAs(), Residual.CloneAs(), this.CurrentLin);

                if (CoupledIteration_Converged == null)
                {
                    CoupledIteration_Converged = delegate() {
                        return(true);
                    }
                }
                ;

                int NoOfCoupledIteration = 0;
                if (Iteration_Count == null)
                {
                    Iteration_Count = delegate(int NoIter, ref int coupledIter) {
                        return(NoIter + 1);
                    }
                }
                ;

                //int[] Velocity_idx = SolutionVec.Mapping.GetSubvectorIndices(false, 0, 1, 2);
                //int[] Stresses_idx = SolutionVec.Mapping.GetSubvectorIndices(false, 3, 4, 5);

                //int[] Velocity_fields = new int[] { 0, 1, 2 };
                //int[] Stress_fields = new int[] { 3, 4, 5 };

                //int NoCoupledIterations = 10;

                // iterate...
                // ==========
                //int NoOfMainIterations = 0;
                using (new BlockTrace("Slv Iter", tr)) {
                    while ((!(ResidualNorm < ConvCrit && CoupledIteration_Converged()) && NoOfIterations < MaxIter && NoOfCoupledIteration < MaxCoupledIter) || (NoOfIterations < MinIter))
                    {
                        NoOfIterations = Iteration_Count(NoOfIterations, ref NoOfCoupledIteration);
                        //Console.WriteLine("NoOfIterations = {0}", NoOfIterations);

                        //DirectSolver ds = new DirectSolver();
                        //ds.Init(this.CurrentLin);
                        //double L2_Res = Residual.L2Norm();
                        this.m_LinearSolver.Init(this.CurrentLin);
                        Correction.ClearEntries();
                        if (Correction.Length != Residual.Length)
                        {
                            Correction = new double[Residual.Length];
                        }
                        this.m_LinearSolver.Solve(Correction, Residual);

                        //if (NoOfIterations > NoCoupledIterations)
                        //{
                        //    if (solveVelocity)
                        //    {
                        //        Console.WriteLine("stress correction = 0");
                        //        foreach (int idx in Stresses_idx)
                        //        {
                        //            Correction[idx] = 0.0;
                        //        }
                        //    }
                        //    else
                        //    {
                        //        Console.WriteLine("velocity correction = 0");
                        //        foreach (int idx in Velocity_idx)
                        //        {
                        //            Correction[idx] = 0.0;
                        //        }
                        //    }
                        //}

                        // Residual may be invalid from now on...
                        Solution.AccV(UnderRelax, Correction);

                        // transform solution back to 'original domain'
                        // to perform the linearization at the new point...
                        // (and for Level-Set-Updates ...)
                        this.CurrentLin.TransformSolFrom(SolutionVec, Solution);

                        // update linearization
                        base.Update(SolutionVec.Mapping.Fields, ref Solution);

                        // residual evaluation & callback
                        base.EvalResidual(Solution, ref Residual);
                        ResidualNorm = Residual.L2NormPow2().MPISum().Sqrt();

                        //if (NoOfIterations > NoCoupledIterations)
                        //{

                        //    double coupledL2Res = 0.0;
                        //    if (solveVelocity)
                        //    {
                        //        foreach (int idx in Velocity_idx)
                        //        {
                        //            coupledL2Res += Residual[idx].Pow2();
                        //        }
                        //    }
                        //    else
                        //    {
                        //        foreach (int idx in Stresses_idx)
                        //        {
                        //            coupledL2Res += Residual[idx].Pow2();
                        //        }
                        //    }
                        //    coupledL2Res = coupledL2Res.Sqrt();

                        //    Console.WriteLine("coupled residual = {0}", coupledL2Res);

                        //    if (solveVelocity && coupledL2Res < this.VelocitySolver_ConvergenceCriterion)
                        //    {
                        //        Console.WriteLine("SolveVelocity = false");
                        //        this.solveVelocity = false;
                        //    }
                        //    else if (!solveVelocity && coupledL2Res < this.StressSolver_ConvergenceCriterion)
                        //    {
                        //        Console.WriteLine("SolveVelocity = true");
                        //        this.solveVelocity = true;
                        //    }
                        //}

                        OnIterationCallback(NoOfIterations, Solution.CloneAs(), Residual.CloneAs(), this.CurrentLin);
                    }
                }
            }
        }
    }
}
Esempio n. 28
0
        private void ComputeAverageU <T>(IEnumerable <T> U0, VectorField <XDGField> U0mean, int order, XQuadSchemeHelper qh) where T : DGField
        {
            using (FuncTrace ft = new FuncTrace()) {
                var    CC     = this.LsTrk.Regions.GetCutCellMask();
                int    D      = this.LsTrk.GridDat.SpatialDimension;
                double minvol = Math.Pow(this.LsTrk.GridDat.Cells.h_minGlobal, D);


                //var qh = new XQuadSchemeHelper(agg);
                foreach (var Spc in this.LsTrk.SpeciesIdS)  // loop over species...
                //var Spc = this.LsTrk.GetSpeciesId("B"); {
                // shadow fields
                {
                    DGField[] U0_Spc     = U0.Select(U0_d => (U0_d is XDGField) ? ((DGField)((U0_d as XDGField).GetSpeciesShadowField(Spc))) : ((DGField)U0_d)).ToArray();
                    var       U0mean_Spc = U0mean.Select(U0mean_d => U0mean_d.GetSpeciesShadowField(Spc)).ToArray();


                    // normal cells:
                    for (int d = 0; d < D; d++)
                    {
                        U0mean_Spc[d].AccLaidBack(1.0, U0_Spc[d], this.LsTrk.Regions.GetSpeciesMask(Spc));
                    }

                    // cut cells
                    var scheme = qh.GetVolumeQuadScheme(Spc, IntegrationDomain: this.LsTrk.Regions.GetCutCellMask());
                    var rule   = scheme.Compile(this.LsTrk.GridDat, order);
                    CellQuadrature.GetQuadrature(new int[] { D + 1 }, // vector components: ( avg_vel[0], ... , avg_vel[D-1], cell_volume )
                                                 this.LsTrk.GridDat,
                                                 rule,
                                                 delegate(int i0, int Length, QuadRule QR, MultidimensionalArray EvalResult) {
                        EvalResult.Clear();
                        for (int d = 0; d < D; d++)
                        {
                            U0_Spc[d].Evaluate(i0, Length, QR.Nodes, EvalResult.ExtractSubArrayShallow(-1, -1, d));
                        }
                        var Vol = EvalResult.ExtractSubArrayShallow(-1, -1, D);
                        Vol.SetAll(1.0);
                    },
                                                 delegate(int i0, int Length, MultidimensionalArray ResultsOfIntegration) {
                        for (int i = 0; i < Length; i++)
                        {
                            int jCell = i + i0;

                            double Volume = ResultsOfIntegration[i, D];
                            if (Math.Abs(Volume) < minvol * 1.0e-12)
                            {
                                // keep current value
                                // since the volume of species 'Spc' in cell 'jCell' is 0.0, the value in this cell should have no effect
                            }
                            else
                            {
                                for (int d = 0; d < D; d++)
                                {
                                    double IntVal = ResultsOfIntegration[i, d];
                                    U0mean_Spc[d].SetMeanValue(jCell, IntVal / Volume);
                                }
                            }
                        }
                    }).Execute();
                }

#if DEBUG
                {
                    var Uncut = LsTrk.Regions.GetCutCellMask().Complement();


                    VectorField <SinglePhaseField> U0mean_check = new VectorField <SinglePhaseField>(D, new Basis(LsTrk.GridDat, 0), SinglePhaseField.Factory);
                    for (int d = 0; d < D; d++)
                    {
                        U0mean_check[d].ProjectField(1.0, U0.ElementAt(d).Evaluate,
                                                     new CellQuadratureScheme(false, Uncut).AddFixedOrderRules(LsTrk.GridDat, U0.ElementAt(d).Basis.Degree + 1));
                    }

                    foreach (var _Spc in this.LsTrk.SpeciesIdS)  // loop over species...
                    {
                        for (int d = 0; d < D; d++)
                        {
                            U0mean_check[d].AccLaidBack(-1.0, U0mean[d].GetSpeciesShadowField(_Spc), Uncut.Intersect(LsTrk.Regions.GetSpeciesMask(_Spc)));
                        }
                    }

                    double checkNorm = U0mean_check.L2Norm();
                    Debug.Assert(checkNorm < 1.0e-6);
                }
#endif


                U0mean.ForEach(F => F.CheckForNanOrInf(true, true, true));
            }
        }
Esempio n. 29
0
        public SolverResult Solve <Tdiag, Tunknowns, Trhs>(double Scale, Tdiag d, Tunknowns x, Trhs rhs)
            where Tdiag : System.Collections.Generic.IList <double>
            where Tunknowns : System.Collections.Generic.IList <double>
            where Trhs : System.Collections.Generic.IList <double>
        {
            using (var tr = new FuncTrace()) {
                // check input arguments
                // =====================

                if (x.Count != m_OrgMatrix.RowPartitioning.LocalLength)
                {
                    throw new ArgumentException("length of x must be equal to matrix size.");
                }
                if (rhs.Count != m_OrgMatrix.RowPartitioning.LocalLength)
                {
                    throw new ArgumentException("length of rhs must be equal to matrix size.");
                }
                if (Math.Abs(Scale) <= double.Epsilon)
                {
                    throw new ArgumentException("scale to small.");
                }

                // prepare vectors
                // ===============
                double[] _x;
                double[] _rhs;
                if (x.GetType() == typeof(double[]))
                {
                    _x = x as double[];
                }
                else
                {
                    _x = new double[x.Count];
                }
                if (rhs.GetType() == typeof(double[]))
                {
                    _rhs = (double[])((ICloneable)rhs).Clone();
                }
                else
                {
                    int L = m_MumpsMatrix.RowPart.LocalLength;
                    _rhs = new double[L];
                    for (int i = 0; i < L; i++)
                    {
                        _rhs[i] = rhs[i];
                    }
                }

                // define matrix
                // =============

                IMutableMatrixEx Mtx;
                //bool throwAwayMtx;
                if (d != null || Scale != 1.0)
                {
                    // not very efficient, but _I_dont_care_ !

                    MsrMatrix _Mtx = new MsrMatrix(m_OrgMatrix);
                    Mtx = _Mtx;
                    _Mtx.Scale(Scale);

                    int dLen = d.Count, L = _Mtx.RowPartitioning.LocalLength, i0 = (int)(_Mtx.RowPartitioning.i0);
                    if ((L % dLen) != 0)
                    {
                        throw new ApplicationException("wrong length of 'd'.");
                    }

                    for (int l = 0; l < L; l++)
                    {
                        _Mtx[i0 + l, i0 + l] += d[l % dLen];
                    }

                    //throwAwayMtx = true;
                }
                else
                {
                    //throwAwayMtx = false;
                    Mtx = m_OrgMatrix;
                }

                // call solver
                // ===========

                SolverResult r = new SolverResult();
                using (new BlockTrace("CALL SOLVER", tr)) {
                    r.Converged      = true;
                    r.NoOfIterations = 1;
                    Stopwatch st = new Stopwatch();
                    st.Reset();

                    double[] gath_x, gath_b;
                    GatherOnProc0(_x, _rhs, out gath_x, out gath_b);

                    r.NoOfIterations = 1;
                    int rank; int size;
                    csMPI.Raw.Comm_Rank(this.m_MPI_Comm, out rank);
                    csMPI.Raw.Comm_Size(this.m_MPI_Comm, out size);

                    r.Converged = MUMPSInitAndSolve(m_OrgMatrix, gath_b);

                    csMPI.Raw.Barrier(this.m_MPI_Comm);
                    unsafe
                    {
                        bool snd = r.Converged;
                        csMPI.Raw.Bcast((IntPtr)(&snd), 1, csMPI.Raw._DATATYPE.BYTE, 0, this.m_MPI_Comm);
                        r.Converged = snd;
                    }

                    ScatterFromProc0(_x, gath_b);

                    if (x.GetType() == typeof(double[]))
                    {
                        // do nothing
                    }
                    else
                    {
                        x.SetV(_x);
                    }


                    csMPI.Raw.Barrier(this.m_MPI_Comm);

                    st.Stop();

                    r.RunTime = st.Elapsed;
                }
                return(r);
            }
        }
Esempio n. 30
0
        protected override void CreateEquationsAndSolvers(GridUpdateDataVaultBase L)
        {
            using (FuncTrace tr = new FuncTrace()) {
                this.BcMap = new IncompressibleBoundaryCondMap(this.GridData, grid.GetBoundaryConfig(), PhysicsMode.Incompressible);


                // assemble system, create matrix
                // ------------------------------



                int D = GridData.SpatialDimension;
                //double penalty_base = ((double)((U[0].Basis.Degree + 1) * (U[0].Basis.Degree + D))) / ((double)D);
                double penalty_base   = 1.0;
                double penalty_factor = 1.2;



                // equation assembly
                // -----------------
                string[] CodNames = D.ForLoop(i => "C" + i);
                Operator = new SpatialOperator(VariableNames.VelocityVector(D), new string[] { VariableNames.ViscosityMolecular }, CodNames, QuadOrderFunc.Linear());

                for (int d = 0; d < D; d++)
                {
                    if ((this.whichTerms & Terms.T1) != 0)
                    {
                        var flx1 = new swipViscosity_Term1(penalty_base * penalty_factor, d, D, BcMap, ViscosityOption.VariableViscosity);

                        flx1.g_Diri_Override = this.solution.U;
                        flx1.g_Neu_Override  = this.solution.dU;
                        Operator.EquationComponents[CodNames[d]].Add(flx1);
                    }
                    if ((this.whichTerms & Terms.T2) != 0)
                    {
                        var flx2 = new swipViscosity_Term2(penalty_base * penalty_factor, d, D, BcMap, ViscosityOption.VariableViscosity);

                        flx2.g_Diri_Override = this.solution.U;
                        flx2.g_Neu_Override  = this.solution.dU;
                        Operator.EquationComponents[CodNames[d]].Add(flx2);
                    }
                    if ((this.whichTerms & Terms.T3) != 0)
                    {
                        var flx3 = new swipViscosity_Term3(penalty_base * penalty_factor, d, D, BcMap, ViscosityOption.VariableViscosity);

                        flx3.g_Diri_Override = this.solution.U;
                        flx3.g_Neu_Override  = this.solution.dU;
                        Operator.EquationComponents[CodNames[d]].Add(flx3);
                    }
                } // */
                Operator.Commit();


                var map = this.U.Mapping;
                OperatorMtx = new MsrMatrix(map, map);
                Operator.ComputeMatrixEx(map, new DGField[] { this.mu }, map,
                                         OperatorMtx, this.bnd.CoordinateVector,
                                         volQuadScheme: null, edgeQuadScheme: null);

                // test for matrix symmetry
                // ========================

                if (base.MPISize == 1)
                {
                    double MatrixAssymmetry = OperatorMtx.SymmetryDeviation();
                    Console.WriteLine("Matrix asymmetry: " + MatrixAssymmetry);
                    Assert.LessOrEqual(Math.Abs(MatrixAssymmetry), 1.0e-10);
                }
            }
        }