1 | <?xml version="1.0" encoding="utf-8" ?> |
---|
2 | <section id="variant.concepts"> |
---|
3 | <title>Concepts</title> |
---|
4 | |
---|
5 | <using-namespace name="boost"/> |
---|
6 | |
---|
7 | <section id="variant.concepts.bounded-type"> |
---|
8 | <title><emphasis>BoundedType</emphasis></title> |
---|
9 | |
---|
10 | <para>The requirements on a <emphasis role="bold">bounded type</emphasis> |
---|
11 | are as follows:</para> |
---|
12 | |
---|
13 | <itemizedlist> |
---|
14 | <listitem><conceptname>CopyConstructible</conceptname> [20.1.3].</listitem> |
---|
15 | <listitem>Destructor upholds the no-throw exception-safety |
---|
16 | guarantee.</listitem> |
---|
17 | <listitem>Complete at the point of <code>variant</code> template |
---|
18 | instantiation. (See |
---|
19 | <code><classname>boost::recursive_wrapper</classname><T></code> |
---|
20 | for a type wrapper that accepts incomplete types to enable recursive |
---|
21 | <code>variant</code> types.)</listitem> |
---|
22 | </itemizedlist> |
---|
23 | |
---|
24 | <para>Every type specified as a template argument to |
---|
25 | <code><classname>variant</classname></code> must at minimum fulfill the |
---|
26 | above requirements. In addition, certain features of <code>variant</code> |
---|
27 | are available only if its bounded types meet the requirements of these |
---|
28 | following additional concepts:</para> |
---|
29 | |
---|
30 | <itemizedlist> |
---|
31 | <listitem><conceptname>Assignable</conceptname>: |
---|
32 | <code>variant</code> is itself <emphasis>Assignable</emphasis> if and |
---|
33 | only if every one of its bounded types meets the requirements of the |
---|
34 | concept. (Note that top-level <code>const</code>-qualified types and |
---|
35 | reference types do <emphasis>not</emphasis> meet these |
---|
36 | requirements.)</listitem> |
---|
37 | <listitem><conceptname>DefaultConstructible</conceptname> [20.1.4]: |
---|
38 | <code>variant</code> is itself |
---|
39 | <conceptname>DefaultConstructible</conceptname> if and only if its first |
---|
40 | bounded type (i.e., <code>T1</code>) meets the requirements of the |
---|
41 | concept.</listitem> |
---|
42 | <listitem><conceptname>EqualityComparable</conceptname>: |
---|
43 | <code>variant</code> is itself <conceptname>EqualityComparable</conceptname> |
---|
44 | if and only if every one of its bounded types meets the requirements |
---|
45 | of the concept.</listitem> |
---|
46 | <listitem><conceptname>LessThanComparable</conceptname>: |
---|
47 | <code>variant</code> is itself <conceptname>LessThanComparable</conceptname> |
---|
48 | if and only if every one of its bounded types meets the requirements |
---|
49 | of the concept.</listitem> |
---|
50 | <listitem><link linkend="variant.concepts.output-streamable"><emphasis>OutputStreamable</emphasis></link>: |
---|
51 | <code>variant</code> is itself <emphasis>OutputStreamable</emphasis> |
---|
52 | if and only if every one of its bounded types meets the requirements |
---|
53 | of the concept.</listitem> |
---|
54 | </itemizedlist> |
---|
55 | </section> |
---|
56 | |
---|
57 | <section id="variant.concepts.static-visitor"> |
---|
58 | <title><emphasis>StaticVisitor</emphasis></title> |
---|
59 | |
---|
60 | <para>The requirements on a <emphasis role="bold">static |
---|
61 | visitor</emphasis> of a type <code>T</code> are as follows:</para> |
---|
62 | |
---|
63 | <itemizedlist> |
---|
64 | <listitem>Must allow invocation as a function by overloading |
---|
65 | <code>operator()</code>, unambiguously accepting any value of type |
---|
66 | <code>T</code>.</listitem> |
---|
67 | <listitem>Must expose inner type <code>result_type</code>. (See |
---|
68 | <code><functionname>boost::visitor_ptr</functionname></code> for a |
---|
69 | solution to using functions as visitors.)</listitem> |
---|
70 | <listitem>If <code>result_type</code> is not <code>void</code>, then |
---|
71 | each operation of the function object must return a value implicitly |
---|
72 | convertible to <code>result_type</code>.</listitem> |
---|
73 | </itemizedlist> |
---|
74 | |
---|
75 | <section id="variant.concepts.static-visitor.examples"> |
---|
76 | <title>Examples</title> |
---|
77 | |
---|
78 | <para>The following class satisfies the requirements of a static visitor |
---|
79 | of several types (i.e., explicitly: <code>int</code> and |
---|
80 | <code>std::string</code>; or, e.g., implicitly: <code>short</code> and |
---|
81 | <code>const char *</code>; etc.):</para> |
---|
82 | |
---|
83 | <programlisting>class my_visitor |
---|
84 | : public <classname>boost::static_visitor</classname><int> |
---|
85 | { |
---|
86 | public: |
---|
87 | |
---|
88 | int operator()(int i) |
---|
89 | { |
---|
90 | return i * 2; |
---|
91 | } |
---|
92 | |
---|
93 | int operator()(const std::string& s) |
---|
94 | { |
---|
95 | return s.length(); |
---|
96 | } |
---|
97 | |
---|
98 | };</programlisting> |
---|
99 | |
---|
100 | <para>Another example is the following class, whose function-call |
---|
101 | operator is a member template, allowing it to operate on values of many |
---|
102 | types. Thus, the following class is a visitor of any type that supports |
---|
103 | streaming output (e.g., <code>int</code>, <code>double</code>, |
---|
104 | <code>std::string</code>, etc.):</para> |
---|
105 | |
---|
106 | <programlisting>class printer |
---|
107 | : public <classname>boost::static_visitor</classname><> |
---|
108 | { |
---|
109 | template <typename T> |
---|
110 | void operator()(const T& t) |
---|
111 | { |
---|
112 | std::cout << t << std::endl; |
---|
113 | } |
---|
114 | };</programlisting> |
---|
115 | |
---|
116 | </section> |
---|
117 | </section> |
---|
118 | |
---|
119 | <section id="variant.concepts.output-streamable"> |
---|
120 | <title><emphasis>OutputStreamable</emphasis></title> |
---|
121 | |
---|
122 | <para>The requirements on an <emphasis role="bold">output |
---|
123 | streamable</emphasis> type <code>T</code> are as follows:</para> |
---|
124 | |
---|
125 | <itemizedlist> |
---|
126 | <listitem>For any object <code>t</code> of type <code>T</code>, |
---|
127 | <code>std::cout << t</code> must be a valid |
---|
128 | expression.</listitem> |
---|
129 | </itemizedlist> |
---|
130 | </section> |
---|
131 | |
---|
132 | </section> |
---|