Ejemplo n.º 1
0
        public Vector CalcLagrangeMultipliers(Feti1FlexibilityMatrix flexibility, IFetiPreconditioner preconditioner,
                                              Feti1Projection projection, Vector disconnectedDisplacements, Vector rigidBodyModesWork, double globalForcesNorm,
                                              SolverLogger logger)
        {
            int               systemOrder       = flexibility.Order;
            PcgMatrix         pcgMatrix         = DefinePcgMatrix(flexibility, projection);
            PcgPreconditioner pcgPreconditioner = DefinePcgPreconditioner(preconditioner, projection);

            // λ0 = Q * G * inv(G^T * Q * G) * e
            Vector lagrangesParticular = projection.CalcParticularLagrangeMultipliers(rigidBodyModesWork);

            // Calculate rhs of the projected interface system: rhs = P^T * (d - F * λ0)
            var r0 = flexibility.Multiply(lagrangesParticular);

            r0.LinearCombinationIntoThis(-1.0, disconnectedDisplacements, 1.0);
            var pcgRhs = Vector.CreateZero(systemOrder);

            projection.ProjectVector(r0, pcgRhs, true);

            // Solve the interface problem using PCG algorithm
            var pcgBuilder = new PcgAlgorithm.Builder();

            pcgBuilder.MaxIterationsProvider = maxIterationsProvider;
            pcgBuilder.ResidualTolerance     = pcgConvergenceTolerance;
            pcgBuilder.Convergence           = pcgConvergenceStrategyFactory.CreateConvergenceStrategy(globalForcesNorm);
            PcgAlgorithm        pcg          = pcgBuilder.Build();
            var                 lagrangesBar = Vector.CreateZero(systemOrder);
            IterativeStatistics stats        = pcg.Solve(pcgMatrix, pcgPreconditioner, pcgRhs, lagrangesBar, true,
                                                         () => Vector.CreateZero(systemOrder));

            if (!stats.HasConverged)
            {
                throw new IterativeSolverNotConvergedException(Feti1Solver.name + " did not converge to a solution. PCG"
                                                               + $" algorithm run for {stats.NumIterationsRequired} iterations and the residual norm ratio was"
                                                               + $" {stats.ResidualNormRatioEstimation}");
            }

            // Calculate the actual lagrange multipliers from the separation formula: λ = λ0 + P * λbar
            var lagranges = Vector.CreateZero(systemOrder);

            projection.ProjectVector(lagrangesBar, lagranges, false);
            lagranges.AddIntoThis(lagrangesParticular);

            // Log statistics about PCG execution
            logger.LogIterativeAlgorithm(stats.NumIterationsRequired, stats.ResidualNormRatioEstimation);
            return(lagranges);
        }
Ejemplo n.º 2
0
        public Vector CalcLagrangeMultipliers(Feti1FlexibilityMatrix flexibility, IFetiPreconditioner preconditioner,
                                              Feti1Projection projection, Vector disconnectedDisplacements, Vector rigidBodyModesWork, double globalForcesNorm,
                                              SolverLogger logger)
        {
            // PCPG starts from the particular lagrange multipliers: λ0 = Q * G * inv(G^T * Q * G) * e
            Vector lagranges = projection.CalcParticularLagrangeMultipliers(rigidBodyModesWork);
            IFetiPcgConvergence pcpgConvergenceStrategy =
                pcgConvergenceStrategyFactory.CreateConvergenceStrategy(globalForcesNorm);
            var pcpg = new PcpgAlgorithm(maxIterationsProvider, pcpgConvergenceTolerance, pcpgConvergenceStrategy);
            IterativeStatistics stats =
                pcpg.Solve(flexibility, preconditioner, projection, disconnectedDisplacements, lagranges);

            if (!stats.HasConverged)
            {
                throw new IterativeSolverNotConvergedException(Feti1Solver.name + " did not converge to a solution. PCPG"
                                                               + $" algorithm run for {stats.NumIterationsRequired} iterations and the residual norm ratio was"
                                                               + $" {stats.ResidualNormRatioEstimation}");
            }

            // Log statistics about PCG execution
            logger.LogIterativeAlgorithm(stats.NumIterationsRequired, stats.ResidualNormRatioEstimation);
            return(lagranges);
        }