c++11 - C++ how to generate all the permutations of function overloads? -
lets have classes date
, classes year
, month
, day
.
struct date { date(year year, month month, day day) : d(day), m(month), y(year) {}; date(month month, day day, year year) : d(day), m(month), y(year) {}; date(day day, month month, year year) : d(day), m(month), y(year) {}; date(day day, year year, month month) : d(day), m(month), y(year) {}; ... ... private: day d; month m; year y; }
this allows me not have specific layout of arguments date
have lot of overloadings.
am able generate permutations/overloadings automatically?
just clear:
- permutations of argument layout, nothing them should change know not possible automate.
- all generated overloadings should have same code layout of arguments changes not logic itself.
with c++14, may do:
struct date { public: date(const year& year, const month& month, const day& day) : d(day), m(month), y(year) {} template <typename t1, typename t2, typename t3> date(const t1& t1, const t2& t2, const t3& t3) : date(std::get<year>(std::tie(t1, t2, t3)), std::get<month>(std::tie(t1, t2, t3)), std::get<day>(std::tie(t1, t2, t3))) {} private: day d; month m; year y; };
edit: if allow default argument, may like:
namespace detail { template <typename t, typename... ts> struct has_t; template <typename t> struct has_t<t> : std::false_type {}; template <typename t, typename... ts> struct has_t<t, t, ts...> : std::true_type {}; template <typename t, typename tail, typename... ts> struct has_t<t, tail, ts...> : has_t<t, ts...> {}; template <typename t, typename... ts> const t& get_or_default_impl(std::true_type, const std::tuple<ts...>& t, const t&) { return std::get<t>(t); } template <typename t, typename... ts> const t& get_or_default_impl(std::false_type, const std::tuple<ts...>&, const t& default_value) { return default_value; } template <typename t1, typename t2> struct is_included; template <typename... ts> struct is_included<std::tuple<>, std::tuple<ts...>> : std::true_type {}; template <typename t, typename... ts, typename ... ts2> struct is_included<std::tuple<t, ts...>, std::tuple<ts2...>> : std::conditional_t<has_t<t, ts2...>::value, is_included<std::tuple<ts...>, std::tuple<ts2...>>, std::false_type> {}; } template <typename t, typename... ts> const t& get_or_default(const std::tuple<ts...>& t, const t& default_value = t{}) { return detail::get_or_default_impl<t>(detail::has_t<t, ts...>{}, t, default_value); }
and then
struct date { public: date(const year& year, const month& month, const day& day) : d(day), m(month), y(year) {} template <typename ... ts, typename std::enable_if_t< detail::is_included<std::tuple<ts...>, std::tuple<year, month, day>>::value>* = nullptr> date(const ts&... ts) : date(get_or_default<const year&>(std::tie(ts...)), get_or_default<const month&>(std::tie(ts...)), get_or_default<const day&>(std::tie(ts...))) {} private: day d; month m; year y; };
Comments
Post a Comment