00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #ifndef MTL_MATRIX_REORDER_INCLUDE
00013 #define MTL_MATRIX_REORDER_INCLUDE
00014
00015 #include <algorithm>
00016
00017 #include <boost/numeric/mtl/mtl_fwd.hpp>
00018 #include <boost/numeric/mtl/matrix/compressed2D.hpp>
00019 #include <boost/numeric/mtl/operation/size.hpp>
00020 #include <boost/numeric/mtl/utility/exception.hpp>
00021 #include <boost/numeric/linear_algebra/identity.hpp>
00022
00023 namespace mtl { namespace matrix {
00024
00025
00026 namespace traits {
00027
00029 template <typename Value= double>
00030 struct reorder
00031 {
00032 typedef ::mtl::compressed2D<Value> type;
00033 };
00034 }
00035
00036
00037 template <typename Value, typename ReorderVector>
00038 typename traits::reorder<Value>::type
00039 reorder(const ReorderVector& v, std::size_t cols= 0)
00040 {
00041 using math::one; using mtl::size;
00042 typedef typename traits::reorder<Value>::type matrix_type;
00043
00044
00045 std::size_t s= static_cast<std::size_t>(size(v)),
00046 my_max= *std::max_element(&v[0], &v[0] + s) + 1;
00047
00048 if (cols == 0)
00049 cols= my_max;
00050 else
00051 MTL_THROW_IF(my_max > cols, range_error("Too large value in reorder vector"));
00052
00053 matrix_type matrix(s, cols);
00054 inserter<matrix_type> ins(matrix, 1);
00055
00056 for (std::size_t i= 0; i < s; i++)
00057 ins[i][v[i]] << one(Value());
00058
00059 return matrix;
00060 }
00061
00062
00064 template <typename ReorderVector>
00065 typename traits::reorder<>::type
00066 inline reorder(const ReorderVector& v, std::size_t cols= 0)
00067 {
00068 return reorder<double>(v, cols);
00069 }
00070
00071
00072 }}
00073
00074 namespace mtl { namespace vector {
00075
00077 using mtl::matrix::reorder;
00078
00079 }}
00080
00081 #endif // MTL_MATRIX_REORDER_INCLUDE