[mlpack-svn] r10749 - mlpack/trunk/src/mlpack/methods/nca
fastlab-svn at coffeetalk-1.cc.gatech.edu
fastlab-svn at coffeetalk-1.cc.gatech.edu
Tue Dec 13 06:31:00 EST 2011
Author: rcurtin
Date: 2011-12-13 06:31:00 -0500 (Tue, 13 Dec 2011)
New Revision: 10749
Modified:
mlpack/trunk/src/mlpack/methods/nca/nca.hpp
mlpack/trunk/src/mlpack/methods/nca/nca_impl.hpp
mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function.hpp
mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function_impl.hpp
Log:
Abstract-ize matrix type used for NCA datasets. The covariance matrix should
not be sparse, though.
Modified: mlpack/trunk/src/mlpack/methods/nca/nca.hpp
===================================================================
--- mlpack/trunk/src/mlpack/methods/nca/nca.hpp 2011-12-13 11:30:22 UTC (rev 10748)
+++ mlpack/trunk/src/mlpack/methods/nca/nca.hpp 2011-12-13 11:31:00 UTC (rev 10749)
@@ -33,8 +33,11 @@
* title = {{Neighbourhood Components Analysis}},
* year = {2004}
* }
+ *
+ * @tparam MetricType Distance metric to use.
+ * @tparam MatType Type of matrix (arma::mat or arma::spmat).
*/
-template<typename Kernel>
+template<typename MetricType, typename MatType = arma::mat>
class NCA
{
public:
@@ -44,7 +47,7 @@
*
* @param dataset Input dataset.
*/
- NCA(const arma::mat& dataset, const arma::uvec& labels);
+ NCA(const MatType& dataset, const arma::uvec& labels);
/**
* Perform Neighborhood Components Analysis. The output distance learning
@@ -52,10 +55,10 @@
*
* @param output_matrix Covariance matrix of Mahalanobis distance.
*/
- void LearnDistance(arma::mat& output_matrix);
+ void LearnDistance(MatType& output_matrix);
private:
- const arma::mat& dataset_;
+ const MatType& dataset_;
const arma::uvec& labels_;
};
Modified: mlpack/trunk/src/mlpack/methods/nca/nca_impl.hpp
===================================================================
--- mlpack/trunk/src/mlpack/methods/nca/nca_impl.hpp 2011-12-13 11:30:22 UTC (rev 10748)
+++ mlpack/trunk/src/mlpack/methods/nca/nca_impl.hpp 2011-12-13 11:31:00 UTC (rev 10749)
@@ -18,19 +18,25 @@
namespace nca {
// Just set the internal matrix reference.
-template<typename Kernel>
-NCA<Kernel>::NCA(const arma::mat& dataset, const arma::uvec& labels) :
- dataset_(dataset), labels_(labels) { /* nothing to do */ }
+template<typename MetricType, typename MatType>
+NCA<MetricType, MatType>::NCA(const MatType& dataset,
+ const arma::uvec& labels) :
+ dataset_(dataset),
+ labels_(labels)
+{
+ /* nothing to do */
+}
-template<typename Kernel>
-void NCA<Kernel>::LearnDistance(arma::mat& output_matrix)
+template<typename MetricType, typename MatType>
+void NCA<MetricType, MatType>::LearnDistance(MatType& output_matrix)
{
- output_matrix = arma::eye<arma::mat>(dataset_.n_rows, dataset_.n_rows);
+ output_matrix = arma::eye<MatType>(dataset_.n_rows, dataset_.n_rows);
- SoftmaxErrorFunction<Kernel> error_func(dataset_, labels_);
+ SoftmaxErrorFunction<MetricType> error_func(dataset_, labels_);
// We will use the L-BFGS optimizer to optimize the stretching matrix.
- optimization::L_BFGS<SoftmaxErrorFunction<Kernel> > lbfgs(error_func, 10);
+ optimization::L_BFGS<SoftmaxErrorFunction<MetricType, MatType> >
+ lbfgs(error_func, 10);
lbfgs.Optimize(0, output_matrix);
}
Modified: mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function.hpp
===================================================================
--- mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function.hpp 2011-12-13 11:30:22 UTC (rev 10748)
+++ mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function.hpp 2011-12-13 11:31:00 UTC (rev 10749)
@@ -24,27 +24,30 @@
* where x_n represents a point and A is the current scaling matrix.
*
* This class is more flexible than the original paper, allowing an arbitrary
- * kernel function to be used, meaning that the Mahalanobis distance is not the
+ * metric function to be used, meaning that the Mahalanobis distance is not the
* only allowed way to run NCA. However, the Mahalanobis distance is probably
* the best way to use this.
+ *
+ * @tparam MetricType Type of metric to be used.
+ * @tparam MatType Type of matrix (arma::mat or arma::spmat).
*/
-template<typename Kernel>
+template<typename MetricType, typename MatType = arma::mat>
class SoftmaxErrorFunction
{
public:
/**
- * Initialize with the given kernel; useful when the kernel has some state to
- * store, which is set elsewhere. If no kernel is given, an empty kernel is
+ * Initialize with the given metric; useful when the metric has some state to
+ * store, which is set elsewhere. If no metric is given, an empty metric is
* used; this way, you can call the constructor with no arguments. A
* reference to the dataset we will be optimizing over is also required.
*
* @param dataset Matrix containing the dataset.
* @param labels Vector of class labels for each point in the dataset.
- * @param kernel Instantiated kernel (optional).
+ * @param metric Instantiated metric (optional).
*/
- SoftmaxErrorFunction(const arma::mat& dataset,
+ SoftmaxErrorFunction(const MatType& dataset,
const arma::uvec& labels,
- Kernel kernel = Kernel());
+ MetricType metric = MetricType());
/**
* Evaluate the softmax function for the given covariance matrix.
@@ -68,13 +71,13 @@
const arma::mat GetInitialPoint() const;
private:
- const arma::mat& dataset_;
+ const MatType& dataset_;
const arma::uvec& labels_;
- Kernel kernel_;
+ MetricType metric_;
arma::mat last_coordinates_;
- arma::mat stretched_dataset_;
+ MatType stretched_dataset_;
arma::vec p_; // Holds calculated p_i.
arma::vec denominators_; // Holds denominators for calculation of p_ij.
Modified: mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function_impl.hpp
===================================================================
--- mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function_impl.hpp 2011-12-13 11:30:22 UTC (rev 10748)
+++ mlpack/trunk/src/mlpack/methods/nca/nca_softmax_error_function_impl.hpp 2011-12-13 11:31:00 UTC (rev 10749)
@@ -13,18 +13,24 @@
namespace mlpack {
namespace nca {
-// Initialize with the given kernel.
-template<typename Kernel>
-SoftmaxErrorFunction<Kernel>::SoftmaxErrorFunction(const arma::mat& dataset,
- const arma::uvec& labels,
- Kernel kernel) :
- dataset_(dataset), labels_(labels), kernel_(kernel),
- last_coordinates_(dataset.n_rows, dataset.n_rows),
- precalculated_(false)
-{ /* nothing to do */ }
+// Initialize with the given metric.
+template<typename MetricType, typename MatType>
+SoftmaxErrorFunction<MetricType, MatType>::SoftmaxErrorFunction(
+ const MatType& dataset,
+ const arma::uvec& labels,
+ MetricType metric) :
+ dataset_(dataset),
+ labels_(labels),
+ metric_(metric),
+ last_coordinates_(dataset.n_rows, dataset.n_rows),
+ precalculated_(false)
+{
+ /* nothing to do */
+}
-template<typename Kernel>
-double SoftmaxErrorFunction<Kernel>::Evaluate(const arma::mat& coordinates)
+template<typename MetricType, typename MatType>
+double SoftmaxErrorFunction<MetricType, MatType>::Evaluate(
+ const arma::mat& coordinates)
{
// Calculate the denominators and numerators, if necessary.
Precalculate(coordinates);
@@ -33,9 +39,10 @@
// minimizes, not maximizes.
};
-template<typename Kernel>
-void SoftmaxErrorFunction<Kernel>::Gradient(const arma::mat& coordinates,
- arma::mat& gradient)
+template<typename MetricType, typename MatType>
+void SoftmaxErrorFunction<MetricType, MatType>::Gradient(
+ const arma::mat& coordinates,
+ arma::mat& gradient)
{
// Calculate the denominators and numerators, if necessary.
Precalculate(coordinates);
@@ -59,8 +66,8 @@
for (size_t k = (i + 1); k < stretched_dataset_.n_cols; k++)
{
// Calculate p_ik and p_ki first.
- double eval = exp(-kernel_.Evaluate(stretched_dataset_.unsafe_col(i),
- stretched_dataset_.unsafe_col(k)));
+ double eval = exp(-metric_.Evaluate(stretched_dataset_.col(i),
+ stretched_dataset_.col(k)));
double p_ik = 0, p_ki = 0;
p_ik = eval / denominators_(i);
p_ki = eval / denominators_(k);
@@ -80,14 +87,16 @@
gradient = -2 * coordinates * sum;
}
-template<typename Kernel>
-const arma::mat SoftmaxErrorFunction<Kernel>::GetInitialPoint() const
+template<typename MetricType, typename MatType>
+const arma::mat SoftmaxErrorFunction<MetricType, MatType>::GetInitialPoint()
+ const
{
return arma::eye<arma::mat>(dataset_.n_rows, dataset_.n_rows);
}
-template<typename Kernel>
-void SoftmaxErrorFunction<Kernel>::Precalculate(const arma::mat& coordinates)
+template<typename MetricType, typename MatType>
+void SoftmaxErrorFunction<MetricType, MatType>::Precalculate(
+ const arma::mat& coordinates)
{
// Make sure the calculation is necessary.
if ((accu(coordinates == last_coordinates_) == coordinates.n_elem) &&
@@ -111,8 +120,8 @@
for (size_t j = (i + 1); j < stretched_dataset_.n_cols; j++)
{
// Evaluate exp(-K(x_i, x_j)).
- double eval = exp(-kernel_.Evaluate(stretched_dataset_.unsafe_col(i),
- stretched_dataset_.unsafe_col(j)));
+ double eval = exp(-metric_.Evaluate(stretched_dataset_.col(i),
+ stretched_dataset_.col(j)));
// Add this to the denominators of both i and j: p_ij = p_ji.
denominators_[i] += eval;
More information about the mlpack-svn
mailing list