mirror of
https://github.com/nlohmann/json.git
synced 2026-08-29 04:17:32 +00:00
Do not require the container iterators to be nothrow move constructible
iter_impl declared its defaulted move operations noexcept. The exception
specification a defaulted function gets implicitly follows from its members,
here internal_iterator, which holds the object and array iterators. libstdc++
gives std::deque's iterator a user-provided copy constructor without noexcept
before version 11, so the implicit specification is noexcept(false) and does
not match the declared one. That deletes the function -- and with g++ 4.8,
which predates CWG 1778, it is an error outright:
error: function 'iter_impl<basic_json<std::map, std::deque> >::iter_impl(
iter_impl&&)' defaulted on its first declaration with an
exception-specification that differs from the implicit declaration
So std::deque, which this branch documents as a usable array type, could not
be used with an older standard library. Leaving the specification to be
computed cannot mismatch; iteration_proxy_value already spells out the same
condition next door.
The default configuration is unaffected: json::iterator, json::const_iterator
and ordered_json::iterator stay nothrow move constructible and move
assignable, which the test now checks so it cannot regress unnoticed.
Signed-off-by: Niels Lohmann <mail@nlohmann.me>
This commit is contained in:
@@ -88,8 +88,13 @@ class iter_impl // NOLINT(cppcoreguidelines-special-member-functions,hicpp-speci
|
|||||||
|
|
||||||
iter_impl() = default;
|
iter_impl() = default;
|
||||||
~iter_impl() = default;
|
~iter_impl() = default;
|
||||||
iter_impl(iter_impl&&) noexcept = default;
|
// the exception specification is left to be computed rather than declared:
|
||||||
iter_impl& operator=(iter_impl&&) noexcept = default;
|
// an array or object type whose iterator is not nothrow move constructible
|
||||||
|
// (std::deque's is not before libstdc++ 11) would make a declared noexcept
|
||||||
|
// differ from the implicit one, which deletes the function -- and is an
|
||||||
|
// error outright with older compilers
|
||||||
|
iter_impl(iter_impl&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor,cppcoreguidelines-noexcept-move-operations)
|
||||||
|
iter_impl& operator=(iter_impl&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor,cppcoreguidelines-noexcept-move-operations)
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
@brief constructor for a given JSON instance
|
@brief constructor for a given JSON instance
|
||||||
|
|||||||
@@ -14764,8 +14764,13 @@ class iter_impl // NOLINT(cppcoreguidelines-special-member-functions,hicpp-speci
|
|||||||
|
|
||||||
iter_impl() = default;
|
iter_impl() = default;
|
||||||
~iter_impl() = default;
|
~iter_impl() = default;
|
||||||
iter_impl(iter_impl&&) noexcept = default;
|
// the exception specification is left to be computed rather than declared:
|
||||||
iter_impl& operator=(iter_impl&&) noexcept = default;
|
// an array or object type whose iterator is not nothrow move constructible
|
||||||
|
// (std::deque's is not before libstdc++ 11) would make a declared noexcept
|
||||||
|
// differ from the implicit one, which deletes the function -- and is an
|
||||||
|
// error outright with older compilers
|
||||||
|
iter_impl(iter_impl&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor,cppcoreguidelines-noexcept-move-operations)
|
||||||
|
iter_impl& operator=(iter_impl&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor,cppcoreguidelines-noexcept-move-operations)
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
@brief constructor for a given JSON instance
|
@brief constructor for a given JSON instance
|
||||||
|
|||||||
@@ -14,6 +14,7 @@
|
|||||||
#include <map>
|
#include <map>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
#include <type_traits>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
@@ -40,6 +41,19 @@ using no_at_json = nlohmann::basic_json<std::map, vector_without_at>;
|
|||||||
|
|
||||||
TEST_CASE("array type without capacity()")
|
TEST_CASE("array type without capacity()")
|
||||||
{
|
{
|
||||||
|
SECTION("the iterators of the default configuration stay nothrow movable")
|
||||||
|
{
|
||||||
|
// basic_json's iterators take their exception specification from the
|
||||||
|
// container iterators; std::deque's is not nothrow move constructible
|
||||||
|
// with older standard libraries, which must not cost the default
|
||||||
|
// configuration its noexcept
|
||||||
|
CHECK(std::is_nothrow_move_constructible<nlohmann::json::iterator>::value);
|
||||||
|
CHECK(std::is_nothrow_move_assignable<nlohmann::json::iterator>::value);
|
||||||
|
CHECK(std::is_nothrow_move_constructible<nlohmann::json::const_iterator>::value);
|
||||||
|
CHECK(std::is_move_constructible<deque_json::iterator>::value);
|
||||||
|
CHECK(std::is_move_assignable<deque_json::iterator>::value);
|
||||||
|
}
|
||||||
|
|
||||||
SECTION("adding elements")
|
SECTION("adding elements")
|
||||||
{
|
{
|
||||||
deque_json j = deque_json::array();
|
deque_json j = deque_json::array();
|
||||||
|
|||||||
Reference in New Issue
Block a user