Implement operators with scalar types.

This commit is contained in:
King_DuckZ 2017-01-27 18:43:21 +00:00
parent 780e6647b2
commit bbaabb695d
3 changed files with 182 additions and 0 deletions

View File

@ -436,6 +436,27 @@ namespace vwr {
Vec<typename std::common_type<V1, V2>::type> operator/ ( const Vec<V1>& parLeft, const Vec<V2>& parRight );
template <typename V1, typename V2>
Vec<typename std::common_type<V1, V2>::type> operator% ( const Vec<V1>& parLeft, const Vec<V2>& parRight );
template <typename V>
Vec<V> operator+ ( const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight );
template <typename V>
Vec<V> operator- ( const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight );
template <typename V>
Vec<V> operator* ( const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight );
template <typename V>
Vec<V> operator/ ( const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight );
template <typename V>
Vec<V> operator% ( const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight );
template <typename V>
Vec<V> operator+ ( const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight );
template <typename V>
Vec<V> operator- ( const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight );
template <typename V>
Vec<V> operator* ( const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight );
template <typename V>
Vec<V> operator/ ( const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight );
template <typename V>
Vec<V> operator% ( const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight );
} //namespace vwr
#include "vectorwrapper/vectorwrapper.inl"

View File

@ -299,6 +299,20 @@ namespace vwr {
return return_type(parOp(parLeft[I], parRight[I])...);
}
template <typename V, typename Op, size_type... I>
inline
Vec<V> binary_op_scalar_right (const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight, Op parOp, bt::number_seq<size_type, I...>) {
typedef Vec<V> return_type;
return return_type(parOp(parLeft[I], parRight)...);
}
template <typename V, typename Op, size_type... I>
inline
Vec<V> binary_op_scalar_left (const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight, Op parOp, bt::number_seq<size_type, I...>) {
typedef Vec<V> return_type;
return return_type(parOp(parLeft, parRight[I])...);
}
template <typename V, size_type... I>
inline
Vec<V> unary_operator_minus (const Vec<V>& parVec, bt::number_seq<size_type, I...>) {
@ -479,4 +493,96 @@ namespace vwr {
bt::number_range<size_type, 0, VectorWrapperInfo<V1>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator+ (const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight) {
return implem::binary_op_scalar_right(
parLeft,
parRight,
std::plus<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator- (const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight) {
return implem::binary_op_scalar_right(
parLeft,
parRight,
std::minus<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator* (const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight) {
return implem::binary_op_scalar_right(
parLeft,
parRight,
std::multiplies<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator/ (const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight) {
return implem::binary_op_scalar_right(
parLeft,
parRight,
std::divides<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator% (const Vec<V>& parLeft, const typename Vec<V>::scalar_type& parRight) {
return implem::binary_op_scalar_right(
parLeft,
parRight,
std::modulus<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator+ (const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight) {
return implem::binary_op_scalar_left(
parLeft,
parRight,
std::plus<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator- (const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight) {
return implem::binary_op_scalar_left(
parLeft,
parRight,
std::minus<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator* (const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight) {
return implem::binary_op_scalar_left(
parLeft,
parRight,
std::multiplies<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator/ (const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight) {
return implem::binary_op_scalar_left(
parLeft,
parRight,
std::divides<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
template <typename V>
inline Vec<V> operator% (const typename Vec<V>::scalar_type& parLeft, const Vec<V>& parRight) {
return implem::binary_op_scalar_left(
parLeft,
parRight,
std::modulus<typename Vec<V>::scalar_type>(),
bt::number_range<size_type, 0, VectorWrapperInfo<V>::dimensions>()
);
}
} //namespace vwr

View File

@ -82,3 +82,58 @@ TEST(vwr, bin_operators) {
EXPECT_EQ(res, a % b);
}
}
TEST(vwr, bin_operators_scalar) {
using namespace vwr;
{
ivec3 a(50, 100, 150);
ivec3 res(50 + 10, 100 + 10, 150 + 10);
EXPECT_EQ(res, a + 10);
}
{
ivec3 a(50, 100, 150);
ivec3 res(50 - 25, 100 - 25, 150 - 25);
EXPECT_EQ(res, a - 25);
}
{
ivec3 a(50, 100, 150);
ivec3 res(50 * 10, 100 * 10, 150 * 10);
EXPECT_EQ(res, a * 10);
}
{
ivec3 a(50, 100, 150);
ivec3 res(50 / 2, 100 / 2, 150 / 2);
EXPECT_EQ(res, a / 2);
}
{
ivec3 a(50, 100, 150);
ivec3 res(50 % 7, 100 % 7, 150 % 7);
EXPECT_EQ(res, a % 7);
}
{
ivec3 a(50, 100, 150);
ivec3 res(25 + 50, 25 + 100, 25 + 150);
EXPECT_EQ(res, 25 + a);
}
{
ivec3 a(50, 100, 150);
ivec3 res(25 - 50, 25 - 100, 25 - 150);
EXPECT_EQ(res, 25 - a);
}
{
ivec3 a(50, 100, 150);
ivec3 res(4 * 50, 4 * 100, 4 * 150);
EXPECT_EQ(res, 4 * a);
}
{
ivec3 a(50, 100, 150);
ivec3 res(1000 / 50, 1000 / 100, 1000 / 150);
EXPECT_EQ(res, 1000 / a);
}
{
ivec3 a(50, 100, 150);
ivec3 res(1000 % 50, 1000 % 100, 1000 % 150);
EXPECT_EQ(res, 1000 % a);
}
}