constexpr const accessor_type&
accessor() const noexcept { return _M_accessor; }
+ // Strengthened noexcept for all `is_*` methods.
+
static constexpr bool
- is_always_unique() { return mapping_type::is_always_unique(); }
+ is_always_unique() noexcept(noexcept(mapping_type::is_always_unique()))
+ { return mapping_type::is_always_unique(); }
static constexpr bool
- is_always_exhaustive() { return mapping_type::is_always_exhaustive(); }
+ is_always_exhaustive()
+ noexcept(noexcept(mapping_type::is_always_exhaustive()))
+ { return mapping_type::is_always_exhaustive(); }
static constexpr bool
- is_always_strided() { return mapping_type::is_always_strided(); }
+ is_always_strided()
+ noexcept(noexcept(mapping_type::is_always_strided()))
+ { return mapping_type::is_always_strided(); }
constexpr bool
- is_unique() const { return _M_mapping.is_unique(); }
+ is_unique() const noexcept(noexcept(_M_mapping.is_unique()))
+ { return _M_mapping.is_unique(); }
constexpr bool
- is_exhaustive() const { return _M_mapping.is_exhaustive(); }
+ is_exhaustive() const noexcept(noexcept(_M_mapping.is_exhaustive()))
+ { return _M_mapping.is_exhaustive(); }
constexpr bool
- is_strided() const { return _M_mapping. is_strided(); }
+ is_strided() const noexcept(noexcept(_M_mapping.is_strided()))
+ { return _M_mapping. is_strided(); }
constexpr index_type
stride(rank_type __r) const { return _M_mapping.stride(__r); }
#ifndef TEST_MDSPAN_LAYOUT_LIKE_H
#define TEST_MDSPAN_LAYOUT_LIKE_H 1
-struct LayoutLike
-{
- template<typename Extents>
- class mapping
- {
- public:
- using extents_type = Extents;
- using index_type = typename extents_type::index_type;
- using size_type = typename extents_type::size_type;
- using rank_type = typename extents_type::rank_type;
- using layout_type = LayoutLike;
-
- constexpr
- mapping() noexcept = default;
-
- constexpr
- mapping(Extents exts)
- : m_exts(exts)
- { }
-
- constexpr const extents_type&
- extents() const noexcept { return m_exts; }
-
- constexpr index_type
- required_span_size() const noexcept
+template<bool Noexcept>
+ struct CustomLayout
+ {
+ template<typename Extents>
+ class mapping
{
- for (size_t i = 0; i < extents_type::rank(); ++i)
- if (m_exts.extent(i) == 0)
- return 0;
- return 1;
- }
-
- template<typename... Indices>
- requires (sizeof...(Indices) == extents_type::rank())
+ public:
+ using extents_type = Extents;
+ using index_type = typename extents_type::index_type;
+ using size_type = typename extents_type::size_type;
+ using rank_type = typename extents_type::rank_type;
+ using layout_type = CustomLayout;
+
+ constexpr
+ mapping() noexcept = default;
+
+ constexpr
+ mapping(Extents exts)
+ : m_exts(exts)
+ { }
+
+ constexpr const extents_type&
+ extents() const noexcept(Noexcept) { return m_exts; }
+
constexpr index_type
- operator()(Indices...) const noexcept
+ required_span_size() const noexcept(Noexcept)
+ {
+ for (size_t i = 0; i < extents_type::rank(); ++i)
+ if (m_exts.extent(i) == 0)
+ return 0;
+ return 1;
+ }
+
+ template<typename... Indices>
+ requires (sizeof...(Indices) == extents_type::rank())
+ constexpr index_type
+ operator()(Indices...) const noexcept(Noexcept)
+ { return 0; }
+
+ static constexpr index_type
+ stride(rank_type) noexcept(Noexcept)
{ return 0; }
- static constexpr index_type
- stride(rank_type) noexcept
- { return 0; }
+ static constexpr bool
+ is_always_unique() noexcept(Noexcept)
+ { return false; }
- static constexpr bool
- is_always_unique() noexcept
- { return false; }
+ static constexpr bool
+ is_always_exhaustive() noexcept(Noexcept)
+ { return true; }
- static constexpr bool
- is_always_exhaustive() noexcept
- { return true; }
+ static constexpr bool
+ is_always_strided() noexcept(Noexcept)
+ { return true; }
- static constexpr bool
- is_always_strided() noexcept
- { return true; }
+ constexpr bool
+ is_unique() const noexcept(Noexcept)
+ {
+ if (required_span_size() == 0)
+ return true;
- constexpr bool
- is_unique() noexcept
- {
- if (required_span_size() == 0)
+ for (size_t i = 0; i < extents_type::rank(); ++i)
+ if (m_exts.extent(i) > 1)
+ return false;
return true;
+ }
- for (size_t i = 0; i < extents_type::rank(); ++i)
- if (m_exts.extent(i) > 1)
- return false;
- return true;
- }
+ static constexpr bool
+ is_exhaustive() noexcept(Noexcept)
+ { return true; }
- static constexpr bool
- is_exhaustive() noexcept
- { return true; }
+ static constexpr bool
+ is_strided() noexcept(Noexcept)
+ { return true; }
- static constexpr bool
- is_strided() noexcept
- { return true; }
+ private:
+ Extents m_exts;
+ };
+ };
- private:
- Extents m_exts;
- };
-};
+using LayoutLike = CustomLayout<true>;
+using ThrowingLayout = CustomLayout<false>;
#endif
test_nothrow_movable<false, false>();
}
+template<typename Layout, bool Expected>
+ constexpr void
+ test_nothrow_is_methods()
+ {
+ using Extents = std::extents<int, dyn>;
+ using MDSpan = std::mdspan<double, Extents, Layout>;
+ static_assert(noexcept(MDSpan::is_always_unique()) == Expected);
+ static_assert(noexcept(MDSpan::is_always_exhaustive()) == Expected);
+ static_assert(noexcept(MDSpan::is_always_strided()) == Expected);
+
+ static_assert(noexcept(std::declval<MDSpan>().is_unique()) == Expected);
+ static_assert(noexcept(std::declval<MDSpan>().is_exhaustive()) == Expected);
+ static_assert(noexcept(std::declval<MDSpan>().is_strided()) == Expected);
+ }
+
int
main()
{
test_swap_adl();
test_nothrow_movable_all();
+ test_nothrow_is_methods<std::layout_right, true>();
+ test_nothrow_is_methods<ThrowingLayout, false>();
return 0;
}