From 3c1fec6058de8c34e3e5e0471ed3ef03b7cf1b81 Mon Sep 17 00:00:00 2001 From: mutouyun Date: Sat, 27 May 2023 16:18:18 +0800 Subject: [PATCH] upd: [imp] span --- include/libconcur/queue.h | 2 +- include/libimp/span.h | 15 +++++++++++++++ test/imp/test_imp_span.cpp | 12 ++++++++++++ 3 files changed, 28 insertions(+), 1 deletion(-) diff --git a/include/libconcur/queue.h b/include/libconcur/queue.h index 25cc1ec..32bc9b8 100644 --- a/include/libconcur/queue.h +++ b/include/libconcur/queue.h @@ -43,7 +43,7 @@ private: data(U &&model) noexcept : header_(std::forward(model)) { auto elements = this->elements(); - decltype(elements)::size_type i = 0; + typename decltype(elements)::size_type i = 0; LIBIMP_TRY { for (; i < elements.size(); ++i) { (void)::LIBIMP::construct>(&elements[i]); diff --git a/include/libimp/span.h b/include/libimp/span.h index 814b584..c05f79b 100644 --- a/include/libimp/span.h +++ b/include/libimp/span.h @@ -19,6 +19,8 @@ #include "libimp/def.h" #include "libimp/detect_plat.h" +#include "libimp/countof.h" +#include "libimp/dataof.h" #if defined(LIBIMP_CPP_20) && defined(__cpp_lib_span) #include @@ -56,6 +58,10 @@ using is_sized_sentinel_for = typename std::enable_if() - std::declval()), std::ptrdiff_t>::value>::type; +template +using is_continuous_container = + decltype(dataof(std::declval()), countof(std::declval())); + /// \brief Obtain the address represented by p /// without forming a reference to the object pointed to by p. /// \see https://en.cppreference.com/w/cpp/memory/to_address @@ -119,6 +125,15 @@ public: : ptr_ (detail::to_address(first)) , extent_(static_cast(last - first)) {} + template , + typename = detail::is_array_convertible()))>, element_type>> + constexpr span(U &&u) noexcept(noexcept(dataof (std::forward(u)), + countof(std::forward(u)))) + : ptr_ (dataof (std::forward(u))) + , extent_(countof(std::forward(u))) {} + template > constexpr span(U (&arr)[E]) noexcept diff --git a/test/imp/test_imp_span.cpp b/test/imp/test_imp_span.cpp index 0304f7e..dd1f717 100644 --- a/test/imp/test_imp_span.cpp +++ b/test/imp/test_imp_span.cpp @@ -60,4 +60,16 @@ TEST(span, span) { TEST(span, fmt) { EXPECT_EQ(imp::fmt(imp::span{}), ""); EXPECT_EQ(imp::fmt(imp::make_span({1, 3, 2, 4, 5, 6, 7})), "1 3 2 4 5 6 7"); +} + +TEST(span, construct) { + struct test_imp_span_construct { + /* data */ + int size() const noexcept { return sizeof(this); } + auto Data() const noexcept { return this; } + } d1; + imp::span sp {d1}; + // imp::span spp {d1}; + EXPECT_EQ(sp.size(), d1.size()); + EXPECT_EQ(sp.data(), d1.Data()); } \ No newline at end of file