Newton-Raphson solver (pyfe3d.solver.newton_raphson)#
Load-controlled Newton-Raphson solver of the non-linear static analyses of
Analysis, selected with Analysis.NL_method = 'NR'. The
module-level constants control the step size and the divergence checks, and
they are shared with the arc-length solvers of arc_length.
- pyfe3d.solver.newton_raphson.DIVERGENCE_FACTOR = 1000.0#
A step diverged when its residual norm becomes larger than this factor times the residual norm at the start of the step
- pyfe3d.solver.newton_raphson.INC_CUT_FACTOR = 0.5#
Factor used to reduce the load increment when a step fails to converge
- pyfe3d.solver.newton_raphson.INC_GROWTH_FACTOR = 1.1111#
Factor used to increase the load increment after a step that converged without being cut
- pyfe3d.solver.newton_raphson.LINE_SEARCH_ALPHA = 0.0001#
Constant of the sufficient-decrease (Armijo) test of the line search
- pyfe3d.solver.newton_raphson.NUM_ITER_BEFORE_DIVERGENCE_CHECK = 5#
Number of iterations of a step before the divergence and too-slow checks are activated. A non-monotonic residual in the first iterations is normal, especially in postbuckling
- pyfe3d.solver.newton_raphson.TOO_SLOW_WINDOW = 5#
The convergence is too slow when the smallest residual norm of the last
TOO_SLOW_WINDOWiterations is not at leasttoo_slow_TOL(relative) smaller than the smallest residual norm of the previous iterations
- pyfe3d.solver.newton_raphson._NR_iterations(an, pb, c, dc, total, fext, w, kT0=None, silent=False, lbd_dependent=False, q=None, K0_abs=None)#
Newton-Raphson iterations at a fixed load factor
Corrects the predictor
dcat the load factortotaluntil the convergence criterion ofcheck_convergence()is satisfied, or until the iterations are stopped by_check_divergence()or by a singular tangent stiffness matrix. The tangent stiffness matrix iscalc_kC + calc_kGat the current iterate, seecallbacks.calc_kT(); its updates and the line search are controlled byan.modified_NR,an.compute_every_n,an.line_searchandan.max_iter_line_search.- Parameters:
- an
Analysis Analysis object with the parameters of the solver.
- pbobject
Object with the callables,
anitself or aFreeDofs.- cnp.ndarray
Solution at the last converged state.
- dcnp.ndarray
Predictor of the solution increment.
- totalfloat
Load factor, dimensionless.
- fextnp.ndarray
External force vector for a unit load factor.
- wnp.ndarray or None
Weights of Crisfield’s criterion, see
crisfield_weights(),Nonewith the relative criterion.- kT0sparse_matrix or None, optional
Tangent stiffness matrix used in the first iteration when
an.modified_NR=True. IfNoneit is calculated atc + dc. DefaultNone.- silentbool, optional
Whether the log messages are suppressed. Default
False.- lbd_dependentbool, optional
Whether
calc_fextacceptslbd, seecallbacks;total*q, with \(\boldsymbol{q} = -\partial \boldsymbol{R}/\partial \lambda\), is then an additional reference of the convergence criterion. \(\boldsymbol{q}\) is evaluated together with the tangent stiffness matrix, at the same iterate, and the last one evaluated is the reference until the next update of the tangent. DefaultFalse.- qnp.ndarray or None, optional
The last \(\boldsymbol{q}\) evaluated before these iterations, the reference until the first update of the tangent stiffness matrix, used only when
lbd_dependent=True. DefaultNone.- K0_abssparse_matrix or None, optional
\(|\boldsymbol{K}_{C0}|\) of the round-off floor of the convergence criteria, see
check_convergence(), computed frompb.calc_kC()whenNone. DefaultNone.
- an
- Returns:
- convergedbool
Whether the iterations converged.
- dcnp.ndarray
Solution increment, such that
c + dcis the solution.- qnp.ndarray or None
The last \(\boldsymbol{q}\) evaluated,
Nonewhenlbd_dependent=False.
Notes
At each iteration, with the load factor \(\lambda\) =
totalfixed,\[\boldsymbol{R} = \boldsymbol{F}_{int}(\boldsymbol{c} + \Delta \boldsymbol{c}, \lambda) - \lambda \boldsymbol{F}_{ext}, \qquad \boldsymbol{K}_T \delta \boldsymbol{c} = -\boldsymbol{R}, \qquad \Delta \boldsymbol{c} \leftarrow \Delta \boldsymbol{c} + \eta \delta \boldsymbol{c}\]With full Newton-Raphson, \(\boldsymbol{K}_T\) is computed and factorized at every iteration at \(c + \Delta c\), and the convergence is quadratic when it is the exact Jacobian \(\partial \boldsymbol{R}/\partial \boldsymbol{c}\) ([1], Section 1.2.2, p. 9). With
an.modified_NR = True, \(\boldsymbol{K}_T\) is computed at the first iteration, or given askT0, and then everyan.compute_every_niterations, its LU factorization being reused in the other iterations.\(\eta = 1\) without line search. With
an.line_search = True, with \(\phi(\eta) = \|\boldsymbol{R}(\boldsymbol{c} + \Delta \boldsymbol{c} + \eta \, \delta \boldsymbol{c})\|^2\) in the norm of the convergence criterion, the scaled norm \(\|\cdot\|_{\boldsymbol{d}}\) of Crisfield’s criterion or the Euclidean norm, the step \(\eta\) is accepted when it satisfies the sufficient-decrease (Armijo) test\[\phi(\eta) \le (1 - 2 \alpha \eta) \phi(0)\]with \(\alpha\) =
LINE_SEARCH_ALPHA, which assumes \(\phi'(0) = -2\phi(0)\), exact for a Newton direction in any norm whose weights do not change along the line, i.e. when \(\boldsymbol{K}_T\) is the exact Jacobian at \(c + \Delta c\); withan.modified_NR = Trueit is an approximation. The full step \(\eta = 1\) is tried first. Otherwise \(\eta\) is replaced by the minimizer \(\phi(0)/A\) of the quadratic interpolation of \(\phi(0)\), \(\phi'(0)\) and \(\phi(\eta)\), with \(A = (\phi(\eta) - \phi(0) + 2\phi(0)\eta)/\eta^2\), or by \(\eta/2\) when \(A\) is not finite or not positive, safeguarded in \([0.1 \eta, 0.5 \eta]\). Afteran.max_iter_line_searchreductions the last \(\eta\) is accepted. The internal force vector of the accepted point is reused in the residual of the next iteration.The line search is adapted from the backtracking line search of [2] (Section 6.3.2, Algorithm 6.3.5, pp. 126-129, and Algorithm A6.3.1, pp. 325-327), applied to nonlinear equations with the merit function \(f = \frac{1}{2}\|D_F F\|^2\) ([2], Section 6.5, Eq. (6.5.3), p. 147, and Algorithm NEFN, p. 303), whose directional derivative along the Newton step is \(-F^\top F = -2f\) (p. 148, with \(D_F\) the identity). With \(F = R\), whose Jacobian is \(\boldsymbol{K}_T\), and \(\phi = 2f\), \(D_F\) being the identity with the Euclidean norm or \(\mathrm{diag}(\sqrt{w_j})\) with Crisfield’s criterion, the test above is their condition (6.3.3) (p. 118) with their \(\alpha = 10^{-4}\) (p. 126), and the first reduction is their quadratic backtrack, Eq. (6.3.17) (p. 127). It differs from Algorithm A6.3.1 in that: the quadratic interpolation through the last trial \(\eta\) is used at every reduction, whereas [2] uses, from the second backtrack on, the cubic interpolation of \(f(0)\), \(f'(0)\) and the last two trial values, Eq. (6.3.18) (p. 128); the bound \(0.5 \eta\) is also imposed at the first reduction, where [2] imposes only the lower bound \(0.1\), the quadratic backtrack being then smaller than \(1/(2(1 - \alpha))\) (p. 127; Algorithm A6.3.1, steps 10.3c.1E.4 and 10.3c.4); and [2] has no maximum number of reductions, but limits the length of the step to
maxstepand stops when the step length becomes smaller than a minimum, returning the current point.References
[1]Crisfield, M. A., Non-linear Finite Element Analysis of Solids and Structures, Volume 1: Essentials, John Wiley & Sons, Chichester, 1991.
- pyfe3d.solver.newton_raphson._abs_matrix(kC0)#
Elementwise absolute value \(|\boldsymbol{K}_{C0}|\) of the linear stiffness matrix
kC0, sparse, for the round-off floor of the convergence criteria, seeroundoff_floor()
- pyfe3d.solver.newton_raphson._check_divergence(an, Rnorm, Rnorms, iteration, silent=False)#
Check if the iterations of a step must be stopped without convergence
The iterations are stopped when the residual is not finite, when
an.maxNumItercorrections were done, and, afterNUM_ITER_BEFORE_DIVERGENCE_CHECKiterations, when the residual diverges or when the convergence is too slow.- Parameters:
- an
Analysis Analysis object with the attributes
maxNumIterandtoo_slow_TOL.- Rnormfloat
Norm of the residual at the current iteration, the norm of the convergence criterion, see
check_convergence().- Rnormslist
Norms of the residual at the previous iterations of the step; the current norm is appended to it.
- iterationint
Current iteration, starting at 1.
- silentbool, optional
Whether the log messages are suppressed. Default
False.
- an
- Returns:
- stopbool
Whether the iterations must be stopped.
Notes
With \(r_i\) the residual norm at the iteration \(i\) of the step, \(r_1\) being the residual of the predictor, the iterations are stopped at the iteration \(j\) when:
\(r_j\) is not finite;
\(j >\)
an.maxNumIter, i.e.an.maxNumItercorrections were done;\(j >\)
NUM_ITER_BEFORE_DIVERGENCE_CHECKand \(r_j >\)DIVERGENCE_FACTOR\(r_1\) (divergence);\(j >\)
NUM_ITER_BEFORE_DIVERGENCE_CHECK, \(j > W\) and \(\min(r_{j-W+1}, ..., r_j) > (1 -\)an.too_slow_TOL\() \min(r_1, ..., r_{j-W})\), with \(W\) =TOO_SLOW_WINDOW(too slow convergence).
The divergence and too-slow checks are delayed because a non-monotonic residual in the first iterations is normal, especially in postbuckling. The checks only compare norms of the same step with each other, and with the scaled norm of Crisfield’s criterion they do not depend on the units of the degrees-of-freedom.
- pyfe3d.solver.newton_raphson._log_iteration(an, iteration, R, zeta, silent, lbd=None, roundoff=False)#
Message of one equilibrium iteration, with \(\zeta\) of Crisfield’s criterion or the relative residual of the relative criterion, marked when the iteration converged by the round-off floor only, see
check_convergence()
- pyfe3d.solver.newton_raphson._norm(v, w)#
Norm of the convergence criterion: \(\|v\|_{\boldsymbol{d}}\) with the weights
wof Crisfield’s criterion, the Euclidean norm whenwisNone
- pyfe3d.solver.newton_raphson._solver_NR(an, pb, silent=False, initialInc=None)#
Newton-Raphson solver with load control
Used by
Analysis.static()whenNL_method='NR'. The load factor goes from zero to one in increments; at each increment the equilibrium of the internal force vector with the external force vector scaled by the load factor is solved with the iterations of_NR_iterations(), starting from a predictor extrapolated from the previous converged increment, and the converged load factors and solutions are appended toan.incrementsandan.cs.The variant of the iterations is selected by
an.modified_NR,an.compute_every_n,an.kT_initial_state,an.line_searchandan.max_iter_line_search, and the convergence criterion byan.convergence, seecheck_convergence(). A step that does not converge withinan.maxNumIteriterations, that diverges or that converges too slowly is repeated with the load increment multiplied byINC_CUT_FACTOR, see_check_divergence(). After a step that converged without being cut, the load increment is multiplied byINC_GROWTH_FACTOR, limited byan.maxInc. The last step is adjusted such that the analysis finishes at a load factor of exactly1.0. The analysis stops earlier, keeping the converged increments, when the load increment becomes smaller thanan.minInc.- Parameters:
- an
Analysis Analysis object; the converged load factors and solutions are appended to
an.incrementsandan.cs.- pbobject
Object with the callables,
anitself or aFreeDofs.- silentbool, optional
Whether the log messages are suppressed. Default
False.- initialIncfloat or None, optional
Initial load increment, dimensionless;
an.initialIncis used ifNone. DefaultNone.
- an
Notes
The load factor \(\lambda\) goes from zero to one in increments, solving at each increment
\[\boldsymbol{R} = \boldsymbol{F}_{int}(\boldsymbol{c}) - \lambda \boldsymbol{F}_{ext} = \boldsymbol{0}\]Each increment starts from a predictor that extrapolates the previous converged increment of the solution, scaled by the ratio between the new and the previous load increments. The first increment uses the linear solution as predictor: \(\Delta\lambda \boldsymbol{K}_{C0}^{-1} \boldsymbol{F}_{ext}\), with \(\boldsymbol{K}_{C0}\) the linear stiffness matrix
calc_kC(), which also gives the scaling of Crisfield’s criterion, computed once for the whole analysis, seeconvergence.The callables that accept the keyword argument
increceive the load factor \(\lambda\) of the step, seecallbacks, which allows configuration-dependent loads such as follower pressures.When
calc_fextaccepts the keyword argumentlbd, e.g. for prescribed displacements imposed exactly, the load vector \(\boldsymbol{q} = -\partial \boldsymbol{R}/\partial \lambda\) at \(\boldsymbol{c} = \boldsymbol{0}\), \(\lambda = 0\) gives the predictor of the first increment, its linear solution \(\boldsymbol{K}_{C0}^{-1} \boldsymbol{q}\), instead of the linear solution of the reference vector, which is null under a prescribed displacement alone, and \(\lambda \boldsymbol{q}\) is an additional reference of the convergence criterion. \(\boldsymbol{q}\) is evaluated together with the tangent stiffness matrix, at the same iterate, i.e.calc_fextis called once per update of the tangent stiffness matrix, and the last \(\boldsymbol{q}\) evaluated is the reference of the next convergence checks, also in the next step.By default full Newton-Raphson is used, i.e. the tangent stiffness matrix is rebuilt at every iteration, which gives quadratic convergence when it is the exact Jacobian of the internal force vector. With
an.modified_NR = Trueit is rebuilt only at the first iteration of each step and everyan.compute_every_niterations, and its LU factorization is reused in the other iterations, at the cost of a linear convergence rate; at the first step withan.kT_initial_state = False, \(\boldsymbol{K}_{C0}\) is used instead of the tangent at the first iteration. The full and modified Newton-Raphson methods, combined with incremental predictors, are described in [1] (Sections 1.2.2 and 1.2.3, pp. 8-13), with the quadratic and the linear convergence rates.The step that would end within
max(an.minInc, 1e-12)of the load factor 1.0, or beyond it, is replaced by the step to exactly 1.0.References
[1]Crisfield, M. A., Non-linear Finite Element Analysis of Solids and Structures, Volume 1: Essentials, John Wiley & Sons, Chichester, 1991.
- pyfe3d.solver.newton_raphson._weights(an, kC0)#
Weights of Crisfield’s criterion from the linear stiffness matrix
kC0, seecrisfield_weights(), orNonewithan.convergence = 'relative'