28 #ifndef VC_COMMON_WHERE_H_ 29 #define VC_COMMON_WHERE_H_ 34 namespace Vc_VERSIONED_NAMESPACE
44 template<
typename _Mask,
typename _LValue>
struct MaskedLValue
47 typedef _LValue LValue;
53 constexpr MaskedLValue(
const Mask &m, LValue &l) : mask(m), lhs(l) {}
54 MaskedLValue(
const MaskedLValue &) =
delete;
55 constexpr MaskedLValue(MaskedLValue &&) =
default;
61 template<
typename T> Vc_ALWAYS_INLINE
void operator =(T &&rhs) { conditional_assign<Operator:: Assign>(lhs, mask, std::forward<T>(rhs)); }
62 template<
typename T> Vc_ALWAYS_INLINE
void operator +=(T &&rhs) { conditional_assign<Operator:: PlusAssign>(lhs, mask, std::forward<T>(rhs)); }
63 template<
typename T> Vc_ALWAYS_INLINE
void operator -=(T &&rhs) { conditional_assign<Operator:: MinusAssign>(lhs, mask, std::forward<T>(rhs)); }
64 template<
typename T> Vc_ALWAYS_INLINE
void operator *=(T &&rhs) { conditional_assign<Operator:: MultiplyAssign>(lhs, mask, std::forward<T>(rhs)); }
65 template<
typename T> Vc_ALWAYS_INLINE
void operator /=(T &&rhs) { conditional_assign<Operator:: DivideAssign>(lhs, mask, std::forward<T>(rhs)); }
66 template<
typename T> Vc_ALWAYS_INLINE
void operator %=(T &&rhs) { conditional_assign<Operator:: RemainderAssign>(lhs, mask, std::forward<T>(rhs)); }
67 template<
typename T> Vc_ALWAYS_INLINE
void operator ^=(T &&rhs) { conditional_assign<Operator:: XorAssign>(lhs, mask, std::forward<T>(rhs)); }
68 template<
typename T> Vc_ALWAYS_INLINE
void operator &=(T &&rhs) { conditional_assign<Operator:: AndAssign>(lhs, mask, std::forward<T>(rhs)); }
69 template<
typename T> Vc_ALWAYS_INLINE
void operator |=(T &&rhs) { conditional_assign<Operator:: OrAssign>(lhs, mask, std::forward<T>(rhs)); }
70 template<
typename T> Vc_ALWAYS_INLINE
void operator<<=(T &&rhs) { conditional_assign<Operator:: LeftShiftAssign>(lhs, mask, std::forward<T>(rhs)); }
71 template<
typename T> Vc_ALWAYS_INLINE
void operator>>=(T &&rhs) { conditional_assign<Operator::RightShiftAssign>(lhs, mask, std::forward<T>(rhs)); }
72 Vc_ALWAYS_INLINE
void operator++() { conditional_assign<Operator:: PreIncrement>(lhs, mask); }
73 Vc_ALWAYS_INLINE
void operator++(
int) { conditional_assign<Operator::PostIncrement>(lhs, mask); }
74 Vc_ALWAYS_INLINE
void operator--() { conditional_assign<Operator:: PreDecrement>(lhs, mask); }
75 Vc_ALWAYS_INLINE
void operator--(
int) { conditional_assign<Operator::PostDecrement>(lhs, mask); }
78 template <
typename _Mask,
typename T_,
typename I_,
typename S_>
79 struct MaskedLValue<_Mask, Common::SubscriptOperation<T_, I_, S_, true>>
82 typedef Common::SubscriptOperation<T_, I_, S_, true> SO;
87 template <
typename T>
using Decay =
typename std::decay<T>::type;
90 constexpr MaskedLValue(
const Mask &m, SO &&l) : mask(m), lhs(l) {}
91 MaskedLValue(
const MaskedLValue &) =
delete;
92 constexpr MaskedLValue(MaskedLValue &&) =
default;
98 template<
typename T> Vc_ALWAYS_INLINE
void operator =(T &&rhs) { std::forward<T>(rhs).scatter(lhs.scatterArguments(), mask); }
123 template<
typename _LValue>
struct MaskedLValue<bool, _LValue>
126 typedef _LValue LValue;
132 constexpr MaskedLValue(
const Mask &m, LValue &l) : mask(m), lhs(l) {}
133 MaskedLValue(
const MaskedLValue &) =
delete;
134 constexpr MaskedLValue(MaskedLValue &&) =
default;
136 template<
typename T> Vc_ALWAYS_INLINE
void operator =(T &&rhs) {
if (mask) lhs = std::forward<T>(rhs); }
137 template<
typename T> Vc_ALWAYS_INLINE
void operator +=(T &&rhs) {
if (mask) lhs += std::forward<T>(rhs); }
138 template<
typename T> Vc_ALWAYS_INLINE
void operator -=(T &&rhs) {
if (mask) lhs -= std::forward<T>(rhs); }
139 template<
typename T> Vc_ALWAYS_INLINE
void operator *=(T &&rhs) {
if (mask) lhs *= std::forward<T>(rhs); }
140 template<
typename T> Vc_ALWAYS_INLINE
void operator /=(T &&rhs) {
if (mask) lhs /= std::forward<T>(rhs); }
141 template<
typename T> Vc_ALWAYS_INLINE
void operator %=(T &&rhs) {
if (mask) lhs %= std::forward<T>(rhs); }
142 template<
typename T> Vc_ALWAYS_INLINE
void operator ^=(T &&rhs) {
if (mask) lhs ^= std::forward<T>(rhs); }
143 template<
typename T> Vc_ALWAYS_INLINE
void operator &=(T &&rhs) {
if (mask) lhs &= std::forward<T>(rhs); }
144 template<
typename T> Vc_ALWAYS_INLINE
void operator |=(T &&rhs) {
if (mask) lhs |= std::forward<T>(rhs); }
145 template<
typename T> Vc_ALWAYS_INLINE
void operator<<=(T &&rhs) {
if (mask) lhs <<= std::forward<T>(rhs); }
146 template<
typename T> Vc_ALWAYS_INLINE
void operator>>=(T &&rhs) {
if (mask) lhs >>= std::forward<T>(rhs); }
147 Vc_ALWAYS_INLINE
void operator++() {
if (mask) ++lhs; }
148 Vc_ALWAYS_INLINE
void operator++(
int) {
if (mask) lhs++; }
149 Vc_ALWAYS_INLINE
void operator--() {
if (mask) --lhs; }
150 Vc_ALWAYS_INLINE
void operator--(
int) {
if (mask) lhs--; }
153 template<
typename _Mask>
struct WhereMask
159 constexpr WhereMask(
const Mask &m) : mask(m) {}
160 WhereMask(
const WhereMask &) =
delete;
162 template <
typename T,
typename I,
typename S>
163 constexpr Vc_WARN_UNUSED_RESULT
164 MaskedLValue<Mask, Common::SubscriptOperation<T, I, S, true>>
165 operator|(Common::SubscriptOperation<T, I, S, true> &&lhs)
const 167 static_assert(!std::is_const<T>::value,
168 "masked scatter to constant memory not possible.");
169 return {mask, std::move(lhs)};
172 template<
typename T> constexpr Vc_WARN_UNUSED_RESULT MaskedLValue<Mask, T>
operator|(T &&lhs)
const 174 static_assert(std::is_lvalue_reference<T>::value,
"Syntax error: Incorrect use of Vc::where. Maybe operator precedence got you by surprise. Examples of correct usage:\n" 175 " Vc::where(x < 2) | x += 1;\n" 176 " (Vc::where(x < 2) | x)++;\n" 177 " Vc::where(x < 2)(x) += 1;\n" 178 " Vc::where(x < 2)(x)++;\n" 180 return { mask, lhs };
183 template<
typename T> constexpr Vc_WARN_UNUSED_RESULT MaskedLValue<Mask, T> operator()(T &&lhs)
const 229 template<
typename M> constexpr Vc_WARN_UNUSED_RESULT WhereImpl::WhereMask<M>
where(
const M &mask)
234 template<
typename M> constexpr Vc_WARN_UNUSED_RESULT WhereImpl::WhereMask<M> _if(
const M &m)
241 #endif // VC_COMMON_WHERE_H_ result_vector_type< L, R > operator|(L &&lhs, R &&rhs)
Applies | component-wise and concurrently.
constexpr WhereImpl::WhereMask< M > where(const M &mask)
Conditional assignment.