Created
May 6, 2014 11:43
-
-
Save lambday/68041d7b4e1aff39a4af to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <iostream> | |
#include <shogun/lib/SGVector.h> | |
#include <Eigen/Eigen> | |
#include <shogun/lib/Time.h> | |
#include <shogun/base/init.h> | |
#include <shogun/io/SGIO.h> | |
using namespace std; | |
using namespace shogun; | |
using namespace Eigen; | |
namespace linalg | |
{ | |
enum class Backend { Naive, Eigen3 }; | |
template <class T> | |
struct linalg_traits | |
{ | |
const static Backend backend = T::backend; | |
}; | |
#ifndef BACKEND_TYPE | |
#define BACKEND_TYPE(TASK, BACKEND) \ | |
struct TASK \ | |
{ \ | |
const static Backend backend = Backend::BACKEND; \ | |
}; | |
#endif // BACKEND_TYPE | |
#ifdef USE_EIGEN3_DOT | |
BACKEND_TYPE(Dot, Eigen3) | |
#else // the default case | |
BACKEND_TYPE(Dot, Naive) | |
#endif | |
#ifdef USE_EIGEN3_SUM | |
BACKEND_TYPE(Sum, Eigen3) | |
#else // the default case | |
BACKEND_TYPE(Sum, Naive) | |
#endif | |
#undef BACKEND_TYPE | |
} | |
namespace impl | |
{ | |
using namespace linalg; | |
template <class Scalar, class Vector, enum Backend> | |
struct dot | |
{ | |
static Scalar compute(Vector a, Vector b) | |
{ | |
// cout << "Generic dot()" << endl; | |
return 0; | |
} | |
}; | |
#if defined HAVE_EIGEN3 & USE_EIGEN3_DOT | |
template <class Scalar> | |
struct dot<Scalar, SGVector<Scalar>, Backend::Eigen3> | |
{ | |
static Scalar compute(SGVector<Scalar> a, SGVector<Scalar> b) | |
{ | |
// cout << "Eigen3 dot()" << endl; | |
typedef Matrix<Scalar, Dynamic, 1> VectorXt; | |
Map<VectorXt> vec_a(a.vector, a.vlen); | |
Map<VectorXt> vec_b(b.vector, b.vlen); | |
return vec_a.dot(vec_b); | |
} | |
}; | |
#endif | |
} | |
namespace linalg | |
{ | |
template <class Scalar, class Vector> | |
Scalar dot(Vector a, Vector b) | |
{ | |
return impl::dot<Scalar, Vector, linalg_traits<Dot>::backend>::compute(a, b); | |
} | |
} | |
int main() | |
{ | |
init_shogun_with_defaults(); | |
auto size = 1000000; | |
SGVector<float> a(size), b(size); | |
auto iter = 1000; | |
CTime* time = new CTime(); | |
double mean = 0, var = 0; | |
for (auto i = 1; i <= iter; ++i) | |
{ | |
SGVector<float>::random_vector(a.vector, a.vlen, 0, 1); | |
SGVector<float>::random_vector(b.vector, b.vlen, 0, 1); | |
time->start(); | |
linalg::dot<float, SGVector<float> >(a, b); | |
auto elapsed = time->cur_time_diff(); | |
auto delta = elapsed - mean; | |
mean += delta/i; | |
var += delta * (elapsed - mean); | |
} | |
var /= iter; | |
SG_SPRINT("mean %.15f, var %.15lf\n", mean, var); | |
SG_UNREF(time); | |
exit_shogun(); | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment