ESPResSo
Extensible Simulation Package for Research on Soft Matter Systems
Loading...
Searching...
No Matches
mask.hpp
Go to the documentation of this file.
1/*
2 * Copyright (C) 2019-2022 The ESPResSo project
3 *
4 * This file is part of ESPResSo.
5 *
6 * ESPResSo is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * ESPResSo is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19#ifndef ESPRESSO_MASK_HPP
20#define ESPRESSO_MASK_HPP
21
22#include "utils/Array.hpp"
23#include "utils/get.hpp"
24#include "utils/type_traits.hpp"
25
26#include <cstddef>
27#include <type_traits>
28#include <utility>
29
30namespace Utils {
31namespace detail {
32template <class T, class Integral, std::size_t... I>
33auto mask_impl(Integral mask, T t, std::index_sequence<I...>) {
34 return T{((mask & (1u << I)) ? get<I>(t) : tuple_element_t<I, T>{})...};
35}
36} // namespace detail
37
38/**
39 * @brief Pick elements of a tuple-like by a bit mask.
40 *
41 * E.g. every element of the input for which the corresponding
42 * bit is set in the mask is set is copied to the output unmodified,
43 * the elements that are not set are set to zero (default constructed
44 * instance of the type).
45 *
46 * Example:
47 * mask(0b1011, {1, 2, 3, 4}) => {1, 0, 3, 4}
48 *
49 * @tparam T implements the tuple interface(get, tuple_size, ...)
50 * @tparam Integral An unsigned integral type
51 * @param mask bit mask, if the i-th bit is set, the i-th element
52 * in @p t is copied to the output, otherwise it is set to zero.
53 * @param t input elements
54 * @return t partially zeroed out according to mask
55 */
56template <class T, class Integral>
57auto mask(Integral mask,
58 T t) -> std::enable_if_t<std::is_unsigned_v<Integral> &&
61 T> {
62 return detail::mask_impl(mask, t,
63 std::make_index_sequence<tuple_size<T>::value>{});
64}
65} // namespace Utils
66
67#endif // ESPRESSO_MASK_HPP
Array implementation with CUDA support.
auto mask(Integral mask, T t) -> std::enable_if_t< std::is_unsigned_v< Integral > &&(size_in_bits< Integral >::value >=tuple_size< T >::value), T >
Pick elements of a tuple-like by a bit mask.
Definition mask.hpp:57
typename tuple_element< I, Tuple >::type tuple_element_t
Definition get.hpp:37
Size of a type in bits.