![]() |
GURLS++
2.0.00
C++ Implementation of GURLS Matlab Toolbox
|
ParamSelSiglam is the sub-class of ParamSelection that implements LOO cross-validation with the dual formulation for a rbf kernel.
#include <siglam.h>


Public Member Functions | |
| GurlsOptionsList * | execute (const gMat2D< T > &X, const gMat2D< T > &Y, const GurlsOptionsList &opt) |
| Performs parameter selection when the dual formulation of RLS is used with rbf kernel. | |
Static Public Member Functions | |
| static ParamSelection< T > * | factory (const std::string &id) throw (BadParamSelectionCreation) |
| Factory function returning a pointer to the newly created object. | |
| GurlsOptionsList * gurls::ParamSelSiglam< T >::execute | ( | const gMat2D< T > & | X, |
| const gMat2D< T > & | Y, | ||
| const GurlsOptionsList & | opt | ||
| ) | [virtual] |
The leave-one-out approach is used oer a 2-dimensional grid of values for the parameters sigma (kernel) and lambda (regularization)
| X | input data matrix |
| Y | labels matrix |
| opt | options with the following:
|
Implements gurls::ParamSelection< T >.
Definition at line 96 of file siglam.h.
{
// [n,T] = size(y);
const unsigned long t = Y.cols();
// GurlsOptionsList* kernel_old = NULL;
// if (opt.hasOpt("kernel"))
// {
// kernel_old = GurlsOptionsList::dynacast(opt.getOpt("kernel"));
// opt.removeOpt("kernel", false);
// }
GurlsOptionsList* nestedOpt = new GurlsOptionsList("nested");
nestedOpt->copyOpt("nlambda", opt);
nestedOpt->copyOpt("hoperf", opt);
nestedOpt->copyOpt("smallnumber", opt);
GurlsOptionsList* kernel = new GurlsOptionsList("kernel");
kernel->addOpt("type", "rbf");
nestedOpt->addOpt("kernel", kernel);
GurlsOptionsList* paramsel;
if(opt.hasOpt("paramsel"))
{
GurlsOptionsList* tmp_opt = new GurlsOptionsList("tmp");
tmp_opt->copyOpt("paramsel", opt);
paramsel = GurlsOptionsList::dynacast(tmp_opt->getOpt("paramsel"));
tmp_opt->removeOpt("paramsel", false);
delete tmp_opt;
paramsel->removeOpt("lambdas");
paramsel->removeOpt("sigma");
}
else
paramsel = new GurlsOptionsList("paramsel");
gMat2D<T>* dist = new gMat2D<T>(X.rows(), X.rows());
// if ~isfield(opt.kernel,'distance')
if(!kernel->hasOpt("distance"))
// opt.kernel.distance = squareform(pdist(X));
{
squareform<T>(X.getData(), X.rows(), X.cols(), dist->getData(), X.rows());
T *distSquared = new T[X.rows()*X.rows()];
copy(distSquared , dist->getData(), X.rows()*X.rows());
mult<T>(distSquared, distSquared, dist->getData(), X.rows()*X.rows());
kernel->addOpt("distance", new OptMatrix<gMat2D<T> >(*dist));
delete [] distSquared;
}
else
dist = &(kernel->getOptValue<OptMatrix<gMat2D<T> > >("distance"));
// if ~isfield(opt,'sigmamin')
if(!opt.hasOpt("sigmamin"))
{
// %D = sort(opt.kernel.distance);
// %opt.sigmamin = median(D(2,:));
// D = sort(squareform(opt.kernel.distance));
int d_len = X.rows()*(X.rows()-1)/2;
T* distY = new T[d_len];
// squareform<T>(dist->getData(), dist->rows(), dist->cols(), distY, 1);
const int size = dist->cols();
T* it = distY;
for(int i=1; i< size; it+=i, ++i)
copy(it , dist->getData()+(i*size), i);
std::sort(distY, distY + d_len);
// firstPercentile = round(0.01*numel(D)+0.5);
int firstPercentile = gurls::round( (T)0.01 * d_len + (T)0.5) -1;
// opt.sigmamin = D(firstPercentile);
nestedOpt->addOpt("sigmamin", new OptNumber(sqrt( distY[firstPercentile]) ));
delete [] distY;
}
else
{
nestedOpt->addOpt("sigmamin", new OptNumber(opt.getOptAsNumber("sigmamin")));
}
T sigmamin = static_cast<T>(nestedOpt->getOptAsNumber("sigmamin"));
// if ~isfield(opt,'sigmamax')
if(!opt.hasOpt("sigmamax"))
{
// %D = sort(opt.kernel.distance);
// %opt.sigmamax = median(D(n,:));
T mAx = *(std::max_element(dist->getData(),dist->getData()+ dist->getSize()));
// opt.sigmamax = max(max(opt.kernel.distance));
nestedOpt->addOpt("sigmamax", new OptNumber( sqrt( mAx )));
}
else
{
nestedOpt->addOpt("sigmamax", new OptNumber(opt.getOptAsNumber("sigmamax")));
}
T sigmamax = static_cast<T>(nestedOpt->getOptAsNumber("sigmamax"));
// if opt.sigmamin <= 0
if( le(sigmamin, (T)0.0) )
{
// opt.sigmamin = eps;
nestedOpt->removeOpt("sigmamin");
nestedOpt->addOpt("sigmamin", new OptNumber(std::numeric_limits<T>::epsilon()));
sigmamin = std::numeric_limits<T>::epsilon();
}
// if opt.sigmamin <= 0
if( le(sigmamin, (T)0.0))
{
// opt.sigmamax = eps;
nestedOpt->removeOpt("sigmamax");
nestedOpt->addOpt("sigmamax", new OptNumber(std::numeric_limits<T>::epsilon()));
sigmamax = std::numeric_limits<T>::epsilon();
}
unsigned long nlambda = static_cast<unsigned long>(opt.getOptAsNumber("nlambda"));
unsigned long nsigma = static_cast<unsigned long>( opt.getOptAsNumber("nsigma"));
T q = pow( sigmamax/sigmamin, static_cast<T>(1.0/(nsigma-1.0)));
// LOOSQE = zeros(opt.nsigma,opt.nlambda,T);
//T* LOOSQE = new T[nsigma*nlambda*t];
T* perf = new T[nlambda];
// sigmas = zeros(1,opt.nsigma);
// for i = 1:opt.nsigma
KernelRBF<T> rbfkernel;
ParamSelLoocvDual<T> loocvdual;
T* work = new T[std::max(nlambda, t+1)];
T maxTmp = (T)-1.0;
int m = -1;
T guess = (T)-1.0;
for(unsigned long i=0; i<nsigma; ++i)
{
nestedOpt->addOpt("paramsel", paramsel);
paramsel->removeOpt("sigma");
paramsel->addOpt("sigma", new OptNumber( sigmamin * pow(q, (T)i)));
// opt.kernel = kernel_rbf(X,y,opt);
GurlsOptionsList* retKernel = rbfkernel.execute(X, Y, *nestedOpt);
nestedOpt->removeOpt("kernel");
nestedOpt->addOpt("kernel", retKernel);
nestedOpt->removeOpt("paramsel", false);
// paramsel = paramsel_loocvdual(X,y,opt);
GurlsOptionsList* ret_paramsel = loocvdual.execute(X, Y, *nestedOpt);
gMat2D<T> &looe_mat = ret_paramsel->getOptValue<OptMatrix<gMat2D<T> > >("perf");
// LOOSQE(i,:,:) = paramsel.looe{1};
// guesses(i,:) = paramsel.guesses;
gMat2D<T> &guesses_mat = ret_paramsel->getOptValue<OptMatrix<gMat2D<T> > >("guesses");
for(unsigned long j=0; j<nlambda; ++j)
{
perf[j] = 0;
T* end = looe_mat.getData()+looe_mat.getSize();
for(T* it = looe_mat.getData()+j; it< end ; it+=nlambda)
perf[j] += *it;
}
unsigned long mm = std::max_element(perf, perf + nlambda) - perf;
if( gt(perf[mm], maxTmp))
{
maxTmp = perf[mm];
m = i;
guess = guesses_mat.getData()[mm*guesses_mat.rows()];
}
delete ret_paramsel;
}
delete [] work;
delete [] perf;
delete nestedOpt;
// M = sum(LOOSQE,3); % sum over classes
//
// [dummy,i] = max(M(:));
// [m,n] = ind2sub(size(M),i);
//
// % opt sigma
// vout.sigma = opt.sigmamin*(q^m);
paramsel->removeOpt("sigma");
paramsel->addOpt("sigma", new OptNumber( sigmamin * pow(q,m) ));
// % opt lambda
// vout.lambdas = guesses(m,n)*ones(1,T);
gMat2D<T> *LAMBDA = new gMat2D<T>(1, t);
set(LAMBDA->getData(), guess, t);
paramsel->addOpt("lambdas", new OptMatrix<gMat2D<T> >(*LAMBDA));
return paramsel;
}
| static ParamSelection<T>* gurls::ParamSelection< T >::factory | ( | const std::string & | id | ) | throw (BadParamSelectionCreation) [inline, static, inherited] |
Definition at line 146 of file paramsel.h.
{
if(id == "loocvprimal")
return new ParamSelLoocvPrimal<T>;
if(id == "loocvdual")
return new ParamSelLoocvDual<T>;
if(id == "fixlambda")
return new ParamSelFixLambda<T>;
if(id == "calibratesgd")
return new ParamSelCalibrateSGD<T>;
if(id == "siglam")
return new ParamSelSiglam<T>;
if(id == "siglamho")
return new ParamSelSiglamHo<T>;
if(id == "hodual")
return new ParamSelHoDual<T>;
if(id == "hodualr")
return new ParamSelHoDualr<T>;
if(id == "hoprimal")
return new ParamSelHoPrimal<T>;
if(id == "hoprimalr")
return new ParamSelHoPrimalr<T>;
if(id == "fixsiglam")
return new ParamSelFixSigLam<T>;
if(id == "loogpregr")
return new ParamSelLooGPRegr<T>;
if(id == "hogpregr")
return new ParamSelHoGPRegr<T>;
if(id == "siglamloogpregr")
return new ParamSelSiglamLooGPRegr<T>;
if(id == "siglamhogpregr")
return new ParamSelSiglamHoGPRegr<T>;
throw BadParamSelectionCreation(id);
}