//--------------------------------------------------------- CSG_Matrix calcRotnMatrix(CSG_Vector params) { CSG_Matrix rMat(3,3); /* omega = params[0]; kappa = params[1]; alpha = params[2]; */ double sw = sin(params[0]); double sk = sin(params[1]); double sa = sin(params[2]); double cw = cos(params[0]); double ck = cos(params[1]); double ca = cos(params[2]); rMat[0][0] = ck * ca; rMat[0][1] = ck * sa; rMat[0][2] = -sk; rMat[1][0] = sw * sk * ca - cw * sa; rMat[1][1] = sw * sk * sa + cw * ca; rMat[1][2] = sw * ck; rMat[2][0] = cw * sk * ca + sw * sa; rMat[2][1] = cw * sk * sa - sw * ca; rMat[2][2] = cw * ck; return rMat; }
cv::Mat CutoutImage::scaleFCMI2InputColorImageSize( const cv::Mat srcMat ) { cv::Mat aMat; cv::Mat rMat = cv::Mat(inputColorImageSize, CV_8UC4, cv::Scalar(0,0,0,0)); if(srcMat.rows >= srcMat.cols) //最终图像是竖直的 { int scaleToHeight = inputColorImageSize.height; int scaleToWidth = (int)(((float)srcMat.cols/(float)srcMat.rows)*(float)inputColorImageSize.height); if(scaleToWidth <= inputColorImageSize.width){ cv::resize(srcMat, aMat, cv::Size(scaleToWidth,scaleToHeight), 0, 0, CV_INTER_NN); cv::Rect copyRect = cv::Rect( (inputColorImageSize.width - scaleToWidth)/2,0,scaleToWidth,scaleToHeight ); aMat.copyTo(rMat(copyRect)); }else{ scaleToWidth = inputColorImageSize.width; scaleToHeight = (int)( ((float)srcMat.rows/(float)srcMat.cols)*(float)inputColorImageSize.width ); cv::resize(srcMat, aMat, cv::Size(scaleToWidth,scaleToHeight), 0, 0, CV_INTER_NN); cv::Rect copyRect = cv::Rect( 0, (inputColorImageSize.height - scaleToHeight)/2, scaleToWidth, scaleToHeight ); aMat.copyTo(rMat(copyRect)); } } else //最终图像是横向的 { int scaleToHeight = int(((float)srcMat.rows/(float)srcMat.cols)*(float)inputColorImageSize.width); int scaleToWidth = inputColorImageSize.width; cv::resize(srcMat, aMat, cv::Size(scaleToWidth,scaleToHeight), 0, 0, CV_INTER_NN); cv::Rect copyRect = cv::Rect( (inputColorImageSize.width - scaleToWidth)/2,0,scaleToWidth,scaleToHeight ); aMat.copyTo(rMat(copyRect)); } int rows = rMat.rows; int cols = rMat.cols; for(int y=0; y<rows; y++){ uchar *rowsData = rMat.ptr<uchar>(y); for (int x = 0; x<cols*4; x = x+4) { //rowsData[x] = 0; rowsData[x + 3] = 0; } } return rMat; }
void NOX::Solver::AndersonAcceleration::qrAdd(NOX::Abstract::Vector& newCol) { // Increment storage depth and resize R factor nStore++; rMat.reshape(nStore,nStore); // Update QR factors // Orthogonalize against previous columns once for (int ii = 0; ii<nStore-1; ii++) { rMat(ii,nStore-1) = qMat[ii]->innerProduct(newCol); newCol.update(-rMat(ii,nStore-1),*(qMat[ii]),1.0); } // Reorthogonalize for (int ii = 0; ii<nStore-1; ii++) { double alpha = qMat[ii]->innerProduct(newCol); newCol.update(-alpha,*(qMat[ii]),1.0); rMat(ii,nStore-1) += alpha; } rMat(nStore-1,nStore-1) = newCol.norm(); if (!disableChecksForUnitTesting) TEUCHOS_TEST_FOR_EXCEPTION((rMat(nStore-1,nStore-1) < 1.0e-16),std::runtime_error,"Error - R factor is singular to machine precision!"); *(qMat[nStore-1]) = newCol.scale(1.0/rMat(nStore-1,nStore-1)); }
void NOX::Solver::AndersonAcceleration::qrDelete() { // Apply sequence of Givens rotations for (int ii = 0; ii<nStore-1; ii++) { double temp = sqrt(rMat(ii,ii+1)*rMat(ii,ii+1) + rMat(ii+1,ii+1)*rMat(ii+1,ii+1)); double c = rMat(ii,ii+1)/temp; double s = rMat(ii+1,ii+1)/temp; rMat(ii,ii+1) = temp; rMat(ii+1,ii+1) = 0; for (int jj = ii+2; jj<nStore; jj++) { temp = c*rMat(ii,jj) + s*rMat(ii+1,jj); rMat(ii+1,jj) = -s*rMat(ii,jj) + c*rMat(ii+1,jj); rMat(ii,jj) = temp; } *workVec = *(qMat[ii]); workVec->update(s, *(qMat[ii+1]), c); qMat[ii+1]->update(-s, *(qMat[ii]), c); *(qMat[ii]) = *workVec; } // Decrement storage depth and shrink R factor nStore--; for (int ii=0; ii<nStore; ii++) { for (int jj = 0; jj<nStore; jj++) rMat(ii,jj) = rMat(ii,jj+1); } rMat.reshape(nStore,nStore); }
NOX::StatusTest::StatusType NOX::Solver::AndersonAcceleration::step() { prePostOperator.runPreIterate(*this); Teuchos::ParameterList lsParams = paramsPtr->sublist("Direction").sublist("Newton").sublist("Linear Solver"); // On the first step, do some initializations if (nIter == 0) { // Compute F of initital guess NOX::Abstract::Group::ReturnType rtype = solnPtr->computeF(); if (rtype != NOX::Abstract::Group::Ok) { utilsPtr->out() << "NOX::Solver::AndersonAcceleration::init - " << "Unable to compute F" << std::endl; throw "NOX Error"; } // Test the initial guess status = testPtr->checkStatus(*this, checkType); if ((status == NOX::StatusTest::Converged) && (utilsPtr->isPrintType(NOX::Utils::Warning))) { utilsPtr->out() << "Warning: NOX::Solver::AndersonAcceleration::init() - " << "The solution passed into the solver (either " << "through constructor or reset method) " << "is already converged! The solver wil not " << "attempt to solve this system since status is " << "flagged as converged." << std::endl; } printUpdate(); // First check status if (status != NOX::StatusTest::Unconverged) { prePostOperator.runPostIterate(*this); printUpdate(); return status; } // Apply preconditioner if enabled if (precond) { if (recomputeJacobian) solnPtr->computeJacobian(); solnPtr->applyRightPreconditioning(false, lsParams, solnPtr->getF(), *oldPrecF); } else *oldPrecF = solnPtr->getF(); // Copy initial guess to old soln *oldSolnPtr = *solnPtr; // Compute step then first iterate with a line search. workVec->update(mixParam,*oldPrecF); bool ok = lineSearchPtr->compute(*solnPtr, stepSize, *workVec, *this); if (!ok) { if (stepSize == 0.0) { utilsPtr->out() << "NOX::Solver::AndersonAcceleratino::iterate - line search failed" << std::endl; status = NOX::StatusTest::Failed; prePostOperator.runPostIterate(*this); printUpdate(); return status; } else if (utilsPtr->isPrintType(NOX::Utils::Warning)) utilsPtr->out() << "NOX::Solver::AndersonAcceleration::iterate - using recovery step for line search" << std::endl; } // Compute F for the first iterate in case it isn't in the line search rtype = solnPtr->computeF(); if (rtype != NOX::Abstract::Group::Ok) { utilsPtr->out() << "NOX::Solver::AndersonAcceleration::iterate - unable to compute F" << std::endl; status = NOX::StatusTest::Failed; prePostOperator.runPostIterate(*this); printUpdate(); return status; } // Evaluate the current status. status = testPtr->checkStatus(*this, checkType); //Update iteration count nIter++; prePostOperator.runPostIterate(*this); printUpdate(); return status; } // First check status if (status != NOX::StatusTest::Unconverged) { prePostOperator.runPostIterate(*this); printUpdate(); return status; } // Apply preconditioner if enabled if (precond) { if (recomputeJacobian) solnPtr->computeJacobian(); solnPtr->applyRightPreconditioning(false, lsParams, solnPtr->getF(), *precF); } else *precF = solnPtr->getF(); // Manage the matrices of past iterates and QR factors if (storeParam > 0) { if (nIter == accelerationStartIteration) { // Initialize nStore = 0; rMat.shape(0,0); oldPrecF->update(1.0, *precF, -1.0); qrAdd(*oldPrecF); xMat[0]->update(1.0, solnPtr->getX(), -1.0, oldSolnPtr->getX(), 0.0); } else if (nIter > accelerationStartIteration) { if (nStore == storeParam) { Teuchos::RCP<NOX::Abstract::Vector> tempPtr = xMat[0]; for (int ii = 0; ii<nStore-1; ii++) xMat[ii] = xMat[ii+1]; xMat[nStore-1] = tempPtr; qrDelete(); } oldPrecF->update(1.0, *precF, -1.0); qrAdd(*oldPrecF); xMat[nStore-1]->update(1.0, solnPtr->getX(), -1.0, oldSolnPtr->getX(), 0.0); } } // Reorthogonalize if ( (nStore > 1) && (orthoFrequency > 0) ) if (nIter % orthoFrequency == 0) reorthogonalize(); // Copy current soln to the old soln. *oldSolnPtr = *solnPtr; *oldPrecF = *precF; // Adjust for condition number if (nStore > 0) { Teuchos::LAPACK<int,double> lapack; char normType = '1'; double invCondNum = 0.0; int info = 0; if ( WORK.size() < static_cast<std::size_t>(4*nStore) ) WORK.resize(4*nStore); if (IWORK.size() < static_cast<std::size_t>(nStore)) IWORK.resize(nStore); lapack.GECON(normType,nStore,rMat.values(),nStore,rMat.normOne(),&invCondNum,&WORK[0],&IWORK[0],&info); if (utilsPtr->isPrintType(Utils::Details)) utilsPtr->out() << " R condition number estimate ("<< nStore << ") = " << 1.0/invCondNum << std::endl; if (adjustForConditionNumber) { while ( (1.0/invCondNum > dropTolerance) && (nStore > 1) ) { Teuchos::RCP<NOX::Abstract::Vector> tempPtr = xMat[0]; for (int ii = 0; ii<nStore-1; ii++) xMat[ii] = xMat[ii+1]; xMat[nStore-1] = tempPtr; qrDelete(); lapack.GECON(normType,nStore,rMat.values(),nStore,rMat.normOne(),&invCondNum,&WORK[0],&IWORK[0],&info); if (utilsPtr->isPrintType(Utils::Details)) utilsPtr->out() << " Adjusted R condition number estimate ("<< nStore << ") = " << 1.0/invCondNum << std::endl; } } } // Solve the least-squares problem. Teuchos::SerialDenseMatrix<int,double> gamma(nStore,1), RHS(nStore,1), Rgamma(nStore,1); for (int ii = 0; ii<nStore; ii++) RHS(ii,0) = precF->innerProduct( *(qMat[ii]) ); //Back-solve for gamma for (int ii = nStore-1; ii>=0; ii--) { gamma(ii,0) = RHS(ii,0); for (int jj = ii+1; jj<nStore; jj++) { gamma(ii,0) -= rMat(ii,jj)*gamma(jj,0); } gamma(ii,0) /= rMat(ii,ii); } if (nStore > 0) Rgamma.multiply(Teuchos::NO_TRANS,Teuchos::NO_TRANS,mixParam,rMat,gamma,0.0); // Compute the step and new solution using the line search. workVec->update(mixParam,*precF); for (int ii=0; ii<nStore; ii++) workVec->update(-gamma(ii,0), *(xMat[ii]), -Rgamma(ii,0),*(qMat[ii]),1.0); bool ok = lineSearchPtr->compute(*solnPtr, stepSize, *workVec, *this); if (!ok) { if (stepSize == 0.0) { utilsPtr->out() << "NOX::Solver::AndersonAcceleratino::iterate - line search failed" << std::endl; status = NOX::StatusTest::Failed; prePostOperator.runPostIterate(*this); printUpdate(); return status; } else if (utilsPtr->isPrintType(NOX::Utils::Warning)) utilsPtr->out() << "NOX::Solver::AndersonAcceleration::iterate - using recovery step for line search" << std::endl; } // Compute F for new current solution in case the line search didn't . NOX::Abstract::Group::ReturnType rtype = solnPtr->computeF(); if (rtype != NOX::Abstract::Group::Ok) { utilsPtr->out() << "NOX::Solver::AndersonAcceleration::iterate - unable to compute F" << std::endl; status = NOX::StatusTest::Failed; prePostOperator.runPostIterate(*this); printUpdate(); return status; } // Update iteration count nIter++; // Evaluate the current status. status = testPtr->checkStatus(*this, checkType); prePostOperator.runPostIterate(*this); printUpdate(); return status; }