int InitialInterpolatedLineSearch::search(double s0, double s1, LinearSOE &theSOE, IncrementalIntegrator &theIntegrator) { double s = s1; //intialize r = ratio of residuals double r0 = 0.0; if ( s0 != 0.0 ) r0 = fabs( s / s0 ); if (r0 <= tolerance ) return 0; // Line Search Not Required Residual Decrease Less Than Tolerance double eta = 1.0; //initial value of line search parameter double etaPrev = 1.0; double r = r0; const Vector &dU = theSOE.getX(); int count = 0; //intial value of iteration counter if (printFlag == 0) { opserr << "InitialInterpolated Line Search - initial " << " eta : " << eta << " , Ratio |s/s0| = " << r0 << endln; } // Solution procedure follows the one in Crissfields book. // (M.A. Crissfield, Nonlinear Finite Element Analysis of Solid and Structures, Wiley. 97). // NOTE: it is not quite linear interpolation/false-position/regula-falsi as eta(0) = 0.0 // does not change. uses eta(i) = eta(i-1)*s0 // ----------- // s0 - s(i-1) to compute eta(i) // opserr << "dU: " << dU; while ( r > tolerance && count < maxIter ) { count++; eta *= s0 / (s0 - s); //-- want to put limits on eta(i) if (eta > maxEta) eta = maxEta; if (r > r0 ) eta = 1.0; if (eta < minEta) eta = minEta; if (eta == etaPrev) break; // no change in response break //dx = ( eta * dx0 ); *x = dU; *x *= eta-etaPrev; if (theIntegrator.update(*x) < 0) { opserr << "WARNInG InitialInterpolatedLineSearch::search() -"; opserr << "the Integrator failed in update()\n"; return -1; } if (theIntegrator.formUnbalance() < 0) { opserr << "WARNInG InitialInterpolatedLineSearch::search() -"; opserr << "the Integrator failed in formUnbalance()\n"; return -2; } //new residual const Vector &ResidI = theSOE.getB(); //new value of s s = dU ^ ResidI; //new value of r r = fabs( s / s0 ); if (printFlag == 0) { opserr << "InitialInterpolated Line Search - iteration: " << count << " , eta(j) : " << eta << " , Ratio |sj/s0| = " << r << endln; } // reset the variables, also check not just hitting bounds over and over if (eta == etaPrev) count = maxIter; else etaPrev = eta; } //end while // set X in the SOE for the revised dU, needed for convergence tests *x = dU; if (eta != 0.0) *x *= eta; theSOE.setX(*x); return 0; }
int PeriodicNewton::solveCurrentStep(void) { // set up some pointers and check they are valid // NOTE this could be taken away if we set Ptrs as protecetd in superclass AnalysisModel *theAnalysisModel = this->getAnalysisModelPtr(); IncrementalIntegrator *theIncIntegratorr = this->getIncrementalIntegratorPtr(); LinearSOE *theSOE = this->getLinearSOEptr(); if ((theAnalysisModel == 0) || (theIncIntegratorr == 0) || (theSOE == 0) || (theTest == 0)){ opserr << "WARNING PeriodicNewton::solveCurrentStep() - setLinks() has"; opserr << " not been called - or no ConvergenceTest has been set\n"; return -5; } // we form the tangent if (theIncIntegratorr->formUnbalance() < 0) { opserr << "WARNING PeriodicNewton::solveCurrentStep() -"; opserr << "the Integrator failed in formUnbalance()\n"; return -2; } if (theIncIntegratorr->formTangent(tangent) < 0){ opserr << "WARNING PeriodicNewton::solveCurrentStep() -"; opserr << "the Integrator failed in formTangent()\n"; return -1; } // set itself as the ConvergenceTest objects EquiSolnAlgo theTest->setEquiSolnAlgo(*this); if (theTest->start() < 0) { opserr << "PeriodicNewton::solveCurrentStep() -"; opserr << "the ConvergenceTest object failed in start()\n"; return -3; } // repeat until convergence is obtained or reach max num iterations int result = -1; int count = 0; int iter = 0; do { if (theSOE->solve() < 0) { opserr << "WARNING PeriodicNewton::solveCurrentStep() -"; opserr << "the LinearSysOfEqn failed in solve()\n"; return -3; } if (theIncIntegratorr->update(theSOE->getX()) < 0) { opserr << "WARNING PeriodicNewton::solveCurrentStep() -"; opserr << "the Integrator failed in update()\n"; return -4; } if (theIncIntegratorr->formUnbalance() < 0) { opserr << "WARNING PeriodicNewton::solveCurrentStep() -"; opserr << "the Integrator failed in formUnbalance()\n"; return -2; } this->record(count++); result = theTest->test(); iter++; if (iter > maxCount) { if (theIncIntegratorr->formTangent(tangent) < 0){ opserr << "WARNING PeriodicNewton::solveCurrentStep() -"; opserr << "the Integrator failed in formTangent()\n"; return -1; } iter = 0; } } while (result == -1); if (result == -2) { opserr << "PeriodicNewton::solveCurrentStep() -"; opserr << "the ConvergenceTest object failed in test()\n"; return -3; } return result; }
int HHTGeneralized_TP::newStep(double _deltaT) { if (beta == 0 || gamma == 0 ) { opserr << "HHTGeneralized_TP::newStep() - error in variable\n"; opserr << "gamma = " << gamma << " beta = " << beta << endln; return -1; } deltaT = _deltaT; if (deltaT <= 0.0) { opserr << "HHTGeneralized_TP::newStep() - error in variable\n"; opserr << "dT = " << deltaT << endln; return -2; } // get a pointer to the LinearSOE and the AnalysisModel LinearSOE *theLinSOE = this->getLinearSOE(); AnalysisModel *theModel = this->getAnalysisModel(); if (theLinSOE == 0 || theModel == 0) { opserr << "WARNING HHT_TP::newStep() - "; opserr << "no LinearSOE or AnalysisModel has been set\n"; return -3; } // set the constants c1 = 1.0; c2 = gamma/(beta*deltaT); c3 = 1.0/(beta*deltaT*deltaT); if (U == 0) { opserr << "HHTGeneralized_TP::newStep() - domainChange() failed or hasn't been called\n"; return -4; } // set response at t to be that at t+deltaT of previous step (*Ut) = *U; (*Utdot) = *Udot; (*Utdotdot) = *Udotdot; // get unbalance at t and store it alphaM = (1.0 - alphaI); alphaD = alphaR = alphaP = (1.0 - alphaF); this->TransientIntegrator::formUnbalance(); (*Put) = theLinSOE->getB(); // determine new velocities and accelerations at t+deltaT double a1 = (1.0 - gamma/beta); double a2 = deltaT*(1.0 - 0.5*gamma/beta); Udot->addVector(a1, *Utdotdot, a2); double a3 = -1.0/(beta*deltaT); double a4 = 1.0 - 0.5/beta; Udotdot->addVector(a4, *Utdot, a3); // set the trial response quantities theModel->setVel(*Udot); theModel->setAccel(*Udotdot); // increment the time to t+deltaT and apply the load double time = theModel->getCurrentDomainTime(); time += deltaT; if (theModel->updateDomain(time, deltaT) < 0) { opserr << "HHTGeneralized_TP::newStep() - failed to update the domain\n"; return -5; } // modify constants for subsequent iterations alphaM = alphaI; alphaD = alphaR = alphaP = alphaF; return 0; }
int HHTGeneralized_TP::domainChanged() { AnalysisModel *myModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); const Vector &x = theLinSOE->getX(); int size = x.Size(); // create the new Vector objects if (Ut == 0 || Ut->Size() != size) { // delete the old if (Ut != 0) delete Ut; if (Utdot != 0) delete Utdot; if (Utdotdot != 0) delete Utdotdot; if (U != 0) delete U; if (Udot != 0) delete Udot; if (Udotdot != 0) delete Udotdot; if (Put != 0) delete Put; // create the new Ut = new Vector(size); Utdot = new Vector(size); Utdotdot = new Vector(size); U = new Vector(size); Udot = new Vector(size); Udotdot = new Vector(size); Put = new Vector(size); // check we obtained the new if (Ut == 0 || Ut->Size() != size || Utdot == 0 || Utdot->Size() != size || Utdotdot == 0 || Utdotdot->Size() != size || U == 0 || U->Size() != size || Udot == 0 || Udot->Size() != size || Udotdot == 0 || Udotdot->Size() != size || Put == 0 || Put->Size() != size) { opserr << "HHTGeneralized_TP::domainChanged - ran out of memory\n"; // delete the old if (Ut != 0) delete Ut; if (Utdot != 0) delete Utdot; if (Utdotdot != 0) delete Utdotdot; if (U != 0) delete U; if (Udot != 0) delete Udot; if (Udotdot != 0) delete Udotdot; if (Put != 0) delete Put; Ut = 0; Utdot = 0; Utdotdot = 0; U = 0; Udot = 0; Udotdot = 0; Put = 0; return -1; } } // now go through and populate U, Udot and Udotdot by iterating through // the DOF_Groups and getting the last committed velocity and accel DOF_GrpIter &theDOFs = myModel->getDOFs(); DOF_Group *dofPtr; while ((dofPtr = theDOFs()) != 0) { const ID &id = dofPtr->getID(); int idSize = id.Size(); int i; const Vector &disp = dofPtr->getCommittedDisp(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*U)(loc) = disp(i); } } const Vector &vel = dofPtr->getCommittedVel(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Udot)(loc) = vel(i); } } const Vector &accel = dofPtr->getCommittedAccel(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Udotdot)(loc) = accel(i); } } } return 0; }
int DisplacementControl::domainChanged(void) { // we first create the Vectors needed AnalysisModel *theModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); if (theModel == 0 || theLinSOE == 0) { opserr << "WARNING DisplacementControl::update() "; opserr << "No AnalysisModel or LinearSOE has been set\n"; return -1; } int size = theModel->getNumEqn(); // ask model in case N+1 space if (deltaUhat == 0 || deltaUhat->Size() != size) { // create new Vector if (deltaUhat != 0) delete deltaUhat; // delete the old deltaUhat = new Vector(size); if (deltaUhat == 0 || deltaUhat->Size() != size) { // check got it opserr << "FATAL DisplacementControl::domainChanged() - ran out of memory for"; opserr << " deltaUhat Vector of size " << size << endln; exit(-1); } } if (deltaUbar == 0 || deltaUbar->Size() != size) { // create new Vector if (deltaUbar != 0) delete deltaUbar; // delete the old deltaUbar = new Vector(size); if (deltaUbar == 0 || deltaUbar->Size() != size) { // check got it opserr << "FATAL DisplacementControl::domainChanged() - ran out of memory for"; opserr << " deltaUbar Vector of size " << size << endln; exit(-1); } } if (deltaU == 0 || deltaU->Size() != size) { // create new Vector if (deltaU != 0) delete deltaU; // delete the old deltaU = new Vector(size); if (deltaU == 0 || deltaU->Size() != size) { // check got it opserr << "FATAL DisplacementControl::domainChanged() - ran out of memory for"; opserr << " deltaU Vector of size " << size << endln; exit(-1); } } if (deltaUstep == 0 || deltaUstep->Size() != size) { if (deltaUstep != 0) delete deltaUstep; deltaUstep = new Vector(size); if (deltaUstep == 0 || deltaUstep->Size() != size) { opserr << "FATAL DisplacementControl::domainChanged() - ran out of memory for"; opserr << " deltaUstep Vector of size " << size << endln; exit(-1); } } if (phat == 0 || phat->Size() != size) { if (phat != 0) delete phat; phat = new Vector(size); if (phat == 0 || phat->Size() != size) { opserr << "FATAL DisplacementControl::domainChanged() - ran out of memory for"; opserr << " phat Vector of size " << size << endln; exit(-1); } } // now we have to determine phat // do this by incrementing lambda by 1, applying load // and getting phat from unbalance. currentLambda = theModel->getCurrentDomainTime(); currentLambda += 1.0; theModel->applyLoadDomain(currentLambda); this->formUnbalance(); // NOTE: this assumes unbalance at last was 0 (*phat) = theLinSOE->getB(); currentLambda -= 1.0; theModel->setCurrentDomainTime(currentLambda); // check there is a reference load int haveLoad = 0; for (int i=0; i<size; i++) if ( (*phat)(i) != 0.0 ) { haveLoad = 1; i = size; } if (haveLoad == 0) { opserr << "WARNING DisplacementControl::domainChanged() - zero reference load"; return -1; } // lastly we determine the id of the nodal dof // EXTRA CODE TO DO SOME ERROR CHECKING REQUIRED Node *theNodePtr = theDomain->getNode(theNode); if (theNodePtr == 0) { opserr << "DisplacementControl::domainChanged - no node\n"; return -1; } DOF_Group *theGroup = theNodePtr->getDOF_GroupPtr(); if (theGroup == 0) { return 0; } const ID &theID = theGroup->getID(); theDofID = theID(theDof); return 0; }
int DisplacementControl::newStep(void) { if (theDofID == -1) { opserr << "DisplacementControl::newStep() - domainChanged has not been called\n"; return -1; } // get pointers to AnalysisModel and LinearSOE AnalysisModel *theModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); if (theModel == 0 || theLinSOE == 0) { opserr << "WARNING DisplacementControl::newStep() "; opserr << "No AnalysisModel or LinearSOE has been set\n"; return -1; } // determine increment for this iteration double factor = specNumIncrStep/numIncrLastStep; theIncrement *=factor; if (theIncrement < minIncrement) theIncrement = minIncrement; else if (theIncrement > maxIncrement) theIncrement = maxIncrement; // get the current load factor currentLambda = theModel->getCurrentDomainTime(); // determine dUhat this->formTangent(); theLinSOE->setB(*phat); if (theLinSOE->solve() < 0) { opserr << "DisplacementControl::newStep(void) - failed in solver\n"; return -1; } (*deltaUhat) = theLinSOE->getX(); Vector &dUhat = *deltaUhat; double dUahat = dUhat(theDofID); if (dUahat == 0.0) { opserr << "WARNING DisplacementControl::newStep() "; opserr << "dUahat is zero -- zero reference displacement at control node DOF\n"; return -1; } // determine delta lambda(1) == dlambda double dLambda = theIncrement/dUahat; deltaLambdaStep = dLambda; currentLambda += dLambda; // opserr << "DisplacementControl: " << dUahat << " " << theDofID << endln; // opserr << "DisplacementControl::newStep() : " << deltaLambdaStep << endln; // determine delta U(1) == dU (*deltaU) = dUhat; (*deltaU) *= dLambda; (*deltaUstep) = (*deltaU); // update model with delta lambda and delta U theModel->incrDisp(*deltaU); theModel->applyLoadDomain(currentLambda); if (theModel->updateDomain() < 0) { opserr << "DisplacementControl::newStep - model failed to update for new dU\n"; return -1; } numIncrLastStep = 0; return 0; }
int SecantLineSearch::search(double s0, double s1, LinearSOE &theSOE, IncrementalIntegrator &theIntegrator) { double r0 = 0.0; if ( s0 != 0.0 ) r0 = fabs( s1 / s0 ); if (r0 <= tolerance ) return 0; // Line Search Not Required Residual Decrease Less Than Tolerance if (s1 == s0) return 0; // Secant will have a divide-by-zero if continue // set some variables double eta = 1.0; double s = s1; double etaJ = 1.0; double etaJm1 = 0.0; double sJ = s1; double sJm1 = s0; double r = r0; const Vector &dU = theSOE.getX(); if (printFlag == 0) { opserr << "Secant Line Search - initial: " << " eta(0) : " << eta << " , Ratio |s/s0| = " << r0 << endln; } // perform the secant iterations: // // eta(j+1) = eta(j) - s(j) * (eta(j-1)-eta(j)) // ------------------------ // s(j-1) - s(j) int count = 0; //intial value of iteration counter while ( r > tolerance && count < maxIter ) { count++; eta = etaJ - sJ * (etaJm1-etaJ) / (sJm1 - sJ); //-- want to put limits on eta and stop solution blowing up if (eta > maxEta) eta = maxEta; if (r > r0 ) eta = 1.0; if (eta < minEta) eta = minEta; //update the incremental difference in response and determine new unbalance if (eta == etaJ) break; // no change in response *x = dU; *x *= eta-etaJ; if (theIntegrator.update(*x) < 0) { opserr << "WARNING SecantLineSearch::search() -"; opserr << "the Integrator failed in update()\n"; return -1; } if (theIntegrator.formUnbalance() < 0) { opserr << "WARNING SecantLineSearch::search() -"; opserr << "the Integrator failed in formUnbalance()\n"; return -2; } //new residual const Vector &ResidJ = theSOE.getB(); //new value of s s = dU ^ ResidJ; //new value of r r = fabs( s / s0 ); if (printFlag == 0) { opserr << "Secant Line Search - iteration: " << count << " , eta(j) : " << eta << " , Ratio |sj/s0| = " << r << endln; } if (etaJ == eta) count = maxIter; // set variables for next iteration etaJm1 = etaJ; etaJ = eta; sJm1 = sJ; sJ = s; if (sJm1 == sJ) count = maxIter; } //end while // set X in the SOE for the revised dU, needed for convergence tests *x = dU; *x *= eta; theSOE.setX(*x); return 0; }
int CollocationHSFixedNumIter::domainChanged() { AnalysisModel *myModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); const Vector &x = theLinSOE->getX(); int size = x.Size(); // if damping factors exist set them in the ele & node of the domain if (alphaM != 0.0 || betaK != 0.0 || betaKi != 0.0 || betaKc != 0.0) myModel->setRayleighDampingFactors(alphaM, betaK, betaKi, betaKc); // create the new Vector objects if (Ut == 0 || Ut->Size() != size) { // delete the old if (Ut != 0) delete Ut; if (Utdot != 0) delete Utdot; if (Utdotdot != 0) delete Utdotdot; if (U != 0) delete U; if (Udot != 0) delete Udot; if (Udotdot != 0) delete Udotdot; if (Utm1 != 0) delete Utm1; if (Utm2 != 0) delete Utm2; if (scaledDeltaU != 0) delete scaledDeltaU; // create the new Ut = new Vector(size); Utdot = new Vector(size); Utdotdot = new Vector(size); U = new Vector(size); Udot = new Vector(size); Udotdot = new Vector(size); Utm1 = new Vector(size); Utm2 = new Vector(size); scaledDeltaU = new Vector(size); // check we obtained the new if (Ut == 0 || Ut->Size() != size || Utdot == 0 || Utdot->Size() != size || Utdotdot == 0 || Utdotdot->Size() != size || U == 0 || U->Size() != size || Udot == 0 || Udot->Size() != size || Udotdot == 0 || Udotdot->Size() != size || Utm1 == 0 || Utm1->Size() != size || Utm2 == 0 || Utm2->Size() != size || scaledDeltaU == 0 || scaledDeltaU->Size() != size) { opserr << "CollocationHSFixedNumIter::domainChanged - ran out of memory\n"; // delete the old if (Ut != 0) delete Ut; if (Utdot != 0) delete Utdot; if (Utdotdot != 0) delete Utdotdot; if (U != 0) delete U; if (Udot != 0) delete Udot; if (Udotdot != 0) delete Udotdot; if (Utm1 != 0) delete Utm1; if (Utm2 != 0) delete Utm2; if (scaledDeltaU != 0) delete scaledDeltaU; Ut = 0; Utdot = 0; Utdotdot = 0; U = 0; Udot = 0; Udotdot = 0; Utm1 = 0; Utm2 = 0; scaledDeltaU = 0; return -1; } } // now go through and populate U, Udot and Udotdot by iterating through // the DOF_Groups and getting the last committed velocity and accel DOF_GrpIter &theDOFs = myModel->getDOFs(); DOF_Group *dofPtr; while ((dofPtr = theDOFs()) != 0) { const ID &id = dofPtr->getID(); int idSize = id.Size(); int i; const Vector &disp = dofPtr->getCommittedDisp(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Utm1)(loc) = disp(i); (*Ut)(loc) = disp(i); (*U)(loc) = disp(i); } } const Vector &vel = dofPtr->getCommittedVel(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Udot)(loc) = vel(i); } } const Vector &accel = dofPtr->getCommittedAccel(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Udotdot)(loc) = accel(i); } } } if (polyOrder == 2) opserr << "\nWARNING: CollocationHSFixedNumIter::domainChanged() - assuming Ut-1 = Ut\n"; else if (polyOrder == 3) opserr << "\nWARNING: CollocationHSFixedNumIter::domainChanged() - assuming Ut-2 = Ut-1 = Ut\n"; return 0; }
int DisplacementPath::update(const Vector &dU) { // opserr << " update is invoked " << endln; if (theDofID == -1) { opserr << "DisplacementControl::newStep() - domainChanged has not been called\n"; return -1; } AnalysisModel *theModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); if (theModel == 0 || theLinSOE == 0) { opserr << "WARNING DisplacementPath::update() "; opserr << "No AnalysisModel or LinearSOE has been set\n"; return -1; } (*deltaUbar) = dU; // have to do this as the SOE is gonna change double dUabar = (*deltaUbar)(theDofID); // determine dUhat theLinSOE->setB(*phat); theLinSOE->solve(); (*deltaUhat) = theLinSOE->getX(); // add by zhong for check purpose //int size = deltaUhat->Size(); //opserr << "\n size of deltaUhat = " << size << endln; //for (int i=0; i<size; i++) { // opserr << " dektaUhat(i) = " << (*deltaUhat)(i) << endln; //} // finish here double dUahat = (*deltaUhat)(theDofID); //opserr << " theDofID = " << theDofID << endln; //opserr << "update( ) " << endln; //opserr << "dUahat = " << dUahat << endln; if (dUahat == 0.0) { opserr << "WARNING DisplacementPath::update() "; opserr << "dUahat is zero -- zero reference displacement at control node DOF\n"; return -1; } // determine delta lambda(1) == dlambda double dLambda = -dUabar/dUahat; // add by zhong //opserr << "\n dUahat = " << dUahat << endln; //opserr << " dUabar = " << dUabar << endln; //opserr << " dLambda = " << dLambda << endln; // finish // determine delta U(i) (*deltaU) = (*deltaUbar); deltaU->addVector(1.0, *deltaUhat,dLambda); // update dU and dlambda (*deltaUstep) += *deltaU; deltaLambdaStep += dLambda; currentLambda += dLambda; // update the model theModel->incrDisp(*deltaU); theModel->applyLoadDomain(currentLambda); if (theModel->updateDomain() < 0) { opserr << "DisplacementPath::update - model failed to update for new dU\n"; return -1; } // set the X soln in linearSOE to be deltaU for convergence Test theLinSOE->setX(*deltaU); return 0; }
int DisplacementPath::newStep(void) { if (theDofID == -1) { opserr << "DisplacementPath::newStep() - domainChanged has not been called\n"; return -1; } // get pointers to AnalysisModel and LinearSOE AnalysisModel *theModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); if (theModel == 0 || theLinSOE == 0) { opserr << "WARNING DisplacementPath::newStep() "; opserr << "No AnalysisModel or LinearSOE has been set\n"; return -1; } // check theIncrementVector Vector if ( theIncrementVector == 0 ) { opserr << "DisplacementPath::newStep() - no theIncrementVector associated with object\n"; return -2; } // determine increment for this iteration if (currentStep < theIncrementVector->Size()) { theCurrentIncrement = (*theIncrementVector)(currentStep); } else { theCurrentIncrement = 0.0; opserr << "DisplacementPath::newStep() - reach the end of specified load path\n"; opserr << " - setting theCurrentIncrement = 0.0\n"; } // get the current load factor currentLambda = theModel->getCurrentDomainTime(); // determine dUhat and dUabar this->formTangent(); this->formUnbalance(); (*deltaUbar) = theLinSOE->getX(); double dUabar = (*deltaUbar)(theDofID); theLinSOE->setB(*phat); if (theLinSOE->solve() < 0) { opserr << "DisplacementControl::newStep(void) - failed in solver\n"; return -1; } (*deltaUhat) = theLinSOE->getX(); Vector &dUhat = *deltaUhat; double dUahat = dUhat(theDofID); //opserr << " newStep( ) " << endln; //opserr << " theDofID = " << theDofID << endln; //opserr << "dUahat = " << dUahat << endln; if (dUahat == 0.0) { opserr << "WARNING DisplacementPath::newStep() "; opserr << "dUahat is zero -- zero reference displacement at control node DOF\n"; opserr << "currentStep = " << currentStep << endln; // add by zhong opserr << " theCurrentIncrement = " << theCurrentIncrement << endln; // zhong return -1; } // determine delta lambda(1) == dlambda double dLambda = (theCurrentIncrement-dUabar)/dUahat; deltaLambdaStep = dLambda; currentLambda += dLambda; // opserr << "DisplacementPath: " << dUahat << " " << theDofID << endln; // opserr << "DisplacementPath::newStep() : " << deltaLambdaStep << endln; // determine delta U(1) == dU (*deltaU) = dUhat; (*deltaU) *= dLambda; (*deltaUstep) = (*deltaU); // update model with delta lambda and delta U theModel->incrDisp(*deltaU); theModel->applyLoadDomain(currentLambda); if (theModel->updateDomain() < 0) { opserr << "DisplacementPath::newStep - model failed to update for new dU\n"; return -1; } currentStep++; return 0; }
int ArcLengthw::newStep(void) { ofstream factor; factor.open("factor.dat",ios::app); // get pointers to AnalysisModel and LinearSOE AnalysisModel *theModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); if (theModel == 0 || theLinSOE == 0) { opserr << "WARNING ArcLengthw::newStep() "; opserr << "No AnalysisModel or LinearSOE has been set\n"; return -1; } // get the current load factor currentLambda = theModel->getCurrentDomainTime(); factor<<"currentLambda"<<endln; factor<<currentLambda<<endln; // determine dUhat this->formTangent(); theLinSOE->setB(*phat); theLinSOE->solve(); (*deltaUhat) = theLinSOE->getX(); Vector &dUhat = *deltaUhat; factor<<"dUhat"<<endln; //factor>>dUhat; int size = dUhat.Size(); int i = 0; double sum = 0.0; int Ji_1 = 0; double dLambda = 0.0; factor<<"dWibefore"<<endln; factor<<dWi<<endln; factor<<"*phat"<<endln; //factor>>*phat; factor<<"dUhat"<<endln; //factor>>dUhat; factor<<"iFactor"<<endln; factor<<iFactor<<endln; factor<<"Jd"<<endln; factor<<Jd<<endln; factor<<"iflag"<<endln; factor<<iflag<<endln; double dJd = Jd; double dJi_1 = 1.0; if( iflag == 0 ){ dWi = ( (*phat) ^ dUhat ) * iFactor * iFactor; dLambda = iFactor; iflag = 1; } else if( iflag == 1 ){ Ji_1 = 10; //theAlgo->getNumIteration(); dJi_1 = Ji_1; dWi = dWi * pow(( dJd / dJi_1 ),0.01); dLambda = dWi / ( (*phat)^(dUhat) ); } if( Ji_1 >0){ factor<<"Jd/Ji-1"<<endln; factor<<dJd/dJi_1<<endln; } factor<<"iflag"<<endln; factor<<iflag<<endln; factor<<"Ji_1"<<endln; factor<<Ji_1<<endln; factor<<"dWi"<<endln; factor<<dWi<<endln; deltaLambdaStep = dLambda; currentLambda += dLambda; (*deltaU) = dUhat; (*deltaU) *= dLambda; (*deltaUstep) = (*deltaU); // update model with delta lambda and delta U theModel->incrDisp(*deltaU); theModel->applyLoadDomain(currentLambda); theModel->updateDomain(); return 0; }
int ArcLengthw::domainChanged(void) { // we first create the Vectors needed AnalysisModel *theModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); if (theModel == 0 || theLinSOE == 0) { opserr << "WARNING ArcLengthw::update() "; opserr << "No AnalysisModel or LinearSOE has been set\n"; return -1; } int size = theModel->getNumEqn(); // ask model in case N+1 space if (deltaUhat == 0 || deltaUhat->Size() != size) { // create new Vector if (deltaUhat != 0) delete deltaUhat; // delete the old deltaUhat = new Vector(size); if (deltaUhat == 0 || deltaUhat->Size() != size) { // check got it opserr << "FATAL ArcLengthw::domainChanged() - ran out of memory for"; opserr << " deltaUhat Vector of size " << size << endln; exit(-1); } } if (deltaUbar == 0 || deltaUbar->Size() != size) { // create new Vector if (deltaUbar != 0) delete deltaUbar; // delete the old deltaUbar = new Vector(size); if (deltaUbar == 0 || deltaUbar->Size() != size) { // check got it opserr << "FATAL ArcLengthw::domainChanged() - ran out of memory for"; opserr << " deltaUbar Vector of size " << size << endln; exit(-1); } } if (deltaU == 0 || deltaU->Size() != size) { // create new Vector if (deltaU != 0) delete deltaU; // delete the old deltaU = new Vector(size); if (deltaU == 0 || deltaU->Size() != size) { // check got it opserr << "FATAL ArcLengthw::domainChanged() - ran out of memory for"; opserr << " deltaU Vector of size " << size << endln; exit(-1); } } if (deltaUstep == 0 || deltaUstep->Size() != size) { if (deltaUstep != 0) delete deltaUstep; deltaUstep = new Vector(size); if (deltaUstep == 0 || deltaUstep->Size() != size) { opserr << "FATAL ArcLengthw::domainChanged() - ran out of memory for"; opserr << " deltaUstep Vector of size " << size << endln; exit(-1); } } if (phat == 0 || phat->Size() != size) { if (phat != 0) delete phat; phat = new Vector(size); if (phat == 0 || phat->Size() != size) { opserr << "FATAL ArcLengthw::domainChanged() - ran out of memory for"; opserr << " phat Vector of size " << size << endln; exit(-1); } } // now we have to determine phat // do this by incrementing lambda by 1, applying load // and getting phat from unbalance. currentLambda = theModel->getCurrentDomainTime(); currentLambda += 1.0; theModel->applyLoadDomain(currentLambda); this->formUnbalance(); // NOTE: this assumes unbalance at last was 0 (*phat) = theLinSOE->getB(); currentLambda -= 1.0; theModel->setCurrentDomainTime(currentLambda); return 0; }
int PFEMIntegrator::formSensitivityRHS(int passedGradNumber) { sensitivityFlag = 1; // Set a couple of data members gradNumber = passedGradNumber; // Get pointer to the SOE LinearSOE *theSOE = this->getLinearSOE(); // Get the analysis model AnalysisModel *theModel = this->getAnalysisModel(); // Randomness in external load (including randomness in time series) // Get domain Domain *theDomain = theModel->getDomainPtr(); // Loop through nodes to zero the unbalaced load Node *nodePtr; NodeIter &theNodeIter = theDomain->getNodes(); while ((nodePtr = theNodeIter()) != 0) nodePtr->zeroUnbalancedLoad(); // Loop through load patterns to add external load sensitivity LoadPattern *loadPatternPtr; LoadPatternIter &thePatterns = theDomain->getLoadPatterns(); double time; while((loadPatternPtr = thePatterns()) != 0) { time = theDomain->getCurrentTime(); loadPatternPtr->applyLoadSensitivity(time); } // Randomness in element/material contributions // Loop through FE elements FE_Element *elePtr; FE_EleIter &theEles = theModel->getFEs(); while((elePtr = theEles()) != 0) { theSOE->addB( elePtr->getResidual(this), elePtr->getID() ); } // Loop through DOF groups (IT IS IMPORTANT THAT THIS IS DONE LAST!) DOF_Group *dofPtr; DOF_GrpIter &theDOFs = theModel->getDOFs(); while((dofPtr = theDOFs()) != 0) { theSOE->addB( dofPtr->getUnbalance(this), dofPtr->getID() ); } // Reset the sensitivity flag sensitivityFlag = 0; return 0; }
int KRAlphaExplicit::newStep(double _deltaT) { updateCount = 0; if (beta == 0 || gamma == 0 ) { opserr << "WARNING KRAlphaExplicit::newStep() - error in variable\n"; opserr << "gamma = " << gamma << " beta = " << beta << endln; return -1; } // get a pointer to the AnalysisModel AnalysisModel *theModel = this->getAnalysisModel(); if (theModel == 0) { opserr << "WARNING KRAlphaExplicit::newStep() - no AnalysisModel set\n"; return -2; } if (initAlphaMatrices || _deltaT != deltaT) { // update time step increment deltaT = _deltaT; if (deltaT <= 0.0) { opserr << "WARNING KRAlphaExplicit::newStep() - error in variable\n"; opserr << "dT = " << deltaT << endln; return -3; } // get the LinearSOE and the ConvergenceTest so we can switch back later LinearSOE *theLinSOE = this->getLinearSOE(); ConvergenceTest *theTest = this->getConvergenceTest(); // set up the FullLinearSOE (needed to compute the alpha matrices) int size = theLinSOE->getNumEqn(); FullGenLinSolver *theFullLinSolver = new FullGenLinLapackSolver(); LinearSOE *theFullLinSOE = new FullGenLinSOE(size, *theFullLinSolver); if (theFullLinSOE == 0) { opserr << "WARNING KRAlphaExplicit::newStep() - failed to create FullLinearSOE\n"; return -4; } theFullLinSOE->setLinks(*theModel); // now switch the SOE to the FullLinearSOE this->IncrementalIntegrator::setLinks(*theModel, *theFullLinSOE, theTest); // get a pointer to the A matrix of the FullLinearSOE const Matrix *tmp = theFullLinSOE->getA(); if (tmp == 0) { opserr << "WARNING KRAlphaExplicit::domainChanged() - "; opserr << "failed to get A matrix of FullGeneral LinearSOE\n"; return -5; } // calculate the integration parameter matrices c1 = beta*deltaT*deltaT; c2 = gamma*deltaT; c3 = 1.0; this->TransientIntegrator::formTangent(INITIAL_TANGENT); Matrix A(*tmp); c1 *= (1.0 - alphaF); c2 *= (1.0 - alphaF); c3 = (1.0 -alphaM); this->TransientIntegrator::formTangent(INITIAL_TANGENT); Matrix B3(*tmp); // solve [M + gamma*deltaT*C + beta*deltaT^2*K]*[alpha3] = // [alphaM*M + alphaF*gamma*deltaT*C + alphaF*beta*deltaT^2*K] for alpha3 A.Solve(B3, *alpha3); c1 = 0.0; c2 = 0.0; c3 = 1.0; this->TransientIntegrator::formTangent(INITIAL_TANGENT); Matrix B1(*tmp); // solve [M + gamma*deltaT*C + beta*deltaT^2*K]*[alpha1] = [M] for alpha1 A.Solve(B1, *alpha1); // calculate the effective mass matrix Mhat Mhat->addMatrix(0.0, B1, 1.0); Mhat->addMatrixProduct(1.0, B1, *alpha3, -1.0); // switch the SOE back to the user specified one this->IncrementalIntegrator::setLinks(*theModel, *theLinSOE, theTest); initAlphaMatrices = 0; } if (U == 0) { opserr << "WARNING KRAlphaExplicit::newStep() - domainChange() failed or hasn't been called\n"; return -6; } // set response at t to be that at t+deltaT of previous step (*Ut) = *U; (*Utdot) = *Udot; (*Utdotdot) = *Udotdot; // determine new response at time t+deltaT //U->addVector(1.0, *Utdot, deltaT); //double a1 = (0.5 + gamma)*deltaT*deltaT //U->addMatrixVector(1.0, *alpha1, *Utdotdot, a1); //Udot->addMatrixVector(1.0, *alpha1, *Utdotdot, deltaT); // determine new response at time t+deltaT Utdothat->addMatrixVector(0.0, *alpha1, *Utdotdot, deltaT); U->addVector(1.0, *Utdot, deltaT); double a1 = (0.5 + gamma)*deltaT; U->addVector(1.0, *Utdothat, a1); Udot->addVector(1.0, *Utdothat, 1.0); // determine the response at t+alpha*deltaT Ualpha->addVector(0.0, *Ut, (1.0-alphaF)); Ualpha->addVector(1.0, *U, alphaF); Ualphadot->addVector(0.0, *Utdot, (1.0-alphaF)); Ualphadot->addVector(1.0, *Udot, alphaF); Ualphadotdot->addMatrixVector(0.0, *alpha3, *Utdotdot, 1.0); // set the trial response quantities theModel->setResponse(*Ualpha, *Ualphadot, *Ualphadotdot); // increment the time to t+alpha*deltaT and apply the load double time = theModel->getCurrentDomainTime(); time += alphaF*deltaT; if (theModel->updateDomain(time, deltaT) < 0) { opserr << "WARNING KRAlphaExplicit::newStep() - failed to update the domain\n"; return -7; } return 0; }
int KRAlphaExplicit::domainChanged() { AnalysisModel *myModel = this->getAnalysisModel(); LinearSOE *theLinSOE = this->getLinearSOE(); const Vector &x = theLinSOE->getX(); int size = x.Size(); // create the new Matrix and Vector objects if (Ut == 0 || Ut->Size() != size) { // delete the old if (alpha1 != 0) delete alpha1; if (alpha3 != 0) delete alpha3; if (Mhat != 0) delete Mhat; if (Ut != 0) delete Ut; if (Utdot != 0) delete Utdot; if (Utdotdot != 0) delete Utdotdot; if (U != 0) delete U; if (Udot != 0) delete Udot; if (Udotdot != 0) delete Udotdot; if (Ualpha != 0) delete Ualpha; if (Ualphadot != 0) delete Ualphadot; if (Ualphadotdot != 0) delete Ualphadotdot; if (Utdothat != 0) delete Utdothat; // create the new alpha1 = new Matrix(size,size); alpha3 = new Matrix(size,size); Mhat = new Matrix(size,size); Ut = new Vector(size); Utdot = new Vector(size); Utdotdot = new Vector(size); U = new Vector(size); Udot = new Vector(size); Udotdot = new Vector(size); Ualpha = new Vector(size); Ualphadot = new Vector(size); Ualphadotdot = new Vector(size); Utdothat = new Vector(size); // check we obtained the new if (alpha1 == 0 || alpha1->noRows() != size || alpha1->noCols() != size || alpha3 == 0 || alpha3->noRows() != size || alpha3->noCols() != size || Mhat == 0 || Mhat->noRows() != size || Mhat->noCols() != size || Ut == 0 || Ut->Size() != size || Utdot == 0 || Utdot->Size() != size || Utdotdot == 0 || Utdotdot->Size() != size || U == 0 || U->Size() != size || Udot == 0 || Udot->Size() != size || Udotdot == 0 || Udotdot->Size() != size || Ualpha == 0 || Ualpha->Size() != size || Ualphadot == 0 || Ualphadot->Size() != size || Ualphadotdot == 0 || Ualphadotdot->Size() != size || Utdothat == 0 || Utdothat->Size() != size) { opserr << "WARNING KRAlphaExplicit::domainChanged() - "; opserr << "ran out of memory\n"; // delete the old if (alpha1 != 0) delete alpha1; if (alpha3 != 0) delete alpha3; if (Mhat != 0) delete Mhat; if (Ut != 0) delete Ut; if (Utdot != 0) delete Utdot; if (Utdotdot != 0) delete Utdotdot; if (U != 0) delete U; if (Udot != 0) delete Udot; if (Udotdot != 0) delete Udotdot; if (Ualpha != 0) delete Ualpha; if (Ualphadot != 0) delete Ualphadot; if (Ualphadotdot != 0) delete Ualphadotdot; if (Utdothat != 0) delete Utdothat; alpha1 = 0; alpha3 = 0; Mhat = 0; Ut = 0; Utdot = 0; Utdotdot = 0; U = 0; Udot = 0; Udotdot = 0; Ualpha = 0; Ualphadot = 0; Ualphadotdot = 0; Utdothat = 0; return -1; } } // now go through and populate U, Udot and Udotdot by iterating through // the DOF_Groups and getting the last committed velocity and accel DOF_GrpIter &theDOFs = myModel->getDOFs(); DOF_Group *dofPtr; while ((dofPtr = theDOFs()) != 0) { const ID &id = dofPtr->getID(); int idSize = id.Size(); int i; const Vector &disp = dofPtr->getCommittedDisp(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*U)(loc) = disp(i); } } const Vector &vel = dofPtr->getCommittedVel(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Udot)(loc) = vel(i); } } const Vector &accel = dofPtr->getCommittedAccel(); for (i=0; i < idSize; i++) { int loc = id(i); if (loc >= 0) { (*Udotdot)(loc) = accel(i); } } } // recalculate integration parameter matrices b/c domain changed initAlphaMatrices = 1; return 0; }