OpenKalman
make_hermitian_matrix.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 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_MAKE_HERMITIAN_MATRIX_HPP
17 #define OPENKALMAN_MAKE_HERMITIAN_MATRIX_HPP
18 
19 namespace OpenKalman
20 {
27 #ifdef __cpp_concepts
28  template<HermitianAdapterType adapter_type = HermitianAdapterType::lower, square_shaped<Applicability::permitted> Arg>
29  requires (adapter_type == HermitianAdapterType::lower) or (adapter_type == HermitianAdapterType::upper)
30  constexpr hermitian_matrix decltype(auto)
31 #else
32  template<HermitianAdapterType adapter_type = HermitianAdapterType::lower, typename Arg, std::enable_if_t<
33  square_shaped<Arg, Applicability::permitted> and
34  (adapter_type == HermitianAdapterType::lower or adapter_type == HermitianAdapterType::upper), int> = 0>
35  constexpr decltype(auto)
36 #endif
38  {
40 
41  if constexpr (hermitian_matrix<Arg, Applicability::permitted>)
42  {
43  if constexpr (hermitian_matrix<Arg>)
44  return std::forward<Arg>(arg);
45  else if constexpr (hermitian_adapter<Arg, adapter_type>)
46  return make_hermitian_matrix<adapter_type>(nested_object(std::forward<Arg>(arg)));
47  else if constexpr (hermitian_adapter<Arg>)
48  return make_hermitian_matrix<transp>(nested_object(std::forward<Arg>(arg)));
49  else
50  return HermitianAdapter<Arg, adapter_type> {std::forward<Arg>(arg)};
51  }
52  else if constexpr (triangular_adapter<Arg>)
53  {
54  if constexpr (triangular_matrix<Arg, static_cast<TriangleType>(adapter_type)>)
55  return make_hermitian_matrix<adapter_type>(nested_object(std::forward<Arg>(arg)));
56  else
57  return make_hermitian_matrix<transp>(nested_object(std::forward<Arg>(arg)));
58  }
59  else if constexpr (interface::make_hermitian_adapter_defined_for<Arg, adapter_type, Arg>)
60  {
62  auto new_h {Traits::template make_hermitian_adapter<adapter_type>(std::forward<Arg>(arg))};
63  static_assert(hermitian_matrix<decltype(new_h), Applicability::permitted>, "make_hermitian_matrix interface must return a hermitian matrix");
64  if constexpr (hermitian_matrix<decltype(new_h)>) return new_h;
65  else return make_hermitian_matrix<adapter_type>(std::move(new_h));
66  }
67  else
68  {
69  // Default behavior if interface function not defined:
70  return HermitianAdapter<Arg, adapter_type> {std::forward<Arg>(arg)};
71  }
72  }
73 
74 
75 } // namespace OpenKalman
76 
77 #endif //OPENKALMAN_MAKE_HERMITIAN_MATRIX_HPP
A hermitian matrix wrapper.
Definition: HermitianAdapter.hpp:31
decltype(auto) constexpr make_hermitian_matrix(Arg &&arg)
Creates a hermitian_matrix by, if necessary, wrapping the argument in a hermitian_adapter.
Definition: make_hermitian_matrix.hpp:37
HermitianAdapterType
The type of a hermitian adapter, indicating which triangle of the nested matrix is used...
Definition: global-definitions.hpp:78
An upper-right triangular matrix.
constexpr bool triangular_matrix
Specifies that a type is a triangular matrix (upper, lower, or diagonal).
Definition: triangular_matrix.hpp:37
The root namespace for OpenKalman.
Definition: basics.hpp:34
An interface to various routines from the linear algebra library associated with indexible object T...
Definition: library_interface.hpp:37
The concept, trait, or restraint is permitted, but whether it applies is not necessarily known at com...
decltype(auto) constexpr nested_object(Arg &&arg)
Retrieve a nested object of Arg, if it exists.
Definition: nested_object.hpp:34
A lower-left triangular matrix.
constexpr bool hermitian_matrix
Specifies that a type is a hermitian matrix (assuming it is square_shaped).
Definition: hermitian_matrix.hpp:50