void MiniTensorVector<T, N>:: axpy(T const alpha, Vector<T> const & x) { Intrepid2::Vector<T, N> const xval = MTfromROL<T, N>(x); auto const dim = xval.get_dimension(); assert(vector_.get_dimension() == dim); for (Intrepid2::Index i{0}; i < dim; ++i) { vector_(i) += alpha * xval(i); } }
Intrepid2::Vector<T, N> CP::ResidualSlipNLS<NumDimT, NumSlipT, EvalT>::gradient( Intrepid2::Vector<T, N> const & x) { // Get a convenience reference to the failed flag in case it is used more // than once. bool & failed = Base::failed; // Tensor mechanical state variables Intrepid2::Tensor<T, NumDimT> Fp_np1(num_dim_); Intrepid2::Tensor<T, NumDimT> Lp_np1(num_dim_); Intrepid2::Tensor<T, NumDimT> sigma_np1(num_dim_); Intrepid2::Tensor<T, NumDimT> S_np1(num_dim_); // Slip system state variables Intrepid2::Vector<T, NumSlipT> state_hardening_np1(num_slip_); Intrepid2::Vector<T, NumSlipT> slip_resistance(num_slip_); Intrepid2::Vector<T, NumSlipT> slip_np1(num_slip_); Intrepid2::Vector<T, NumSlipT> slip_computed(num_slip_); Intrepid2::Vector<T, NumSlipT> shear_np1(num_slip_); Intrepid2::Vector<T, NumSlipT> rate_slip(num_slip_); auto const num_unknowns = x.get_dimension(); Intrepid2::Vector<T, N> residual(num_unknowns); // Return immediately if something failed catastrophically. if (failed == true) { residual.fill(Intrepid2::ZEROS); return residual; } Intrepid2::Tensor<T, NumDimT> const F_np1_peeled = LCM::peel_tensor<EvalT, T, N, NumDimT>()(F_np1_); Intrepid2::Tensor4<T, NumDimT> const C_peeled = LCM::peel_tensor4<EvalT, T, N, NumDimT>()(C_); for (int i = 0; i< num_slip_; ++i){ slip_np1[i] = x[i]; } if(dt_ > 0.0){ rate_slip = (slip_np1 - slip_n_) / dt_; } else{ rate_slip.fill(Intrepid2::ZEROS); } // Ensure that the slip increment is bounded if (Intrepid2::norm(rate_slip * dt_) > 1.0) { failed = true; return residual; } // Compute Lp_np1, and Fp_np1 CP::applySlipIncrement<NumDimT, NumSlipT, T>( slip_systems_, dt_, slip_n_, slip_np1, Fp_n_, Lp_np1, Fp_np1); // Compute sigma_np1, S_np1, and shear_np1 CP::computeStress<NumDimT, NumSlipT, T>( slip_systems_, C_peeled, F_np1_peeled, Fp_np1, sigma_np1, S_np1, shear_np1); // Compute state_hardening_np1 CP::updateHardness<NumDimT, NumSlipT, T>( slip_systems_, slip_families_, dt_, rate_slip, state_hardening_n_, state_hardening_np1, slip_resistance); // Compute slips CP::updateSlip<NumDimT, NumSlipT, T>( slip_systems_, slip_families_, dt_, slip_resistance, shear_np1, slip_n_, slip_computed); for (int i = 0; i< num_slip_; ++i){ residual[i] = slip_np1[i] - slip_computed[i]; } // ***** Residual scaling done below is commented out for now since it is in a preliminary stage. // RealType // norm_resid = Sacado::ScalarValue<T>::eval(Intrepid2::norm(residual)); // RealType // max_tol = std::numeric_limits<RealType>::max(); // if (norm_resid > 0.5 * std::pow(max_tol, 1.0 / 10.0)) { // residual *= 1.0 / norm_resid; // } return residual; }
void FerroicModel<EvalT>:: computeState( const Intrepid2::Tensor<ScalarT, FM::THREE_D>& x, const Intrepid2::Vector<ScalarT, FM::THREE_D>& E, const Teuchos::Array<RealType>& oldfractions, Intrepid2::Tensor<ScalarT, FM::THREE_D>& X, Intrepid2::Vector<ScalarT, FM::THREE_D>& D, Teuchos::Array<ScalarT>& newfractions) /******************************************************************************/ { // create non-linear system // using NLS = FM::DomainSwitching<EvalT>; NLS domainSwitching(crystalVariants, transitions, tBarriers, oldfractions, aMatrix, x, E, /* dt= */ 1.0); // solution variable // Intrepid2::Vector<ScalarT,FM::MAX_TRNS> xi; // solve for xi // switch (m_integrationType){ default: break; case FM::IntegrationType::EXPLICIT: { switch (m_explicitMethod){ default: break; case FM::ExplicitMethod::SCALED_DESCENT: { FM::ScaledDescent(domainSwitching, xi); } case FM::ExplicitMethod::DESCENT_NORM: { FM::DescentNorm(domainSwitching, xi); } } } case FM::IntegrationType::IMPLICIT: { // create minimizer using ValueT = typename Sacado::ValueType<ScalarT>::type; using MIN = Intrepid2::Minimizer<ValueT, MAX_TRNS>; MIN minimizer; // create stepper using STEP = Intrepid2::StepBase<NLS, ValueT, MAX_TRNS>; std::unique_ptr<STEP> pstep = Intrepid2::stepFactory<NLS, ValueT, MAX_TRNS>(m_step_type); STEP &step = *pstep; // create solution vector with initial guess int ntrans = domainSwitching.getNumStates(); xi.set_dimension(ntrans); for(int itrans=0; itrans<ntrans; itrans++) xi(itrans) = Sacado::ScalarValue<ScalarT>::eval(0.0); // solve LCM::MiniSolver<MIN, STEP, NLS, EvalT, MAX_TRNS> mini_solver(minimizer, step, domainSwitching, xi); } } // update based on new xi values // }