OpenKalman
get_component.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 
16 #ifndef OPENKALMAN_GET_COMPONENT_HPP
17 #define OPENKALMAN_GET_COMPONENT_HPP
18 
23 
24 namespace OpenKalman
25 {
26  // \todo Add functions that return stl-compatible iterators.
27 
28  namespace detail
29  {
30  template<typename Arg, typename Indices>
31  constexpr decltype(auto)
32  get_component_impl(Arg&& arg, const Indices& indices)
33  {
34  using Trait = interface::library_interface<std::decay_t<Arg>>;
35  return Trait::get_component(std::forward<Arg>(arg), internal::truncate_indices(indices, count_indices(arg)));
36  }
37  } // namespace detail
38 
39 
46 #ifdef __cpp_lib_concepts
47  template<indexible Arg, index_range_for<Arg> Indices> requires (not empty_object<Arg>)
48  constexpr values::scalar decltype(auto)
49 #else
50  template<typename Arg, typename Indices, std::enable_if_t<
51  index_range_for<Indices, Arg> and (not empty_object<Arg>), int> = 0>
52  constexpr decltype(auto)
53 #endif
54  get_component(Arg&& arg, const Indices& indices)
55  {
56  return detail::get_component_impl(std::forward<Arg>(arg), indices);
57  }
58 
59 
64 #ifdef __cpp_lib_concepts
65  template<indexible Arg, values::index Ix> requires (not empty_object<Arg>)
66  constexpr values::scalar decltype(auto)
67 #else
68  template<typename Arg, typename Ix, std::enable_if_t<values::index<Ix> and (not empty_object<Arg>), int> = 0>
69  constexpr decltype(auto)
70 #endif
71  get_component(Arg&& arg, const std::initializer_list<Ix>& indices)
72  {
73  return detail::get_component_impl(std::forward<Arg>(arg), indices);
74  }
75 
76 
77  namespace internal
78  {
79  namespace detail
80  {
81  template<typename Arg, typename...V, std::size_t...Ix>
82  constexpr bool static_indices_within_bounds_impl(std::index_sequence<Ix...>)
83  {
84  return ([]{
85  if constexpr (values::fixed<V>)
86  return (std::decay_t<V>::value >= 0 and std::decay_t<V>::value < index_dimension_of_v<Arg, Ix>);
87  else
88  return true;
89  }() and ...);
90  }
91  } // namespace detail
92 
93 
94  template<typename Arg, typename...I>
96  : std::bool_constant<(detail::static_indices_within_bounds_impl<Arg, I...>(std::index_sequence_for<I...>{}))> {};
97 
98  } // namespace internal
99 
100 
107 #ifdef __cpp_lib_concepts
108  template<indexible Arg, values::index...I> requires
109  (index_count_v<Arg> == dynamic_size or sizeof...(I) >= index_count_v<Arg>) and
110  (not empty_object<Arg>) and internal::static_indices_within_bounds<Arg, I...>::value
111  constexpr values::scalar decltype(auto)
112 #else
113  template<typename Arg, typename...I, std::enable_if_t<indexible<Arg> and (... and values::index<I>) and
115  (not empty_object<Arg>) and internal::static_indices_within_bounds<Arg, I...>::value, int> = 0>
116  constexpr decltype(auto)
117 #endif
118  get_component(Arg&& arg, I&&...i)
119  {
120  if constexpr (sizeof...(I) == 0)
121  return detail::get_component_impl(std::forward<Arg>(arg), std::array<std::size_t, 0> {});
122  else
123  return detail::get_component_impl(std::forward<Arg>(arg),
124  std::array {static_cast<std::common_type_t<I...>>(std::forward<I>(i))...});
125  }
126 
127 
128 } // namespace OpenKalman
129 
130 #endif //OPENKALMAN_GET_COMPONENT_HPP
constexpr auto count_indices(const T &t)
Get the number of indices available to address the components of an indexible object.
Definition: count_indices.hpp:33
Definition for values::index.
constexpr bool indexible
T is a generalized tensor type.
Definition: indexible.hpp:32
constexpr bool value
T is numerical value or is reducible to a numerical value.
Definition: value.hpp:31
The root namespace for OpenKalman.
Definition: basics.hpp:34
Forward declaration of library_interface, which must be defined for all objects used in OpenKalman...
Definition for index_range_for.
Definition for empty_object.
constexpr bool index
T is an index value.
Definition: index.hpp:56
decltype(auto) constexpr get_component(Arg &&arg, const Indices &indices)
Get a component of an object at a particular set of indices.
Definition: get_component.hpp:54
decltype(auto) constexpr get_component(Arg &&arg, I &&...i)
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: get_component.hpp:118
The minimum number of indices need to access all the components of an object.
Definition: index_count.hpp:33
constexpr std::size_t dynamic_size
A constant indicating that a size or index is dynamic.
Definition: global-definitions.hpp:33