Lumiera 0.pre.04~rc.1
»edit your freedom«
Loading...
Searching...
No Matches
variadic-argument-picker-test.cpp
Go to the documentation of this file.
1/*
2 VariadicArgumentPicker(Test) - access individual arguments from a variadic template
3
4 Copyright (C)
5 2008, Hermann Vosseler <Ichthyostega@web.de>
6
7  **Lumiera** is free software; you can redistribute it and/or modify it
8  under the terms of the GNU General Public License as published by the
9  Free Software Foundation; either version 2 of the License, or (at your
10  option) any later version. See the file COPYING for further details.
11
12* *****************************************************************/
13
14
37#include "lib/test/run.hpp"
39#include "lib/format-string.hpp"
40#include "lib/format-cout.hpp"
41#include "lib/format-util.hpp"
42
43#include <utility>
44
45using util::_Fmt;
46using util::join;
47using util::toString;
48using std::forward;
49using std::string;
50
51
52namespace lib {
53namespace meta {
54namespace test {
55
56
57 namespace { // test data
58
59 template<int n>
60 struct N
61 {
63 static int instanceCnt;
64
65 N (uint x = rani(1 + abs(n)))
66 : i_{x}
67 {
68 ++instanceCnt;
69 }
71 {
72 --instanceCnt;
73 }
74 N (N const& r)
75 : i_{r.i_}
76 {
77 ++instanceCnt;
78 }
79 N (N&& rr)
80 {
81 std::swap (i_, rr.i_);
82 ++instanceCnt;
83 }
84
85 // instanceCnt remains same...
86 N& operator= (N const&) = default;
87 N& operator= (N&&) = default;
88
89 operator string() const
90 {
91 static _Fmt format{"%s──%s─"};
92 return format % typeStr(*this) % i_;
93 }
94 friend bool operator== (N const& l, N const& r) { return l.i_ == r.i_; }
95 friend bool operator!= (N const& l, N const& r) { return l.i_ != r.i_; }
96 };
97
98 template<int n>
99 int N<n>::instanceCnt = 0;
100
101
105 template<class...ARGS>
106 string
107 fun (ARGS&& ...args)
108 {
109 static _Fmt format{"%2d╎%s┤"};
110 return format % sizeof...(ARGS) % join({toString(args)...}, "┼");
111 }
112 } // (End) test data
113
114
115
116
117
118
119 /****************************************************************************/
125 class VariadicArgumentPicker_test : public Test
126 {
127 virtual void
128 run (Arg)
129 {
130 seedRand();
132 check_pickArg ();
135
136 CHECK (0 == N<0>::instanceCnt);
137 CHECK (0 == N<1>::instanceCnt);
138 CHECK (0 == N<2>::instanceCnt);
139 CHECK (0 == N<3>::instanceCnt);
140 }
141
142
143 void
145 {
146 CHECK (0 == N<0>::instanceCnt);
147 CHECK (0 == N<1>::instanceCnt);
148 CHECK (0 == N<2>::instanceCnt);
149 CHECK (0 == N<3>::instanceCnt);
150 {
151 N<1> n1;
152 N<2> n2;
153 N<3> n3;
154 N<3> nn{n3};
155 cout << fun (n1,n2,n3,nn) << endl;
156
157 CHECK (0 == N<0>::instanceCnt);
158 CHECK (1 == N<1>::instanceCnt);
159 CHECK (1 == N<2>::instanceCnt);
160 CHECK (2 == N<3>::instanceCnt);
161
162 }
163 CHECK (0 == N<0>::instanceCnt);
164 CHECK (0 == N<1>::instanceCnt);
165 CHECK (0 == N<2>::instanceCnt);
166 CHECK (0 == N<3>::instanceCnt);
167 }
168
169
170 void
172 {
173 N<1> n1;
174 N<2> n2;
175 N<3> n3;
176
177 CHECK (n1 == pickArg<0> (n1,n2,n3));
178 CHECK (n2 == pickArg<1> (n1,n2,n3));
179 CHECK (n3 == pickArg<2> (n1,n2,n3));
180
181 // does not compile...
182// pickArg<3> (n1,n2,n3);
183
184 N<0> n0{42};
185 CHECK (n0 != pickArg<0> (N<0>{23}));
186 CHECK (n0 == pickArg<0> (N<0>{n0}));
187 }
188
189
190 void
192 {
193 N<1> n1;
194 N<2> n2;
195 using N0 = N<0>;
196
197 CHECK (1 == (pickInit<0,int> (1,2) ));
198 CHECK (2 == (pickInit<1,int> (1,2) ));
199 CHECK (0 == (pickInit<2,int> (1,2) ));
200
201 CHECK (n1 == (pickInit<0,N0> (n1,n2) ));
202 CHECK (n2 == (pickInit<1,N0> (n1,n2) ));
203
204 CHECK ("N<0>" == typeStr(pickInit<3,N0> (n1,n2)));
205 CHECK ("N<0>" == typeStr(pickInit<3,N0> (1,"2")));
206 CHECK ("N<0>" == typeStr(pickInit<3,N0> ()));
207 }
208
209
210
228 template<class...ARGS, size_t...idx>
229 static auto
231 {
232 return fun (pickArg<idx> (forward<ARGS>(args)...) ...);
233 }
234
236 void
238 {
239 N<0> n0;
240 N<1> n1;
241 N<2> n2;
242 N<3> n3;
243
244 cout << fun (n0,n1,n2,n3) << endl;
245
246 using Backwards = BuildIndexSeq<4>::Descending; // 3,2,1,0
247 using Back2 = BuildIndexSeq<2>::Descending; // 1,0
248 using After2 = BuildIndexSeq<4>::After<2>; // 2,3
249
250 cout << call_with_reversed_arguments (Backwards(), n0,n1,n2,n3) <<endl;
251 cout << call_with_reversed_arguments (Back2() , n0,n1,n2,n3) <<endl;
252 cout << call_with_reversed_arguments (After2() , n0,n1,n2,n3) <<endl;
253 }
254 };
255
256
259
260
261
262}}} // namespace lib::meta::test
static auto call_with_reversed_arguments(IndexSeq< idx... >, ARGS &&...args)
Demonstration of argument manipulation through metaprogramming.
A front-end for using printf-style formatting.
Automatically use custom string conversion in C++ stream output.
Front-end for printf-style string template interpolation.
Collection of small helpers and convenience shortcuts for diagnostics & formatting.
unsigned int uint
Definition integral.hpp:29
std::string typeStr(TY const *obj=nullptr) noexcept
failsafe human readable type display
enable_if_c< Cond::value, T >::type enable_if
SFINAE helper to control the visibility of specialisations and overloads.
Definition meta/util.hpp:87
BuildIndexSeq< n-1 >::Descending::template PrependElm< n-1 > Descending
BuildIndexSeq<(n >c)? n-c :0 >::template OffsetBy< c > After
Implementation namespace for support and library code.
int rani(uint bound=_iBOUND())
Definition random.hpp:135
Test runner and basic definitions for tests.
std::string toString(TY const &val) noexcept
get some string representation of any object, reliably.
string join(COLL &&coll, string const &delim=", ")
enumerate a collection's contents, separated by delimiter.
Simplistic test class runner.
#define LAUNCHER(_TEST_CLASS_, _GROUPS_)
Definition run.hpp:116
Metaprogramming with type sequences based on variadic template parameters.