You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

140 line
4.0 KiB

  1. #pragma once
  2. #include <variant>
  3. #include "result.pre.h"
  4. namespace asyncpp
  5. {
  6. namespace __impl
  7. {
  8. struct result_not_ready
  9. { };
  10. struct result_done
  11. { };
  12. template<typename T_value>
  13. struct result_ready
  14. {
  15. using value_type = T_value;
  16. value_type value;
  17. template<typename... T_args>
  18. inline result_ready(T_args&&... p_args);
  19. };
  20. template<bool for_stream, typename T_value>
  21. struct result
  22. {
  23. public:
  24. using value_type = T_value;
  25. using not_ready_type = result_not_ready;
  26. using ready_type = result_ready<value_type>;
  27. using done_type = result_done;
  28. using storage_type = std::conditional_t<
  29. for_stream,
  30. std::variant<not_ready_type, ready_type, done_type>,
  31. std::variant<not_ready_type, ready_type>>;
  32. using clean_value_type = std::remove_reference_t<value_type>;
  33. using pointer_type = clean_value_type*;
  34. using reference_type = clean_value_type&;
  35. using const_pointer_type = clean_value_type const *;
  36. using const_reference_type = clean_value_type const &;
  37. private:
  38. storage_type _storage; //!< Stores the actual result.
  39. private:
  40. /**
  41. * @brief Constructor.
  42. */
  43. inline result(storage_type&& p_storage);
  44. public:
  45. /**
  46. * @brief returns a result that is not ready.
  47. */
  48. static inline auto& not_ready();
  49. /**
  50. * @brief returns a result that is not ready.
  51. */
  52. template<typename... X_args>
  53. static inline auto ready(X_args&&... p_args);
  54. /**
  55. * @brief returns a result that is not ready.
  56. */
  57. template<
  58. bool X = for_stream,
  59. typename = std::enable_if_t<X>>
  60. static inline auto& done();
  61. public:
  62. /**
  63. * @brief Get the status of the result.
  64. */
  65. template<
  66. bool X = for_stream,
  67. typename = std::enable_if_t<X>>
  68. inline result_status status() const;
  69. /**
  70. * @brief Check if the result is not ready (is pending).
  71. */
  72. inline bool is_not_ready() const;
  73. /**
  74. * @brief Check if the result is ready (has a value).
  75. */
  76. inline bool is_ready() const;
  77. /**
  78. * @brief Check if the result is done (stream is finished).
  79. */
  80. template<
  81. bool X = for_stream,
  82. typename = std::enable_if_t<X>>
  83. inline bool is_done() const;
  84. /**
  85. * @brief Get the value of the result.
  86. */
  87. inline reference_type value();
  88. /**
  89. * @brief Get the value of the result.
  90. */
  91. inline const_reference_type value() const;
  92. /**
  93. * @brief Call the passed closure with the value stored in the result.
  94. */
  95. template<typename X_lambda>
  96. inline auto call(const X_lambda& p_lambda);
  97. /**
  98. * @brief Call the passed closure with the value stored in the result.
  99. */
  100. template<typename X_lambda>
  101. inline auto call(const X_lambda& p_lambda) const;
  102. public:
  103. inline operator bool() const;
  104. inline pointer_type operator-> ();
  105. inline reference_type operator* ();
  106. inline const_pointer_type operator-> () const;
  107. inline const_reference_type operator* () const;
  108. };
  109. template<bool for_stream>
  110. struct result<for_stream, void>;
  111. }
  112. }