OpenKalman
make_fixed_size_adapter_like.hpp
Go to the documentation of this file.
1 /* This file is part of OpenKalman, a header-only C++ library for
2  * Kalman filters and other recursive filters.
3  *
4  * Copyright (c) 2022-2023 Christopher Lee Ogden <ogden@gatech.edu>
5  *
6  * This Source Code Form is subject to the terms of the Mozilla Public
7  * License, v. 2.0. If a copy of the MPL was not distributed with this
8  * file, You can obtain one at https://mozilla.org/MPL/2.0/.
9  */
10 
17 #ifndef OPENKALMAN_MAKE_FIXED_SIZE_ADAPTER_LIKE_HPP
18 #define OPENKALMAN_MAKE_FIXED_SIZE_ADAPTER_LIKE_HPP
19 
20 namespace OpenKalman::internal
21 {
22  namespace detail
23  {
24  template<std::size_t I, typename...Ts>
25  constexpr decltype(auto) best_desc_Ts_impl(const Ts&...ts)
26  {
27  return most_fixed_pattern(get_pattern_collection<I>(ts)...);
28  }
29 
30 
31  template<typename...Ts, typename Arg, std::size_t...Ix>
32  constexpr decltype(auto) make_fixed_size_adapter_like_impl(Arg&& arg, std::index_sequence<Ix...>)
33  {
34  if constexpr (sizeof...(Ts) == 0) return std::forward<Arg>(arg);
35  else
36  {
37  using F = decltype(make_fixed_size_adapter<decltype(best_desc_Ts_impl<Ix>(std::declval<Ts>()...))...>(std::declval<Arg&&>()));
38  constexpr bool better = (... or (dynamic_dimension<Arg, Ix> and not dynamic_dimension<F, Ix>));
39  if constexpr (better) return F {std::forward<Arg>(arg)};
40  else return std::forward<Arg>(arg);
41  }
42  }
43  }
44 
45 
51 #ifdef __cpp_concepts
52  template<indexible...Ts, vector_space_descriptors_may_match_with<Ts...> Arg> requires (index_count_v<Arg> != stdex::dynamic_extent)
53 #else
54  template<typename...Ts, typename Arg, std::enable_if_t<(... and indexible<Ts>) and
55  vector_space_descriptors_may_match_with<Arg, Ts...> and (index_count_v<Arg> != stdex::dynamic_extent), int> = 0>
56 #endif
57  constexpr decltype(auto)
58  make_fixed_size_adapter_like(Arg&& arg)
59  {
60  constexpr auto min_count = std::min({index_count_v<Arg>,
61  (index_count_v<Ts> == stdex::dynamic_extent ? index_count_v<Arg> : index_count_v<Ts>)...});
62  return detail::make_fixed_size_adapter_like_impl<Ts...>(std::forward<Arg>(arg), std::make_index_sequence<min_count>{});
63  }
64 
65 
66 }
67 
68 #endif
constexpr bool indexible
T is a multidimensional array type.
Definition: indexible.hpp:32
decltype(auto) constexpr most_fixed_pattern(P &&p)
Given a fixed-size /ref coordinates::pattern_collection, return the first component, if any, that is a fixed_pattern.
Definition: most_fixed_pattern.hpp:63
Definition: basics.hpp:48