@@ -272,57 +272,100 @@ class Comparable {
272
272
friend bool operator ==(const Comparable& lhs, long long rhs) { return comparable_data[lhs.index_ ] == rhs; }
273
273
};
274
274
275
- void test_deque () {
276
- { // empty deque
277
- std::deque<int > data;
278
- assert (std::ranges::find (data, 4 ) == data.end ());
279
- assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end ());
280
- }
281
-
282
- { // single element - match
283
- std::deque<int > data = {4 };
284
- assert (std::ranges::find (data, 4 ) == data.begin ());
285
- assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.begin ());
286
- }
287
-
288
- { // single element - no match
289
- std::deque<int > data = {3 };
290
- assert (std::ranges::find (data, 4 ) == data.end ());
291
- assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end ());
292
- }
293
-
294
- // many elements
295
- for (auto size : {2 , 3 , 1023 , 1024 , 1025 , 2047 , 2048 , 2049 }) {
296
- { // last element match
275
+ void test_segmented_iterator_types () {
276
+ // Test the optimized find algorithm for types that implement the segment iterator trait
277
+ // deque
278
+ {
279
+ { // empty deque
297
280
std::deque<int > data;
298
- data.resize (size);
299
- std::fill (data.begin (), data.end (), 3 );
300
- data[size - 1 ] = 4 ;
301
- assert (std::ranges::find (data, 4 ) == data.end () - 1 );
302
- assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end () - 1 );
281
+ assert (std::ranges::find (data, 4 ) == data.end ());
282
+ assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end ());
303
283
}
304
284
305
- { // second-last element match
306
- std::deque<int > data;
307
- data.resize (size);
308
- std::fill (data.begin (), data.end (), 3 );
309
- data[size - 2 ] = 4 ;
310
- assert (std::ranges::find (data, 4 ) == data.end () - 2 );
311
- assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end () - 2 );
285
+ { // single element - match
286
+ std::deque<int > data = {4 };
287
+ assert (std::ranges::find (data, 4 ) == data.begin ());
288
+ assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.begin ());
312
289
}
313
290
314
- { // no match
315
- std::deque<int > data;
316
- data.resize (size);
317
- std::fill (data.begin (), data.end (), 3 );
291
+ { // single element - no match
292
+ std::deque<int > data = {3 };
318
293
assert (std::ranges::find (data, 4 ) == data.end ());
319
294
assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end ());
320
295
}
296
+
297
+ // many elements
298
+ for (auto size : {2 , 3 , 1023 , 1024 , 1025 , 2047 , 2048 , 2049 }) {
299
+ { // last element match
300
+ std::deque<int > data;
301
+ data.resize (size);
302
+ std::fill (data.begin (), data.end (), 3 );
303
+ data[size - 1 ] = 4 ;
304
+ assert (std::ranges::find (data, 4 ) == data.end () - 1 );
305
+ assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end () - 1 );
306
+ }
307
+
308
+ { // second-last element match
309
+ std::deque<int > data;
310
+ data.resize (size);
311
+ std::fill (data.begin (), data.end (), 3 );
312
+ data[size - 2 ] = 4 ;
313
+ assert (std::ranges::find (data, 4 ) == data.end () - 2 );
314
+ assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end () - 2 );
315
+ }
316
+
317
+ { // no match
318
+ std::deque<int > data;
319
+ data.resize (size);
320
+ std::fill (data.begin (), data.end (), 3 );
321
+ assert (std::ranges::find (data, 4 ) == data.end ());
322
+ assert (std::ranges::find (data.begin (), data.end (), 4 ) == data.end ());
323
+ }
324
+ }
325
+ }
326
+ // join_view ranges adaptor
327
+ {
328
+ { // single element - match
329
+ int data[1 ][1 ] = {{4 }};
330
+ auto joined = std::views::join (data);
331
+ assert (std::ranges::find (joined, 4 ) == std::ranges::begin (joined));
332
+ }
333
+ { // single element - no match
334
+ // (reproducer for https://llvm.org/PR158279, where the iterator would never reach the end sentinel)
335
+ int data[1 ][1 ] = {{3 }};
336
+ auto joined = std::views::join (data);
337
+ assert (std::ranges::find (joined, 4 ) == std::ranges::end (joined));
338
+ }
339
+ { // several sub-arrays of size 1 - match
340
+ int data[3 ][1 ] = {{0 }, {4 }, {0 }};
341
+ auto joined = std::views::join (data);
342
+ assert (std::ranges::find (joined, 4 ) == std::next (std::ranges::begin (joined)));
343
+ }
344
+ { // several sub-arrays of size 2 - match in second element of an array
345
+ int data[3 ][2 ] = {{0 , 0 }, {0 , 4 }, {0 , 0 }};
346
+ auto joined = std::views::join (data);
347
+ assert (std::ranges::find (joined, 4 ) == std::ranges::next (std::ranges::begin (joined), 3 ));
348
+ }
349
+ { // vector of empty vectors
350
+ std::vector<std::vector<int >> data = {{}, {}};
351
+ auto joined = std::views::join (data);
352
+ assert (std::ranges::find (joined, 4 ) == std::ranges::end (joined));
353
+ }
354
+ { // vector of variably sized vectors - match
355
+ std::vector<std::vector<int >> data = {{}, {}, {3 , 4 }, {}, {}};
356
+ auto joined = std::views::join (data);
357
+ assert (std::ranges::find (joined, 4 ) == std::ranges::next (std::ranges::begin (joined)));
358
+ }
359
+ { // vector of variably sized vectors - no match
360
+ std::vector<std::vector<int >> data = {{}, {}, {3 , 5 }, {}, {}};
361
+ auto joined = std::views::join (data);
362
+ assert (std::ranges::find (joined, 4 ) == std::ranges::end (joined));
363
+ }
321
364
}
322
365
}
323
366
324
367
int main (int , char **) {
325
- test_deque ();
368
+ test_segmented_iterator_types ();
326
369
test ();
327
370
static_assert (test ());
328
371
0 commit comments