1 //===----------------------------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 // UNSUPPORTED: c++03, c++11, c++14, c++17
10 // UNSUPPORTED: libcpp-no-concepts
11 
12 // template<class T, class U>
13 // concept regular_invocable;
14 
15 #include <chrono>
16 #include <concepts>
17 #include <memory>
18 #include <random>
19 #include <type_traits>
20 
21 template <class R, class... Args>
22 constexpr bool check_invocable() {
23   constexpr bool result = std::regular_invocable<R(Args...), Args...>;
24   static_assert(std::regular_invocable<R(Args...) noexcept, Args...> == result);
25   static_assert(std::regular_invocable<R (*)(Args...), Args...> == result);
26   static_assert(std::regular_invocable<R (*)(Args...) noexcept, Args...> ==
27                 result);
28   static_assert(std::regular_invocable<R (&)(Args...), Args...> == result);
29   static_assert(std::regular_invocable<R (&)(Args...) noexcept, Args...> ==
30                 result);
31 
32   return result;
33 }
34 
35 static_assert(check_invocable<void>());
36 static_assert(check_invocable<void, int>());
37 static_assert(check_invocable<void, int&>());
38 static_assert(check_invocable<void, int*, double>());
39 static_assert(check_invocable<int>());
40 static_assert(check_invocable<int, int[]>());
41 
42 struct S;
43 static_assert(check_invocable<int, int S::*, std::nullptr_t>());
44 static_assert(check_invocable<int, int (S::*)(), int (S::*)(int), int>());
45 static_assert(std::regular_invocable<void (*)(int const&), int&>);
46 static_assert(std::regular_invocable<void (*)(int const&), int&&>);
47 static_assert(std::regular_invocable<void (*)(int volatile&), int&>);
48 static_assert(std::regular_invocable<void (*)(int const volatile&), int&>);
49 
50 static_assert(!std::regular_invocable<void(), int>);
51 static_assert(!std::regular_invocable<void(int)>);
52 static_assert(!std::regular_invocable<void(int*), double*>);
53 static_assert(!std::regular_invocable<void (*)(int&), double*>);
54 static_assert(std::regular_invocable<int S::*, std::unique_ptr<S> >);
55 static_assert(std::regular_invocable<int S::*, std::shared_ptr<S> >);
56 static_assert(!std::regular_invocable<void (*)(int&&), int&>);
57 static_assert(!std::regular_invocable<void (*)(int&&), int const&>);
58 
59 static_assert(!std::regular_invocable<void>);
60 static_assert(!std::regular_invocable<void*>);
61 static_assert(!std::regular_invocable<int>);
62 static_assert(!std::regular_invocable<int&>);
63 static_assert(!std::regular_invocable<int&&>);
64 
65 namespace function_objects {
66 struct function_object {
67   void operator()();
68 };
69 static_assert(std::regular_invocable<function_object>);
70 static_assert(!std::regular_invocable<function_object const>);
71 static_assert(!std::regular_invocable<function_object volatile>);
72 static_assert(!std::regular_invocable<function_object const volatile>);
73 static_assert(std::regular_invocable<function_object&>);
74 static_assert(!std::regular_invocable<function_object const&>);
75 static_assert(!std::regular_invocable<function_object volatile&>);
76 static_assert(!std::regular_invocable<function_object const volatile&>);
77 
78 struct const_function_object {
79   void operator()(int) const;
80 };
81 static_assert(std::regular_invocable<const_function_object, int>);
82 static_assert(std::regular_invocable<const_function_object const, int>);
83 static_assert(!std::regular_invocable<const_function_object volatile, int>);
84 static_assert(
85     !std::regular_invocable<const_function_object const volatile, int>);
86 static_assert(std::regular_invocable<const_function_object&, int>);
87 static_assert(std::regular_invocable<const_function_object const&, int>);
88 static_assert(!std::regular_invocable<const_function_object volatile&, int>);
89 static_assert(
90     !std::regular_invocable<const_function_object const volatile&, int>);
91 
92 struct volatile_function_object {
93   void operator()(int, int) volatile;
94 };
95 static_assert(std::regular_invocable<volatile_function_object, int, int>);
96 static_assert(
97     !std::regular_invocable<volatile_function_object const, int, int>);
98 static_assert(
99     std::regular_invocable<volatile_function_object volatile, int, int>);
100 static_assert(
101     !std::regular_invocable<volatile_function_object const volatile, int, int>);
102 static_assert(std::regular_invocable<volatile_function_object&, int, int>);
103 static_assert(
104     !std::regular_invocable<volatile_function_object const&, int, int>);
105 static_assert(
106     std::regular_invocable<volatile_function_object volatile&, int, int>);
107 static_assert(!std::regular_invocable<volatile_function_object const volatile&,
108                                       int, int>);
109 
110 struct cv_function_object {
111   void operator()(int[]) const volatile;
112 };
113 static_assert(std::regular_invocable<cv_function_object, int*>);
114 static_assert(std::regular_invocable<cv_function_object const, int*>);
115 static_assert(std::regular_invocable<cv_function_object volatile, int*>);
116 static_assert(std::regular_invocable<cv_function_object const volatile, int*>);
117 static_assert(std::regular_invocable<cv_function_object&, int*>);
118 static_assert(std::regular_invocable<cv_function_object const&, int*>);
119 static_assert(std::regular_invocable<cv_function_object volatile&, int*>);
120 static_assert(std::regular_invocable<cv_function_object const volatile&, int*>);
121 
122 struct lvalue_function_object {
123   void operator()() &;
124 };
125 static_assert(!std::regular_invocable<lvalue_function_object>);
126 static_assert(!std::regular_invocable<lvalue_function_object const>);
127 static_assert(!std::regular_invocable<lvalue_function_object volatile>);
128 static_assert(!std::regular_invocable<lvalue_function_object const volatile>);
129 static_assert(std::regular_invocable<lvalue_function_object&>);
130 static_assert(!std::regular_invocable<lvalue_function_object const&>);
131 static_assert(!std::regular_invocable<lvalue_function_object volatile&>);
132 static_assert(!std::regular_invocable<lvalue_function_object const volatile&>);
133 
134 struct lvalue_const_function_object {
135   void operator()(int) const&;
136 };
137 static_assert(std::regular_invocable<lvalue_const_function_object, int>);
138 static_assert(std::regular_invocable<lvalue_const_function_object const, int>);
139 static_assert(
140     !std::regular_invocable<lvalue_const_function_object volatile, int>);
141 static_assert(
142     !std::regular_invocable<lvalue_const_function_object const volatile, int>);
143 static_assert(std::regular_invocable<lvalue_const_function_object&, int>);
144 static_assert(std::regular_invocable<lvalue_const_function_object const&, int>);
145 static_assert(
146     !std::regular_invocable<lvalue_const_function_object volatile&, int>);
147 static_assert(
148     !std::regular_invocable<lvalue_const_function_object const volatile&, int>);
149 
150 struct lvalue_volatile_function_object {
151   void operator()(int, int) volatile&;
152 };
153 static_assert(
154     !std::regular_invocable<lvalue_volatile_function_object, int, int>);
155 static_assert(
156     !std::regular_invocable<lvalue_volatile_function_object const, int, int>);
157 static_assert(!std::regular_invocable<lvalue_volatile_function_object volatile,
158                                       int, int>);
159 static_assert(!std::regular_invocable<
160               lvalue_volatile_function_object const volatile, int, int>);
161 static_assert(
162     std::regular_invocable<lvalue_volatile_function_object&, int, int>);
163 static_assert(
164     !std::regular_invocable<lvalue_volatile_function_object const&, int, int>);
165 static_assert(std::regular_invocable<lvalue_volatile_function_object volatile&,
166                                      int, int>);
167 static_assert(!std::regular_invocable<
168               lvalue_volatile_function_object const volatile&, int, int>);
169 
170 struct lvalue_cv_function_object {
171   void operator()(int[]) const volatile&;
172 };
173 static_assert(!std::regular_invocable<lvalue_cv_function_object, int*>);
174 static_assert(!std::regular_invocable<lvalue_cv_function_object const, int*>);
175 static_assert(
176     !std::regular_invocable<lvalue_cv_function_object volatile, int*>);
177 static_assert(
178     !std::regular_invocable<lvalue_cv_function_object const volatile, int*>);
179 static_assert(std::regular_invocable<lvalue_cv_function_object&, int*>);
180 static_assert(std::regular_invocable<lvalue_cv_function_object const&, int*>);
181 static_assert(
182     std::regular_invocable<lvalue_cv_function_object volatile&, int*>);
183 static_assert(
184     std::regular_invocable<lvalue_cv_function_object const volatile&, int*>);
185 //
186 struct rvalue_function_object {
187   void operator()() &&;
188 };
189 static_assert(std::regular_invocable<rvalue_function_object>);
190 static_assert(!std::regular_invocable<rvalue_function_object const>);
191 static_assert(!std::regular_invocable<rvalue_function_object volatile>);
192 static_assert(!std::regular_invocable<rvalue_function_object const volatile>);
193 static_assert(!std::regular_invocable<rvalue_function_object&>);
194 static_assert(!std::regular_invocable<rvalue_function_object const&>);
195 static_assert(!std::regular_invocable<rvalue_function_object volatile&>);
196 static_assert(!std::regular_invocable<rvalue_function_object const volatile&>);
197 
198 struct rvalue_const_function_object {
199   void operator()(int) const&&;
200 };
201 static_assert(std::regular_invocable<rvalue_const_function_object, int>);
202 static_assert(std::regular_invocable<rvalue_const_function_object const, int>);
203 static_assert(
204     !std::regular_invocable<rvalue_const_function_object volatile, int>);
205 static_assert(
206     !std::regular_invocable<rvalue_const_function_object const volatile, int>);
207 static_assert(!std::regular_invocable<rvalue_const_function_object&, int>);
208 static_assert(
209     !std::regular_invocable<rvalue_const_function_object const&, int>);
210 static_assert(
211     !std::regular_invocable<rvalue_const_function_object volatile&, int>);
212 static_assert(
213     !std::regular_invocable<rvalue_const_function_object const volatile&, int>);
214 
215 struct rvalue_volatile_function_object {
216   void operator()(int, int) volatile&&;
217 };
218 static_assert(
219     std::regular_invocable<rvalue_volatile_function_object, int, int>);
220 static_assert(
221     !std::regular_invocable<rvalue_volatile_function_object const, int, int>);
222 static_assert(
223     std::regular_invocable<rvalue_volatile_function_object volatile, int, int>);
224 static_assert(!std::regular_invocable<
225               rvalue_volatile_function_object const volatile, int, int>);
226 static_assert(
227     !std::regular_invocable<rvalue_volatile_function_object&, int, int>);
228 static_assert(
229     !std::regular_invocable<rvalue_volatile_function_object const&, int, int>);
230 static_assert(!std::regular_invocable<rvalue_volatile_function_object volatile&,
231                                       int, int>);
232 static_assert(!std::regular_invocable<
233               rvalue_volatile_function_object const volatile&, int, int>);
234 
235 struct rvalue_cv_function_object {
236   void operator()(int[]) const volatile&&;
237 };
238 static_assert(std::regular_invocable<rvalue_cv_function_object, int*>);
239 static_assert(std::regular_invocable<rvalue_cv_function_object const, int*>);
240 static_assert(std::regular_invocable<rvalue_cv_function_object volatile, int*>);
241 static_assert(
242     std::regular_invocable<rvalue_cv_function_object const volatile, int*>);
243 static_assert(!std::regular_invocable<rvalue_cv_function_object&, int*>);
244 static_assert(!std::regular_invocable<rvalue_cv_function_object const&, int*>);
245 static_assert(
246     !std::regular_invocable<rvalue_cv_function_object volatile&, int*>);
247 static_assert(
248     !std::regular_invocable<rvalue_cv_function_object const volatile&, int*>);
249 
250 struct multiple_overloads {
251   struct A {};
252   struct B { B(int); };
253   struct AB : A, B {};
254   struct O {};
255   void operator()(A) const;
256   void operator()(B) const;
257 };
258 static_assert(std::regular_invocable<multiple_overloads, multiple_overloads::A>);
259 static_assert(std::regular_invocable<multiple_overloads, multiple_overloads::B>);
260 static_assert(std::regular_invocable<multiple_overloads, int>);
261 static_assert(!std::regular_invocable<multiple_overloads, multiple_overloads::AB>);
262 static_assert(!std::regular_invocable<multiple_overloads, multiple_overloads::O>);
263 } // namespace function_objects
264 
265 namespace pointer_to_member_functions {
266 // clang-format off
267   template<class Member, class T, class... Args>
268   constexpr bool check_member_is_invocable()
269   {
270     constexpr bool result = std::regular_invocable<Member, T, Args...>;
271     using uncv_t = std::remove_cvref_t<T>;
272     static_assert(std::regular_invocable<Member, uncv_t*, Args...> == result);
273     static_assert(std::regular_invocable<Member, std::unique_ptr<uncv_t>, Args...> == result);
274     static_assert(std::regular_invocable<Member, std::reference_wrapper<uncv_t>, Args...> == result);
275     static_assert(!std::regular_invocable<Member, std::nullptr_t, Args...>);
276     static_assert(!std::regular_invocable<Member, int, Args...>);
277     static_assert(!std::regular_invocable<Member, int*, Args...>);
278     static_assert(!std::regular_invocable<Member, double*, Args...>);
279     struct S2 {};
280     static_assert(!std::regular_invocable<Member, S2*, Args...>);
281     return result;
282   }
283 // clang-format on
284 
285 static_assert(check_member_is_invocable<int S::*, S>());
286 static_assert(std::regular_invocable<int S::*, S&>);
287 static_assert(std::regular_invocable<int S::*, S const&>);
288 static_assert(std::regular_invocable<int S::*, S volatile&>);
289 static_assert(std::regular_invocable<int S::*, S const volatile&>);
290 static_assert(std::regular_invocable<int S::*, S&&>);
291 static_assert(std::regular_invocable<int S::*, S const&&>);
292 static_assert(std::regular_invocable<int S::*, S volatile&&>);
293 static_assert(std::regular_invocable<int S::*, S const volatile&&>);
294 
295 static_assert(check_member_is_invocable<int (S::*)(int), S, int>());
296 static_assert(!check_member_is_invocable<int (S::*)(int), S>());
297 using unqualified = void (S::*)();
298 static_assert(std::regular_invocable<unqualified, S&>);
299 static_assert(!std::regular_invocable<unqualified, S const&>);
300 static_assert(!std::regular_invocable<unqualified, S volatile&>);
301 static_assert(!std::regular_invocable<unqualified, S const volatile&>);
302 static_assert(std::regular_invocable<unqualified, S&&>);
303 static_assert(!std::regular_invocable<unqualified, S const&&>);
304 static_assert(!std::regular_invocable<unqualified, S volatile&&>);
305 static_assert(!std::regular_invocable<unqualified, S const volatile&&>);
306 
307 static_assert(check_member_is_invocable<int (S::*)(double) const, S, double>());
308 using const_qualified = void (S::*)() const;
309 static_assert(std::regular_invocable<const_qualified, S&>);
310 static_assert(std::regular_invocable<const_qualified, S const&>);
311 static_assert(!std::regular_invocable<const_qualified, S volatile&>);
312 static_assert(!std::regular_invocable<const_qualified, S const volatile&>);
313 static_assert(std::regular_invocable<const_qualified, S&&>);
314 static_assert(std::regular_invocable<const_qualified, S const&&>);
315 static_assert(!std::regular_invocable<const_qualified, S volatile&&>);
316 static_assert(!std::regular_invocable<const_qualified, S const volatile&&>);
317 
318 static_assert(
319     check_member_is_invocable<int (S::*)(double[]) volatile, S, double*>());
320 using volatile_qualified = void (S::*)() volatile;
321 static_assert(std::regular_invocable<volatile_qualified, S&>);
322 static_assert(!std::regular_invocable<volatile_qualified, S const&>);
323 static_assert(std::regular_invocable<volatile_qualified, S volatile&>);
324 static_assert(!std::regular_invocable<volatile_qualified, S const volatile&>);
325 static_assert(std::regular_invocable<volatile_qualified, S&&>);
326 static_assert(!std::regular_invocable<volatile_qualified, S const&&>);
327 static_assert(std::regular_invocable<volatile_qualified, S volatile&&>);
328 static_assert(!std::regular_invocable<volatile_qualified, S const volatile&&>);
329 
330 static_assert(check_member_is_invocable<int (S::*)(int, S&) const volatile, S,
331                                         int, S&>());
332 using cv_qualified = void (S::*)() const volatile;
333 static_assert(std::regular_invocable<cv_qualified, S&>);
334 static_assert(std::regular_invocable<cv_qualified, S const&>);
335 static_assert(std::regular_invocable<cv_qualified, S volatile&>);
336 static_assert(std::regular_invocable<cv_qualified, S const volatile&>);
337 static_assert(std::regular_invocable<cv_qualified, S&&>);
338 static_assert(std::regular_invocable<cv_qualified, S const&&>);
339 static_assert(std::regular_invocable<cv_qualified, S volatile&&>);
340 static_assert(std::regular_invocable<cv_qualified, S const volatile&&>);
341 
342 static_assert(check_member_is_invocable<int (S::*)() &, S&>());
343 using lvalue_qualified = void (S::*)() &;
344 static_assert(std::regular_invocable<lvalue_qualified, S&>);
345 static_assert(!std::regular_invocable<lvalue_qualified, S const&>);
346 static_assert(!std::regular_invocable<lvalue_qualified, S volatile&>);
347 static_assert(!std::regular_invocable<lvalue_qualified, S const volatile&>);
348 static_assert(!std::regular_invocable<lvalue_qualified, S&&>);
349 static_assert(!std::regular_invocable<lvalue_qualified, S const&&>);
350 static_assert(!std::regular_invocable<lvalue_qualified, S volatile&&>);
351 static_assert(!std::regular_invocable<lvalue_qualified, S const volatile&&>);
352 
353 static_assert(check_member_is_invocable<int (S::*)() const&, S>());
354 using lvalue_const_qualified = void (S::*)() const&;
355 static_assert(std::regular_invocable<lvalue_const_qualified, S&>);
356 static_assert(std::regular_invocable<lvalue_const_qualified, S const&>);
357 static_assert(!std::regular_invocable<lvalue_const_qualified, S volatile&>);
358 static_assert(
359     !std::regular_invocable<lvalue_const_qualified, S const volatile&>);
360 static_assert(std::regular_invocable<lvalue_const_qualified, S&&>);
361 static_assert(std::regular_invocable<lvalue_const_qualified, S const&&>);
362 static_assert(!std::regular_invocable<lvalue_const_qualified, S volatile&&>);
363 static_assert(
364     !std::regular_invocable<lvalue_const_qualified, S const volatile&&>);
365 
366 static_assert(check_member_is_invocable<int (S::*)() volatile&, S&>());
367 using lvalue_volatile_qualified = void (S::*)() volatile&;
368 static_assert(std::regular_invocable<lvalue_volatile_qualified, S&>);
369 static_assert(!std::regular_invocable<lvalue_volatile_qualified, S const&>);
370 static_assert(std::regular_invocable<lvalue_volatile_qualified, S volatile&>);
371 static_assert(
372     !std::regular_invocable<lvalue_volatile_qualified, S const volatile&>);
373 static_assert(!std::regular_invocable<lvalue_volatile_qualified, S&&>);
374 static_assert(!std::regular_invocable<lvalue_volatile_qualified, S const&&>);
375 static_assert(!std::regular_invocable<lvalue_volatile_qualified, S volatile&&>);
376 static_assert(
377     !std::regular_invocable<lvalue_volatile_qualified, S const volatile&&>);
378 
379 static_assert(check_member_is_invocable<int (S::*)() const volatile&, S&>());
380 using lvalue_cv_qualified = void (S::*)() const volatile&;
381 static_assert(std::regular_invocable<lvalue_cv_qualified, S&>);
382 static_assert(std::regular_invocable<lvalue_cv_qualified, S const&>);
383 static_assert(std::regular_invocable<lvalue_cv_qualified, S volatile&>);
384 static_assert(std::regular_invocable<lvalue_cv_qualified, S const volatile&>);
385 static_assert(!std::regular_invocable<lvalue_cv_qualified, S&&>);
386 static_assert(!std::regular_invocable<lvalue_cv_qualified, S const&&>);
387 static_assert(!std::regular_invocable<lvalue_cv_qualified, S volatile&&>);
388 static_assert(!std::regular_invocable<lvalue_cv_qualified, S const volatile&&>);
389 
390 using rvalue_unqualified = void (S::*)() &&;
391 static_assert(!std::regular_invocable<rvalue_unqualified, S&>);
392 static_assert(!std::regular_invocable<rvalue_unqualified, S const&>);
393 static_assert(!std::regular_invocable<rvalue_unqualified, S volatile&>);
394 static_assert(!std::regular_invocable<rvalue_unqualified, S const volatile&>);
395 static_assert(std::regular_invocable<rvalue_unqualified, S&&>);
396 static_assert(!std::regular_invocable<rvalue_unqualified, S const&&>);
397 static_assert(!std::regular_invocable<rvalue_unqualified, S volatile&&>);
398 static_assert(!std::regular_invocable<rvalue_unqualified, S const volatile&&>);
399 
400 using rvalue_const_unqualified = void (S::*)() const&&;
401 static_assert(!std::regular_invocable<rvalue_const_unqualified, S&>);
402 static_assert(!std::regular_invocable<rvalue_const_unqualified, S const&>);
403 static_assert(!std::regular_invocable<rvalue_const_unqualified, S volatile&>);
404 static_assert(
405     !std::regular_invocable<rvalue_const_unqualified, S const volatile&>);
406 static_assert(std::regular_invocable<rvalue_const_unqualified, S&&>);
407 static_assert(std::regular_invocable<rvalue_const_unqualified, S const&&>);
408 static_assert(!std::regular_invocable<rvalue_const_unqualified, S volatile&&>);
409 static_assert(
410     !std::regular_invocable<rvalue_const_unqualified, S const volatile&&>);
411 
412 using rvalue_volatile_unqualified = void (S::*)() volatile&&;
413 static_assert(!std::regular_invocable<rvalue_volatile_unqualified, S&>);
414 static_assert(!std::regular_invocable<rvalue_volatile_unqualified, S const&>);
415 static_assert(
416     !std::regular_invocable<rvalue_volatile_unqualified, S volatile&>);
417 static_assert(
418     !std::regular_invocable<rvalue_volatile_unqualified, S const volatile&>);
419 static_assert(std::regular_invocable<rvalue_volatile_unqualified, S&&>);
420 static_assert(!std::regular_invocable<rvalue_volatile_unqualified, S const&&>);
421 static_assert(
422     std::regular_invocable<rvalue_volatile_unqualified, S volatile&&>);
423 static_assert(
424     !std::regular_invocable<rvalue_volatile_unqualified, S const volatile&&>);
425 
426 using rvalue_cv_unqualified = void (S::*)() const volatile&&;
427 static_assert(!std::regular_invocable<rvalue_cv_unqualified, S&>);
428 static_assert(!std::regular_invocable<rvalue_cv_unqualified, S const&>);
429 static_assert(!std::regular_invocable<rvalue_cv_unqualified, S volatile&>);
430 static_assert(
431     !std::regular_invocable<rvalue_cv_unqualified, S const volatile&>);
432 static_assert(std::regular_invocable<rvalue_cv_unqualified, S&&>);
433 static_assert(std::regular_invocable<rvalue_cv_unqualified, S const&&>);
434 static_assert(std::regular_invocable<rvalue_cv_unqualified, S volatile&&>);
435 static_assert(
436     std::regular_invocable<rvalue_cv_unqualified, S const volatile&&>);
437 } // namespace pointer_to_member_functions
438 
439 // Check the concept with closure types (and also check for subsumption)
440 template<class F, class... Args>
441 constexpr bool is_regular_invocable(F, Args&&...) {
442   return false;
443 }
444 
445 template<class F, class... Args>
446 requires std::invocable<F, Args...>
447 constexpr bool is_regular_invocable(F, Args&&...) {
448   return false;
449 }
450 
451 template<class F, class... Args>
452 requires std::regular_invocable<F, Args...> && true
453 constexpr bool is_regular_invocable(F, Args&&...) {
454   return true;
455 }
456 
457 static_assert(is_regular_invocable([] {}));
458 static_assert(is_regular_invocable([](int) {}, 0));
459 static_assert(is_regular_invocable([](int) {}, 0L));
460 static_assert(!is_regular_invocable([](int) {}, nullptr));
461 
462 int i = 0;
463 static_assert(is_regular_invocable([](int&) {}, i));
464