Loading...
Searching...
No Matches
utility/tuple/concept.hpp
Go to the documentation of this file.
// SPDX-FileCopyrightText: 2006-2025 Knut Reinert & Freie Universität Berlin
// SPDX-FileCopyrightText: 2016-2025 Knut Reinert & MPI für molekulare Genetik
// SPDX-License-Identifier: BSD-3-Clause
#pragma once
#include <concepts>
#include <tuple>
#include <type_traits>
#include <seqan3/core/detail/template_inspection.hpp>
#include <seqan3/utility/tuple/pod_tuple.hpp>
#include <seqan3/utility/type_list/type_list.hpp>
#include <seqan3/utility/type_traits/basic.hpp>
namespace seqan3::detail
{
template <typename tuple_t>
concept tuple_size = requires (tuple_t v) {
{ std::tuple_size<tuple_t>::value } -> std::convertible_to<size_t>;
};
template <typename tuple_t>
concept tuple_get = requires (tuple_t & v, tuple_t const & v_c) {
requires std::tuple_size_v<tuple_t> > 0;
typename std::tuple_element<0, tuple_t>::type;
{ get<0>(v) } -> std::convertible_to<typename std::tuple_element<0, tuple_t>::type>;
// requires weakly_assignable_from<decltype(get<0>(v)), typename std::tuple_element<0, tuple_t>::type>;
//TODO check that the previous returns something that can be assigned to
// unfortunately std::assignable_from requires lvalue-reference, but we want to accept xvalues too (returned
// proxies)
{ get<0>(v_c) } -> std::convertible_to<typename std::tuple_element<0, tuple_t>::type>;
{ get<0>(std::move(v)) } -> std::convertible_to<typename std::tuple_element<0, tuple_t>::type>;
{ get<0>(std::move(v_c)) } -> std::convertible_to<typename std::tuple_element<0, tuple_t>::type const &&>;
};
template <detail::tuple_size tuple_t>
struct tuple_type_list
{
protected:
template <size_t... Is>
static constexpr auto invoke_to_type_list(std::index_sequence<Is...>)
{
return type_list<std::tuple_element_t<Is, tuple_t>...>{};
}
public:
using type = decltype(invoke_to_type_list(std::make_index_sequence<std::tuple_size<tuple_t>::value>{}));
};
template <detail::tuple_size tuple_t>
using tuple_type_list_t = typename tuple_type_list<tuple_t>::type;
template <typename... elements_t>
inline constexpr auto all_elements_model_totally_ordered(seqan3::type_list<elements_t...>)
-> std::bool_constant<(std::totally_ordered<elements_t> && ... && true)>;
template <typename tuple_t>
requires requires () {
{ detail::all_elements_model_totally_ordered(tuple_type_list_t<tuple_t>{}) };
}
static constexpr bool all_elements_model_totally_ordered_v =
decltype(detail::all_elements_model_totally_ordered(tuple_type_list_t<tuple_t>{}))::value;
} // namespace seqan3::detail
namespace seqan3
{
// ----------------------------------------------------------------------------
// tuple_like
// ----------------------------------------------------------------------------
template <typename t>
concept tuple_like = detail::tuple_size<std::remove_reference_t<t>> && requires (t v) {
typename detail::tuple_type_list<std::remove_cvref_t<t>>::type;
// NOTE(rrahn): To check the full tuple_concept including the get interface and the std::totally_ordered
// we need to make some assumptions. In general these checks can only be executed if the tuple is not
// empty. Furthermore, the std::totally_ordered can only be checked if all elements in the
// tuple are strict_totally_ordered. This is done, by the fold expression in the second part.
requires (std::tuple_size<std::remove_reference_t<t>>::value == 0)
|| (detail::tuple_get<std::remove_cvref_t<t>>
&& (!detail::all_elements_model_totally_ordered_v<std::remove_cvref_t<t>>
|| std::totally_ordered<std::remove_cvref_t<t>>));
};
template <typename t>
concept pair_like = tuple_like<t> && std::tuple_size_v<std::remove_reference_t<t>> == 2;
} // namespace seqan3
basic.hpp
Provides various type traits on generic types.
pair_like
Whether a type behaves like a tuple with exactly two elements.
tuple_like
Whether a type behaves like a tuple.
seqan3
The main SeqAn3 namespace.
Definition aligned_sequence_concept.hpp:26
seqan3::get
constexpr auto const & get(configuration< configs_t... > const &config) noexcept
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition configuration.hpp:412
pod_tuple.hpp
Provides seqan3::pod_tuple.
template_inspection.hpp
Provides type traits for working with templates.
tuple
std::tuple_size_v
T tuple_size_v
type_list.hpp
Provides seqan3::type_list.
type_traits
Hide me