Ejemplo n.º 1
0
int
KrylovAccelerator2::accelerate(Vector &vStar, LinearSOE &theSOE, 
			      IncrementalIntegrator &theIntegrator)
{
  const Vector &R = theSOE.getB();

  int k = dimension;

  // Store residual for differencing at next iteration
  *(Av[k]) = R;

  // If subspace is not empty
  if (dimension > 0) {

    // Compute Av_k = f(y_{k-1}) - f(y_k) = r_{k-1} - r_k
    Av[k-1]->addVector(1.0, R, -1.0);
    
    int i,j;
    
    // Put subspace vectors into AvData
    Matrix A(AvData, numEqns, k);
    for (i = 0; i < k; i++) {
      Vector &Ai = *(Av[i]);
      for (j = 0; j < numEqns; j++)
	A(j,i) = Ai(j);
    }

    for (i = 0; i < k; i++) {
      for (int j = i+1; j < k; j++) {
	double sum = 0.0;
	double sumi = 0.0;
	double sumj = 0.0;
	for (int ii = 0; ii < numEqns; ii++) {
	  sum += A(ii,i)*A(ii,j);
	  sumi += A(ii,i)*A(ii,i);
	  sumj += A(ii,j)*A(ii,j);
	}
	sumi = sqrt(sumi);
	sumj = sqrt(sumj);
	sum = sum/(sumi*sumj);
	//if (fabs(sum) > 0.99)
	  //opserr << sum << ' ' << i << ' ' << j << "   ";
      }
    }

    // Put residual vector into rData (need to save r for later!)
    Vector B(rData, numEqns);
    B = R;
    
    // No transpose
    char *trans = "N";
    
    // The number of right hand side vectors
    int nrhs = 1;
    
    // Leading dimension of the right hand side vector
    int ldb = (numEqns > k) ? numEqns : k;
    
    // Subroutine error flag
    int info = 0;
    
    // Call the LAPACK least squares subroutine
#ifdef _WIN32
    unsigned int sizeC = 1;
    DGELS(trans, &sizeC, &numEqns, &k, &nrhs, AvData, &numEqns,
	  rData, &ldb, work, &lwork, &info);
#else
    //SUBROUTINE DGELS( TRANS, M, N, NRHS, A, LDA, B, LDB, WORK, LWORK,
    //		      $                  INFO )

    dgels_(trans, &numEqns, &k, &nrhs, AvData, &numEqns,
	   rData, &ldb, work, &lwork, &info);
#endif
    
    // Check for error returned by subroutine
    if (info < 0) {
      opserr << "WARNING KrylovAccelerator2::accelerate() - \n";
      opserr << "error code " << info << " returned by LAPACK dgels\n";
      return info;
    }
    
    Vector Q(numEqns);
    Q = R;

    // Compute the correction vector
    double cj;
    for (j = 0; j < k; j++) {
      
      // Solution to least squares is written to rData
      cj = rData[j];
      
      // Compute w_{k+1} = c_1 v_1 + ... + c_k v_k
      vStar.addVector(1.0, *(v[j]), cj);

      // Compute least squares residual
      // q_{k+1} = r_k - (c_1 Av_1 + ... + c_k Av_k)
      Q.addVector(1.0, *(Av[j]), -cj);
    }

    theSOE.setB(Q);
    //opserr << "Q: " << Q << endln;
  }

  theSOE.solve();
  vStar.addVector(1.0, theSOE.getX(), 1.0);

  // Put accelerated vector into storage for next iteration
  *(v[k]) = vStar;

  dimension++;

  return 0; 
}
Ejemplo n.º 2
0
/* return 0 if ok
* otherwise return !=0
*/
int solveLeastSquareProblem(LinearSystemProblem* problem, double *z ,  SolverOptions* options)
{


  /* Checks inputs */
  if (problem == NULL || z == NULL)
    numericsError("EqualityProblem", "null input for EqualityProblem and/or unknowns (z)");

  /* Output info. : 0: ok -  >0: problem (depends on solver) */
  int info = -1;
  int n = problem->size;
  int n2 = n * n;

  double * Maux = 0;
  int * ipiv = 0;
  if (options && options->dWork)
    Maux = options->dWork;
  else
    Maux = (double *) malloc(LinearSystem_getNbDwork(problem, options) * sizeof(double));

  if (options && options->iWork)
    ipiv = options->iWork;
  else
    ipiv = (int *) malloc(LinearSystem_getNbIwork(problem, options) * sizeof(int));
  int LAinfo = 0;
  //displayLS(problem);

  assert(problem->M->matrix0);
  assert(problem->q);

  memcpy(Maux, problem->M->matrix0, n2 * sizeof(double));
  //  memcpy(z,problem->q,n*sizeof(double));
  for (int ii = 0; ii < n; ii++)
    z[ii] = -problem->q[ii];


  printf("LinearSystem : solveLeastSquareProblem LWORK is :%d\n", LWORK);


  DGELS(LA_NOTRANS,n, n, 1, Maux, n, z, n, &LAinfo);
  if (LAinfo)
  {
    printf("LinearSystem_driver: DGELS  failed:\n");
    goto __fin;
  }

  int ii;
  for (ii = 0; ii < n; ii++)
  {
    if (isnan(z[ii]) || isinf(z[ii]))
    {
      printf("DGELS FAILED\n");
      goto __fin;
    }
  }
  info = 0;
  printf("LinearSystem_driver: computeError of LinearSystem : %e\n", LinearSystem_computeError(problem, z));
__fin:
  if (!(options && options->dWork))
    free(Maux);

  if (!(options && options->iWork))
    free(ipiv);

  return info;


}