aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/development/c++
diff options
context:
space:
mode:
authorJohannes Stoelp <johannes.stoelp@gmail.com>2022-09-28 22:10:29 +0200
committerJohannes Stoelp <johannes.stoelp@gmail.com>2022-09-28 22:10:29 +0200
commit99c1f88e7396ee87a812f8d114aac8d903eb7afb (patch)
tree7352e9d3e131af424be5b2a941860568c9e6db3f /src/development/c++
parent47218d271f20b39610d5f63b3bc7dfc86642bdba (diff)
downloadnotes-99c1f88e7396ee87a812f8d114aac8d903eb7afb.tar.gz
notes-99c1f88e7396ee87a812f8d114aac8d903eb7afb.zip
c++: pre c++20 concept example
Diffstat (limited to 'src/development/c++')
-rw-r--r--src/development/c++/concepts-11.cc53
1 files changed, 53 insertions, 0 deletions
diff --git a/src/development/c++/concepts-11.cc b/src/development/c++/concepts-11.cc
new file mode 100644
index 0000000..888ff4d
--- /dev/null
+++ b/src/development/c++/concepts-11.cc
@@ -0,0 +1,53 @@
+// Copyright (C) 2022 johannst
+#include <type_traits>
+
+template<typename T, template<typename> class Checker, typename = void>
+struct is_valid : std::false_type {};
+
+template<typename T, template<typename> class Checker>
+struct is_valid<T, Checker, std::void_t<Checker<T>>> : std::true_type {};
+
+template<typename T, template<typename> class Checker>
+static constexpr bool is_valid_v = is_valid<T, Checker>::value;
+
+// -----------------------------------------------------------------------------
+
+template<typename T, typename R, template<typename> class Checker, typename = void>
+struct is_valid_with_ret : std::false_type {};
+
+template<typename T, typename R, template<typename> class Checker>
+struct is_valid_with_ret<T, R, Checker, std::void_t<Checker<T>>> : std::is_same<R, Checker<T>> {};
+
+template<typename T, typename R, template<typename> class Checker>
+static constexpr bool is_valid_with_ret_v = is_valid_with_ret<T, R, Checker>::value;
+
+// -----------------------------------------------------------------------------
+
+template<typename T>
+struct is_entry {
+ template<typename TT>
+ using init = decltype(std::declval<TT>().init());
+ template<typename TT>
+ using tag = decltype(std::declval<TT>().tag());
+ template<typename TT>
+ using val = decltype(std::declval<TT>().val());
+
+ static constexpr bool value = is_valid_v<T, init> &&
+ is_valid_with_ret_v<T, int, tag> &&
+ is_valid_with_ret_v<T, typename T::Type, val>;
+};
+
+template<typename T>
+static constexpr bool is_entry_v = is_entry<T>::value;
+
+template<typename E>
+struct Entry {
+ using Type = E;
+ void init();
+ int tag() const;
+ E val() const;
+};
+
+int main() {
+ static_assert(is_entry_v<Entry<bool>>, "");
+}