void normalize(Eigen::VectorXd& v) { if (v.sum() == 0.0) { std::cout << "ERRO no portfolio:\n"; std::cout << v; std::cout << "ERRO no portfolio."; system("pause"); } v = (1.0/ v.sum())*v; }
gaussian_process::gaussian_process( const Eigen::MatrixXd& domains , const Eigen::VectorXd& targets , const gaussian_process::covariance& covariance , double self_covariance ) : domains_( domains ) , targets_( targets ) , covariance_( covariance ) , self_covariance_( self_covariance ) , offset_( targets.sum() / targets.rows() ) , K_( domains.rows(), domains.rows() ) { if( domains.rows() != targets.rows() ) { COMMA_THROW( comma::exception, "expected " << domains.rows() << " row(s) in targets, got " << targets.rows() << " row(s)" ); } targets_.array() -= offset_; // normalise //use m_K as Kxx + variance*I, then invert it //fill Kxx with values from covariance function //for elements r,c in upper triangle for( std::size_t r = 0; r < std::size_t( domains.rows() ); ++r ) { K_( r, r ) = self_covariance_; const Eigen::VectorXd& row = domains.row( r ); for( std::size_t c = r + 1; c < std::size_t( domains.rows() ); ++c ) { K_( c, r ) = K_( r, c ) = covariance_( row, domains.row( c ) ); } } L_.compute( K_ ); // invert Kxx + variance * I to become (by definition) B alpha_ = L_.solve( targets_ ); }
void PCATestCase::decorrelation() { OpenANN::RandomNumberGenerator rng; const int N = 100; const int D = 2; Eigen::MatrixXd X(N, D); rng.fillNormalDistribution(X); // Linear transformation (correlation) Eigen::MatrixXd A(D, D); A << 1.0, 0.5, 0.5, 2.0; Eigen::MatrixXd Xt = X * A.transpose(); // Decorrelation (without dimensionality reduction) OpenANN::PCA pca(D); pca.fit(Xt); Eigen::MatrixXd Y = pca.transform(Xt); // Covariance matrix should be identity matrix Eigen::MatrixXd cov = Y.transpose() * Y; ASSERT_EQUALS_DELTA(cov(0, 0), (double) N, 1e-5); ASSERT_EQUALS_DELTA(cov(1, 1), (double) N, 1e-5); ASSERT_EQUALS_DELTA(cov(0, 1), 0.0, 1e-5); ASSERT_EQUALS_DELTA(cov(1, 0), 0.0, 1e-5); Eigen::VectorXd evr = pca.explainedVarianceRatio(); double evrSum = evr.sum(); ASSERT_EQUALS_DELTA(evrSum, 1.0, 1e-5); }
Eigen::VectorXd grad(const Eigen::VectorXd &x1, const Eigen::VectorXd &x2) const { Eigen::VectorXd grad(_input_dim + 1); Eigen::VectorXd z = (x1 - x2).cwiseQuotient(_ell).array().square(); double k = _sf2 * exp(-0.5 * z.sum()); grad.head(_input_dim) = z * k; grad(_input_dim) = 2.0 * k; return grad; }
Solver(const int N, const int m, double* alpha_in, double* beta_in, double* t_in, double* yerr) { Eigen::Map<Eigen::VectorXd> alpha(alpha_in, m); Eigen::Map<Eigen::VectorXd> beta(beta_in, m); Eigen::Map<Eigen::VectorXd> t(t_in, N); Eigen::Map<Eigen::VectorXd> d(yerr, N); for (int i=0; i<N; i++) { d(i) = alpha.sum() + yerr[i]*yerr[i]; } this->N = N; this->m = m; grp_ = new GRP(N, m, alpha, beta, t, d); };
void calcMeanAndCovarWeighedVectorized(const Eigen::MatrixXf &input, const Eigen::VectorXd &inputWeights, Eigen::MatrixXf &out_covMat, Eigen::VectorXf &out_mean,Eigen::MatrixXf &temp) { out_mean=input.col(0); //to resize out_mean.setZero(); double wSumInv=1.0/inputWeights.sum(); for (int k=0;k<inputWeights.size();k++){ double w=inputWeights[k]; out_mean+=input.col(k)*(float)(w*wSumInv); } out_mean = input.rowwise().mean(); temp = (input.colwise() - out_mean); for (int k=0;k<inputWeights.size();k++){ temp.col(k) *= (float)(sqrt(inputWeights(k)*wSumInv)); //using square roots, as we only want the normalized weights to be included once for each result element in the multiplication below } out_covMat = temp*temp.transpose(); }
SimuEuro(const option & o, long path, const std::vector<double> & RN){ opt=o; N= path; asset_price.resize(N); asset_price.setZero(); option_value= asset_price; for (long i=0; i< N; i++) { asset_price(i)=opt.S* exp((opt.r- opt.q)*opt.T-.5*opt.sigma*opt.sigma*opt.T+ opt.sigma* sqrt(opt.T)* RN[i]); if(opt.Call) option_value(i)= fmax(asset_price(i)- opt.K,0.0); else option_value(i)= fmax(-asset_price(i)+opt.K, 0.0); } mean= option_value.sum()/ option_value.size() * exp(-opt.T*opt.r); stdiv= option_value.squaredNorm()/ option_value.size()* exp(-opt.r*opt.T *2); stdiv= stdiv- pow(mean,2.0); stdiv= sqrt(stdiv/ N); };
int cMathUtil::SampleDiscreteProb(const Eigen::VectorXd& probs) { assert(std::abs(probs.sum() - 1) < 0.00001); double rand = RandDouble(); int rand_idx = gInvalidIdx; int num_probs = static_cast<int>(probs.size()); for (int i = 0; i < num_probs; ++i) { double curr_prob = probs[i]; rand -= curr_prob; if (rand <= 0) { rand_idx = i; break; } } return rand_idx; }
SimuEuro(const option &o, long path, unsigned int seed= int(time(0))) { opt=o; N= path; asset_price.resize(N); asset_price.setZero(); option_value= asset_price; boost::mt19937 eng(seed); boost::normal_distribution<double> normal(0.0, 1.0); boost::variate_generator<boost::mt19937&, boost::normal_distribution<double>> rng(eng, normal); for (long i=0; i< N; i++) { asset_price(i)=opt.S* exp((opt.r- opt.q)*opt.T-.5*opt.sigma*opt.sigma*opt.T+ opt.sigma* sqrt(opt.T)* rng()); if(opt.Call) option_value(i)= fmax(asset_price(i)- opt.K,0.0); else option_value(i)= fmax(-asset_price(i)+opt.K, 0.0); } mean= option_value.sum()/ option_value.size() * exp(-opt.T*opt.r); stdiv= option_value.squaredNorm()/ option_value.size()* exp(-opt.r*opt.T *2); stdiv= stdiv- pow(mean,2.0); stdiv= sqrt(stdiv/ N); };
IEFSolver aniso_solver(symm); aniso_solver.buildAnisotropicMatrix(cavity, gf_i, gf_o, op); IEFSolver iso_solver(symm); iso_solver.buildIsotropicMatrix(cavity, gf_i, gf_o, op); int size = cavity.size(); Eigen::VectorXd fake_mep = computeMEP(cavity.elements(), charge); THEN("the total apparent surface charge is") { Eigen::VectorXd aniso_fake_asc = aniso_solver.computeCharge(fake_mep); Eigen::VectorXd iso_fake_asc = iso_solver.computeCharge(fake_mep); int nr_irrep = cavity.pointGroup().nrIrrep(); double totalAnisoASC = aniso_fake_asc.sum() * nr_irrep; double totalIsoASC = iso_fake_asc.sum() * nr_irrep; CAPTURE(totalASC); CAPTURE(totalAnisoASC); CAPTURE(totalASC - totalAnisoASC); REQUIRE(totalIsoASC == Approx(totalAnisoASC)); REQUIRE(totalASC == Approx(totalAnisoASC).epsilon(1.0e-03)); } } /*! \class IEFSolver * \test \b pointChargeGePolC2 tests IEFSolver using a point charge with a GePol * cavity in C2 symmetry * We are forcing the usage of the buildAnisotropicMatrix method. * The results are compared with Gauss' theorem and the results from the
SEXP cleanZ(SEXP X,SEXP Z,SEXP bic_vide_vect,SEXP methode_BIC,SEXP plot,SEXP bla,SEXP Rstar) { BEGIN_RCPP //déclaration des varibles const Map<MatrixXd> matZ(as<Map<MatrixXd> >(Z));//Z const Map<MatrixXd> matX(as<Map<MatrixXd> >(X));//X const Map<VectorXd> Bic_vide_vect(as<Map<VectorXd> >(bic_vide_vect));//bic_vide_vect bool star = Rcpp::as<bool>(Rstar); // BICstar Rcpp::NumericVector met_BIC(methode_BIC),Plot(plot),Bla(bla); typedef Rcpp::NumericVector::iterator vec_iterator; vec_iterator imet_BIC=met_BIC.begin(),iplot=Plot.begin(),ibla=Bla.begin(); int p=matZ.cols();//nombre de colonne de la matrice Z Eigen::MatrixXd Zopt;//meilleur Z obtenu double Bicbest;//BIC associe au meilleur modèle Eigen::VectorXd bicvect;//vecteur BIC des matrices Z retenues Eigen::MatrixXd newZ;//matrice Z modifie a chaque etapes Eigen::MatrixXd list_cand;//matrice qui contient les coordonnées des candidats (liste candidats) int compte;//permet de cree la matrice liste en désignant le numéro du candidat (liste candidats) int nbcand;//nombre de candidats int numcand;//numero du candidat int i_loc;//premiere coordonnee du candidat (modification Z) int j_loc;//duexieme coordonnee du candidat (modification Z) Eigen::MatrixXd Zcand;//matrice Z du candidat (modification Z) Eigen::VectorXd BIC_cand;//vecteur qui contient les BIC de chaque colonne des la matrice Zcand (calcul du BIC) double Sum_BIC_cand;//somme des BIC de BIC_cand (calcul BIC) Eigen::VectorXd stock_bool;//vecteur qui permet de savoir si un candidat peut etre choisi (stock) Eigen::VectorXd stock_BIC;//vecteur qui contient le BIC de tout les candidats (stock) double sumbic;//BIC de chaque etapes double BIC_min; bool minimum; int i; int iret; nbcand=matZ.sum(); Eigen::VectorXd bic_etape(nbcand);//vecteur qui stock le BIC de chaque etapes Eigen::VectorXd complexite_etape(nbcand);//vecteur qui stock la complexite de Z a chaque etapes Eigen::VectorXd BIC_step;//vecteur qui stock le BIC de chaque etapes Eigen::VectorXd complexite_step ;//vecteur qui stock la compléxité de Z a chaque etapes // Eigen::ArrayXXd SumCol(1,p);//SumCol est un vecteur qui contient la somme de chaque colonne de Zcand (modification Z) //initialisation bicvect=BicZ_cpp2(matX,matZ,Bic_vide_vect,imet_BIC[0]); //somme a la main sumbic=bicvect.sum(); if (star) { sumbic=sumbic-ProbaZ_cpp(matZ); } if (ibla[0]>0) { Rcout<<sumbic<<"\n"; } Bicbest =sumbic; Zopt=matZ; newZ=matZ; compte=nbcand+1; int step =0; while(step<nbcand) { list_cand.resize(compte-1,2);//le nombre de candidats est la complexite du modele compte=0;//initialisation du vecteur liste designe le numero du candidat //liste candidats (couples [i,j]) // list_cand.resize(nbcand,2);//le nombre de candidats est la complexite du modele for(int m=0;m<p;m++)//parcours ligne { for(int n=0;n<p;n++)//parcours colonne { if(newZ(m,n)==1)//on cherche les candidats { list_cand(compte,0)=m;//stock la ligne du candidat list_cand(compte,1)=n;//stock la colonne du candidat compte=compte+1;//passage au candidat suivant } } } //pour chaque candidat for (numcand=0;numcand<compte;numcand++) { //modification (calcul du Z) (Zcand avec methode (rejet ou relax) Z,i,j,methode="relax", p2max=inf,rmax=inf) i_loc=list_cand(numcand,0); j_loc=list_cand(numcand,1); Zcand=newZ; Zcand(i_loc,j_loc)=1-Zcand(i_loc,j_loc);//modification de Z par rapport au candidat selectionne //calcul du bic (du nouveau Z genere) (bicZ) BIC_cand=BicZ_cpp(matX,Zcand,Bic_vide_vect,bicvect,imet_BIC[0],newZ);//calcul du vecteur BIC du candidat Sum_BIC_cand=BIC_cand.sum(); if (star) { Sum_BIC_cand=Sum_BIC_cand-ProbaZ_cpp(Zcand); } //stockage du BIC stock_BIC.resize(compte); stock_BIC(numcand)=Sum_BIC_cand; } //choix du candidat retenu (tirage au sort ou meilleur selon le cas) BIC_min=Bicbest; minimum=false; for(i=0;i<compte;i++) { if(stock_BIC(i)<Bicbest)//si on a trouve un minimum { iret=i;//on retient sa position minimum=true; Bicbest=stock_BIC(i);//on modifie Bicbest } } if (minimum==true)//si il y a un minimum, on y va { Zopt=newZ;//initialisation a la stationarite Zopt(list_cand(iret,0),list_cand(iret,1))=1-Zopt(list_cand(iret,0),list_cand(iret,1));//modification du Zopt bicvect=BicZ_cpp(matX,Zopt,Bic_vide_vect,bicvect,imet_BIC[0],newZ);//calcul du vecteur BIC du nouveau Zopt newZ=Zopt; //partie commentaires if (ibla[0]>0) { Rcout<<"etape : "<<step<<"\n"; Rcout<<" Bicbest: "<<Bicbest<<" complexite: "<<newZ.sum()<<"\n"; if (ibla[0]==2) { Rcout<<"nb_cand "<<compte<<"BIC min "<<BIC_min<<"\n"; } } //partie graphiques if(iplot[0]==1)//si on veut des graphiques on mets a jour les vecteurs { bic_etape (step)=Bicbest; complexite_etape (step)=newZ.sum(); } step=step+1;//passage a l'etape suivante s'il y a eu un minimum } else//pas de minimum { if (ibla[0]>0){ Rcout<<"nettoyage fini"; } step=nbcand+1;//arret des etapes } }//fin des etapes if(iplot[0]==1) { BIC_step.resize(nbcand-compte);//on met les vecteurs sorti de bonne dimension complexite_step.resize(nbcand-compte); if(nbcand-compte>0)//s'il y'a eu au moins une etape alors on tranfert les donnees des vecteurs { for(int k=0;k<nbcand-compte;k++) { BIC_step(k)=bic_etape(k); complexite_step(k)=complexite_etape(k); } } return List::create( Named("Z")= newZ, Named("Z_opt")= Zopt, Named("bic_opt")= Bicbest, Named("bic_step")= BIC_step, Named("complexity_step")= complexite_step ); } else { return List::create( Named("Z")= newZ, Named("Z_opt")= Zopt, Named("bic_opt")= Bicbest ); } END_RCPP }
SEXP rechercheZ_relax(SEXP X,SEXP Z,SEXP bic_vide_vect,SEXP methode_tirage,SEXP methode_BIC,SEXP Rmax,SEXP p2max,SEXP Maxiter,SEXP plot,SEXP best,SEXP better,SEXP random,SEXP bla,SEXP nb_opt_max,SEXP Rexact,SEXP Rstar) { BEGIN_RCPP //déclaration des varibles const Map<MatrixXd> matZ(as<Map<MatrixXd> >(Z));//Z const Map<MatrixXd> matX(as<Map<MatrixXd> >(X));//X const Map<VectorXd> Bic_vide_vect(as<Map<VectorXd> >(bic_vide_vect));//bic_vide_vect bool Exact = Rcpp::as<bool>(Rexact); // length vector bool star = Rcpp::as<bool>(Rstar); // BICstar Rcpp::NumericVector met_tirage(methode_tirage),met_BIC(methode_BIC),rmax(Rmax),P2max(p2max),maxiter(Maxiter),Plot(plot),Best(best),Better(better),Random(random),Bla(bla),Nb_opt_max(nb_opt_max); typedef Rcpp::NumericVector::iterator vec_iterator; vec_iterator imet_tirage = met_tirage.begin(),imet_BIC=met_BIC.begin(),irmax=rmax.begin(),ip2max=P2max.begin(),imaxiter=maxiter.begin(),iplot=Plot.begin(),ibest=Best.begin(),ibetter=Better.begin(),irandom=Random.begin(),ibla=Bla.begin(),inb_opt_max=Nb_opt_max.begin(); int p=matZ.cols();//nombre de colonne de la matrice Z Eigen::MatrixXd Zopt;//meilleur Z obtenu double Bicbest;//BIC associé au meilleur modèle Eigen::VectorXd bicvect;//vecteur BIC des matrices Z retenues Eigen::MatrixXd newZ;//matrice Z modifié à chaque étapes Eigen::MatrixXd list_cand;//matrice qui contient les coordonnées des candidats int nbcand=0;//nombre de candidats int nb_opt;//nombre de fois ou on a retrouve bicbest int step_opt=0;//étape où l'on découvre BIC_opt int sumZ=0; int k;//nombre du tirage aleatoire (liste candidats) int compte;//permet de cree la matrice liste en désignant le numéro du candidat (liste candidats) int i;//coordonnée (x ou y) des candidats (liste candidats) int rand1;//nombre aleatoire pour la 3ème méthode de tirage des candidats (liste candidats) int rand2;//nombre aleatoire pour la 3ème méthode de tirage des candidats (liste candidats) int numcand;//numero du candidat int i_loc;//premiere coordonnée du candidat (modification Z) int j_loc;//duexième coordonnée du candidat (modification Z) int realisable;//booléen qui permet de savoir si on peut effectuer un changement dans Z (modification Z) Eigen::MatrixXd Zcand;//matrice Z du candidat (modification Z) Eigen::ArrayXXd SumCol(1,Zcand.cols());//SumCol est un vecteur qui contient la somme de chaque colonne de Zcand (modification Z) int val;//permet de mettre une colonne et une ligne a 0 (modification Z) Eigen::VectorXd BIC_cand;//vecteur qui contient les BIC de chaque colonne des la matrice Zcand (calcul du BIC) double Sum_BIC_cand;//somme des BIC de BIC_cand (calcul BIC) Eigen::VectorXd stock_bool;//vecteur qui permet de savoir si un candidat peut etre choisi (stock) Eigen::VectorXd stock_BIC;//vecteur qui contient le BIC de tout les candidats (stock) double sumbic;//BIC de chaque etapes Eigen::VectorXd bic_etape (imaxiter[0]);//vecteur qui stock le BIC de chaque etapes Eigen::VectorXd complexite_etape (imaxiter[0]);//vecteur qui stock la compléxité de Z a chaque etapes Eigen::VectorXd etape (imaxiter[0]);//vecteur qui stock le type de changement de chaque etapes bool station;//permet de savoir si on est stationnaire ou non //initialisation Zopt = MatrixXd::Zero(p,p); //somme a la main Bicbest = Bic_vide_vect.sum(); bicvect=BicZ_cpp(matX,matZ,Bic_vide_vect,Bic_vide_vect,imet_BIC[0],Zopt); //somme a la main sumbic=bicvect.sum(); if(star){ sumbic=sumbic-ProbaZ_cpp(matZ); } if (ibla[0]>0) { Rcout<<sumbic<<"\n"; } if (sumbic<Bicbest) { Bicbest =sumbic; Zopt=matZ; } newZ=matZ; int step =0; if (imet_tirage[0]==0)//methode de changement de la ligne et de la colonne { nbcand=2*p-2; list_cand.resize(nbcand,2);//2p-2 candidats } else if(imet_tirage[0]==-1) { nbcand=p-1; list_cand.resize(nbcand,2);//p-1 candidats (colonne uniquement) } else if(imet_tirage[0]==-2) { nbcand=p*(p-1); list_cand.resize(nbcand,2);//p-1 candidats (colonne uniquement) } else if(imet_tirage[0]>0)//methode de tirage aléatoire { nbcand=imet_tirage[0]; list_cand.resize(nbcand,2);//le nombre de candidats est determine pas l'utilisateur } else if(imet_tirage[0]!=-3) //si methode a une valeur aberante { throw std::range_error("methode de tirage incorrecte"); } if (irandom[0]==0) { ibetter[0]=1; ibest[0]=1; } else if (ibetter[0]==1) { ibest[0]=1; } nb_opt=0; while(step<imaxiter[0]) // initialisation des variables { compte=0;//initialisation du vecteur liste désigne le numéro du candidat //liste candidats (couples [i,j]) if (imet_tirage[0]==0)//methode de changement de la ligne et de la colonne { k=int(p*runif(1)[0]);//on tire un numero aleatoire pour savoir quel est la ligne et la colonne de candidats for(i=0;i<p;i++) { if(i!=k)//on ne veut pas avoir de 1 sur la diagonale { list_cand(compte,0)=i; list_cand(compte,1)=k; compte=compte+1; list_cand(compte,0)=k; list_cand(compte,1)=i; compte=compte+1; } } } else if (imet_tirage[0]==-1)//seulement la colonne { k=int(p*runif(1)[0]); for(i=0;i<p;i++) { if(i!=k) { list_cand(compte,0)=i; list_cand(compte,1)=k; compte=compte+1; } } } else if (imet_tirage[0]==-2)//tout le monde sauf la diagonale { for(k=0;k<p;k++) { for(i=0;i<p;i++) { if(i!=k) { list_cand(compte,0)=i; list_cand(compte,1)=k; compte=compte+1; } } } } else if (imet_tirage[0]==-3)//tout le monde sauf la diagonale { nbcand=0; sumZ=newZ.sum(); if(sumZ!=0) { list_cand.resize(newZ.sum(),2);//autant de candidats que de points } for(k=0;k<p;k++) { for(i=0;i<p;i++) { if(i!=k) { if(newZ(i,k)!=0) { list_cand(compte,0)=i; list_cand(compte,1)=k; compte=compte+1; nbcand++; } } } } if(nbcand==0)//aucun candidat donc on arrête { step=imaxiter[0]+10; } } else if (imet_tirage[0]>0)//methode de tirage aléatoire { for(i=0;i<nbcand;i++) { rand1=int(p*runif(1)[0]);//nombres aleatoire pour avoir le numero de la ligne rand2=int(p*runif(1)[0]);//nombres aleatoire pour avoir le numero de la colonne if (rand1==rand2)//on ne veut pas de 1 sur la diagonale { if(rand1<p-1) { rand2=rand1+1; } else { rand2=rand1-1; } } list_cand(i,0)=rand1; list_cand(i,1)=rand2; } } //pour chaque candidat for (numcand=0;numcand<nbcand;numcand++) { //modification (calcul du Z) (Zcand avec methode (rejet ou relax) Z,i,j,methode="relax", p2max=inf,rmax=inf) i_loc=list_cand(numcand,0); j_loc=list_cand(numcand,1); realisable=1;//le changement est vrai par defaut Zcand=newZ; Zcand(i_loc,j_loc)=1-Zcand(i_loc,j_loc); for(val=0;val<Zcand.cols();val++)//la ligne et la colonne deviennent 0 car on est en mode rejet { Zcand(val,i_loc)=0; Zcand(j_loc,val)=0; } if (Zcand.col(j_loc).sum()>irmax[0]) { realisable=0; } else { SumCol=Zcand.colwise().sum();//SumCol est un vecteur qui contient la somme de chaque colonne de Zcand if ((SumCol > 0).count()>ip2max[0])//si SumCol a plus de p2max valeur > 0 alors on ne modifiera pas la matrice { realisable=0; } } //calcul du bic (du nouveau Z généré) (bicZ) if (realisable==0) { Sum_BIC_cand=0; } else { BIC_cand=BicZ_cpp(matX,Zcand,Bic_vide_vect,bicvect,imet_BIC[0],newZ); if(Exact){ for(val=0;val<BIC_cand.size();val++){ if(BIC_cand(val)==0){ Rcout <<val+1<< " depends on"; //on recherche l'emplacement des 1 dans le vecteur colonne (variables a droite) for(int i=0;i<=p-1;i++) { if (Zcand(i,val)==1) { Rcout<< " "<< i+1 << " "; }//fin if }//fin for i Rcout<<"\n"; step=imaxiter[0]; } } } Sum_BIC_cand=BIC_cand.sum(); if(star){ Sum_BIC_cand=Sum_BIC_cand-ProbaZ_cpp(Zcand); } } //stockage des valeurs (bic,changement) stock_bool.resize(nbcand); stock_bool(numcand)=realisable; stock_BIC.resize(nbcand); stock_BIC(numcand)=Sum_BIC_cand; } //choix du candidat retenu (tirage au sort ou meilleur selon le cas) int nb_cand_retenu=stock_bool.sum()+1;//nombre de candidats retenu (certain ne peuvent pas etre pri en compte) // à faire à la main Eigen::VectorXd ind_stock_bool1(nb_cand_retenu-1);//vecteur contenant les numeros des individus retenus Eigen::VectorXd stockBIC1(nb_cand_retenu);//vecteur contenant les bic des individus retenus int compteur=0;//compteur permattant de remplir stockBIC1 et ind_stock_bool1 int bettercand=0; int iret,jret;//coordonnees du candidat ayant le meilleur bic depuis le debut double sumcum=0; int cha; int w; NumericVector ran; Eigen::VectorXd bicweight(nb_cand_retenu); double sumexp=0; double BIC_min=sumbic; station=false; stockBIC1(0)=sumbic; for (i=0;i<stock_BIC.size();i++)//on garde que les individus retunus { if(stock_bool(i,0)==1) { ind_stock_bool1(compteur)=i;//seulement les individus possibles stockBIC1(compteur+1)=stock_BIC(i); if(stockBIC1(compteur+1)<BIC_min)//on cherche le plus petit BIC { BIC_min=stockBIC1(compteur+1); bettercand=compteur+1; } compteur=compteur+1; } } //prise de décision if(BIC_min<Bicbest) //regarde s'il y'a un BIC meilleur que le meuilleur rencontré { step_opt=step; nb_opt=0;//il y a un nouveau bicbest donc le compteur revient a 0 Bicbest=BIC_min; iret=list_cand(ind_stock_bool1(bettercand-1),0);//-1 a cause de la stationarité jret=list_cand(ind_stock_bool1(bettercand-1),1); Zopt=newZ;//initialisation à la stationarité Zopt(iret,jret)=1-Zopt(iret,jret); if (Zopt(iret,jret)==1)//si on a ajouter { for(cha=0;cha<p;cha++) { Zopt(cha,iret)=0; Zopt(jret,cha)=0; } } if (ibla[0]>0) { Rcout<<step<<" Bicbest: "<<Bicbest<<" complexite: "<<Zopt.sum()<<"\n"; if (ibla[0]==2) { Rcout<<"nb_cand "<<nb_cand_retenu<<"BIC min "<<BIC_min<<"\n"; } } if(ibest[0]==1)//on a vu le meilleur absolu donc si on veut y aller, on y va { bicvect=BicZ_cpp(matX,Zopt,Bic_vide_vect,bicvect,imet_BIC[0],newZ); newZ=Zopt; sumbic=Bicbest; } else //tirage au sort { bicweight=stockBIC1; for (int v=0;v<nb_cand_retenu;v++) { bicweight(v)=bicweight(v)-BIC_min; bicweight(v)=exp(-bicweight(v)/2); sumexp=sumexp+bicweight(v); } w=-1;//initialisation candidat choisi (il est a -1 car on va rajouter un "+1" avec le while) ran=runif(1); sumcum=0; while (ran[0]>=sumcum)//choix du candidat { w++; bicweight(w)=bicweight(w)/sumexp; sumcum=sumcum+bicweight(w); } if(w==0) { station=true; } else { iret=list_cand(ind_stock_bool1(w-1),0);//-1 car stationarité en premier dans bicweight jret=list_cand(ind_stock_bool1(w-1),1); Zcand=newZ; Zcand(iret,jret)=1-Zcand(iret,jret); if (Zcand(iret,jret)==1)//si on a ajouter { for(cha=0;cha<p;cha++) { Zcand(cha,iret)=0; Zcand(jret,cha)=0; } } bicvect=BicZ_cpp(matX,Zcand,Bic_vide_vect,bicvect,imet_BIC[0],newZ); newZ=Zcand; sumbic=stockBIC1(w); } } } else if(nb_cand_retenu==1) //si la stationarité est le seul candidat { station=true; } else if(ibetter[0]==1 && bettercand!=0)//si on a un meilleur local et qu'on veut y aller, on y va { iret=list_cand(ind_stock_bool1(bettercand-1),0);//-1 a cause de la stationarité jret=list_cand(ind_stock_bool1(bettercand-1),1); Zcand=newZ; Zcand(iret,jret)=1-Zcand(iret,jret); if (Zcand(iret,jret)==1)//si on a ajouter { for(cha=0;cha<p;cha++) { Zcand(cha,iret)=0; Zcand(jret,cha)=0; } } bicvect=BicZ_cpp(matX,Zcand,Bic_vide_vect,bicvect,imet_BIC[0],newZ); newZ=Zcand; sumbic=BIC_min; } else if (irandom[0]==0) { station=true; } else//tirage au sort (on a pas de saut systématique) { bicweight=stockBIC1; for (int v=0;v<nb_cand_retenu;v++) { bicweight(v)=bicweight(v)-BIC_min; bicweight(v)=exp(-bicweight(v)/2); sumexp=sumexp+bicweight(v); } w=-1;//initialisation candidat choisi (il est a -1 car on va rajouter un "+1" avec le while) ran=runif(1); sumcum=0; while (ran[0]>=sumcum)//choix du candidat { w++; bicweight(w)=bicweight(w)/sumexp; sumcum=sumcum+bicweight(w); } if(w==0) { station=true; } else { iret=list_cand(ind_stock_bool1(w-1),0);//-1 car stationarité en premier dans bicweight jret=list_cand(ind_stock_bool1(w-1),1); Zcand=newZ; Zcand(iret,jret)=1-Zcand(iret,jret); if (Zcand(iret,jret)==1)//i we have added { for(cha=0;cha<p;cha++) { Zcand(cha,iret)=0; Zcand(jret,cha)=0; } } bicvect=BicZ_cpp(matX,Zcand,Bic_vide_vect,bicvect,imet_BIC[0],newZ); newZ=Zcand; sumbic=stockBIC1(w); } } if(sumbic==Bicbest)//on regarde si le le BIC est le meme que le BIC optimal { nb_opt=nb_opt+1;//si c'est le cas alors on a retrouve une fois de plus BICbest if(nb_opt==inb_opt_max[0])//si on a atteint le nombre maximum de fois ou on a retrouvé BICbest { imaxiter[0]=step;//alors on sort du while Rcout<<"convergence atteinte"; } } if(iplot[0]==1)//si on veut des graphiques on mets à jour les vecteurs { bic_etape (step)=sumbic; complexite_etape (step)=newZ.sum(); if (station==true) { etape (step)=2;//stationarité } else if(newZ(iret,jret)==0) { etape (step)=0;//suppression } else { etape (step)=1;//ajout } } if(ibla[0]>2) { Rcout<<step<<" BIC local: "<<sumbic<<" compléxité local: "<<newZ.sum()<<"\n"; } step=step+1; }//fin des étapes (while) if(iplot[0]==1) { Eigen::VectorXd BIC_step(step);//on met les vecteurs sorti de bonne dimension Eigen::VectorXd complexite_step(step); if(step>1)//s'il y'a eu au moins une etape alors on tranfert les donnees des vecteurs { for(int k=0;k<step;k++) { BIC_step(k)=bic_etape(k); complexite_step(k)=complexite_etape(k); } } return List::create( Named("Z")= newZ, Named("bic_loc")= sumbic, Named("Z_opt")= Zopt, Named("bic_opt")= Bicbest, Named("bic_step")= BIC_step, Named("complexity_step")= complexite_step, Named("step")= etape, Named("step_opt")= step_opt ); } else { return List::create( Named("Z")= newZ, Named("bic_loc")= sumbic, Named("Z_opt")= Zopt, Named("bic_opt")= Bicbest, Named("step_opt")= step_opt ); } END_RCPP }
SEXP cleancolZ(SEXP X,SEXP Z,SEXP bic_vide_vect,SEXP methode_BIC,SEXP plot,SEXP bla,SEXP Rstar) { BEGIN_RCPP //declaration des variables const Map<MatrixXd> matZ(as<Map<MatrixXd> >(Z));//Z const Map<MatrixXd> matX(as<Map<MatrixXd> >(X));//X const Map<VectorXd> Bic_vide_vect(as<Map<VectorXd> >(bic_vide_vect));//bic_vide_vect bool star = Rcpp::as<bool>(Rstar); // BICstar Rcpp::NumericVector met_BIC(methode_BIC),Plot(plot),Bla(bla); typedef Rcpp::NumericVector::iterator vec_iterator; vec_iterator imet_BIC=met_BIC.begin(),iplot=Plot.begin(),ibla=Bla.begin(); int p=matZ.cols();//nombre de colonne de la matrice Z Eigen::MatrixXd Zopt;//meilleur Z obtenu double Bicbest;//BIC associe au meilleur modele Eigen::VectorXd bicvect;//vecteur BIC des matrices Z retenues Eigen::MatrixXd newZ;//matrice Z modifie a chaque etapes Eigen::VectorXd list_cand;//vecteur qui contient les indices des colonnes candidates (liste candidats) int compte=0;//permet de cree la matrice liste en designant le numero du candidat (liste candidats) int nbcand;//nombre de candidats int numcand;//numero du candidat int i_loc;//premiere coordonnee du candidat (modification Z) Eigen::MatrixXd Zcand;//matrice Z du candidat (modification Z) Eigen::ArrayXXd SumCol(1,p);//SumCol est un vecteur qui contient la somme de chaque colonne de Zcand (modification Z) Eigen::VectorXd BIC_cand;//vecteur qui contient les BIC de chaque colonne des la matrice Zcand (calcul du BIC) double Sum_BIC_cand;//somme des BIC de BIC_cand (calcul BIC) Eigen::VectorXd stock_BIC;//vecteur qui contient le BIC de tout les candidats (stock) double sumbic;//BIC de chaque etapes double BIC_min; bool minimum; int i; int iret=1; Eigen::VectorXd bic_etape;//vecteur qui stock le BIC de chaque etapes Eigen::VectorXd complexite_etape;//vecteur qui stock la complexite de Z a chaque etapes Eigen::VectorXd BIC_step;//vecteur qui stock le BIC de chaque etapes Eigen::VectorXd complexite_step ;//vecteur qui stock la complexite de Z a chaque etapes //initialisation bicvect=BicZ_cpp2(matX,matZ,Bic_vide_vect,imet_BIC[0]); //somme a la main sumbic=bicvect.sum(); if(star) { sumbic=sumbic-ProbaZ_cpp(matZ); } if (ibla[0]>0) { Rcout<<sumbic<<"\n"; } Bicbest =sumbic; Zopt=matZ; newZ=matZ; int step =0; SumCol=matZ.colwise().sum();//nombre d'elements dans chaque colonne nbcand=(SumCol>0).count();//nombre de colonnes candidates (quand il y'a au moins 1 element dans une colonne) list_cand.resize(nbcand);//le nombre de candidats est la complexite du modele bic_etape.resize(nbcand); complexite_etape.resize(nbcand); while(step<nbcand) { compte=0;//initialisation du vecteur liste designe le numero du candidat //liste candidats (couples [i,j]) for(int n=0;n<p;n++)//parcours les colonnes { if(newZ.col(n).sum()>0)//on cherche les candidats { list_cand(compte)=n;//stock la colonne du candidat compte=compte+1;//passage au candidat suivant } } stock_BIC.resize(compte); //pour chaque candidat for (numcand=0;numcand<compte;numcand++) { //modification (calcul du Z) (Zcand avec methode (rejet ou relax) Z,i,j,methode="relax", p2max=inf,rmax=inf) Zcand=newZ; for(i_loc=0;i_loc<p;i_loc++)//parcours des lignes { Zcand(i_loc,list_cand(numcand))=0;//modification de Z par rapport a la colonne candidate } //calcul du bic (du nouveau Z genere) BIC_cand=BicZ_cpp(matX,Zcand,Bic_vide_vect,bicvect,imet_BIC[0],newZ);//calcul du vecteur BIC du candidat Sum_BIC_cand=BIC_cand.sum(); if (star) { Sum_BIC_cand=Sum_BIC_cand-ProbaZ_cpp(Zcand); } //stockage du BIC stock_BIC(numcand)=Sum_BIC_cand; } //on regarde la meilleur candidat BIC_min=Bicbest;//initialisation BIC_min minimum=false; for(i=0;i<compte;i++) { if(stock_BIC(i)<Bicbest)//si on a trouve un minimum { iret=i;//on retient sa position minimum=true; Bicbest=stock_BIC(i);//on modifie Bicbest } } if (minimum==true)//si il y a un minimum, on y va { Zopt=newZ;//initialisation a la stationarite for(int i_opt=0;i_opt<p;i_opt++)//on met la colonne a 0 { Zopt(i_opt,list_cand(iret))=0; } bicvect=BicZ_cpp(matX,Zopt,Bic_vide_vect,bicvect,imet_BIC[0],newZ);//calcul du vecteur BIC du nouveau Zopt newZ=Zopt; //partie commentaires if (ibla[0]>0) { Rcout<<"etape : "<<step<<"\n"; Rcout<<" Bicbest: "<<Bicbest<<" complexite: "<<newZ.sum()<<"\n"; if (ibla[0]==2) { Rcout<<"nb_cand "<<compte<<"BIC min "<<BIC_min<<"\n"; } } //partie graphiques if(iplot[0]==1)//si on veut des graphiques on mets a jour les vecteurs { bic_etape(step)=Bicbest; complexite_etape(step)=newZ.sum(); } step=step+1;//passage a l'etape suivante s'il y a eu un minimum } else//pas de minimum { if (ibla[0]>0){ Rcout<<"nettoyage fini"; } step=nbcand+1;//arret des etapes } }//fin des étapes if(iplot[0]==1)//si on veut des graphiques on mets a jour les vecteurs { BIC_step.resize(nbcand-compte);//on redimensionne pour les plot complexite_step.resize(nbcand-compte); if(nbcand-compte>0)//si il y'a eu au moins une etape { for(int k=0;k<nbcand-compte;k++) { BIC_step(k)=bic_etape(k); complexite_step(k)=complexite_etape(k); } } return List::create( Named("Z")= newZ, // Named("Z_opt")= Zopt, Named("bic_opt")= Bicbest, Named("bic_step")= BIC_step, Named("complexity_step")= complexite_step ); } else { return List::create( Named("Z")= newZ, // Named("Z_opt")= Zopt, Named("bic_opt")= Bicbest ); } END_RCPP }
int main(int argc, char *argv[]) { using namespace std; // Load a mesh in OFF format igl::readOBJ(TUTORIAL_SHARED_PATH "/camel_b.obj", V, F); Eigen::MatrixXd bnd_uv, uv_init; Eigen::VectorXd M; igl::doublearea(V, F, M); std::vector<std::vector<int>> all_bnds; igl::boundary_loop(F, all_bnds); // Heuristic primary boundary choice: longest auto primary_bnd = std::max_element(all_bnds.begin(), all_bnds.end(), [](const std::vector<int> &a, const std::vector<int> &b) { return a.size()<b.size(); }); Eigen::VectorXi bnd = Eigen::Map<Eigen::VectorXi>(primary_bnd->data(), primary_bnd->size()); igl::map_vertices_to_circle(V, bnd, bnd_uv); bnd_uv *= sqrt(M.sum() / (2 * igl::PI)); if (all_bnds.size() == 1) { if (bnd.rows() == V.rows()) // case: all vertex on boundary { uv_init.resize(V.rows(), 2); for (int i = 0; i < bnd.rows(); i++) uv_init.row(bnd(i)) = bnd_uv.row(i); } else { igl::harmonic(V, F, bnd, bnd_uv, 1, uv_init); if (igl::flipped_triangles(uv_init, F).size() != 0) igl::harmonic(F, bnd, bnd_uv, 1, uv_init); // fallback uniform laplacian } } else { // if there is a hole, fill it and erase additional vertices. all_bnds.erase(primary_bnd); Eigen::MatrixXi F_filled; igl::topological_hole_fill(F, bnd, all_bnds, F_filled); igl::harmonic(F_filled, bnd, bnd_uv ,1, uv_init); uv_init = uv_init.topRows(V.rows()); } Eigen::VectorXi b; Eigen::MatrixXd bc; igl::scaf_precompute(V, F, uv_init, scaf_data, igl::MappingEnergyType::SYMMETRIC_DIRICHLET, b, bc, 0); // Plot the mesh igl::opengl::glfw::Viewer viewer; viewer.data().set_mesh(V, F); const auto& V_uv = uv_scale * scaf_data.w_uv.topRows(V.rows()); viewer.data().set_uv(V_uv); viewer.callback_key_down = &key_down; // Enable wireframe viewer.data().show_lines = true; // Draw checkerboard texture viewer.data().show_texture = true; std::cerr << "Press space for running an iteration." << std::endl; std::cerr << "Press 1 for Mesh 2 for UV" << std::endl; // Launch the viewer viewer.launch(); }
template <typename PointSource, typename PointTarget> int TransformationEstimationJointOptimize<PointSource, PointTarget>::OptimizationFunctor::operator() (const Eigen::VectorXd &x, Eigen::VectorXd &fvec) const { const pcl::PointCloud<PointSource> & src_points = *estimator_->tmp_src_; const pcl::PointCloud<PointTarget> & tgt_points = *estimator_->tmp_tgt_; const std::vector<int> & src_indices = *estimator_->tmp_idx_src_; const std::vector<int> & tgt_indices = *estimator_->tmp_idx_tgt_; const std::vector<int> & src_indices_dfp = *estimator_->tmp_idx_src_dfp_; const std::vector<int> & tgt_indices_dfp = *estimator_->tmp_idx_tgt_dfp_; const std::vector<int> & src_indices_handles = *estimator_->tmp_idx_src_handles_; const std::vector<int> & tgt_indices_handles = *estimator_->tmp_idx_tgt_handles_; const float visualWeight = estimator_->visualFeatureWeight; const float denseWeight = estimator_->denseCloudWeight; const float handleWeight = estimator_->handleFeatureWeight; // Initialize the warp function with the given parameters Eigen::VectorXf params = x.cast<float> (); estimator_->warp_point_->setParam (params); Eigen::Matrix4f curr_transformation_matrix = estimator_->warp_point_->getTransform (); //std::cout << "[OptimizationFunctor::operator()] current transform = " << std::endl << curr_transformation_matrix << std::endl; //std::cerr << "[error function] before visual points: " << fvec.sum() << "\n"; // Sum of squared distances of distinctive feature points // double diff_value_dfp = 0; const double dfp_factor = visualWeight/number_dfp; for (int i = 0; i < number_dfp; ++i) { std::cerr << "[error function] entered visual points loop: " << fvec.sum() << "\n"; const PointSource & p_src = src_points.points[src_indices_dfp[i]]; const PointTarget & p_tgt = tgt_points.points[tgt_indices_dfp[i]]; // Transform the source point based on the current warp parameters PointSource p_src_warped; estimator_->warp_point_->warpPoint (p_src, p_src_warped); // Estimate the distance (cost function) // diff_value_dfp += estimator_->computeDistance (p_src_warped, p_tgt); fvec[i] = dfp_factor * estimator_->computeDistance (p_src_warped, p_tgt); } //std::cerr << "[error function] after visual points: " << fvec.sum() << "\n"; const double p_factor = (denseWeight)/number_p; for (int i = 0; i < number_p; ++i) { const PointSource & p_src = src_points.points[src_indices[i]]; const PointTarget & p_tgt = tgt_points.points[tgt_indices[i]]; // Transform the source point based on the current warp parameters PointSource p_src_warped; estimator_->warp_point_->warpPoint (p_src, p_src_warped); // Estimate the distance (cost function) // diff_value_p += estimator_->computeDistance (p_src_warped, p_tgt); fvec[i+number_dfp] = p_factor * estimator_->computeDistancePointToPlane (p_src_warped, p_tgt); if(fvec[i+number_dfp] != fvec[i+number_dfp]) { std::cerr << "i: " << i << " is nan! fvec[i]= " << fvec[i+number_dfp] << "\n"; std::cerr << "source point : " << p_src << "\n"; std::cerr << "source point warped: " << p_src_warped << "\n"; std::cerr << "target point : " << p_tgt << "\n"; } // std::cerr << "fvec point " << (int)i << ":" << fvec[i+number_dfp] << "\n"; } //std::cerr << "[error function] after points and features: " << fvec.sum() << "\n"; const double handle_factor = (handleWeight)/number_handle_p; double totalError = 0.0; for (int i = 0; i < number_handle_p; ++i) { const PointSource & p_src = src_points.points[src_indices_handles[i]]; const PointTarget & p_tgt = tgt_points.points[tgt_indices_handles[i]]; // Transform the source point based on the current warp parameters PointSource p_src_warped; estimator_->warp_point_->warpPoint (p_src, p_src_warped); // Estimate the distance (cost function) // diff_value_p += estimator_->computeDistance (p_src_warped, p_tgt); fvec[i+number_dfp+number_p] = handle_factor * estimator_->computeDistance (p_src_warped, p_tgt); totalError += fvec[i+number_dfp+number_p]; //std::cerr << "i: " << i << " src indice: " << src_indices_handles[i] << " src point: " << p_src_warped // << " tgt indice: " << tgt_indices_handles[i] << " tgt point: " << p_tgt //std::cerr << "i: " << i << " Distance error: " << fvec[i+number_dfp+number_p] << "\n"; //std::cerr << "fvec handle point " << (int)i << ":" << fvec[i+number_dfp+number_p] << "\n"; } //std::cerr << "[error function] after points and features and handles: " << fvec.sum() << "\n"; //fvec[0] = totalError; //for (int i = 1; i < (number_handle_p + number_p + number_dfp); ++i) //{ // std::cerr << "i: " << i << "error: " << fvec[i] << "\n"; // fvec[i] = 0.0; //} //std::cerr << "[error functino] fvec total error : " << fvec.sum() << "\n"; //std::cerr << "[error functino] my total error : " << totalError << "\n"; //std::cerr << "##############Other debug info: ##########\n" // << "Visual weight: " << visualWeight << " visual points: " << number_dfp << " visual factor: " << dfp_factor << "\n" // << "dense weight: " << denseWeight << " dense points: " << number_p << " dense factor: " << p_factor << "\n" // << "handle weight: " << handleWeight << " handle points: " << number_handle_p << " handle factor: " << handle_factor << "\n"; // Divide by number of points // diff_value_p = diff_value_p/number_p; // Update function value // fvec[0] = ((alpha * diff_value_dfp) + ((1-alpha) * diff_value_p))*1000; //std::cout << "[OptimizationFunctor::operator()] fvec.blueNorm = " << fvec.blueNorm() << std::endl; return (0); }
void state::compute(int want, FitContext *fc) { state *st = (state*) this; auto *oo = this; for (auto c1 : components) { if (c1->fitFunction) { omxFitFunctionCompute(c1->fitFunction, want, fc); } else { omxRecompute(c1, fc); } } if (!(want & FF_COMPUTE_FIT)) return; int nrow = components[0]->rows; for (auto c1 : components) { if (c1->rows != nrow) { mxThrow("%s: component '%s' has %d rows but component '%s' has %d rows", oo->name(), components[0]->name(), nrow, c1->name(), c1->rows); } } Eigen::VectorXd expect; Eigen::VectorXd rowResult; int numC = components.size(); Eigen::VectorXd tp(numC); double lp=0; for (int rx=0; rx < nrow; ++rx) { if (expectation->loadDefVars(rx) || rx == 0) { omxExpectationCompute(fc, expectation, NULL); if (!st->transition || rx == 0) { EigenVectorAdaptor Einitial(st->initial); expect = Einitial; if (expect.rows() != numC || expect.cols() != 1) { omxRaiseErrorf("%s: initial prob matrix must be %dx%d not %dx%d", name(), numC, 1, expect.rows(), expect.cols()); return; } } if (st->transition && (st->transition->rows != numC || st->transition->cols != numC)) { omxRaiseErrorf("%s: transition prob matrix must be %dx%d not %dx%d", name(), numC, numC, st->transition->rows, st->transition->cols); return; } } for (int cx=0; cx < int(components.size()); ++cx) { EigenVectorAdaptor Ecomp(components[cx]); tp[cx] = Ecomp[rx]; } if (st->verbose >= 4) { mxPrintMat("tp", tp); } if (st->transition) { EigenMatrixAdaptor Etransition(st->transition); expect = (Etransition * expect).eval(); } rowResult = tp.array() * expect.array(); double rowp = rowResult.sum(); rowResult /= rowp; lp += log(rowp); if (st->transition) expect = rowResult; } oo->matrix->data[0] = Global->llScale * lp; if (st->verbose >= 2) mxLog("%s: fit=%f", oo->name(), lp); }
void NuTo::StructureBase::ConstraintLinearEquationNodeToElementCreate(int rNode, int rElementGroup, NuTo::Node::eDof, const double rTolerance, Eigen::Vector3d rNodeCoordOffset) { const int dim = GetDimension(); Eigen::VectorXd queryNodeCoords = NodeGetNodePtr(rNode)->Get(Node::eDof::COORDINATES); queryNodeCoords = queryNodeCoords + rNodeCoordOffset.head(dim); std::vector<int> elementGroupIds = GroupGetMemberIds(rElementGroup); ElementBase* elementPtr = nullptr; Eigen::VectorXd elementNaturalNodeCoords; bool nodeInElement = false; for (auto const& eleId : elementGroupIds) { elementPtr = ElementGetElementPtr(eleId); // Coordinate interpolation must be linear so the shape function derivatives are constant! assert(elementPtr->GetInterpolationType().Get(Node::eDof::COORDINATES).GetTypeOrder() == Interpolation::eTypeOrder::EQUIDISTANT1); const Eigen::MatrixXd& derivativeShapeFunctionsGeometryNatural = elementPtr->GetInterpolationType() .Get(Node::eDof::COORDINATES) .DerivativeShapeFunctionsNatural( Eigen::VectorXd::Zero(dim)); // just as _some_ point, as said, constant // real coordinates of every node in rElement Eigen::VectorXd elementNodeCoords = elementPtr->ExtractNodeValues(NuTo::Node::eDof::COORDINATES); switch (mDimension) { case 2: { Eigen::Matrix2d invJacobian = dynamic_cast<ContinuumElement<2>*>(elementPtr) ->CalculateJacobian(derivativeShapeFunctionsGeometryNatural, elementNodeCoords) .inverse(); elementNaturalNodeCoords = invJacobian * (queryNodeCoords - elementNodeCoords.head(2)); } break; case 3: { Eigen::Matrix3d invJacobian = dynamic_cast<ContinuumElement<3>*>(elementPtr) ->CalculateJacobian(derivativeShapeFunctionsGeometryNatural, elementNodeCoords) .inverse(); elementNaturalNodeCoords = invJacobian * (queryNodeCoords - elementNodeCoords.head(3)); } break; default: throw NuTo::Exception(std::string(__PRETTY_FUNCTION__) + ": \t Only implemented for 2D and 3D"); } if ((elementNaturalNodeCoords.array() > -rTolerance).all() and elementNaturalNodeCoords.sum() <= 1. + rTolerance) { nodeInElement = true; break; } } if (not nodeInElement) { GetLogger() << "Natural node coordinates: \n" << elementNaturalNodeCoords << "\n"; throw Exception(__PRETTY_FUNCTION__, "Node is not inside any element."); } auto shapeFunctions = elementPtr->GetInterpolationType().Get(Node::eDof::DISPLACEMENTS).ShapeFunctions(elementNaturalNodeCoords); std::vector<Constraint::Equation> equations(dim); // default construction of Equation with rhs = Constant = 0 for (int iDim = 0; iDim < dim; ++iDim) { equations[iDim].AddTerm(Constraint::Term(*NodeGetNodePtr(rNode), iDim, 1.)); } for (int iNode = 0; iNode < shapeFunctions.rows(); ++iNode) { int localNodeId = elementPtr->GetInterpolationType().Get(Node::eDof::DISPLACEMENTS).GetNodeIndex(iNode); auto globalNode = elementPtr->GetNode(localNodeId, Node::eDof::DISPLACEMENTS); // std::cout << "globalNodeId \t" << globalNodeId << std::endl; double coefficient = -shapeFunctions(iNode, 0); for (int iDim = 0; iDim < dim; ++iDim) equations[iDim].AddTerm(Constraint::Term(*globalNode, iDim, coefficient)); } Constraints().Add(Node::eDof::DISPLACEMENTS, equations); }
TEST_CASE("Test solver for the IEFPCM with NH3 molecule and a GePol cavity", "[solver][iefpcm][iefpcm_gepol-NH3]") { Molecule molec = NH3(); double area = 0.4; double probeRadius = 0.0; double minRadius = 100.0; GePolCavity cavity = GePolCavity(molec, area, probeRadius, minRadius); cavity.saveCavity("nh3.npz"); double permittivity = 78.39; Vacuum<AD_directional, CollocationIntegrator> gfInside = Vacuum<AD_directional, CollocationIntegrator>(); UniformDielectric<AD_directional, CollocationIntegrator> gfOutside = UniformDielectric<AD_directional, CollocationIntegrator>(permittivity); bool symm = true; IEFSolver solver(symm); solver.buildSystemMatrix(cavity, gfInside, gfOutside); double Ncharge = 7.0; double Hcharge = 1.0; size_t size = cavity.size(); Eigen::VectorXd fake_mep = computeMEP(molec, cavity.elements()); // The total ASC for a dielectric is -Q*(epsilon-1)/epsilon Eigen::VectorXd fake_asc = Eigen::VectorXd::Zero(size); fake_asc = solver.computeCharge(fake_mep); double totalASC = - (Ncharge + 3.0 * Hcharge) * (permittivity - 1) / permittivity; double totalFakeASC = fake_asc.sum(); CAPTURE(totalASC - totalFakeASC); REQUIRE(totalASC == Approx(totalFakeASC).epsilon(1.0e-03)); }
/// <summary> /// use a kernel matrix and solve the svm problem /// </summary> /// <param name="Kernel">precomputed kernel</param> DualSolution libSVMWrapper::Solve(const Eigen::MatrixXd &Kernel) { // unfortunately libsvm needs "svm_nodes", so we have to copy everything // workaround pointer to matrix entries (eigen3 does not allow it?) // copy entries (code from libSVM) int j = 0, sc = NumberOfData + 1; // TODO // libSVM_x_space[j+k].value = *(Kernel.data() + (k-1)*NumberOfData + i); // by reference or pointer #pragma omp parallel for for (int i = 0; i < libSVM_Problem.l; i++) { j = (sc+1)*i ; for (int k = 0; k < sc; k++) { libSVM_x_space[j].index = k + 1; if (k == 0) { libSVM_x_space[j].value = i + 1; } else { libSVM_x_space[j+k].value = Kernel(i, k - 1); } } j = ((sc+1)*i+sc) ; libSVM_x_space[j+1].index = -1; } #ifdef DEBUG for (int i = 0; i < libSVM_Problem.l; i++) { if ((int) libSVM_Problem.x[i][0].value <= 0 || (int) libSVM_Problem.x[i][0].value > sc) { printf("Wrong input format: sample_serial_number out of range\n"); exit(0); } } const char *error_msg; error_msg = svm_check_parameter(&libSVM_Problem, &libSVM_Parameter); if (error_msg) { fprintf(stderr, "ERROR: %s\n", error_msg); exit(1); } #endif // train the model if (libSVM_Model != NULL) { svm_free_model_content(libSVM_Model); libSVM_Model = NULL; } libSVM_Model = svm_train(&libSVM_Problem, &libSVM_Parameter); // extract results // bias is easy double Bias = -1 * libSVM_Model->rho[0]; // alpha should be dense now Eigen::VectorXd Alpha = Eigen::MatrixXd::Zero(NumberOfData, 1); for (int i = 0; i < libSVM_Model->l; i++) { Alpha(libSVM_Model->sv_indices[i] - 1) = (libSVM_Model->sv_coef[0][i] < 0) ? -1 * libSVM_Model->sv_coef[0][i] : libSVM_Model->sv_coef[0][i]; } DualSolution DS; DS.Bias = Bias; DS.Alpha = Alpha; Eigen::VectorXd tt = Alpha.cwiseProduct(Y); // objective value of dual solution DS.Value = Alpha.sum() - 0.5* (double)(tt.transpose() * (Kernel*tt)); return DS; }