/* This file is part of Telegram Desktop, the official desktop application for the Telegram messaging service. For license and copyright information please follow this link: https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL */ #pragma once #include namespace rpl { namespace details { namespace type_list { template struct list { }; template struct list { using head = Type; using tail = list; }; using empty_list = list<>; template using head_t = typename TypeList::head; template using tail_t = typename TypeList::tail; template struct construct; template using construct_t = typename construct::type; template struct construct> { using type = list; }; template struct size; template constexpr std::size_t size_v = size::value; template struct size> : std::integral_constant< std::size_t, sizeof...(Types)> { }; template constexpr bool empty_v = (size_v == 0); template struct empty : std::bool_constant> { }; template struct get; template using get_t = typename get::type; template struct get { using type = get_t>; }; template struct get<0, TypeList> { using type = head_t; }; template struct concat; template using concat_t = typename concat::type; template struct concat, list> { using type = list; }; template struct remove_all; template using remove_all_t = typename remove_all::type; template struct remove_all { using head = head_t; using tail = tail_t; using clean_tail = remove_all_t; using type = std::conditional_t< std::is_same_v, clean_tail, construct_t>; }; template struct remove_all { using type = empty_list; }; template struct last; template using last_t = typename last::type; template struct last { using type = last_t>; }; template struct last> { using type = Type; }; template struct chop_last; template using chop_last_t = typename chop_last::type; template struct chop_last { using type = construct_t< head_t, chop_last_t>>; }; template struct chop_last> { using type = empty_list; }; template struct distinct; template using distinct_t = typename distinct::type; template struct distinct { using type = construct_t< head_t, distinct_t< remove_all_t, head_t>>>; }; template <> struct distinct { using type = empty_list; }; template typename To> struct extract_to; template typename To> using extract_to_t = typename extract_to::type; template typename To> struct extract_to, To> { using type = To; }; } // namespace type_list } // namespace details } // namespace rpl