diff --git a/docs/mkdocs/docs/api/basic_json_view/begin.md b/docs/mkdocs/docs/api/basic_json_view/begin.md index afc662ee7..a294fd46d 100644 --- a/docs/mkdocs/docs/api/basic_json_view/begin.md +++ b/docs/mkdocs/docs/api/basic_json_view/begin.md @@ -6,7 +6,7 @@ iterator begin() const noexcept; Returns an iterator to the first element of an array, or the first member value of an object, in **document order** -- the order the values appear in the source text, not sorted by key. A primitive value iterates as a range of one -element (itself); `#!json null` and a [discarded](is_discarded.md) view iterate as an empty range. +element (itself), and a `#!json null` value or a [discarded](is_discarded.md) view iterates as an empty range. ## Return value diff --git a/docs/mkdocs/docs/api/basic_json_view/end.md b/docs/mkdocs/docs/api/basic_json_view/end.md index d0346c049..ceac53b69 100644 --- a/docs/mkdocs/docs/api/basic_json_view/end.md +++ b/docs/mkdocs/docs/api/basic_json_view/end.md @@ -5,9 +5,8 @@ iterator end() const noexcept; ``` Returns an iterator to one past the last element of an array, one past the last member value of an object, in -**document order** -- see [`begin()`](begin.md). A primitive value iterates as a range of one element (itself); -`#!json null` and a [discarded](is_discarded.md) view iterate as an empty range, so `#!cpp begin() == end()` for -them. +**document order** -- see [`begin()`](begin.md). A primitive value iterates as a range of one element (itself), and a +`#!json null` value or a [discarded](is_discarded.md) view iterates as an empty range (`#!cpp begin() == end()`). ## Return value diff --git a/docs/mkdocs/docs/api/basic_json_view/index.md b/docs/mkdocs/docs/api/basic_json_view/index.md index d0fdb6fc5..6ef14da4a 100644 --- a/docs/mkdocs/docs/api/basic_json_view/index.md +++ b/docs/mkdocs/docs/api/basic_json_view/index.md @@ -22,12 +22,12 @@ Moving the document itself does not invalidate its views: the index is heap-allo `basic_json_view` provides the read-only part of the `BasicJsonType` interface: -- the type-inspection functions, -- element access, -- lookup, -- iteration, and +- the type-inspection functions +- element access +- lookup +- iteration - conversion: [`get()`](get.md), [`get_string()`](get_string.md), [`number_token()`](number_token.md), and - [`materialize()`](materialize.md) to build the `BasicJsonType` value of a subtree on demand. + [`materialize()`](materialize.md) to build the `BasicJsonType` value of a subtree on demand [`operator[]`](operator%5B%5D.md), [`at`](at.md), [`contains`](contains.md), and [`value`](value.md) also accept a [`json_pointer`](../json_pointer/index.md). It does not (yet) provide `dump()` or comparison. Unlike `basic_json`, diff --git a/include/nlohmann/detail/view/document_data.hpp b/include/nlohmann/detail/view/document_data.hpp index a72227aa5..f7396759a 100644 --- a/include/nlohmann/detail/view/document_data.hpp +++ b/include/nlohmann/detail/view/document_data.hpp @@ -10,7 +10,7 @@ #include // array #include // size_t -#include // memcpy +#include // memcmp, memcpy #include // numeric_limits #include // bad_alloc, operator new, placement new #include // string @@ -141,6 +141,12 @@ struct document_data return base[n.flags & node_flags::storage] + n.off; } + /// whether the string of node k (a key) is the n bytes at key + bool key_equals(const node& k, const char* key, std::size_t n) const noexcept + { + return k.len == n && (n == 0 || std::memcmp(str(k), key, n) == 0); + } + /// the node after n's subtree (containers span `next` nodes, scalars one) static NLOHMANN_VIEW_ALWAYS_INLINE const node* after(const node* n) noexcept { diff --git a/include/nlohmann/detail/view/lookup.hpp b/include/nlohmann/detail/view/lookup.hpp index ee377a5e3..daaa7fdff 100644 --- a/include/nlohmann/detail/view/lookup.hpp +++ b/include/nlohmann/detail/view/lookup.hpp @@ -105,7 +105,7 @@ inline const node* find_member(const document_data& d, const node* object, const } for (const node* m = document_data::first_child(object); m != end; m = document_data::after(m + 1)) { - if (m->len == n && std::memcmp(d.str(*m), key, n) == 0) + if (d.key_equals(*m, key, n)) { return m; } @@ -120,7 +120,7 @@ inline std::size_t count_members(const document_data& d, const node* object, con const node* const end = document_data::child_end(object); for (const node* m = document_data::first_child(object); m != end; m = document_data::after(m + 1)) { - if (m->len == n && (n == 0 || std::memcmp(d.str(*m), key, n) == 0)) + if (d.key_equals(*m, key, n)) { ++result; }