◆ shuffle() [3/4]

template<typename Permutation , typename T >
T boost::simd::shuffle ( T const &  x)

Shuffle the elements of a boost::simd::pack using an index permutation described by compile-time meta-function.

Semantic:

For any boost::simd::pack x of base type T and cardinal N and a meta-function Perm, the following code:

boost::simd::pack<T,N> r = shuffle<Perm>(x);

is equivalent to:

boost::simd::pack<T,N> r = shuffle<Perm::apply<0,N>::value,...,Perm::apply<N-1,N>::value>(x);

The permutation computed by the meta-function Perm is mapped at compile-time to the optimal sequence of intrinsics to apply the desired permutation.

Defining a permutation meta-function

Permutation meta-function can be built in two different ways:

  • Define a Permutation meta-function as a struct with an internal apply structure that proceed to compute a given permutation index at compile-time. This apply internal structure takes two integral constant types as parameter: C the cardinal of the boost::simd::pack to be shuffled and I the index of the permutation index computed.
  • Define a constexpr function taking two integers: c the cardinal of the boost::simd::pack to be shuffled and i the index of the permutation index computed. This function returns the computed value of the permutation index computed. Said function is then wrapped inside the boost::simd::pattern template type before being used with boost::simd::shuffle.

The special index value -1 can be returned to specify that, instead of fetching a data from inside the shuffled boost::simd::pack, the value 0 has to be inserted in the result.

Note
Using permutation expressed as a metafunction has the advantage to be cardinal agnostic, thus making a given shuffle calls independant of the actual pack cardinal, leading to a more generic code
Example:
#include <boost/simd/detail/nsm.hpp>
#include <boost/simd/pack.hpp>
#include <boost/simd/function/shuffle.hpp>
#include <iostream>
struct last_
{
template<typename I, typename C> struct apply : nsm::type_traits::integral_constant<int, C::value-1> {};
};
constexpr int reverse(int i, int c)
{
return c - 1 - i;
}
int main()
{
boost::simd::pack<float,4> x{1.f,2.f,3.f,4.f};
std::cout << "Original: " << x << std::endl
<< "Permuted: " << boost::simd::shuffle<boost::simd::pattern<reverse>>(x) << std::endl
<< "Permuted: " << boost::simd::shuffle<last_>(x) << std::endl;
return 0;
}
Possible output:
Original: (1, 2, 3, 4)
Permuted: (4, 3, 2, 1)
Permuted: (4, 4, 4, 4)
Template Parameters
PermutationPermutation meta-function generating the permutation index
Parameters
xboost::simd::pack to shuffle