get_index.pass.cpp 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268
  1. // -*- C++ -*-
  2. //===----------------------------------------------------------------------===//
  3. //
  4. // The LLVM Compiler Infrastructure
  5. //
  6. // This file is dual licensed under the MIT and the University of Illinois Open
  7. // Source Licenses. See LICENSE.TXT for details.
  8. //
  9. //===----------------------------------------------------------------------===//
  10. // UNSUPPORTED: c++98, c++03, c++11, c++14
  11. // <variant>
  12. // template <size_t I, class... Types>
  13. // constexpr variant_alternative_t<I, variant<Types...>>&
  14. // get(variant<Types...>& v);
  15. // template <size_t I, class... Types>
  16. // constexpr variant_alternative_t<I, variant<Types...>>&&
  17. // get(variant<Types...>&& v);
  18. // template <size_t I, class... Types>
  19. // constexpr variant_alternative_t<I, variant<Types...>> const& get(const
  20. // variant<Types...>& v);
  21. // template <size_t I, class... Types>
  22. // constexpr variant_alternative_t<I, variant<Types...>> const&& get(const
  23. // variant<Types...>&& v);
  24. #include "test_macros.h"
  25. #include "variant_test_helpers.hpp"
  26. #include <cassert>
  27. #include <type_traits>
  28. #include <utility>
  29. #include <variant>
  30. void test_const_lvalue_get() {
  31. {
  32. using V = std::variant<int>;
  33. constexpr V v(42);
  34. // ASSERT_NOT_NOEXCEPT(std::get<0>(v));
  35. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), int const &);
  36. static_assert(std::get<0>(v) == 42, "");
  37. }
  38. {
  39. using V = std::variant<int, long>;
  40. constexpr V v(42l);
  41. ASSERT_SAME_TYPE(decltype(std::get<1>(v)), long const &);
  42. static_assert(std::get<1>(v) == 42, "");
  43. }
  44. // FIXME: Remove these once reference support is reinstated
  45. #if !defined(TEST_VARIANT_HAS_NO_REFERENCES)
  46. {
  47. using V = std::variant<int &>;
  48. int x = 42;
  49. const V v(x);
  50. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), int &);
  51. assert(&std::get<0>(v) == &x);
  52. }
  53. {
  54. using V = std::variant<int &&>;
  55. int x = 42;
  56. const V v(std::move(x));
  57. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), int &);
  58. assert(&std::get<0>(v) == &x);
  59. }
  60. {
  61. using V = std::variant<const int &&>;
  62. int x = 42;
  63. const V v(std::move(x));
  64. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), const int &);
  65. assert(&std::get<0>(v) == &x);
  66. }
  67. #endif
  68. }
  69. void test_lvalue_get() {
  70. {
  71. using V = std::variant<int>;
  72. V v(42);
  73. ASSERT_NOT_NOEXCEPT(std::get<0>(v));
  74. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), int &);
  75. assert(std::get<0>(v) == 42);
  76. }
  77. {
  78. using V = std::variant<int, long>;
  79. V v(42l);
  80. ASSERT_SAME_TYPE(decltype(std::get<1>(v)), long &);
  81. assert(std::get<1>(v) == 42);
  82. }
  83. // FIXME: Remove these once reference support is reinstated
  84. #if !defined(TEST_VARIANT_HAS_NO_REFERENCES)
  85. {
  86. using V = std::variant<int &>;
  87. int x = 42;
  88. V v(x);
  89. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), int &);
  90. assert(&std::get<0>(v) == &x);
  91. }
  92. {
  93. using V = std::variant<const int &>;
  94. int x = 42;
  95. V v(x);
  96. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), const int &);
  97. assert(&std::get<0>(v) == &x);
  98. }
  99. {
  100. using V = std::variant<int &&>;
  101. int x = 42;
  102. V v(std::move(x));
  103. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), int &);
  104. assert(&std::get<0>(v) == &x);
  105. }
  106. {
  107. using V = std::variant<const int &&>;
  108. int x = 42;
  109. V v(std::move(x));
  110. ASSERT_SAME_TYPE(decltype(std::get<0>(v)), const int &);
  111. assert(&std::get<0>(v) == &x);
  112. }
  113. #endif
  114. }
  115. void test_rvalue_get() {
  116. {
  117. using V = std::variant<int>;
  118. V v(42);
  119. ASSERT_NOT_NOEXCEPT(std::get<0>(std::move(v)));
  120. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), int &&);
  121. assert(std::get<0>(std::move(v)) == 42);
  122. }
  123. {
  124. using V = std::variant<int, long>;
  125. V v(42l);
  126. ASSERT_SAME_TYPE(decltype(std::get<1>(std::move(v))), long &&);
  127. assert(std::get<1>(std::move(v)) == 42);
  128. }
  129. // FIXME: Remove these once reference support is reinstated
  130. #if !defined(TEST_VARIANT_HAS_NO_REFERENCES)
  131. {
  132. using V = std::variant<int &>;
  133. int x = 42;
  134. V v(x);
  135. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), int &);
  136. assert(&std::get<0>(std::move(v)) == &x);
  137. }
  138. {
  139. using V = std::variant<const int &>;
  140. int x = 42;
  141. V v(x);
  142. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), const int &);
  143. assert(&std::get<0>(std::move(v)) == &x);
  144. }
  145. {
  146. using V = std::variant<int &&>;
  147. int x = 42;
  148. V v(std::move(x));
  149. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), int &&);
  150. int &&xref = std::get<0>(std::move(v));
  151. assert(&xref == &x);
  152. }
  153. {
  154. using V = std::variant<const int &&>;
  155. int x = 42;
  156. V v(std::move(x));
  157. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), const int &&);
  158. const int &&xref = std::get<0>(std::move(v));
  159. assert(&xref == &x);
  160. }
  161. #endif
  162. }
  163. void test_const_rvalue_get() {
  164. {
  165. using V = std::variant<int>;
  166. const V v(42);
  167. ASSERT_NOT_NOEXCEPT(std::get<0>(std::move(v)));
  168. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), const int &&);
  169. assert(std::get<0>(std::move(v)) == 42);
  170. }
  171. {
  172. using V = std::variant<int, long>;
  173. const V v(42l);
  174. ASSERT_SAME_TYPE(decltype(std::get<1>(std::move(v))), const long &&);
  175. assert(std::get<1>(std::move(v)) == 42);
  176. }
  177. // FIXME: Remove these once reference support is reinstated
  178. #if !defined(TEST_VARIANT_HAS_NO_REFERENCES)
  179. {
  180. using V = std::variant<int &>;
  181. int x = 42;
  182. const V v(x);
  183. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), int &);
  184. assert(&std::get<0>(std::move(v)) == &x);
  185. }
  186. {
  187. using V = std::variant<const int &>;
  188. int x = 42;
  189. const V v(x);
  190. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), const int &);
  191. assert(&std::get<0>(std::move(v)) == &x);
  192. }
  193. {
  194. using V = std::variant<int &&>;
  195. int x = 42;
  196. const V v(std::move(x));
  197. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), int &&);
  198. int &&xref = std::get<0>(std::move(v));
  199. assert(&xref == &x);
  200. }
  201. {
  202. using V = std::variant<const int &&>;
  203. int x = 42;
  204. const V v(std::move(x));
  205. ASSERT_SAME_TYPE(decltype(std::get<0>(std::move(v))), const int &&);
  206. const int &&xref = std::get<0>(std::move(v));
  207. assert(&xref == &x);
  208. }
  209. #endif
  210. }
  211. template <std::size_t I> using Idx = std::integral_constant<size_t, I>;
  212. void test_throws_for_all_value_categories() {
  213. #ifndef TEST_HAS_NO_EXCEPTIONS
  214. using V = std::variant<int, long>;
  215. V v0(42);
  216. const V &cv0 = v0;
  217. assert(v0.index() == 0);
  218. V v1(42l);
  219. const V &cv1 = v1;
  220. assert(v1.index() == 1);
  221. std::integral_constant<size_t, 0> zero;
  222. std::integral_constant<size_t, 1> one;
  223. auto test = [](auto idx, auto &&v) {
  224. using Idx = decltype(idx);
  225. try {
  226. std::get<Idx::value>(std::forward<decltype(v)>(v));
  227. } catch (std::bad_variant_access const &) {
  228. return true;
  229. } catch (...) { /* ... */
  230. }
  231. return false;
  232. };
  233. { // lvalue test cases
  234. assert(test(one, v0));
  235. assert(test(zero, v1));
  236. }
  237. { // const lvalue test cases
  238. assert(test(one, cv0));
  239. assert(test(zero, cv1));
  240. }
  241. { // rvalue test cases
  242. assert(test(one, std::move(v0)));
  243. assert(test(zero, std::move(v1)));
  244. }
  245. { // const rvalue test cases
  246. assert(test(one, std::move(cv0)));
  247. assert(test(zero, std::move(cv1)));
  248. }
  249. #endif
  250. }
  251. int main() {
  252. test_const_lvalue_get();
  253. test_lvalue_get();
  254. test_rvalue_get();
  255. test_const_rvalue_get();
  256. test_throws_for_all_value_categories();
  257. }