From Jason Turner

[meta.reflection.substitute]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmpb20g4jdg/{from.md → to.md} +79 -0
tmp/tmpb20g4jdg/{from.md → to.md} RENAMED
@@ -0,0 +1,79 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ### Reflection substitution <a id="meta.reflection.substitute">[[meta.reflection.substitute]]</a>
2
+
3
+ ``` cpp
4
+ template<class R>
5
+ concept reflection_range =
6
+ ranges::input_range<R> &&
7
+ same_as<ranges::range_value_t<R>, info> &&
8
+ same_as<remove_cvref_t<ranges::range_reference_t<R>>, info>;
9
+
10
+ template<reflection_range R = initializer_list<info>>
11
+ consteval bool can_substitute(info templ, R&& arguments);
12
+ ```
13
+
14
+ Let `Z` be the template represented by `templ` and let `Args...` be a
15
+ sequence of prvalue constant expressions that compute the reflections
16
+ held by the elements of `arguments`, in order.
17
+
18
+ *Returns:* `true` if `Z<[:Args:]...>` is a valid
19
+ *template-id*[[temp.names]] that does not name a function whose type
20
+ contains an undeduced placeholder type. Otherwise, `false`.
21
+
22
+ *Throws:* `meta::exception` unless `templ` represents a template, and
23
+ every reflection in `arguments` represents a construct usable as a
24
+ template argument [[temp.arg]].
25
+
26
+ [*Note 1*: If forming `Z<[:Args:]...>` leads to a failure outside of
27
+ the immediate context, the program is ill-formed. — *end note*]
28
+
29
+ ``` cpp
30
+ template<reflection_range R = initializer_list<info>>
31
+ consteval info substitute(info templ, R&& arguments);
32
+ ```
33
+
34
+ Let `Z` be the template represented by `templ` and let `Args...` be a
35
+ sequence of prvalue constant expressions that compute the reflections
36
+ held by the elements of `arguments`, in order.
37
+
38
+ *Returns:* .
39
+
40
+ *Throws:* `meta::exception` unless `can_substitute(templ, arguments)` is
41
+ `true`.
42
+
43
+ [*Note 2*: If forming `Z<[:Args:]...>` leads to a failure outside of
44
+ the immediate context, the program is ill-formed. — *end note*]
45
+
46
+ [*Example 1*:
47
+
48
+ ``` cpp
49
+ template<class T>
50
+ auto fn1();
51
+
52
+ static_assert(!can_substitute(^^fn1, {^^int})); // OK
53
+ constexpr info r1 = substitute(^^fn1, {^^int}); // error: fn1<int> contains an undeduced
54
+ // placeholder type for its return type
55
+
56
+ template<class T>
57
+ auto fn2() {
58
+ static_assert(^^T != ^^int); // static assertion failed during instantiation of fn2<int>
59
+ return 0;
60
+ }
61
+
62
+ constexpr bool r2 = can_substitute(^^fn2, {^^int}); // error: instantiation of body of fn2<int>
63
+ // is needed to deduce return type
64
+ ```
65
+
66
+ — *end example*]
67
+
68
+ [*Example 2*:
69
+
70
+ ``` cpp
71
+ consteval info to_integral_constant(unsigned i) {
72
+ return substitute(^^integral_constant, {^^unsigned, reflect_constant(i)});
73
+ }
74
+ constexpr info r = to_integral_constant(2); // OK, r represents the type
75
+ // integral_constant<unsigned, 2>
76
+ ```
77
+
78
+ — *end example*]
79
+