Ejemplo n.º 1
0
  ScaledMatrixSpace::ScaledMatrixSpace(
    const SmartPtr<const Vector>& row_scaling,
    bool row_scaling_reciprocal,
    const SmartPtr<const MatrixSpace>& unscaled_matrix_space,
    const SmartPtr<const Vector>& column_scaling,
    bool column_scaling_reciprocal)
      :
      MatrixSpace(unscaled_matrix_space->NRows(),
                  unscaled_matrix_space->NCols()),
      unscaled_matrix_space_(unscaled_matrix_space)
  {
    if (IsValid(row_scaling)) {
      row_scaling_ = row_scaling->MakeNewCopy();
      if (row_scaling_reciprocal) {
        row_scaling_->ElementWiseReciprocal();
      }
    }
    else {
      row_scaling_ = NULL;
    }

    if (IsValid(column_scaling)) {
      column_scaling_ = column_scaling->MakeNewCopy();
      if (column_scaling_reciprocal) {
        column_scaling_->ElementWiseReciprocal();
      }
    }
    else {
      column_scaling_ = NULL;
    }
  }
Ejemplo n.º 2
0
 inline
 Index  Matrix::NCols() const
 {
   return owner_space_->NCols();
 }
Ejemplo n.º 3
0
ESymSolverStatus LowRankAugSystemSolver::UpdateFactorization(
   const SymMatrix* W,
   double           W_factor,
   const Vector*    D_x,
   double           delta_x,
   const Vector*    D_s,
   double           delta_s,
   const Matrix&    J_c,
   const Vector*    D_c,
   double           delta_c,
   const Matrix&    J_d,
   const Vector*    D_d,
   double           delta_d,
   const Vector&    proto_rhs_x,
   const Vector&    proto_rhs_s,
   const Vector&    proto_rhs_c,
   const Vector&    proto_rhs_d,
   bool             check_NegEVals,
   Index            numberOfNegEVals
   )
{
   DBG_START_METH("LowRankAugSystemSolver::UpdateFactorization",
      dbg_verbosity);

   DBG_ASSERT(W_factor == 0.0 || W_factor == 1.0);
   ESymSolverStatus retval = SYMSOLVER_SUCCESS;

   // Get the low update information out of W
   const LowRankUpdateSymMatrix* LR_W = static_cast<const LowRankUpdateSymMatrix*>(W);
   DBG_ASSERT(LR_W); DBG_PRINT_MATRIX(2, "LR_W", *LR_W);

   SmartPtr<const Vector> B0;
   SmartPtr<const MultiVectorMatrix> V;
   SmartPtr<const MultiVectorMatrix> U;
   if( W_factor == 1.0 )
   {
      V = LR_W->GetV();
      U = LR_W->GetU();
      B0 = LR_W->GetDiag();
   }
   SmartPtr<const Matrix> P_LM = LR_W->P_LowRank();
   SmartPtr<const VectorSpace> LR_VecSpace = LR_W->LowRankVectorSpace();

   if( IsNull(B0) )
   {
      SmartPtr<Vector> zero_B0 = (IsValid(P_LM)) ? LR_VecSpace->MakeNew() : proto_rhs_x.MakeNew();
      zero_B0->Set(0.0);
      B0 = GetRawPtr(zero_B0);
   }

   // set up the Hessian for the underlying augmented system solver
   // without the low-rank update
   if( IsValid(P_LM) && LR_W->ReducedDiag() )
   {
      DBG_ASSERT(IsValid(B0));
      SmartPtr<Vector> fullx = proto_rhs_x.MakeNew();
      P_LM->MultVector(1., *B0, 0., *fullx);
      Wdiag_->SetDiag(*fullx);
   }
   else
   {
      Wdiag_->SetDiag(*B0);
      DBG_PRINT_VECTOR(2, "B0", *B0);
   }

   SmartPtr<MultiVectorMatrix> Vtilde1_x;
   if( IsValid(V) )
   {
      SmartPtr<MultiVectorMatrix> V_x;
      Index nV = V->NCols();
      //DBG_PRINT((1, "delta_x  = %e\n", delta_x));
      //DBG_PRINT_MATRIX(2, "V", *V);
      retval = SolveMultiVector(D_x, delta_x, D_s, delta_s, J_c, D_c, delta_c, J_d, D_d, delta_d, proto_rhs_x,
         proto_rhs_s, proto_rhs_c, proto_rhs_d, *V, P_LM, V_x, Vtilde1_, Vtilde1_x, check_NegEVals, numberOfNegEVals);
      if( retval != SYMSOLVER_SUCCESS )
      {
         Jnlst().Printf(J_DETAILED, J_SOLVE_PD_SYSTEM,
            "LowRankAugSystemSolver: SolveMultiVector returned retval = %d for V.\n", retval);
         return retval;
      }
      //DBG_PRINT_MATRIX(2, "Vtilde1_x", *Vtilde1_x);

      SmartPtr<DenseSymMatrixSpace> M1space = new DenseSymMatrixSpace(nV);
      SmartPtr<DenseSymMatrix> M1 = M1space->MakeNewDenseSymMatrix();
      M1->FillIdentity();
      M1->HighRankUpdateTranspose(1., *Vtilde1_x, *V_x, 1.);
      //DBG_PRINT_MATRIX(2, "M1", *M1);
      SmartPtr<DenseGenMatrixSpace> J1space = new DenseGenMatrixSpace(nV, nV);
      J1_ = J1space->MakeNewDenseGenMatrix();
      bool retchol = J1_->ComputeCholeskyFactor(*M1);
      // M1 must be positive definite!
      //DBG_ASSERT(retchol);
      if( !retchol )
      {
         Jnlst().Printf(J_DETAILED, J_SOLVE_PD_SYSTEM, "LowRankAugSystemSolver: Cholesky for M1 returned error!\n");
         retval = SYMSOLVER_WRONG_INERTIA;
         num_neg_evals_++;
         return retval;
      }
   }
   else
   {
      Vtilde1_ = NULL;
      J1_ = NULL;
   }

   if( IsValid(U) )
   {
      Index nU = U->NCols();
      SmartPtr<MultiVectorMatrix> U_x;
      SmartPtr<MultiVectorMatrix> Utilde1;
      SmartPtr<MultiVectorMatrix> Utilde1_x;
      SmartPtr<MultiVectorMatrix> Utilde2_x;
      retval = SolveMultiVector(D_x, delta_x, D_s, delta_s, J_c, D_c, delta_c, J_d, D_d, delta_d, proto_rhs_x,
         proto_rhs_s, proto_rhs_c, proto_rhs_d, *U, P_LM, U_x, Utilde1, Utilde1_x, check_NegEVals, numberOfNegEVals);
      if( retval != SYMSOLVER_SUCCESS )
      {
         Jnlst().Printf(J_DETAILED, J_SOLVE_PD_SYSTEM,
            "LowRankAugSystemSolver: SolveMultiVector returned retval = %d for U.\n", retval);
         return retval;
      }

      if( IsNull(Vtilde1_) )
      {
         Utilde2_ = Utilde1;
         Utilde2_x = Utilde1_x;
      }
      else
      {
         Index nV = Vtilde1_->NCols();
         SmartPtr<DenseGenMatrixSpace> Cspace = new DenseGenMatrixSpace(nV, nU);
         SmartPtr<DenseGenMatrix> C = Cspace->MakeNewDenseGenMatrix();
         C->HighRankUpdateTranspose(1., *Vtilde1_x, *U_x, 0.);
         J1_->CholeskySolveMatrix(*C);
         Utilde2_ = Utilde1;
         Utilde2_->AddRightMultMatrix(-1, *Vtilde1_, *C, 1.);
         Utilde2_x = Utilde1_x->MakeNewMultiVectorMatrix();
         for( Index i = 0; i < Utilde1_x->NCols(); i++ )
         {
            const CompoundVector* cvec = static_cast<const CompoundVector*>(GetRawPtr(Utilde2_->GetVector(i)));
            DBG_ASSERT(cvec);
            Utilde2_x->SetVector(i, *cvec->GetComp(0));
         }
      }

      SmartPtr<DenseSymMatrixSpace> M2space = new DenseSymMatrixSpace(nU);
      SmartPtr<DenseSymMatrix> M2 = M2space->MakeNewDenseSymMatrix();
      M2->FillIdentity();
      M2->HighRankUpdateTranspose(-1., *Utilde2_x, *U_x, 1.);
      SmartPtr<DenseGenMatrixSpace> J2space = new DenseGenMatrixSpace(nU, nU);
      J2_ = J2space->MakeNewDenseGenMatrix();
      //DBG_PRINT_MATRIX(2, "M2", *M2);
      bool retchol = J2_->ComputeCholeskyFactor(*M2);
      if( !retchol )
      {
         Jnlst().Printf(J_DETAILED, J_SOLVE_PD_SYSTEM, "LowRankAugSystemSolver: Cholesky for M2 returned error.\n");
         retval = SYMSOLVER_WRONG_INERTIA;
         num_neg_evals_++;
         return retval;
      }
   }
   else
   {
      J2_ = NULL;
      Utilde2_ = NULL;
   }

   return retval;
}