SeqAn3  3.0.3
The Modern C++ library for sequence analysis.
alphabet_tuple_base.hpp
Go to the documentation of this file.
1 // -----------------------------------------------------------------------------------------------------
2 // Copyright (c) 2006-2020, Knut Reinert & Freie Universität Berlin
3 // Copyright (c) 2016-2020, Knut Reinert & MPI für molekulare Genetik
4 // This file may be used, modified and/or redistributed under the terms of the 3-clause BSD-License
5 // shipped with this file and also available at: https://github.com/seqan/seqan3/blob/master/LICENSE.md
6 // -----------------------------------------------------------------------------------------------------
7 
13 #pragma once
14 
15 #include <cassert>
16 #include <seqan3/std/concepts>
17 #include <utility>
18 
19 #include <meta/meta.hpp>
20 
31 
32 namespace seqan3::detail
33 {
34 
36 template <typename tuple_derived_t, typename rhs_t, typename ... component_types>
37 inline constexpr bool tuple_general_guard =
38  (!std::same_as<rhs_t, tuple_derived_t>) &&
39  (!std::same_as<rhs_t, alphabet_tuple_base<component_types...>>) &&
40  (!std::is_base_of_v<tuple_derived_t, rhs_t>) &&
41  (!(std::same_as<rhs_t, component_types> || ...)) &&
42  (!list_traits::contains<tuple_derived_t, recursive_required_types_t<rhs_t>>);
43 
44 
46 template <typename lhs_t, typename tuple_derived_t, typename rhs_t, typename ... component_types>
47 inline constexpr bool tuple_eq_guard =
48  (instantiate_if_v<lazy<weakly_equality_comparable_with_trait, rhs_t, component_types>,
49  std::same_as<lhs_t, tuple_derived_t> &&
50  tuple_general_guard<tuple_derived_t, rhs_t, component_types...>
51  > || ...);
52 
54 template <typename lhs_t, typename tuple_derived_t, typename rhs_t, typename ... component_types>
55 inline constexpr bool tuple_order_guard =
56  (instantiate_if_v<lazy<weakly_ordered_with_trait, rhs_t, component_types>,
57  std::same_as<lhs_t, tuple_derived_t> &&
58  tuple_general_guard<lhs_t, tuple_derived_t, rhs_t, component_types...>
59  > || ...);
60 
61 } // namespace seqan3::detail
62 
63 namespace seqan3
64 {
65 
66 // forwards
68 template <typename t>
69 decltype(auto) get();
70 
71 template <size_t i>
72 decltype(auto) get();
74 
114 template <typename derived_type,
115  typename ...component_types>
117  requires (detail::writable_constexpr_semialphabet<component_types> && ...) &&
118  (std::regular<component_types> && ...)
121  public alphabet_base<derived_type,
122  (1 * ... * alphabet_size<component_types>),
123  void> // no char type, because this is only semi_alphabet
124 {
125 private:
128  (1 * ... * alphabet_size<component_types>),
129  void>; // no char type, because this is only semi_alphabet
130 
132  using component_list = meta::list<component_types...>;
133 
135  template <typename type>
136  static constexpr bool is_component =
137  meta::in<component_list, type>::value;
138 
140  template <typename type>
141  static constexpr bool is_unique_component =
142  is_component<type> &&
143  (meta::find_index<component_list, type>::value == meta::reverse_find_index<component_list, type>::value);
144 
145  // forward declaration: see implementation below
146  template <typename alphabet_type, size_t index>
147  class component_proxy;
148 
152  constexpr alphabet_tuple_base() noexcept : base_t{} {}
153  constexpr alphabet_tuple_base(alphabet_tuple_base const &) = default;
154  constexpr alphabet_tuple_base(alphabet_tuple_base &&) = default;
155  constexpr alphabet_tuple_base & operator=(alphabet_tuple_base const &) = default;
157  ~alphabet_tuple_base() = default;
158 
159  using base_t::base_t;
161 
164  friend derived_type;
165 
166  // Import from base:
167  using typename base_t::rank_type;
168 
169 public:
170  // Import from base:
171  using base_t::alphabet_size;
172  using base_t::to_rank;
173  using base_t::assign_rank;
174 
183  meta::list<>>...>;
186  static constexpr bool seqan3_alphabet_tuple_like = true;
187 
196  constexpr alphabet_tuple_base(component_types ... components) noexcept
197  {
198  assign_rank(rank_sum_helper(components..., std::make_index_sequence<sizeof...(component_types)>{}));
199  }
200 
211  template <typename component_type>
213  requires (!std::is_base_of_v<alphabet_tuple_base, component_type>) &&
214  is_unique_component<component_type>
216  constexpr explicit alphabet_tuple_base(component_type const alph) noexcept : alphabet_tuple_base{}
217  {
218  get<component_type>(*this) = alph;
219  }
220 
236  template <typename indirect_component_type>
238  requires ((detail::instantiate_if_v<
239  detail::lazy<std::is_convertible, indirect_component_type, component_types>,
240  detail::tuple_general_guard<derived_type, indirect_component_type, component_types...>> || ...))
242  constexpr explicit alphabet_tuple_base(indirect_component_type const alph) noexcept : alphabet_tuple_base{}
243  {
244  using component_type = meta::front<meta::find_if<component_list, detail::implicitly_convertible_from<indirect_component_type>>>;
245  component_type tmp(alph); // delegate construction
246  get<component_type>(*this) = tmp;
247  }
248 
250  template <typename indirect_component_type>
251  requires ((!(detail::instantiate_if_v<
252  detail::lazy<std::is_convertible, indirect_component_type, component_types>,
253  detail::tuple_general_guard<derived_type, indirect_component_type, component_types...>> || ...)) &&
254  (detail::instantiate_if_v<
255  detail::lazy<std::is_constructible, component_types, indirect_component_type>,
256  detail::tuple_general_guard<derived_type, indirect_component_type, component_types...>> || ...))
257  constexpr explicit alphabet_tuple_base(indirect_component_type const alph) noexcept : alphabet_tuple_base{}
258  {
259  using component_type = meta::front<meta::find_if<component_list, detail::constructible_from<indirect_component_type>>>;
260  component_type tmp(alph); // delegate construction
261  get<component_type>(*this) = tmp;
262  }
264 
275  template <typename component_type>
277  requires (!std::derived_from<component_type, alphabet_tuple_base>) &&
278  is_unique_component<component_type>
280  constexpr derived_type & operator=(component_type const alph) noexcept
281  {
282  get<component_type>(*this) = alph;
283  return static_cast<derived_type &>(*this);
284  }
285 
297  template <typename indirect_component_type>
299  requires ((!std::derived_from<indirect_component_type, alphabet_tuple_base>) &&
300  (!is_unique_component<indirect_component_type>) &&
301  (std::assignable_from<component_types, indirect_component_type> || ...))
303  constexpr derived_type & operator=(indirect_component_type const alph) noexcept
304  {
305  using component_type = meta::front<meta::find_if<component_list, detail::assignable_from<indirect_component_type>>>;
306  get<component_type>(*this) = alph; // delegate assignment
307  return static_cast<derived_type &>(*this);
308  }
310  // If not assignable but implicit convertible, convert first and assign afterwards
311  template <typename indirect_component_type>
312  requires ((!std::derived_from<indirect_component_type, alphabet_tuple_base>) &&
313  (!is_unique_component<indirect_component_type>) &&
314  (!(std::assignable_from<component_types, indirect_component_type> || ...)) &&
315  (std::convertible_to<indirect_component_type, component_types> || ...))
316  constexpr derived_type & operator=(indirect_component_type const alph) noexcept
317  {
318  using component_type = meta::front<meta::find_if<component_list, detail::implicitly_convertible_from<indirect_component_type>>>;
319  component_type tmp(alph);
320  get<component_type>(*this) = tmp;
321  return static_cast<derived_type &>(*this);
322  }
323 
324  template <typename indirect_component_type>
325  requires ((!std::derived_from<indirect_component_type, alphabet_tuple_base>) &&
326  (!is_unique_component<indirect_component_type>) &&
327  (!(std::assignable_from<component_types, indirect_component_type> || ...)) &&
328  (!(std::convertible_to<indirect_component_type, component_types> || ...)) &&
329  (std::constructible_from<component_types, indirect_component_type> || ...))
330  constexpr derived_type & operator=(indirect_component_type const alph) noexcept
331  {
332  using component_type = meta::front<meta::find_if<component_list, detail::constructible_from<indirect_component_type>>>;
333  component_type tmp(alph); // delegate construction
334  get<component_type>(*this) = tmp;
335  return static_cast<derived_type &>(*this);
336  }
339 
350  template <size_t index>
351  friend constexpr auto get(alphabet_tuple_base & l) noexcept
352  {
353  static_assert(index < sizeof...(component_types), "Index out of range.");
354 
355  using t = meta::at_c<component_list, index>;
356  t val{};
357 
358  seqan3::assign_rank_to(l.to_component_rank<index>(), val);
359 
360  return component_proxy<t, index>{val, l};
361  }
362 
369  template <typename type>
370  friend constexpr auto get(alphabet_tuple_base & l) noexcept
372  requires is_unique_component<type>
374  {
375  return get<meta::find_index<component_list, type>::value>(l);
376  }
377 
384  template <size_t index>
385  friend constexpr auto get(alphabet_tuple_base const & l) noexcept
386  {
387  static_assert(index < sizeof...(component_types), "Index out of range.");
388 
389  using t = meta::at_c<component_list, index>;
390 
391  return seqan3::assign_rank_to(l.to_component_rank<index>(), t{});
392  }
393 
400  template <typename type>
401  friend constexpr type get(alphabet_tuple_base const & l) noexcept
403  requires is_unique_component<type>
405  {
406  return get<meta::find_index<component_list, type>::value>(l);
407  }
408 
413  template <typename type>
414  constexpr operator type() const noexcept
416  requires is_unique_component<type>
418  {
419  return get<type>(*this);
420  }
422 
440  template <typename derived_type_t, typename indirect_component_type>
441  friend constexpr auto operator==(derived_type_t const lhs, indirect_component_type const rhs) noexcept
442  -> std::enable_if_t<detail::tuple_eq_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
443  bool>
444  {
445  using component_type = meta::front<meta::find_if<component_list, detail::weakly_equality_comparable_with_<indirect_component_type>>>;
446  return get<component_type>(lhs) == rhs;
447  }
448 
450  template <typename derived_type_t, typename indirect_component_type>
451  friend constexpr auto operator==(indirect_component_type const lhs, derived_type_t const rhs) noexcept
452  -> std::enable_if_t<detail::tuple_eq_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
453  bool>
454  {
455  return rhs == lhs;
456  }
457 
459  template <typename derived_type_t, typename indirect_component_type>
460  friend constexpr auto operator!=(derived_type_t const lhs, indirect_component_type const rhs) noexcept
461  -> std::enable_if_t<detail::tuple_eq_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
462  bool>
463  {
464  using component_type = meta::front<meta::find_if<component_list, detail::weakly_equality_comparable_with_<indirect_component_type>>>;
465  return get<component_type>(lhs) != rhs;
466  }
467 
469  template <typename derived_type_t, typename indirect_component_type>
470  friend constexpr auto operator!=(indirect_component_type const lhs, derived_type_t const rhs) noexcept
471  -> std::enable_if_t<detail::tuple_eq_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
472  bool>
473  {
474  return rhs != lhs;
475  }
476 
478  template <typename derived_type_t, typename indirect_component_type>
479  friend constexpr auto operator<(derived_type_t const lhs, indirect_component_type const rhs) noexcept
480  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
481  bool>
482  {
483  using component_type = meta::front<meta::find_if<component_list, detail::weakly_ordered_with_<indirect_component_type>>>;
484  return get<component_type>(lhs) < rhs;
485  }
486 
488  template <typename derived_type_t, typename indirect_component_type>
489  friend constexpr auto operator<(indirect_component_type const lhs, derived_type_t const rhs) noexcept
490  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
491  bool>
492  {
493  return rhs > lhs;
494  }
495 
497  template <typename derived_type_t, typename indirect_component_type>
498  friend constexpr auto operator<=(derived_type_t const lhs, indirect_component_type const rhs) noexcept
499  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
500  bool>
501  {
502  using component_type = meta::front<meta::find_if<component_list, detail::weakly_ordered_with_<indirect_component_type>>>;
503  return get<component_type>(lhs) <= rhs;
504  }
505 
507  template <typename derived_type_t, typename indirect_component_type>
508  friend constexpr auto operator<=(indirect_component_type const lhs, derived_type_t const rhs) noexcept
509  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
510  bool>
511  {
512  return rhs >= lhs;
513  }
514 
516  template <typename derived_type_t, typename indirect_component_type>
517  friend constexpr auto operator>(derived_type_t const lhs, indirect_component_type const rhs) noexcept
518  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
519  bool>
520  {
521  using component_type = meta::front<meta::find_if<component_list, detail::weakly_ordered_with_<indirect_component_type>>>;
522  return get<component_type>(lhs) > rhs;
523  }
524 
526  template <typename derived_type_t, typename indirect_component_type>
527  friend constexpr auto operator>(indirect_component_type const lhs, derived_type_t const rhs) noexcept
528  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
529  bool>
530  {
531  return rhs < lhs;
532  }
533 
535  template <typename derived_type_t, typename indirect_component_type>
536  friend constexpr auto operator>=(derived_type_t const lhs, indirect_component_type const rhs) noexcept
537  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
538  bool>
539  {
540  using component_type = meta::front<meta::find_if<component_list, detail::weakly_ordered_with_<indirect_component_type>>>;
541  return get<component_type>(lhs) >= rhs;
542  }
543 
545  template <typename derived_type_t, typename indirect_component_type>
546  friend constexpr auto operator>=(indirect_component_type const lhs, derived_type_t const rhs) noexcept
547  -> std::enable_if_t<detail::tuple_order_guard<derived_type_t, derived_type, indirect_component_type, component_types...>,
548  bool>
549  {
550  return rhs <= lhs;
551  }
553 
554 private:
556  template <size_t index>
557  constexpr rank_type to_component_rank() const noexcept
558  {
559  if constexpr (alphabet_size < 1024) // computation is cached for small alphabets
560  {
561  return rank_to_component_rank[index][to_rank()];
562  }
563  else
564  {
565  return (to_rank() / cummulative_alph_sizes[index]) %
566  seqan3::alphabet_size<pack_traits::at<index, component_types...>>;
567  }
568  }
569 
571  template <size_t index>
572  constexpr void assign_component_rank(ptrdiff_t const r) noexcept
573  {
574  assign_rank(static_cast<ptrdiff_t>(to_rank()) +
575  ((r - static_cast<ptrdiff_t>(to_component_rank<index>())) *
576  static_cast<ptrdiff_t>(cummulative_alph_sizes[index])));
577  }
578 
581  {
582  [] () constexpr
583  {
584  // create array (1, |sigma1|, |sigma1|*|sigma2|, ... , |sigma1|*...*|sigmaN|)
586  ret[0] = 1;
587  size_t count = 1;
588  meta::for_each(meta::reverse<component_list>{}, [&] (auto alph) constexpr
589  {
590  ret[count] = static_cast<rank_type>(seqan3::alphabet_size<decltype(alph)> * ret[count - 1]);
591  ++count;
592  });
593 
594  // reverse and strip one: (|sigma1|*...*|sigmaN-1|, ... |sigma1|*|sigma2|, |sigma1|, 1)
595  // reverse order guarantees that the first alphabet is the most significant rank contributer
596  // resulting in element-wise alphabetical ordering on comparison
598  for (size_t i = 0; i < component_list::size(); ++i)
599  ret2[i] = ret[component_list::size() - i - 1];
600 
601  return ret2;
602  }()
603  };
604 
606  template <std::size_t ...idx>
607  static constexpr rank_type rank_sum_helper(component_types ... components, std::index_sequence<idx...> const &) noexcept
608  {
609  return ((seqan3::to_rank(components) * cummulative_alph_sizes[idx]) + ...);
610  }
611 
614  list_traits::size<component_list>> rank_to_component_rank
615  {
616  [] () constexpr
617  {
619  list_traits::size<component_list>> ret{};
620 
621  if constexpr (alphabet_size < 1024)
622  {
623  std::array<size_t, alphabet_size> alph_sizes{ seqan3::alphabet_size<component_types>... };
624 
625  for (size_t i = 0; i < list_traits::size<component_list>; ++i)
626  for (size_t j = 0; j < static_cast<size_t>(alphabet_size); ++j)
627  ret[i][j] = (j / cummulative_alph_sizes[i]) % alph_sizes[i];
628  }
629 
630  return ret;
631  }()
632  };
633 };
634 
641 template <typename derived_type, typename ...component_types>
642 template <typename alphabet_type, size_t index>
643 class alphabet_tuple_base<derived_type, component_types...>::component_proxy : public alphabet_proxy<component_proxy<alphabet_type, index>, alphabet_type>
644 {
645 private:
649  friend base_t;
650 
653 
655  constexpr void on_update() noexcept
656  {
657  parent->assign_component_rank<index>(to_rank());
658  }
659 
660 public:
661  //Import from base type:
662  using base_t::operator=;
663 
668  component_proxy() = delete;
669  constexpr component_proxy(component_proxy const &) = default;
670  constexpr component_proxy(component_proxy &&) = default;
671  constexpr component_proxy & operator=(component_proxy const &) = default;
672  constexpr component_proxy & operator=(component_proxy &&) = default;
673  ~component_proxy() = default;
674 
676  constexpr component_proxy(alphabet_type const l, alphabet_tuple_base & p) :
677  base_t{l}, parent{&p}
678  {}
679 
680  // Does not inherit the base's constructor for alphabet_type so as not to cause ambiguity
682 
692  friend constexpr bool operator==(derived_type const lhs, component_proxy const rhs) noexcept
693  {
694  return get<index>(lhs) == static_cast<alphabet_type>(rhs);
695  }
696 
698  friend constexpr bool operator==(component_proxy<alphabet_type, index> const lhs, derived_type const rhs) noexcept
699  {
700  return rhs == lhs;
701  }
702 
704  friend constexpr bool operator!=(derived_type const lhs, component_proxy const rhs) noexcept
705  {
706  return get<index>(lhs) != static_cast<alphabet_type>(rhs);
707  }
708 
710  friend constexpr bool operator!=(component_proxy<alphabet_type, index> const lhs, derived_type const rhs) noexcept
711  {
712  return rhs != lhs;
713  }
714 
716  friend constexpr bool operator<(derived_type const lhs, component_proxy const rhs) noexcept
717  {
718  return get<index>(lhs) < static_cast<alphabet_type>(rhs);
719  }
720 
722  friend constexpr bool operator<(component_proxy<alphabet_type, index> const lhs, derived_type const rhs) noexcept
723  {
724  return rhs > lhs;
725  }
726 
728  friend constexpr bool operator<=(derived_type const lhs, component_proxy const rhs) noexcept
729  {
730  return get<index>(lhs) <= static_cast<alphabet_type>(rhs);
731  }
732 
734  friend constexpr bool operator<=(component_proxy<alphabet_type, index> const lhs, derived_type const rhs) noexcept
735  {
736  return rhs >= lhs;
737  }
738 
740  friend constexpr bool operator>(derived_type const lhs, component_proxy const rhs) noexcept
741  {
742  return get<index>(lhs) > static_cast<alphabet_type>(rhs);
743  }
744 
746  friend constexpr bool operator>(component_proxy<alphabet_type, index> const lhs, derived_type const rhs) noexcept
747  {
748  return rhs < lhs;
749  }
750 
752  friend constexpr bool operator>=(derived_type const lhs, component_proxy const rhs) noexcept
753  {
754  return get<index>(lhs) >= static_cast<alphabet_type>(rhs);
755  }
756 
758  friend constexpr bool operator>=(component_proxy<alphabet_type, index> const lhs, derived_type const rhs) noexcept
759  {
760  return rhs <= lhs;
761  }
763 };
764 
765 } // namespace seqan3
766 
767 namespace std
768 {
769 
777 template <std::size_t i, seqan3::detail::alphabet_tuple_like tuple_t>
778 struct tuple_element<i, tuple_t>
779 {
781  using type = meta::at_c<typename tuple_t::seqan3_required_types, i>;
782 };
783 
791 template <seqan3::detail::alphabet_tuple_like tuple_t>
792 struct tuple_size<tuple_t> :
793  public std::integral_constant<size_t, seqan3::list_traits::size<typename tuple_t::seqan3_required_types>>
794 {};
795 
796 } // namespace std
Provides implementation detail for seqan3::alphabet_variant and seqan3::alphabet_tuple_base.
Core alphabet concept and free function/type trait wrappers.
Provides seqan3::alphabet_base.
Provides seqan3::alphabet_proxy.
A CRTP-base that makes defining a custom alphabet easier.
Definition: alphabet_base.hpp:81
constexpr rank_type to_rank() const noexcept
Return the letter's numeric value (rank in the alphabet).
Definition: alphabet_base.hpp:185
detail::min_viable_uint_t< size - 1 > rank_type
The type of the alphabet when represented as a number (e.g. via to_rank()).
Definition: alphabet_base.hpp:104
static constexpr detail::min_viable_uint_t< size > alphabet_size
The size of the alphabet, i.e. the number of different values it can take.
Definition: alphabet_base.hpp:276
constexpr derived_type & assign_rank(rank_type const c) noexcept
Assign from a numeric value.
Definition: alphabet_base.hpp:264
A CRTP-base that eases the definition of proxy types returned in place of regular alphabets.
Definition: alphabet_proxy.hpp:66
Specialisation of seqan3::alphabet_proxy that updates the rank of the alphabet_tuple_base.
Definition: alphabet_tuple_base.hpp:644
constexpr void on_update() noexcept
The implementation updates the rank in the parent object.
Definition: alphabet_tuple_base.hpp:655
constexpr component_proxy(component_proxy const &)=default
Defaulted.
constexpr friend bool operator>=(derived_type const lhs, component_proxy const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:752
constexpr friend bool operator<(derived_type const lhs, component_proxy const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:716
constexpr friend bool operator>(derived_type const lhs, component_proxy const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:740
constexpr component_proxy & operator=(component_proxy &&)=default
Defaulted.
constexpr friend bool operator==(derived_type const lhs, component_proxy const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:692
alphabet_tuple_base * parent
Store a pointer to the parent object so we can update it.
Definition: alphabet_tuple_base.hpp:652
constexpr friend bool operator>=(component_proxy< alphabet_type, index > const lhs, derived_type const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:758
constexpr friend bool operator<=(derived_type const lhs, component_proxy const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:728
constexpr friend bool operator>(component_proxy< alphabet_type, index > const lhs, derived_type const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:746
constexpr friend bool operator!=(derived_type const lhs, component_proxy const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:704
constexpr component_proxy & operator=(component_proxy const &)=default
Defaulted.
constexpr friend bool operator<(component_proxy< alphabet_type, index > const lhs, derived_type const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:722
constexpr friend bool operator!=(component_proxy< alphabet_type, index > const lhs, derived_type const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:710
constexpr component_proxy(alphabet_type const l, alphabet_tuple_base &p)
Construct from an alphabet letter and reference to the parent object.
Definition: alphabet_tuple_base.hpp:676
friend base_t
Befriend the base type so it can call our seqan3::alphabet_tuple_base::component_proxy::on_update().
Definition: alphabet_tuple_base.hpp:649
constexpr friend bool operator==(component_proxy< alphabet_type, index > const lhs, derived_type const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:698
constexpr friend bool operator<=(component_proxy< alphabet_type, index > const lhs, derived_type const rhs) noexcept
Comparison against the alphabet tuple by casting self and tuple to the emulated type.
Definition: alphabet_tuple_base.hpp:734
constexpr component_proxy(component_proxy &&)=default
Defaulted.
component_proxy()=delete
Deleted, because using this proxy without parent would be undefined behaviour.
The CRTP base for a combined alphabet that contains multiple values of different alphabets at the sam...
Definition: alphabet_tuple_base.hpp:124
constexpr friend auto operator>(indirect_component_type const lhs, derived_type_t const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:527
~alphabet_tuple_base()=default
Defaulted.
constexpr friend auto operator<=(indirect_component_type const lhs, derived_type_t const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:508
constexpr friend auto operator==(indirect_component_type const lhs, derived_type_t const rhs) noexcept -> std::enable_if_t< detail::tuple_eq_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:451
constexpr friend auto operator==(derived_type_t const lhs, indirect_component_type const rhs) noexcept -> std::enable_if_t< detail::tuple_eq_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:441
component_list seqan3_required_types
Export this type's components in a visible manner.
Definition: alphabet_tuple_base.hpp:177
constexpr rank_type to_component_rank() const noexcept
Return the rank of the i-th component.
Definition: alphabet_tuple_base.hpp:557
constexpr derived_type & operator=(component_type const alph) noexcept
Assignment via a value of one of the components.
Definition: alphabet_tuple_base.hpp:280
static constexpr rank_type rank_sum_helper(component_types ... components, std::index_sequence< idx... > const &) noexcept
For the given components, compute the combined rank.
Definition: alphabet_tuple_base.hpp:607
meta::concat< component_list, detail::transformation_trait_or_t< detail::recursive_required_types< component_types >, meta::list<> >... > seqan3_recursive_required_types
Export this type's components and possibly the components' components in a visible manner.
Definition: alphabet_tuple_base.hpp:183
constexpr friend auto operator<(indirect_component_type const lhs, derived_type_t const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:489
constexpr alphabet_tuple_base & operator=(alphabet_tuple_base const &)=default
Defaulted.
constexpr friend type get(alphabet_tuple_base const &l) noexcept
Tuple-like access to the contained components.
Definition: alphabet_tuple_base.hpp:401
static constexpr bool seqan3_alphabet_tuple_like
Make specialisations of this template identifiable in metapgrogramming contexts.
Definition: alphabet_tuple_base.hpp:186
constexpr friend auto operator>=(indirect_component_type const lhs, derived_type_t const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:546
constexpr alphabet_tuple_base(alphabet_tuple_base const &)=default
Defaulted.
meta::list< component_types... > component_list
A meta::list The types of each component in the composite.
Definition: alphabet_tuple_base.hpp:132
constexpr friend auto operator<=(derived_type_t const lhs, indirect_component_type const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:498
constexpr friend auto operator!=(derived_type_t const lhs, indirect_component_type const rhs) noexcept -> std::enable_if_t< detail::tuple_eq_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:460
constexpr friend auto operator>=(derived_type_t const lhs, indirect_component_type const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:536
constexpr alphabet_tuple_base(alphabet_tuple_base &&)=default
Defaulted.
static constexpr bool is_unique_component
Is set to true if the type is uniquely contained in the type list.
Definition: alphabet_tuple_base.hpp:141
constexpr alphabet_tuple_base() noexcept
Defaulted.
Definition: alphabet_tuple_base.hpp:152
constexpr friend auto operator<(derived_type_t const lhs, indirect_component_type const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:479
constexpr alphabet_tuple_base(component_types ... components) noexcept
Construction from initialiser-list.
Definition: alphabet_tuple_base.hpp:196
constexpr alphabet_tuple_base & operator=(alphabet_tuple_base &&)=default
Defaulted.
constexpr friend auto operator!=(indirect_component_type const lhs, derived_type_t const rhs) noexcept -> std::enable_if_t< detail::tuple_eq_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:470
static constexpr std::array< rank_type, component_list::size()> cummulative_alph_sizes
The cumulative alphabet size products are cached.
Definition: alphabet_tuple_base.hpp:581
constexpr friend auto get(alphabet_tuple_base const &l) noexcept
Tuple-like access to the contained components.
Definition: alphabet_tuple_base.hpp:385
static constexpr bool is_component
Is set to true if the type is contained in the type list.
Definition: alphabet_tuple_base.hpp:136
constexpr void assign_component_rank(ptrdiff_t const r) noexcept
Assign via the rank of i-th component (does not update other components' state).
Definition: alphabet_tuple_base.hpp:572
constexpr friend auto operator>(derived_type_t const lhs, indirect_component_type const rhs) noexcept -> std::enable_if_t< detail::tuple_order_guard< derived_type_t, derived_type, indirect_component_type, component_types... >, bool >
Comparison against types comparable with components.
Definition: alphabet_tuple_base.hpp:517
constexpr alphabet_tuple_base(component_type const alph) noexcept
Construction via a value of one of the components.
Definition: alphabet_tuple_base.hpp:216
friend derived_type
Befriend the derived type so that it can instantiate.
Definition: alphabet_tuple_base.hpp:164
constexpr friend auto get(alphabet_tuple_base &l) noexcept
Tuple-like access to the contained components.
Definition: alphabet_tuple_base.hpp:351
The Concepts library.
Provides concepts for core language types and relations that don't have concepts in C++20 (yet).
constexpr auto alphabet_size
A type trait that holds the size of a (semi-)alphabet.
Definition: concept.hpp:858
constexpr auto assign_rank_to
Assign a rank to an alphabet object.
Definition: concept.hpp:291
constexpr auto to_rank
Return the rank representation of a (semi-)alphabet object.
Definition: concept.hpp:155
constexpr void for_each(unary_function_t &&fn, pack_t &&...args)
Applies a function to each element of the given function parameter pack.
Definition: pack_algorithm.hpp:195
decltype(detail::concat(lists_t{}...)) concat
Join two seqan3::type_list s into one.
Definition: traits.hpp:292
constexpr bool contains
Whether a type occurs in a type list or not.
Definition: traits.hpp:194
constexpr ptrdiff_t count
Count the occurrences of a type in a pack.
Definition: traits.hpp:168
typename decltype(detail::at< idx, pack_t... >())::type at
Return the type at given index from the type pack.
Definition: traits.hpp:255
constexpr size_t size
The size of a type pack.
Definition: traits.hpp:150
typename transformation_trait_or< type_t, default_t >::type transformation_trait_or_t
Helper type of seqan3::detail::transformation_trait_or (transformation_trait shortcut).
Definition: transformation_trait_or.hpp:51
Provides metaprogramming utilities for integer types.
Subconcept definition for seqan3::tuple_like to test for std::tuple_size-interface.
The internal SeqAn3 namespace.
Definition: aligned_sequence_concept.hpp:29
constexpr bool tuple_general_guard
Prevents wrong instantiations of seqan3::alphabet_tuple_base's equality comparison operators.
Definition: alphabet_tuple_base.hpp:37
constexpr bool tuple_eq_guard
Prevents wrong instantiations of seqan3::alphabet_tuple_base's equality comparison operators.
Definition: alphabet_tuple_base.hpp:47
constexpr bool tuple_order_guard
Prevents wrong instantiations of seqan3::alphabet_tuple_base's ordered comparison operators.
Definition: alphabet_tuple_base.hpp:55
The main SeqAn3 namespace.
Definition: aligned_sequence_concept.hpp:29
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:434
SeqAn specific customisations in the standard namespace.
meta::at_c< typename tuple_t::seqan3_required_types, i > type
Element type.
Definition: alphabet_tuple_base.hpp:781
Provides seqan3::tuple_like.
Provides traits for seqan3::type_list.
Provides various traits for template packs.
Provides seqan3::detail::transformation_trait_or.