@@ -400,22 +400,85 @@ constexpr void check_required_span_size() {
400400}
401401
402402constexpr void check_is_exhaustive () {
403- { // Check exhaustive mappings (all possibilities)
404- using E = extents<int , 2 , 3 , 5 >;
405- assert ((layout_stride::mapping<E>{E{}, array{1 , 2 , 6 }}.is_exhaustive ()));
406- assert ((layout_stride::mapping<E>{E{}, array{1 , 10 , 2 }}.is_exhaustive ()));
407- assert ((layout_stride::mapping<E>{E{}, array{3 , 1 , 6 }}.is_exhaustive ()));
408- assert ((layout_stride::mapping<E>{E{}, array{15 , 1 , 3 }}.is_exhaustive ()));
409- assert ((layout_stride::mapping<E>{E{}, array{5 , 10 , 1 }}.is_exhaustive ()));
410- assert ((layout_stride::mapping<E>{E{}, array{15 , 5 , 1 }}.is_exhaustive ()));
411- }
412-
413- { // Check non-exhaustive mappings
414- using E = extents<int , 2 , 5 , 8 >;
415- assert ((!layout_stride::mapping<E>{E{}, array{1 , 2 , 12 }}.is_exhaustive ()));
416- assert ((!layout_stride::mapping<E>{E{}, array{8 , 18 , 1 }}.is_exhaustive ()));
417- assert ((!layout_stride::mapping<E>{E{}, array{5 , 1 , 12 }}.is_exhaustive ()));
418- }
403+ auto check = [](const auto & exts, const auto & strides, bool expected) {
404+ layout_stride::mapping m{exts, strides};
405+ assert (m.is_exhaustive () == expected);
406+ };
407+
408+ // rank() is equal to 0
409+ check (extents<int >{}, array<int , 0 >{}, true );
410+
411+ // rank() is equal to 1
412+ check (extents<int , 0 >{}, array{1 }, true );
413+ check (dextents<int , 1 >{0 }, array{2 }, false );
414+ check (extents<int , 1 >{}, array{3 }, false );
415+ check (dextents<int , 1 >{2 }, array{2 }, false );
416+ check (extents<int , 3 >{}, array{1 }, true );
417+ check (dextents<int , 1 >{4 }, array{1 }, true );
418+
419+ // rank() is equal to 2
420+ check (extents<int , 3 , 3 >{}, array{1 , 3 }, true );
421+ check (extents<int , dynamic_extent, 3 >{3 }, array{3 , 1 }, true );
422+ check (extents<int , 3 , dynamic_extent>{3 }, array{4 , 1 }, false );
423+ check (dextents<int , 2 >{3 , 3 }, array{3 , 1 }, true );
424+ check (extents<int , 4 , 5 >{}, array{5 , 1 }, true );
425+ check (extents<int , 6 , dynamic_extent>{5 }, array{1 , 6 }, true );
426+ check (extents<int , dynamic_extent, 7 >{5 }, array{1 , 8 }, false );
427+ check (dextents<int , 2 >{6 , 5 }, array{1 , 10 }, false );
428+ check (extents<int , 0 , 3 >{}, array{3 , 1 }, true );
429+ check (extents<int , 0 , 3 >{}, array{6 , 2 }, false );
430+ check (extents<int , dynamic_extent, 3 >{0 }, array{6 , 1 }, false );
431+ check (extents<int , 0 , dynamic_extent>{3 }, array{6 , 2 }, false );
432+ check (dextents<int , 2 >{0 , 3 }, array{7 , 2 }, false );
433+ check (extents<int , 0 , 0 >{}, array{1 , 1 }, false );
434+ check (extents<int , 0 , dynamic_extent>{0 , 0 }, array{1 , 1 }, false );
435+ check (dextents<int , 2 >{0 , 0 }, array{1 , 2 }, false );
436+ check (extents<int , 1 , dynamic_extent>{0 }, array{1 , 2 }, false );
437+
438+ // rank() is greater than 2
439+ check (extents<int , 2 , 3 , 5 >{}, array{1 , 2 , 6 }, true );
440+ check (extents<int , dynamic_extent, 3 , 5 >{2 }, array{1 , 10 , 2 }, true );
441+ check (extents<int , 2 , 3 , dynamic_extent>{5 }, array{3 , 1 , 6 }, true );
442+ check (extents<int , dynamic_extent, dynamic_extent, 5 >{2 , 3 }, array{15 , 1 , 3 }, true );
443+ check (extents<int , 2 , dynamic_extent, dynamic_extent>{3 , 5 }, array{5 , 10 , 1 }, true );
444+ check (dextents<int , 3 >{2 , 3 , 5 }, array{15 , 5 , 1 }, true );
445+ check (extents<int , 2 , 5 , 8 >{}, array{1 , 2 , 12 }, false );
446+ check (extents<int , 2 , dynamic_extent, 8 >{5 }, array{8 , 18 , 1 }, false );
447+ check (dextents<int , 3 >{2 , 5 , 8 }, array{5 , 1 , 12 }, false );
448+
449+ // rank() is greater than 2 and some extents are equal to 0
450+ check (extents<int , 2 , 0 , 7 >{}, array{7 , 14 , 1 }, true );
451+ check (extents<int , dynamic_extent, 0 , 7 >{2 }, array{1 , 14 , 2 }, true );
452+ check (extents<int , 2 , dynamic_extent, 7 >{0 }, array{14 , 28 , 1 }, false );
453+ check (extents<int , 2 , dynamic_extent, dynamic_extent>{0 , 7 }, array{1 , 2 , 2 }, false );
454+ check (dextents<int , 3 >{2 , 0 , 7 }, array{2 , 28 , 4 }, false );
455+ check (extents<int , 5 , 0 , 0 >{}, array{3 , 1 , 1 }, false );
456+ check (extents<int , 5 , dynamic_extent, 0 >{0 }, array{1 , 5 , 1 }, false );
457+ check (dextents<int , 3 >{5 , 0 , 0 }, array{2 , 1 , 10 }, false );
458+ check (extents<int , 0 , 0 , 0 >{}, array{1 , 1 , 1 }, false );
459+ check (extents<int , 0 , 1 , 1 >{}, array{1 , 1 , 1 }, true );
460+
461+ // rank() is greater than 2 - one extent is equal to 0 while others are equal to each other
462+ check (extents<int , 3 , 0 , 3 >{}, array{1 , 9 , 3 }, true );
463+ check (extents<int , dynamic_extent, 0 , 3 >{3 }, array{3 , 9 , 1 }, true );
464+ check (extents<int , 3 , dynamic_extent, dynamic_extent>{0 , 3 }, array{1 , 3 , 3 }, false );
465+ check (dextents<int , 3 >{3 , 0 , 3 }, array{1 , 4 , 8 }, false );
466+ check (dextents<int , 3 >{0 , 1 , 1 }, array{1 , 1 , 1 }, true );
467+
468+ // required_span_size() is equal to 1
469+ check (extents<int , 1 >{}, array{1 }, true );
470+ check (dextents<int , 1 >{1 }, array{3 }, false );
471+ check (extents<int , 1 , dynamic_extent>{1 }, array{1 , 1 }, true );
472+ check (extents<int , 1 , 1 , 1 >{}, array{1 , 2 , 1 }, false );
473+
474+ // Mapping is exhaustive, but is_exhaustive() should return false because of the way standard defined this function
475+ check (extents<int , 3 , 1 >{}, array{1 , 4 }, false );
476+ check (dextents<int , 3 >{5 , 1 , 2 }, array{2 , 11 , 1 }, false );
477+ check (dextents<int , 3 >{2 , 3 , 1 }, array{3 , 1 , 8 }, false );
478+ check (extents<int , 1 , dynamic_extent, 7 >{6 }, array{50 , 7 , 1 }, false );
479+ check (dextents<int , 2 >{1 , 2 }, array{5 , 1 }, false );
480+ check (extents<int , 6 , 1 >{}, array{1 , 10 }, false );
481+ check (dextents<int , 3 >{2 , 1 , 2 }, array{3 , 3 , 1 }, false );
419482}
420483
421484constexpr void check_call_operator () {
0 commit comments