Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
bdcfc178af | ||
|
|
30e1adef93 | ||
|
|
afea570755 | ||
|
|
e7d245db7e | ||
|
|
d38a04bd3e |
No files matched your search
@@ -113,22 +113,19 @@ basic_json(basic_json&& other) noexcept;
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A(["initializer_list init"]) --> B{{"empty, or every element is a 2-element<br/>array whose first element is a string?"}}
|
||||
B -->|"yes"| C{{"type_deduction"}}
|
||||
B -->|"no"| D{{"type_deduction"}}
|
||||
A(["initializer_list init"]) --> B{"empty, or every element is a 2-element<br/>array whose first element is a string?"}
|
||||
B -->|"yes"| C{"type_deduction"}
|
||||
B -->|"no"| D{"type_deduction"}
|
||||
C -->|"true"| OBJ["create object"]
|
||||
C -->|"false"| E{{"manual_type"}}
|
||||
C -->|"false"| E{"manual_type"}
|
||||
E -->|"object"| OBJ
|
||||
E -->|"array"| ARR["create array"]
|
||||
D -->|"true"| ARR
|
||||
D -->|"false"| F{{"manual_type"}}
|
||||
D -->|"false"| F{"manual_type"}
|
||||
F -->|"array"| ARR
|
||||
F -->|"object"| ERR["throw type_error.301"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Decision flow for an initializer list: hexagons are checks, edge labels are their
|
||||
outcomes, and rectangles are the resulting value or exception.</p>
|
||||
|
||||
The rules aim to create the best fit between a C++ initializer list and JSON values. The rationale is as follows:
|
||||
|
||||
1. The empty initializer list is written as `#!cpp {}` which is exactly an empty JSON object.
|
||||
|
||||
@@ -7,12 +7,7 @@ const_iterator begin() const noexcept;
|
||||
|
||||
Returns an iterator to the first element.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-begin-end.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`begin()` points to the first element and `end()` to the position after the last element;
|
||||
the dashed cell is the past-the-last position, which must not be dereferenced.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -6,12 +6,7 @@ const_iterator cbegin() const noexcept;
|
||||
|
||||
Returns an iterator to the first element.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-begin-end.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`cbegin()` points to the first element, like `begin()`, and `end()` to the position after
|
||||
the last element; the dashed cell is the past-the-last position, which must not be dereferenced.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -6,12 +6,7 @@ const_iterator cend() const noexcept;
|
||||
|
||||
Returns an iterator to one past the last element.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-begin-end.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`cend()` points to the position after the last element, like `end()`, and `begin()` to
|
||||
the first element; the dashed cell is the past-the-last position, which must not be dereferenced.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -6,13 +6,7 @@ const_reverse_iterator crbegin() const noexcept;
|
||||
|
||||
Returns an iterator to the reverse-beginning; that is, the last element.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-rbegin-rend.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`crbegin()` points to the last element, like `rbegin()`, and `rend()` to the position
|
||||
before the first element. The upper row is the reversed sequence and the lower row the forward sequence; dashed arrows
|
||||
link each reverse iterator to the forward iterator it stores, and dashed cells are past-the-last positions.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -7,13 +7,7 @@ const_reverse_iterator crend() const noexcept;
|
||||
Returns an iterator to the reverse-end; that is, one before the first element. This element acts as a placeholder,
|
||||
attempting to access it results in undefined behavior.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-rbegin-rend.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`crend()` points to the position before the first element, like `rend()`, and `rbegin()`
|
||||
to the last element. The upper row is the reversed sequence and the lower row the forward sequence; dashed arrows link
|
||||
each reverse iterator to the forward iterator it stores, and dashed cells are past-the-last positions.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -7,12 +7,7 @@ const_iterator end() const noexcept;
|
||||
|
||||
Returns an iterator to one past the last element.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-begin-end.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`end()` points to the position after the last element and `begin()` to the first element;
|
||||
the dashed cell is the past-the-last position, which must not be dereferenced.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -40,9 +40,6 @@ classDiagram
|
||||
style json_exception fill:#CCCCFF
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class hierarchy of the library's exceptions; arrows point from a derived class to its
|
||||
base class, and the highlighted box is `basic_json::exception`.</p>
|
||||
|
||||
Subclasses:
|
||||
|
||||
- [`parse_error`](parse_error.md) for exceptions indicating a parse error
|
||||
|
||||
@@ -40,9 +40,6 @@ classDiagram
|
||||
style json_invalid_iterator fill:#CCCCFF
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class hierarchy of the library's exceptions; arrows point from a derived class to its
|
||||
base class, and the highlighted box is `basic_json::invalid_iterator`.</p>
|
||||
|
||||
## Member functions
|
||||
|
||||
- **what** - returns explanatory string
|
||||
|
||||
@@ -40,9 +40,6 @@ classDiagram
|
||||
style json_other_error fill:#CCCCFF
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class hierarchy of the library's exceptions; arrows point from a derived class to its
|
||||
base class, and the highlighted box is `basic_json::other_error`.</p>
|
||||
|
||||
## Member functions
|
||||
|
||||
- **what** - returns explanatory string
|
||||
|
||||
@@ -41,9 +41,6 @@ classDiagram
|
||||
style json_out_of_range fill:#CCCCFF
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class hierarchy of the library's exceptions; arrows point from a derived class to its
|
||||
base class, and the highlighted box is `basic_json::out_of_range`.</p>
|
||||
|
||||
## Member functions
|
||||
|
||||
- **what** - returns explanatory string
|
||||
|
||||
@@ -43,9 +43,6 @@ classDiagram
|
||||
style json_parse_error fill:#CCCCFF
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class hierarchy of the library's exceptions; arrows point from a derived class to its
|
||||
base class, and the highlighted box is `basic_json::parse_error`.</p>
|
||||
|
||||
## Member functions
|
||||
|
||||
- **what** - returns explanatory string
|
||||
|
||||
@@ -22,12 +22,7 @@ The parser callback distinguishes the following events:
|
||||
|
||||
## Examples
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/callback_events.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Each coloured dot marks where the parser reports a `parse_event_t` event while reading
|
||||
the JSON text on the left; the legend on the right names the event per colour.</p>
|
||||

|
||||
|
||||
??? example
|
||||
|
||||
|
||||
@@ -23,12 +23,7 @@ table describes the values of the parameters `depth`, `event`, and `parsed`.
|
||||
| `parse_event_t::array_end` | the parser read `]` and finished processing a JSON array | depth of the parent of the JSON array | the parsed JSON array |
|
||||
| `parse_event_t::value` | the parser finished reading a JSON value | depth of the value | the parsed JSON value |
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/callback_events.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Parse events for a small JSON text: each coloured dot marks the position at which the
|
||||
parser calls the callback, and the legend on the right names the event per colour.</p>
|
||||

|
||||
|
||||
Discarding a value (i.e., returning `#!cpp false`) has different effects depending on the context in which function was
|
||||
called:
|
||||
|
||||
@@ -7,13 +7,7 @@ const_reverse_iterator rbegin() const noexcept;
|
||||
|
||||
Returns an iterator to the reverse-beginning; that is, the last element.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-rbegin-rend.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`rbegin()` points to the last element and `rend()` to the position before the first
|
||||
element. The upper row is the reversed sequence and the lower row the forward sequence; dashed arrows link each reverse
|
||||
iterator to the forward iterator it stores, and dashed cells are past-the-last positions.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -8,13 +8,7 @@ const_reverse_iterator rend() const noexcept;
|
||||
Returns an iterator to the reverse-end; that is, one before the first element. This element acts as a placeholder,
|
||||
attempting to access it results in undefined behavior.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-rbegin-rend.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>`rend()` points to the position before the first element and `rbegin()` to the last
|
||||
element. The upper row is the reversed sequence and the lower row the forward sequence; dashed arrows link each reverse
|
||||
iterator to the forward iterator it stores, and dashed cells are past-the-last positions.</p>
|
||||

|
||||
|
||||
## Return value
|
||||
|
||||
|
||||
@@ -41,9 +41,6 @@ classDiagram
|
||||
style json_type_error fill:#CCCCFF
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class hierarchy of the library's exceptions; arrows point from a derived class to its
|
||||
base class, and the highlighted box is `basic_json::type_error`.</p>
|
||||
|
||||
## Member functions
|
||||
|
||||
- **what** - returns explanatory string
|
||||
|
||||
@@ -48,9 +48,6 @@ functions [`is_null`](is_null.md), [`is_object`](is_object.md), [`is_array`](is_
|
||||
F --> G[binary]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Arrows point from a type to the next greater type in the ordering used by
|
||||
`operator<`.</p>
|
||||
|
||||
!!! note "Types of numbers"
|
||||
|
||||
There are three enumerators for numbers (`number_integer`, `number_unsigned`, and `number_float`) to distinguish
|
||||
|
||||
@@ -36,9 +36,6 @@ flowchart LR
|
||||
parent["parent_pointer() returns /a/b"] -.-> B
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Boxes are the reference tokens in order; dotted arrows show which token each member
|
||||
function reads, removes, or adds to.</p>
|
||||
|
||||
The diagram shows the reference tokens of the JSON pointer `/a/b/c`.
|
||||
|
||||
## Member types
|
||||
|
||||
@@ -25,9 +25,6 @@ sequenceDiagram
|
||||
P->>H: end_object()
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Each arrow is one call from the parser to the SAX handler, from top to bottom in the
|
||||
order the calls happen.</p>
|
||||
|
||||
Note `elements` is passed as `#!cpp std::numeric_limits<std::size_t>::max()` (i.e., "unknown") for JSON text input;
|
||||
only binary formats such as CBOR or MessagePack may report the actual number of elements in `start_object`/
|
||||
`start_array`. Also note that `1` is reported via `number_unsigned` rather than `number_integer` because it has no
|
||||
|
||||
@@ -41,8 +41,6 @@ flowchart LR
|
||||
E --> F[Trusted caller]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The trust boundary: untrusted input enters on the left through the parser, the SAX interface, or the binary readers, and only a value tree reaches the trusted caller on the right.</p>
|
||||
|
||||
## Secure design
|
||||
|
||||
- **Strict parsing.** The parser accepts exactly the JSON grammar of [RFC 8259](https://datatracker.ietf.org/doc/html/rfc8259).
|
||||
|
||||
@@ -4,15 +4,6 @@ Ensuring quality is paramount for this project, particularly because [numerous o
|
||||
depend on it. Each commit to the library undergoes rigorous checks against the following requirements, and any
|
||||
violations will result in a failed build.
|
||||
|
||||
The overview shows the checks a change passes on its way from a push or pull request to a release; the sections below
|
||||
describe each of them.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/qa_pipeline.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>The checks grouped by the stage at which they run, from push or pull request through the merge into develop to a release. The badge on each card says whether the check runs on every push or PR, on a schedule, or continuously.</p>
|
||||
|
||||
## C++ language compliance and compiler compatibility
|
||||
|
||||
!!! success "Requirement: Compiler support"
|
||||
|
||||
@@ -91,14 +91,6 @@ Version 4.0 is therefore the sum of these macros: you can try it on the 3.x rele
|
||||
to its 4.0 value and fixing what no longer compiles or behaves differently. Once your code works with all of them, it
|
||||
is ready for version 4.0.
|
||||
|
||||
Each macro has a default value in 3.x and a different value in version 4.0. Define the macro to the 4.0 value to try it on the 3.x release train today; version 4.0 makes that value the default:
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/roadmap_lanes.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Each row is one macro: the 3.x release that added it, its default in 3.x, and its value in version 4.0 (highlighted) or "removed". Versions on the 3.x lane are not to scale.</p>
|
||||
|
||||
The following macros guard changes that are planned to become the default in version 4.0:
|
||||
|
||||
| Macro | 3.x default | 4.0 behavior | CMake option | Added |
|
||||
@@ -113,8 +105,6 @@ The following macros guard changes that are planned to become the default in ver
|
||||
| [`JSON_DISABLE_TUPLE_REFERENCE_CONVERSION`](../api/macros/json_disable_tuple_reference_conversion.md) | `0` | `1`: a `basic_json` value can no longer be created from a one-element tuple of a reference to it, such as `std::forward_as_tuple(j)`| [`JSON_DisableTupleReferenceConversion`](../integration/cmake.md#json_disabletuplereferenceconversion) | 3.13.0 |
|
||||
| [`JSON_DELETE_DEPRECATED_FUNCTIONS`](../api/macros/json_delete_deprecated_functions.md) | `0` | removed: the deprecated functions are removed (see below); the `from_*(ptr, len)` overloads stay deleted | [`JSON_DeleteDeprecatedFunctions`](../integration/cmake.md#json_deletedeprecatedfunctions) | 3.13.0 |
|
||||
|
||||
<p class="nj-table-caption" markdown>Opt-in macros for the version 4.0 behavior. "3.x default" is the value the library uses when the macro is not defined, "Added" is the release that introduced the macro, and – means there is no CMake option.</p>
|
||||
|
||||
For example, the following makes a 3.x release behave like version 4.0 with respect to these changes:
|
||||
|
||||
```cpp
|
||||
@@ -156,8 +146,6 @@ to the `strict` parameter.
|
||||
| Comparing a [`json_pointer`](../api/json_pointer/index.md) with a string via [`operator==`](../api/json_pointer/operator_eq.md) or [`operator!=`](../api/json_pointer/operator_ne.md) | 3.11.2 | [JSON Pointers](../integration/migration_guide.md#json-pointers) |
|
||||
| [`from_bjdata`](../api/basic_json/from_bjdata.md) and [`from_bon8`](../api/basic_json/from_bon8.md) with `(ptr, len)` | 3.13.0 | [Parsing](../integration/migration_guide.md#parsing) |
|
||||
|
||||
<p class="nj-table-caption" markdown>Deprecated functions, with the release that deprecated each one and the section of the migration guide that shows its replacement.</p>
|
||||
|
||||
The deprecated legacy comparison of discarded values is controlled by a macro and therefore listed in the table above.
|
||||
|
||||
New breaking changes will follow the same path: they are added to these tables when they land in a 3.x release.
|
||||
@@ -1,782 +0,0 @@
|
||||
/* nlohmann/json brand for Material for MkDocs (values from brand/kit/tokens.css) */
|
||||
|
||||
@font-face {
|
||||
font-family: "Inter";
|
||||
src: url("fonts/Inter.woff2") format("woff2");
|
||||
font-weight: 100 900;
|
||||
font-display: swap;
|
||||
}
|
||||
@font-face {
|
||||
font-family: "Inter";
|
||||
src: url("fonts/Inter-Italic.woff2") format("woff2");
|
||||
font-style: italic;
|
||||
font-weight: 100 900;
|
||||
font-display: swap;
|
||||
}
|
||||
@font-face {
|
||||
font-family: "JetBrains Mono";
|
||||
src: url("fonts/JetBrainsMono.woff2") format("woff2");
|
||||
font-weight: 100 800;
|
||||
font-display: swap;
|
||||
}
|
||||
@font-face {
|
||||
font-family: "JetBrains Mono";
|
||||
src: url("fonts/JetBrainsMono-Italic.woff2") format("woff2");
|
||||
font-style: italic;
|
||||
font-weight: 400;
|
||||
font-display: swap;
|
||||
}
|
||||
|
||||
:root {
|
||||
--md-text-font: "Inter";
|
||||
--md-code-font: "JetBrains Mono";
|
||||
}
|
||||
|
||||
/* light */
|
||||
[data-md-color-scheme="default"] {
|
||||
--nj-blue: #1747a6;
|
||||
--nj-blue-deep: #10357d;
|
||||
--nj-blue-soft: #eaf1fd;
|
||||
--nj-band: #1747a6;
|
||||
--nj-red: #d93a3f;
|
||||
--nj-red-soft: #fdeced;
|
||||
--nj-string: #b4322a;
|
||||
--nj-comment: #646d7a;
|
||||
|
||||
--md-primary-fg-color: var(--nj-band);
|
||||
--md-primary-fg-color--light: #1d55c4;
|
||||
--md-primary-fg-color--dark: #10357d;
|
||||
--md-accent-fg-color: var(--nj-blue-deep);
|
||||
--md-accent-fg-color--transparent: rgba(23, 71, 166, .1);
|
||||
--md-typeset-a-color: var(--nj-blue);
|
||||
--md-default-fg-color: #0f1419;
|
||||
--md-default-fg-color--light: #4a515c;
|
||||
--md-default-fg-color--lighter: #8a919c;
|
||||
--md-default-fg-color--lightest: #e3e6eb;
|
||||
--md-typeset-color: #0f1419;
|
||||
--md-code-bg-color: #f5f7fa;
|
||||
--md-code-fg-color: #0f1419;
|
||||
}
|
||||
|
||||
/* dark */
|
||||
[data-md-color-scheme="slate"] {
|
||||
--nj-blue: #7aa7f5;
|
||||
--nj-blue-deep: #a9c6f8;
|
||||
--nj-blue-soft: #16233b;
|
||||
--nj-band: #173e8c;
|
||||
--nj-red: #f06a6e;
|
||||
--nj-red-soft: #3a1c1e;
|
||||
--nj-string: #f08a7e;
|
||||
--nj-comment: #8b929e;
|
||||
|
||||
--md-hue: 220;
|
||||
--md-primary-fg-color: var(--nj-band);
|
||||
--md-primary-fg-color--light: #163f93;
|
||||
--md-primary-fg-color--dark: #0c2556;
|
||||
--md-accent-fg-color: var(--nj-blue-deep);
|
||||
--md-accent-fg-color--transparent: rgba(122, 167, 245, .12);
|
||||
--md-typeset-a-color: var(--nj-blue);
|
||||
--md-default-bg-color: #0f1218;
|
||||
--md-default-fg-color: #f2f4f7;
|
||||
--md-default-fg-color--light: #b3b9c4;
|
||||
--md-default-fg-color--lighter: #7b828e;
|
||||
--md-default-fg-color--lightest: #272c36;
|
||||
--md-typeset-color: #f2f4f7;
|
||||
--md-code-bg-color: #171b23;
|
||||
--md-code-fg-color: #f2f4f7;
|
||||
--md-footer-bg-color: #0b0e13;
|
||||
--md-footer-bg-color--dark: #08090d;
|
||||
}
|
||||
|
||||
/* syntax colours (all at least 4.5:1 on the code panel in both schemes) */
|
||||
[data-md-color-scheme="default"] {
|
||||
--nj-hl-keyword: #1747a6;
|
||||
--nj-hl-type: #0d6e72;
|
||||
--nj-hl-function: #6b3fb8;
|
||||
--nj-hl-string: #23793a;
|
||||
--nj-hl-escape: #0f5d2a;
|
||||
--nj-hl-key: #10357d;
|
||||
--nj-hl-number: #b04a07;
|
||||
--nj-hl-preproc: #a3247a;
|
||||
}
|
||||
[data-md-color-scheme="slate"] {
|
||||
--nj-hl-keyword: #7aa7f5;
|
||||
--nj-hl-type: #4fd1c5;
|
||||
--nj-hl-function: #c4a3ff;
|
||||
--nj-hl-string: #7ed491;
|
||||
--nj-hl-escape: #b2ecc0;
|
||||
--nj-hl-key: #a9c6f8;
|
||||
--nj-hl-number: #f5a65b;
|
||||
--nj-hl-preproc: #f48fc8;
|
||||
}
|
||||
.md-typeset .highlight :is(.k, .kd, .kn, .kr, .kp, .kv, .ow) { color: var(--nj-hl-keyword); font-weight: 600; }
|
||||
.md-typeset .highlight :is(.kt, .nc, .nn, .na) { color: var(--nj-hl-type); }
|
||||
.md-typeset .highlight :is(.nf, .fm, .nb, .bp) { color: var(--nj-hl-function); }
|
||||
.md-typeset .highlight :is(.s, .s1, .s2, .sb, .sc, .sd, .sh, .sx, .sr, .ss, .sa, .dl, .cpf) { color: var(--nj-hl-string); }
|
||||
.md-typeset .highlight :is(.se, .si) { color: var(--nj-hl-escape); font-weight: 600; }
|
||||
.md-typeset .highlight .nt { color: var(--nj-hl-key); }
|
||||
.md-typeset .highlight :is(.m, .mi, .mf, .mh, .mo, .mb, .il, .kc) { color: var(--nj-hl-number); }
|
||||
.md-typeset .highlight .kc { font-weight: 500; }
|
||||
.md-typeset .highlight .cp { color: var(--nj-hl-preproc); }
|
||||
.md-typeset .highlight :is(.c, .c1, .cm, .ch, .cs) { color: var(--nj-comment); font-style: italic; }
|
||||
.md-typeset .highlight :is(.o, .p) { color: var(--md-default-fg-color--light); }
|
||||
.md-typeset .highlight :is(.n, .nx, .nv, .no, .ni, .nl, .py) { color: var(--md-code-fg-color); }
|
||||
.md-typeset .highlight .err { color: inherit; background: none; }
|
||||
|
||||
/* typography: Inter with cv11/ss03, bold headlines with negative tracking */
|
||||
body {
|
||||
font-feature-settings: "cv11", "ss03";
|
||||
}
|
||||
.md-typeset {
|
||||
font-size: .85rem; /* 17 px body */
|
||||
line-height: 1.65;
|
||||
}
|
||||
.md-typeset h1 {
|
||||
color: var(--md-typeset-color);
|
||||
font-weight: 800;
|
||||
letter-spacing: -.035em;
|
||||
line-height: 1.1;
|
||||
}
|
||||
.md-typeset h2 {
|
||||
font-weight: 800;
|
||||
letter-spacing: -.025em;
|
||||
line-height: 1.15;
|
||||
}
|
||||
.md-typeset h3 {
|
||||
font-weight: 700;
|
||||
letter-spacing: -.015em;
|
||||
}
|
||||
.md-typeset table:not([class]) {
|
||||
font-variant-numeric: tabular-nums;
|
||||
}
|
||||
|
||||
/* header and tabs: one blue band with the faint syntax pattern; wordmark instead of the site name.
|
||||
A veil over the tile keeps the glyphs from running through the navigation text; the hero shows the pattern at full strength. */
|
||||
.md-header, .md-tabs {
|
||||
--nj-veil: linear-gradient(color-mix(in srgb, var(--md-primary-fg-color) 62%, transparent), color-mix(in srgb, var(--md-primary-fg-color) 62%, transparent));
|
||||
background-color: var(--md-primary-fg-color);
|
||||
background-image: var(--nj-veil), url("pattern-on-blue.svg");
|
||||
background-size: auto, 160px 160px;
|
||||
background-position: 0 0, 0 0;
|
||||
}
|
||||
.md-tabs {
|
||||
background-position: 0 0, 0 -48px; /* continue the header's tile */
|
||||
}
|
||||
.md-header__button.md-logo img {
|
||||
width: auto;
|
||||
height: 1.5rem;
|
||||
}
|
||||
.md-header__topic:first-child .md-ellipsis { /* the wordmark replaces the site name at every width */
|
||||
display: none;
|
||||
}
|
||||
@media screen and (max-width: 76.234375em) { /* Material hides the header logo here: show the wordmark on phones, too */
|
||||
.md-header__button.md-logo {
|
||||
display: block;
|
||||
margin: 0 0 0 .2rem;
|
||||
padding: .4rem .2rem;
|
||||
}
|
||||
.md-header__button[for="__drawer"] {
|
||||
order: -1;
|
||||
}
|
||||
}
|
||||
.md-nav__button.md-logo img {
|
||||
width: auto;
|
||||
height: 1.4rem;
|
||||
}
|
||||
|
||||
/* shapes: 6 px corners on blocks, 4 px on inline code */
|
||||
.md-typeset pre > code, .md-typeset .highlight, .md-typeset .highlighttable,
|
||||
.md-typeset .admonition, .md-typeset details, .md-typeset .tabbed-set,
|
||||
.md-typeset .grid.cards > ul > li, .md-typeset .md-button {
|
||||
border-radius: 6px;
|
||||
}
|
||||
.md-typeset code {
|
||||
border-radius: 4px;
|
||||
}
|
||||
|
||||
/* inline code: the font alone marks it, no grey box; linked code keeps the link colour */
|
||||
.md-typeset :not(pre) > code {
|
||||
padding: 0;
|
||||
background-color: transparent;
|
||||
box-shadow: none;
|
||||
color: inherit;
|
||||
font-size: .88em;
|
||||
}
|
||||
.md-typeset .highlight pre > code, .md-typeset .highlighttable {
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
}
|
||||
|
||||
/* callouts: 3 px left border; note/info/tip in blue on blue-soft, danger/bug in red on red-soft */
|
||||
.md-typeset .admonition, .md-typeset details {
|
||||
border-width: 0 0 0 3px;
|
||||
box-shadow: none;
|
||||
font-size: .8rem;
|
||||
}
|
||||
.md-typeset :is(.admonition, details):is(.note, .info, .tip, .abstract, .example, .question) {
|
||||
border-color: var(--nj-blue);
|
||||
background-color: var(--nj-blue-soft);
|
||||
}
|
||||
.md-typeset :is(.note, .info, .tip, .abstract, .example, .question) > :is(.admonition-title, summary) {
|
||||
background-color: transparent;
|
||||
}
|
||||
.md-typeset :is(.note, .info, .tip, .abstract, .example, .question) > :is(.admonition-title, summary)::before {
|
||||
background-color: var(--nj-blue);
|
||||
}
|
||||
.md-typeset :is(.admonition, details):is(.danger, .bug, .failure) {
|
||||
border-color: var(--nj-red);
|
||||
background-color: var(--nj-red-soft);
|
||||
}
|
||||
.md-typeset :is(.danger, .bug, .failure) > :is(.admonition-title, summary) {
|
||||
background-color: transparent;
|
||||
}
|
||||
.md-typeset :is(.danger, .bug, .failure) > :is(.admonition-title, summary)::before {
|
||||
background-color: var(--nj-red);
|
||||
}
|
||||
|
||||
/* buttons */
|
||||
.md-typeset .md-button--primary {
|
||||
background-color: var(--nj-blue);
|
||||
border-color: var(--nj-blue);
|
||||
}
|
||||
|
||||
/* home page hero (overrides/home.html): blue band with the syntax pattern, headline, lead, buttons, code panel */
|
||||
.nj-hero {
|
||||
--nj-hero-to: #123a8a;
|
||||
color: #fff;
|
||||
background-color: var(--md-primary-fg-color);
|
||||
background-image: url("pattern-on-blue.svg"), linear-gradient(160deg, var(--md-primary-fg-color), var(--nj-hero-to));
|
||||
background-size: 160px 160px, auto;
|
||||
background-position: 0 -96px, 0 0; /* continue the tile of header and tabs */
|
||||
}
|
||||
[data-md-color-scheme="slate"] .nj-hero {
|
||||
--nj-hero-to: #0c2556;
|
||||
}
|
||||
.nj-hero__inner {
|
||||
display: grid;
|
||||
grid-template-columns: minmax(0, 1.1fr) minmax(0, 1fr);
|
||||
gap: 2.4rem;
|
||||
align-items: center;
|
||||
padding: 3rem .8rem 3.6rem;
|
||||
}
|
||||
.nj-hero__kicker {
|
||||
display: inline-block;
|
||||
margin: 0;
|
||||
padding: .15rem .55rem;
|
||||
border: 1px solid rgba(255, 255, 255, .35);
|
||||
border-radius: 4px;
|
||||
color: #bcd3fb;
|
||||
font-family: var(--md-code-font-family);
|
||||
font-size: .65rem; /* 13 px */
|
||||
font-weight: 500;
|
||||
letter-spacing: .02em;
|
||||
}
|
||||
.nj-hero__title {
|
||||
margin: 0 0 .8rem;
|
||||
color: #fff;
|
||||
font-size: clamp(1.7rem, 4.2vw, 3.2rem); /* 34-64 px */
|
||||
font-weight: 800;
|
||||
line-height: 1.02;
|
||||
letter-spacing: -.035em;
|
||||
}
|
||||
.nj-hero__title span {
|
||||
color: #bcd3fb;
|
||||
}
|
||||
.nj-hero__lead {
|
||||
max-width: 22em;
|
||||
margin: 0 0 2rem;
|
||||
color: rgba(255, 255, 255, .9);
|
||||
font-size: clamp(1.1rem, 2.2vw, 1.6rem); /* 22-32 px */
|
||||
font-style: italic;
|
||||
font-weight: 500;
|
||||
line-height: 1.35;
|
||||
letter-spacing: -.015em;
|
||||
}
|
||||
.nj-hero__actions {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: .6rem;
|
||||
margin: 0;
|
||||
}
|
||||
.nj-hero .md-button.nj-hero__button {
|
||||
margin: 0;
|
||||
padding: .55em 1.3em;
|
||||
border: 1px solid rgba(255, 255, 255, .6);
|
||||
border-radius: 6px;
|
||||
color: #fff;
|
||||
font-size: .75rem;
|
||||
font-weight: 600;
|
||||
}
|
||||
.nj-hero .md-button--primary.nj-hero__button {
|
||||
border-color: #fff;
|
||||
background-color: #fff;
|
||||
color: var(--md-primary-fg-color);
|
||||
}
|
||||
.nj-hero .md-button.nj-hero__button:is(:hover, :focus) {
|
||||
border-color: #fff;
|
||||
background-color: rgba(255, 255, 255, .12);
|
||||
color: #fff;
|
||||
}
|
||||
.nj-hero .md-button--primary.nj-hero__button:is(:hover, :focus) {
|
||||
background-color: #eaf1fd;
|
||||
color: var(--md-primary-fg-color);
|
||||
}
|
||||
.nj-hero__code {
|
||||
border-radius: 6px;
|
||||
background-color: var(--md-code-bg-color);
|
||||
box-shadow: 0 12px 32px rgba(5, 18, 48, .35);
|
||||
}
|
||||
.nj-hero__code pre {
|
||||
margin: 0;
|
||||
padding: 1.1rem 1.3rem;
|
||||
overflow-x: auto;
|
||||
color: var(--md-code-fg-color);
|
||||
font-family: var(--md-code-font-family);
|
||||
font-size: .7rem; /* 14 px */
|
||||
line-height: 1.7;
|
||||
}
|
||||
.nj-hero__code .nj-k { color: var(--nj-hl-type); }
|
||||
.nj-hero__code .nj-s { color: var(--nj-hl-string); }
|
||||
.nj-hero__code .nj-n { color: var(--nj-hl-number); }
|
||||
.nj-hero__code .nj-c { color: var(--nj-comment); font-style: italic; }
|
||||
@media screen and (max-width: 59.984375em) {
|
||||
.nj-hero__inner {
|
||||
grid-template-columns: minmax(0, 1fr);
|
||||
gap: 1.8rem;
|
||||
padding: 2rem .8rem 2.4rem;
|
||||
}
|
||||
}
|
||||
@media screen and (max-width: 29.984375em) {
|
||||
.nj-hero__code pre {
|
||||
font-size: .6rem;
|
||||
}
|
||||
}
|
||||
|
||||
/* the hero carries the headline: keep the page's h1 for the title and screen readers only */
|
||||
body:has(.nj-hero) .md-content__inner > h1 {
|
||||
position: absolute;
|
||||
width: 1px;
|
||||
height: 1px;
|
||||
overflow: hidden;
|
||||
clip: rect(0 0 0 0);
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
/* cards: 1 px line border, 6 px corners, blue icon on soft blue, blue border on hover */
|
||||
.md-typeset .grid.cards > ul > li {
|
||||
padding: 1rem 1.1rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
background-color: var(--md-default-bg-color);
|
||||
transition: border-color 150ms, box-shadow 150ms, transform 150ms;
|
||||
}
|
||||
.md-typeset .grid.cards > ul > li:is(:hover, :focus-within) {
|
||||
border-color: var(--nj-blue);
|
||||
box-shadow: 0 6px 18px rgba(23, 71, 166, .12);
|
||||
transform: translateY(-1px);
|
||||
}
|
||||
.md-typeset .grid.cards > ul > li > hr {
|
||||
display: none;
|
||||
}
|
||||
.md-typeset .grid.cards .twemoji.lg {
|
||||
box-sizing: content-box;
|
||||
margin-right: .5rem;
|
||||
padding: .3rem;
|
||||
border-radius: 6px;
|
||||
background-color: var(--nj-blue-soft);
|
||||
color: var(--nj-blue);
|
||||
}
|
||||
.md-typeset .grid.cards > ul > li > p:first-child strong {
|
||||
font-size: .9rem;
|
||||
font-weight: 700;
|
||||
letter-spacing: -.01em;
|
||||
}
|
||||
.md-typeset .grid.cards > ul > li > p:last-child a {
|
||||
font-weight: 600;
|
||||
}
|
||||
@media (prefers-reduced-motion: reduce) {
|
||||
.md-typeset .grid.cards > ul > li { transition: none; transform: none !important; }
|
||||
}
|
||||
|
||||
/* home page: no table of contents, so keep the text at reading width and the cards in three columns */
|
||||
body:has(.nj-hero) .md-content {
|
||||
max-width: 58rem;
|
||||
margin: 0 auto;
|
||||
}
|
||||
@media screen and (min-width: 60em) {
|
||||
body:has(.nj-hero) .md-typeset .grid.cards {
|
||||
grid-template-columns: repeat(3, minmax(0, 1fr));
|
||||
}
|
||||
}
|
||||
|
||||
/* lists: Material's indent, bullets as small blue squares, numbers in the secondary text colour */
|
||||
.md-typeset ul:not(.task-list, .md-annotation-list) > li {
|
||||
position: relative;
|
||||
list-style: none;
|
||||
}
|
||||
.md-typeset ul:not(.task-list, .md-annotation-list) > li::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: .65em; /* middle of the first line at line-height 1.65 */
|
||||
left: -.95em;
|
||||
width: .36em;
|
||||
height: .36em;
|
||||
background-color: var(--nj-blue);
|
||||
}
|
||||
.md-typeset ol > li::marker {
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-variant-numeric: tabular-nums;
|
||||
}
|
||||
.md-typeset .grid.cards > ul > li::before {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/* wider page: Material's grid stops at 61rem (1220 px) */
|
||||
.md-grid {
|
||||
max-width: 72rem; /* 1440 px */
|
||||
}
|
||||
|
||||
/* tables: full width, 1 px line border with 6 px corners, header row on the panel colour, 15 px text */
|
||||
.md-typeset__table {
|
||||
display: block; /* Material: inline-block, so tables only grow to their content */
|
||||
}
|
||||
.md-typeset table:not([class]) {
|
||||
display: table;
|
||||
width: 100%;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 6px;
|
||||
font-size: .75rem;
|
||||
line-height: 1.55;
|
||||
}
|
||||
.md-typeset table:not([class]) th {
|
||||
padding: .65em 1em;
|
||||
border-bottom: 1px solid var(--md-default-fg-color--lightest);
|
||||
background-color: var(--md-code-bg-color);
|
||||
color: var(--md-typeset-color);
|
||||
font-weight: 600;
|
||||
vertical-align: bottom;
|
||||
}
|
||||
.md-typeset table:not([class]) th:first-child { border-top-left-radius: 5px; }
|
||||
.md-typeset table:not([class]) th:last-child { border-top-right-radius: 5px; }
|
||||
.md-typeset table:not([class]) td {
|
||||
padding: .65em 1em;
|
||||
border-top: 1px solid var(--md-default-fg-color--lightest);
|
||||
}
|
||||
.md-typeset table:not([class]) tbody tr:first-child td {
|
||||
border-top: 0;
|
||||
}
|
||||
.md-typeset table:not([class]) tbody tr:hover {
|
||||
background-color: var(--nj-blue-soft);
|
||||
box-shadow: none;
|
||||
}
|
||||
.md-typeset table:not([class]) td code {
|
||||
white-space: nowrap;
|
||||
}
|
||||
/* numbers and header code stay on one line; a table wider than the screen scrolls sideways instead */
|
||||
.md-typeset table:not([class]) :is(td, th):is([align="right"], [style*="right"]),
|
||||
.md-typeset table:not([class]) th code {
|
||||
white-space: nowrap;
|
||||
}
|
||||
@media screen and (max-width: 44.984375em) {
|
||||
.md-typeset table:not([class]) {
|
||||
font-size: .7rem;
|
||||
}
|
||||
.md-typeset table:not([class]) :is(th, td) {
|
||||
padding: .55em .75em;
|
||||
}
|
||||
}
|
||||
|
||||
/* more room before headings (Material: h2 1.6em, h3 1.6em, h4-h6 1-1.25em) and at the end of each page (1.2rem) */
|
||||
.md-typeset h2 { margin-top: 2.4em; }
|
||||
.md-typeset h3 { margin-top: 2.2em; }
|
||||
.md-typeset h2 + h3 { margin-top: .8em; }
|
||||
.md-typeset :is(h4, h5, h6) { margin-top: 1.8em; }
|
||||
.md-content__inner {
|
||||
margin-bottom: 4.8rem; /* 96 px */
|
||||
}
|
||||
|
||||
/* Mermaid diagrams: white boxes with a blue outline, grey lines, Inter; shapes and spacing in js/mermaid-brand.js */
|
||||
:root > * {
|
||||
--md-mermaid-font-family: var(--md-text-font-family), sans-serif;
|
||||
--md-mermaid-edge-color: var(--md-default-fg-color--lighter);
|
||||
--md-mermaid-node-bg-color: var(--md-default-bg-color);
|
||||
--md-mermaid-node-fg-color: var(--nj-blue);
|
||||
--md-mermaid-label-bg-color: var(--md-default-bg-color);
|
||||
--md-mermaid-label-fg-color: var(--md-default-fg-color);
|
||||
--md-mermaid-sequence-actor-bg-color: var(--nj-blue-soft);
|
||||
--md-mermaid-sequence-actor-line-color: var(--md-default-fg-color--lighter);
|
||||
--md-mermaid-sequence-note-bg-color: var(--md-code-bg-color);
|
||||
--md-mermaid-sequence-note-border-color: var(--md-default-fg-color--lightest);
|
||||
--md-mermaid-sequence-number-fg-color: #fff;
|
||||
}
|
||||
|
||||
/* a diagram wider than the column scrolls sideways (js/mermaid-brand.js stops shrinking it at 80 %) */
|
||||
.md-typeset .mermaid {
|
||||
overflow-x: auto;
|
||||
}
|
||||
|
||||
|
||||
/* ---- polish pass ---- */
|
||||
|
||||
/* header: a search field that reads as a field on the band, tabs with an active marker, readable GitHub facts */
|
||||
.md-header .md-search__form {
|
||||
border: 1px solid rgba(255, 255, 255, .22);
|
||||
border-radius: 6px;
|
||||
background-color: rgba(255, 255, 255, .12);
|
||||
transition: background-color 150ms, border-color 150ms;
|
||||
}
|
||||
.md-header .md-search__form:hover {
|
||||
border-color: rgba(255, 255, 255, .4);
|
||||
background-color: rgba(255, 255, 255, .2);
|
||||
}
|
||||
.md-search__output {
|
||||
border-radius: 0 0 6px 6px;
|
||||
box-shadow: 0 16px 40px rgba(5, 18, 48, .28);
|
||||
}
|
||||
.md-search-result__link:focus-visible, .md-search-result__more summary:focus-visible {
|
||||
outline: 2px solid var(--nj-blue);
|
||||
outline-offset: -2px;
|
||||
}
|
||||
.md-tabs__link {
|
||||
font-size: .72rem;
|
||||
font-weight: 500;
|
||||
opacity: .85;
|
||||
}
|
||||
.md-tabs__item--active .md-tabs__link, .md-tabs__link:hover {
|
||||
opacity: 1;
|
||||
}
|
||||
.md-tabs__item--active {
|
||||
box-shadow: inset 0 -2px 0 #fff;
|
||||
}
|
||||
.md-source__facts {
|
||||
font-size: .62rem;
|
||||
}
|
||||
|
||||
/* footer: deep brand blue instead of neutral black (the dark scheme keeps its own near-black) */
|
||||
[data-md-color-scheme="default"] {
|
||||
--md-footer-bg-color: #0d2a66;
|
||||
--md-footer-bg-color--dark: #0a2152;
|
||||
}
|
||||
.md-footer-meta .md-copyright, .md-footer-meta .md-copyright a {
|
||||
color: rgba(255, 255, 255, .72);
|
||||
}
|
||||
.md-footer__link {
|
||||
border-radius: 6px;
|
||||
transition: background-color 150ms;
|
||||
}
|
||||
.md-footer__link:is(:hover, :focus-visible) {
|
||||
background-color: rgba(255, 255, 255, .08);
|
||||
}
|
||||
|
||||
/* page title: tighter to the first paragraph; page actions (view/edit source) stay in the background */
|
||||
.md-typeset h1 {
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
.md-content__button {
|
||||
opacity: .55;
|
||||
transition: opacity 150ms;
|
||||
}
|
||||
.md-content__button:is(:hover, :focus-visible) {
|
||||
opacity: 1;
|
||||
}
|
||||
body:has(.nj-hero) .md-content__button {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/* sidebars: bold marker for the current page, rail and marker for the table of contents */
|
||||
.md-nav__link--active {
|
||||
font-weight: 600;
|
||||
}
|
||||
.md-nav--secondary > .md-nav__list {
|
||||
margin-left: -.1rem;
|
||||
border-left: 1px solid color-mix(in srgb, var(--md-default-fg-color) 16%, transparent);
|
||||
}
|
||||
.md-nav--secondary .md-nav__link {
|
||||
margin-left: -1px;
|
||||
padding-left: .6rem;
|
||||
border-left: 2px solid transparent;
|
||||
}
|
||||
.md-nav--secondary .md-nav__link--active {
|
||||
border-left-color: var(--nj-blue);
|
||||
color: var(--nj-blue);
|
||||
}
|
||||
.md-nav--secondary .md-nav__list .md-nav__list {
|
||||
padding-left: .6rem;
|
||||
}
|
||||
.md-nav--secondary .md-nav__title {
|
||||
font-size: .64rem;
|
||||
letter-spacing: .04em;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
|
||||
/* keyboard focus: one visible ring in the brand blue */
|
||||
.md-typeset a:focus-visible, .md-typeset .md-button:focus-visible, .md-typeset summary:focus-visible,
|
||||
.md-nav__link:focus-visible, .md-tabs__link:focus-visible, .md-top:focus-visible {
|
||||
outline: 2px solid var(--nj-blue);
|
||||
outline-offset: 2px;
|
||||
border-radius: 3px;
|
||||
}
|
||||
.md-header :is(a, button, label):focus-visible, .nj-hero a:focus-visible {
|
||||
outline: 2px solid #fff;
|
||||
outline-offset: 2px;
|
||||
}
|
||||
|
||||
/* inline code must not stretch the line box (JetBrains Mono has tall metrics), abbreviations stay quiet */
|
||||
.md-typeset :not(pre) > code {
|
||||
line-height: 1;
|
||||
}
|
||||
.md-typeset abbr {
|
||||
border-bottom-color: var(--md-default-fg-color--lighter);
|
||||
}
|
||||
.md-typeset :is(h1, h2, h3, h4, a, .grid.cards > ul > li > p:first-child) abbr {
|
||||
border-bottom-color: transparent;
|
||||
}
|
||||
|
||||
/* number railroad diagram: inline SVG (docs/images/json_syntax_number.svg), follows the colour scheme */
|
||||
.md-typeset .railroad-wrap, .md-typeset .nj-fig-wrap {
|
||||
overflow-x: auto;
|
||||
margin: 1.5rem 0;
|
||||
}
|
||||
.md-typeset svg.railroad {
|
||||
display: block;
|
||||
width: 100%;
|
||||
min-width: 36rem;
|
||||
max-width: 52rem;
|
||||
margin-inline: auto;
|
||||
color: var(--md-default-fg-color);
|
||||
font-family: var(--md-text-font-family), sans-serif;
|
||||
}
|
||||
.railroad .rr-t { fill: color-mix(in srgb, var(--md-typeset-a-color) 10%, transparent); stroke: var(--md-typeset-a-color); stroke-width: 2; }
|
||||
.railroad .rr-track, .railroad .rr-n { stroke: color-mix(in srgb, currentColor 60%, var(--md-default-bg-color)); stroke-opacity: 1; } /* opaque, so overlapping segments do not darken */
|
||||
.railroad .rr-n { fill: color-mix(in srgb, currentColor 6%, transparent); stroke-width: 2; }
|
||||
.railroad .rr-bg { fill: var(--md-default-bg-color); }
|
||||
.railroad .rr-arrow { fill: currentColor; fill-opacity: .6; }
|
||||
.railroad text { fill: currentColor; text-anchor: middle; }
|
||||
.railroad .rr-c { font-family: var(--md-code-font-family), monospace; font-size: 16px; font-weight: 500; }
|
||||
.railroad .rr-b { font-size: 14.5px; font-weight: 500; }
|
||||
.railroad .rr-l { font-size: 14px; text-anchor: start; fill-opacity: .6; }
|
||||
.railroad .rr-name { font-size: 17px; font-weight: 700; fill-opacity: 1; }
|
||||
/* figures drawn as inline SVG (docs/images/callback_events.svg, range-*.svg): they follow the colour scheme */
|
||||
.md-typeset svg.nj-fig {
|
||||
display: block;
|
||||
width: 100%;
|
||||
height: auto;
|
||||
margin-inline: auto;
|
||||
color: var(--md-default-fg-color);
|
||||
font-family: var(--md-text-font-family), sans-serif;
|
||||
}
|
||||
.md-typeset svg.nj-fig--range { min-width: 30rem; max-width: 40rem; }
|
||||
.md-typeset svg.nj-fig--cb { max-width: 30rem; }
|
||||
.nj-fig { --fg-line: color-mix(in srgb, currentColor 55%, var(--md-default-bg-color)); }
|
||||
.nj-fig .fg-cell { fill: color-mix(in srgb, var(--md-typeset-a-color) 14%, var(--md-default-bg-color)); stroke: var(--fg-line); stroke-width: 1.5; }
|
||||
.nj-fig .fg-cell--end { fill: none; stroke-dasharray: 4 3; }
|
||||
.nj-fig .fg-pill { fill: color-mix(in srgb, var(--md-typeset-a-color) 10%, var(--md-default-bg-color)); stroke: var(--md-typeset-a-color); stroke-width: 1.5; }
|
||||
.nj-fig .fg-pilltext { fill: var(--md-typeset-a-color); font-family: var(--md-code-font-family), monospace; font-size: 14px; font-weight: 500; text-anchor: middle; }
|
||||
.nj-fig .fg-arrow { stroke: var(--fg-line); stroke-width: 1.5; fill: none; }
|
||||
.nj-fig .fg-arrow--dash { stroke-dasharray: 3 3; }
|
||||
.nj-fig .fg-head { fill: var(--fg-line); }
|
||||
.nj-fig .fg-note { fill: currentColor; fill-opacity: .7; font-size: 13.5px; text-anchor: middle; }
|
||||
.nj-fig .fg-note--r { text-anchor: end; }
|
||||
.nj-fig .fg-note--l { text-anchor: start; }
|
||||
.nj-fig .fg-h { fill: currentColor; fill-opacity: .7; font-size: 15px; font-weight: 600; }
|
||||
.nj-fig .fg-code { fill: currentColor; font-family: var(--md-code-font-family), monospace; font-size: 16px; white-space: pre; }
|
||||
.nj-fig .fg-leg { font-size: 15px; }
|
||||
.nj-fig { --cb-os: #4eb05a; --cb-oe: #1a6b34; --cb-k: #e5534b; --cb-as: #f0c000; --cb-ae: #b07d00; --cb-v: #1f6fd1; }
|
||||
[data-md-color-scheme="slate"] .nj-fig { --cb-os: #7ee787; --cb-oe: #2ea043; --cb-k: #ff7b72; --cb-as: #f2cc60; --cb-ae: #c69026; --cb-v: #58a6ff; }
|
||||
.nj-fig .cb-os { fill: var(--cb-os); }
|
||||
.nj-fig .cb-oe { fill: var(--cb-oe); }
|
||||
.nj-fig .cb-k { fill: var(--cb-k); }
|
||||
.nj-fig .cb-as { fill: var(--cb-as); }
|
||||
.nj-fig .cb-ae { fill: var(--cb-ae); }
|
||||
.nj-fig .cb-v { fill: var(--cb-v); }
|
||||
.md-typeset img[src*="json-light"], .md-typeset img[src*="json-dark"] {
|
||||
border-radius: 8px;
|
||||
}
|
||||
.md-typeset img {
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
}
|
||||
|
||||
/* home page: content uses the same column as every other page */
|
||||
body:has(.nj-hero) .md-content {
|
||||
max-width: none;
|
||||
margin: 0;
|
||||
}
|
||||
.md-typeset .grid.cards {
|
||||
width: auto;
|
||||
}
|
||||
|
||||
/* 404 page (overrides/404.html) */
|
||||
.nj-404 {
|
||||
max-width: 30rem;
|
||||
padding: 2rem 0 3rem;
|
||||
}
|
||||
.nj-404__code {
|
||||
margin: 0 0 .4rem;
|
||||
color: var(--nj-blue);
|
||||
font-family: var(--md-code-font-family);
|
||||
font-size: .8rem;
|
||||
font-weight: 500;
|
||||
}
|
||||
.md-typeset .nj-404 h1 {
|
||||
margin-bottom: .8rem;
|
||||
}
|
||||
.nj-404 .md-button {
|
||||
margin: .4rem .4rem 0 0;
|
||||
}
|
||||
|
||||
/* touch targets and phones */
|
||||
@media screen and (max-width: 59.984375em) {
|
||||
.md-nav__link {
|
||||
padding-block: .2rem;
|
||||
}
|
||||
}
|
||||
@media screen and (max-width: 29.984375em) {
|
||||
.md-typeset h1 {
|
||||
font-size: 1.7em;
|
||||
}
|
||||
.md-typeset .highlight pre > code {
|
||||
font-size: .68rem;
|
||||
}
|
||||
}
|
||||
|
||||
/* figure captions: "Figure N." in bold, close to the figure, set in from the text column; figures and tables are
|
||||
numbered per page, each with its own counter */
|
||||
.md-content__inner { counter-reset: nj-figure nj-table; }
|
||||
.md-typeset :is(.nj-caption, .nj-charts-caption) {
|
||||
max-width: none;
|
||||
margin: .3rem 2rem 1.5rem;
|
||||
font-size: .75rem;
|
||||
line-height: 1.5;
|
||||
text-align: left;
|
||||
color: var(--md-default-fg-color--light);
|
||||
}
|
||||
.md-typeset :is(.nj-fig-wrap, .railroad-wrap, .nj-charts-grid-wrap) + :is(.nj-caption, .nj-charts-caption) { margin-top: -1.1rem; }
|
||||
.md-typeset .nj-charts-grid-wrap + :is(.nj-caption, .nj-charts-caption) { margin-top: .3rem; }
|
||||
.md-typeset :is(.nj-caption, .nj-charts-caption)::before {
|
||||
counter-increment: nj-figure;
|
||||
content: "Figure " counter(nj-figure) ". ";
|
||||
font-weight: 700;
|
||||
color: var(--md-default-fg-color);
|
||||
}
|
||||
@media screen and (max-width: 44.9375em) {
|
||||
.md-typeset :is(.nj-caption, .nj-charts-caption) { margin-inline: 1rem; }
|
||||
}
|
||||
|
||||
/* table captions: "Table N." in bold, directly below the table, in the figure caption style */
|
||||
.md-typeset .nj-table-caption {
|
||||
max-width: none;
|
||||
margin: .3rem 2rem 1.5rem;
|
||||
font-size: .75rem;
|
||||
line-height: 1.5;
|
||||
text-align: left;
|
||||
color: var(--md-default-fg-color--light);
|
||||
}
|
||||
.md-typeset :is(.md-typeset__scrollwrap, .md-typeset__table) + .nj-table-caption { margin-top: -.4rem; }
|
||||
.md-typeset .nj-table-caption::before {
|
||||
counter-increment: nj-table;
|
||||
content: "Table " counter(nj-table) ". ";
|
||||
font-weight: 700;
|
||||
color: var(--md-default-fg-color);
|
||||
}
|
||||
@media screen and (max-width: 44.9375em) {
|
||||
.md-typeset .nj-table-caption { margin-inline: 1rem; }
|
||||
}
|
||||
@@ -1,142 +0,0 @@
|
||||
/* figures: charts (docs/images/compile_times.svg, binary_sizes_*.svg, ordered_json_scaling.svg from
|
||||
scripts/figures/charts.py) and the number literal explorer on features/types/number_handling.md */
|
||||
|
||||
/* series colours: categorical slots validated for CVD separation on the light and the slate surface */
|
||||
.nj-charts, .nj-charts-key {
|
||||
--nj-charts-c1: #2a78d6;
|
||||
--nj-charts-c2: #eb6834;
|
||||
--nj-charts-c3: #1baf7a;
|
||||
--nj-charts-c4: #eda100;
|
||||
--nj-charts-c5: #e87ba4;
|
||||
--nj-charts-c6: #008300;
|
||||
--nj-charts-ink2: var(--md-default-fg-color--light);
|
||||
--nj-charts-grid: color-mix(in srgb, currentColor 12%, var(--md-default-bg-color));
|
||||
--nj-charts-base: color-mix(in srgb, currentColor 35%, var(--md-default-bg-color));
|
||||
}
|
||||
[data-md-color-scheme="slate"] :is(.nj-charts, .nj-charts-key) {
|
||||
--nj-charts-c1: #3987e5;
|
||||
--nj-charts-c2: #d95926;
|
||||
--nj-charts-c3: #199e70;
|
||||
--nj-charts-c4: #c98500;
|
||||
--nj-charts-c5: #d55181;
|
||||
--nj-charts-c6: #008300;
|
||||
}
|
||||
/* concepts: two compilers, two object types */
|
||||
.nj-charts { --nj-charts-clang-c: var(--nj-charts-c1); --nj-charts-gcc-c: var(--nj-charts-c2);
|
||||
--nj-charts-json-c: var(--nj-charts-c1); --nj-charts-ojson-c: var(--nj-charts-c2); }
|
||||
|
||||
.md-typeset svg.nj-charts--compile, .md-typeset svg.nj-charts--scaling { max-width: 26rem; }
|
||||
.md-typeset svg.nj-charts--sizes { max-width: 26rem; }
|
||||
|
||||
.nj-charts text { fill: currentColor; font-size: 13px; }
|
||||
.nj-charts .nj-charts-leg { font-size: 13.5px; }
|
||||
.nj-charts .nj-charts-rowlabel { font-size: 13.5px; font-weight: 500; }
|
||||
.nj-charts .nj-charts-code { font-family: var(--md-code-font-family), monospace; font-size: 12.5px; }
|
||||
.nj-charts .nj-charts-sub { fill: var(--nj-charts-ink2); font-weight: 400; }
|
||||
.nj-charts .nj-charts-fmt { text-anchor: end; font-weight: 400; }
|
||||
.nj-charts .nj-charts-best { font-weight: 700; }
|
||||
.nj-charts .nj-charts-panel { font-family: var(--md-code-font-family), monospace; font-size: 14px; font-weight: 600; }
|
||||
.nj-charts .nj-charts-tick { fill: var(--nj-charts-ink2); font-size: 12px; text-anchor: middle; font-variant-numeric: tabular-nums; }
|
||||
.nj-charts .nj-charts-tick--l { text-anchor: start; }
|
||||
.nj-charts .nj-charts-tick--r { text-anchor: end; }
|
||||
.nj-charts .nj-charts-val { font-size: 12px; font-variant-numeric: tabular-nums;
|
||||
paint-order: stroke; stroke: var(--md-default-bg-color); stroke-width: 4px; stroke-linejoin: round; }
|
||||
.nj-charts .nj-charts-factor { fill: var(--nj-charts-ink2); font-size: 12px; font-weight: 600; text-anchor: middle; }
|
||||
.nj-charts .nj-charts-note { fill: var(--nj-charts-ink2); font-size: 12px; }
|
||||
|
||||
.nj-charts .nj-charts-grid { stroke: var(--nj-charts-grid); stroke-width: 1; }
|
||||
.nj-charts .nj-charts-zero, .nj-charts .nj-charts-axis { stroke: var(--nj-charts-base); stroke-width: 1.5; }
|
||||
.nj-charts .nj-charts-ref { stroke: currentColor; stroke-width: 1.5; }
|
||||
|
||||
.nj-charts .nj-charts-c1 { fill: var(--nj-charts-c1); }
|
||||
.nj-charts .nj-charts-c2 { fill: var(--nj-charts-c2); }
|
||||
.nj-charts .nj-charts-c3 { fill: var(--nj-charts-c3); }
|
||||
.nj-charts .nj-charts-c4 { fill: var(--nj-charts-c4); }
|
||||
.nj-charts .nj-charts-c5 { fill: var(--nj-charts-c5); }
|
||||
.nj-charts .nj-charts-c6 { fill: var(--nj-charts-c6); }
|
||||
.nj-charts .nj-charts-dim { fill-opacity: .45; }
|
||||
.nj-charts .nj-charts-clang { fill: var(--nj-charts-clang-c); }
|
||||
.nj-charts .nj-charts-gcc { fill: var(--nj-charts-gcc-c); }
|
||||
.nj-charts polyline.nj-charts-json, .nj-charts line.nj-charts-json { stroke: var(--nj-charts-json-c); stroke-width: 2; fill: none; }
|
||||
.nj-charts polyline.nj-charts-ojson, .nj-charts line.nj-charts-ojson { stroke: var(--nj-charts-ojson-c); stroke-width: 2; fill: none; }
|
||||
.nj-charts .nj-charts-json-dot { fill: var(--nj-charts-json-c); stroke: var(--md-default-bg-color); stroke-width: 2; }
|
||||
.nj-charts .nj-charts-ojson-dot { fill: var(--nj-charts-ojson-c); stroke: var(--md-default-bg-color); stroke-width: 2; }
|
||||
|
||||
/* single wide charts: larger text on phones, where the SVG is scaled down */
|
||||
@media screen and (max-width: 44.9375em) {
|
||||
svg.nj-charts.nj-charts--compile text, svg.nj-charts.nj-charts--scaling text { font-size: 15px; }
|
||||
svg.nj-charts.nj-charts--compile .nj-charts-code { font-size: 14px; }
|
||||
svg.nj-charts:is(.nj-charts--compile, .nj-charts--scaling) :is(.nj-charts-tick, .nj-charts-val, .nj-charts-factor, .nj-charts-note) { font-size: 14px; }
|
||||
}
|
||||
|
||||
/* small multiples: two panels per row, one on narrow screens */
|
||||
.md-typeset .nj-charts-grid-wrap {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fit, minmax(16rem, 1fr));
|
||||
gap: 1rem 2rem;
|
||||
margin: 1.5rem 0 .5rem;
|
||||
}
|
||||
.md-typeset .nj-charts-grid-wrap > .nj-fig-wrap { margin: 0; }
|
||||
|
||||
/* number literal explorer */
|
||||
.md-typeset .nj-charts-num-ui {
|
||||
margin: 1rem 0 .75rem;
|
||||
padding: .8rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 8px;
|
||||
}
|
||||
.md-typeset .nj-charts-num-ui label { display: block; font-weight: 600; font-size: .75rem; margin-bottom: .3rem; }
|
||||
.md-typeset .nj-charts-num-input {
|
||||
width: 100%;
|
||||
box-sizing: border-box;
|
||||
min-height: 44px;
|
||||
padding: .4rem .6rem;
|
||||
font-family: var(--md-code-font-family), monospace;
|
||||
font-size: .8rem;
|
||||
color: var(--md-default-fg-color);
|
||||
background: var(--md-code-bg-color);
|
||||
border: 1px solid var(--md-default-fg-color--lighter);
|
||||
border-radius: 6px;
|
||||
}
|
||||
.md-typeset .nj-charts-num-input:focus-visible, .md-typeset .nj-charts-num-chip:focus-visible {
|
||||
outline: 2px solid var(--md-typeset-a-color);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
.md-typeset .nj-charts-num-ui ul.nj-charts-num-chips:not([hidden]) { display: flex; flex-wrap: wrap; gap: .35rem; margin: .6rem 0; padding: 0; list-style: none; }
|
||||
.md-typeset .nj-charts-num-ui ul.nj-charts-num-chips > li { margin: 0; padding: 0; list-style: none; }
|
||||
.md-typeset .nj-charts-num-ui ul.nj-charts-num-chips > li::before, .md-typeset .nj-charts-num-ui ul.nj-charts-num-chips > li::marker { content: none; }
|
||||
.md-typeset .nj-charts-num-chip {
|
||||
min-height: 44px;
|
||||
max-width: 100%;
|
||||
padding: .25rem .6rem;
|
||||
overflow-wrap: anywhere;
|
||||
font-family: var(--md-code-font-family), monospace;
|
||||
font-size: .7rem;
|
||||
color: var(--md-typeset-a-color);
|
||||
background: color-mix(in srgb, var(--md-typeset-a-color) 8%, var(--md-default-bg-color));
|
||||
border: 1px solid color-mix(in srgb, var(--md-typeset-a-color) 35%, var(--md-default-bg-color));
|
||||
border-radius: 6px;
|
||||
cursor: pointer;
|
||||
text-align: left;
|
||||
}
|
||||
.md-typeset .nj-charts-num-chip[aria-pressed="true"] {
|
||||
color: var(--md-default-bg-color);
|
||||
background: var(--md-typeset-a-color);
|
||||
border-color: var(--md-typeset-a-color);
|
||||
}
|
||||
.md-typeset .nj-charts-num-out {
|
||||
display: grid;
|
||||
grid-template-columns: max-content 1fr;
|
||||
gap: .2rem .8rem;
|
||||
margin: 0;
|
||||
font-size: .75rem;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.md-typeset .nj-charts-num-out dt { color: var(--md-default-fg-color--light); margin: 0; }
|
||||
.md-typeset .nj-charts-num-out dd { margin: 0; }
|
||||
.md-typeset .nj-charts-num-miss { font-size: .75rem; color: var(--md-default-fg-color--light); margin: 0; }
|
||||
.md-typeset .nj-charts-num tr.nj-charts-num-hit td { background: var(--md-accent-fg-color--transparent); }
|
||||
|
||||
/* direct line labels replace the legend */
|
||||
.nj-charts .nj-charts-name-json { fill: var(--nj-charts-json-c); font-weight: 600; }
|
||||
.nj-charts .nj-charts-name-ojson { fill: var(--nj-charts-ojson-c); font-weight: 600; }
|
||||
@@ -1,75 +0,0 @@
|
||||
/* figures: exceptions (home/exceptions.md exception map, community/quality_assurance.md pipeline) */
|
||||
|
||||
/* the generated SVGs hold a wide and a narrow drawing; show one of them */
|
||||
.md-typeset svg.nj-exceptions-map--wide, .md-typeset svg.nj-exceptions-qa--wide { max-width: 47.5rem; }
|
||||
.md-typeset svg.nj-exceptions-map--narrow, .md-typeset svg.nj-exceptions-qa--narrow { display: none; max-width: 24rem; }
|
||||
@media screen and (max-width: 37.5em) {
|
||||
.md-typeset svg.nj-exceptions-map--wide, .md-typeset svg.nj-exceptions-qa--wide { display: none; }
|
||||
.md-typeset svg.nj-exceptions-map--narrow, .md-typeset svg.nj-exceptions-qa--narrow { display: block; }
|
||||
}
|
||||
|
||||
/* shared */
|
||||
.nj-fig { --nj-exceptions-line: color-mix(in srgb, currentColor 45%, var(--md-default-bg-color)); }
|
||||
.nj-fig .nj-exceptions-edge { stroke: var(--nj-exceptions-line); stroke-width: 1.5; fill: none; }
|
||||
.nj-fig .nj-exceptions-tri { fill: var(--md-default-bg-color); stroke: var(--nj-exceptions-line); stroke-width: 1.3; }
|
||||
.nj-fig .nj-exceptions-box {
|
||||
fill: color-mix(in srgb, currentColor 4%, var(--md-default-bg-color));
|
||||
stroke: color-mix(in srgb, currentColor 30%, var(--md-default-bg-color));
|
||||
stroke-width: 1.5;
|
||||
}
|
||||
.nj-fig .nj-exceptions-box--fam {
|
||||
fill: color-mix(in srgb, var(--md-typeset-a-color) 9%, var(--md-default-bg-color));
|
||||
stroke: color-mix(in srgb, var(--md-typeset-a-color) 55%, var(--md-default-bg-color));
|
||||
}
|
||||
.nj-fig .nj-exceptions-name { fill: currentColor; font-family: var(--md-code-font-family), monospace; font-size: 14px; font-weight: 600; }
|
||||
.nj-fig .nj-exceptions-sub { fill: currentColor; fill-opacity: .68; font-size: 12.5px; }
|
||||
|
||||
/* exception map: id chips are links */
|
||||
.nj-fig .nj-exceptions-chip rect {
|
||||
fill: color-mix(in srgb, var(--md-typeset-a-color) 7%, var(--md-default-bg-color));
|
||||
stroke: color-mix(in srgb, var(--md-typeset-a-color) 40%, var(--md-default-bg-color));
|
||||
stroke-width: 1.2;
|
||||
transition: fill .15s;
|
||||
}
|
||||
.nj-fig .nj-exceptions-chip--named rect {
|
||||
fill: color-mix(in srgb, var(--md-typeset-a-color) 16%, var(--md-default-bg-color));
|
||||
stroke: var(--md-typeset-a-color);
|
||||
}
|
||||
.nj-fig .nj-exceptions-id { fill: var(--md-typeset-a-color); font-family: var(--md-code-font-family), monospace; font-size: 13px; font-weight: 600; }
|
||||
.nj-fig .nj-exceptions-label { fill: currentColor; font-size: 12.5px; font-weight: 500; }
|
||||
.nj-fig a:hover rect, .nj-fig a:focus-visible rect {
|
||||
fill: color-mix(in srgb, var(--md-typeset-a-color) 28%, var(--md-default-bg-color));
|
||||
}
|
||||
.nj-fig a:focus { outline: none; }
|
||||
.nj-fig a:focus-visible rect { stroke: var(--md-typeset-a-color); stroke-width: 2.5; }
|
||||
.nj-fig a:hover .nj-exceptions-name, .nj-fig a:focus-visible .nj-exceptions-name { text-decoration: underline; }
|
||||
@media (prefers-reduced-motion: reduce) {
|
||||
.nj-fig .nj-exceptions-chip rect { transition: none; }
|
||||
}
|
||||
|
||||
/* quality assurance pipeline */
|
||||
.nj-fig { --nj-exceptions-push: var(--md-typeset-a-color); --nj-exceptions-sched: #a86400; --nj-exceptions-cont: #1a7f37; }
|
||||
[data-md-color-scheme="slate"] .nj-fig { --nj-exceptions-sched: #e3a33b; --nj-exceptions-cont: #56c46e; }
|
||||
.nj-fig .nj-exceptions-groupbox {
|
||||
fill: color-mix(in srgb, currentColor 2.5%, var(--md-default-bg-color));
|
||||
stroke: color-mix(in srgb, currentColor 22%, var(--md-default-bg-color));
|
||||
stroke-width: 1.2;
|
||||
stroke-dasharray: 5 4;
|
||||
}
|
||||
.nj-fig .nj-exceptions-group { fill: currentColor; fill-opacity: .68; font-size: 13px; font-weight: 600; letter-spacing: .02em; }
|
||||
.nj-fig .nj-exceptions-card .nj-exceptions-box { fill: var(--md-default-bg-color); }
|
||||
.nj-fig .nj-exceptions-ctitle { fill: currentColor; font-size: 15px; font-weight: 700; }
|
||||
.nj-fig .nj-exceptions-line { fill: currentColor; fill-opacity: .8; font-size: 12.5px; }
|
||||
.nj-fig .nj-exceptions-badge { stroke-width: 1.2; }
|
||||
.nj-fig .nj-exceptions-badgetext { font-size: 11px; font-weight: 600; text-anchor: middle; }
|
||||
.nj-fig .nj-exceptions-badge--push { fill: color-mix(in srgb, var(--nj-exceptions-push) 12%, var(--md-default-bg-color)); stroke: var(--nj-exceptions-push); }
|
||||
.nj-fig .nj-exceptions-badge--sched { fill: color-mix(in srgb, var(--nj-exceptions-sched) 12%, var(--md-default-bg-color)); stroke: var(--nj-exceptions-sched); }
|
||||
.nj-fig .nj-exceptions-badge--cont { fill: color-mix(in srgb, var(--nj-exceptions-cont) 12%, var(--md-default-bg-color)); stroke: var(--nj-exceptions-cont); }
|
||||
.nj-fig .nj-exceptions-badgetext--push { fill: var(--nj-exceptions-push); }
|
||||
.nj-fig .nj-exceptions-badgetext--sched { fill: var(--nj-exceptions-sched); }
|
||||
.nj-fig .nj-exceptions-badgetext--cont { fill: var(--nj-exceptions-cont); }
|
||||
.nj-fig .nj-exceptions-stage { fill: var(--md-typeset-a-color); }
|
||||
.nj-fig .nj-exceptions-stagetext { fill: #fff; font-size: 14px; font-weight: 700; text-anchor: middle; }
|
||||
.nj-fig .nj-exceptions-stagesub { fill: #fff; fill-opacity: .85; font-size: 12px; text-anchor: middle; }
|
||||
[data-md-color-scheme="slate"] .nj-fig .nj-exceptions-stage { fill: #1747a6; }
|
||||
.nj-fig .nj-exceptions-qa .fg-head, .nj-exceptions-qa .fg-head { fill: var(--nj-exceptions-line); }
|
||||
@@ -1,176 +0,0 @@
|
||||
/* figures: integration */
|
||||
|
||||
/* namespace name builder (features/namespace.md, js/fig-integration.js) */
|
||||
.md-typeset .nj-integration-ns {
|
||||
--nj-int-line: color-mix(in srgb, currentColor 30%, var(--md-default-bg-color));
|
||||
display: block;
|
||||
width: auto;
|
||||
max-width: none;
|
||||
margin: 1.5rem 0;
|
||||
padding: .9rem 1rem;
|
||||
text-align: left;
|
||||
border: 1px solid var(--nj-int-line);
|
||||
border-radius: 8px;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__strip {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
align-items: flex-start;
|
||||
gap: .5rem .15rem;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg {
|
||||
display: inline-flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
min-width: 0;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg code {
|
||||
padding: .25em .5em;
|
||||
border: 1.5px solid var(--nj-int-line);
|
||||
border-radius: 6px;
|
||||
background: var(--md-default-bg-color);
|
||||
color: var(--md-default-fg-color);
|
||||
font-size: .8rem;
|
||||
font-weight: 600;
|
||||
word-break: normal;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg small {
|
||||
max-width: 10rem;
|
||||
margin-top: .25rem;
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-size: .58rem;
|
||||
line-height: 1.25;
|
||||
text-align: center;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg--sep code {
|
||||
border-color: transparent;
|
||||
padding-inline: .1em;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg--abi code {
|
||||
border-color: var(--md-typeset-a-color);
|
||||
background: color-mix(in srgb, var(--md-typeset-a-color) 12%, var(--md-default-bg-color));
|
||||
color: var(--md-typeset-a-color);
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg--tag code {
|
||||
border-style: dashed;
|
||||
border-color: var(--md-typeset-a-color);
|
||||
color: var(--md-typeset-a-color);
|
||||
}
|
||||
.md-typeset .nj-integration-ns__seg--ver code {
|
||||
background: color-mix(in srgb, currentColor 8%, var(--md-default-bg-color));
|
||||
}
|
||||
.md-typeset .nj-integration-ns figcaption {
|
||||
max-width: none;
|
||||
margin: .8rem 0 0;
|
||||
font-size: .75rem;
|
||||
text-align: left;
|
||||
color: var(--md-default-fg-color--light);
|
||||
}
|
||||
.md-typeset .nj-integration-ns__controls {
|
||||
margin-top: 1rem;
|
||||
padding-top: .8rem;
|
||||
border-top: 1px solid var(--nj-int-line);
|
||||
font-size: .7rem;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__version select {
|
||||
min-height: 2rem;
|
||||
margin-left: .3rem;
|
||||
padding: 0 .4rem;
|
||||
border: 1px solid var(--nj-int-line);
|
||||
border-radius: 6px;
|
||||
background: var(--md-default-bg-color);
|
||||
color: var(--md-default-fg-color);
|
||||
font: inherit;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__list {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fill, minmax(min(100%, 21rem), 1fr));
|
||||
gap: 0 1rem;
|
||||
margin: .7rem 0 0;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__list legend {
|
||||
padding: 0;
|
||||
margin-bottom: .3rem;
|
||||
font-weight: 600;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__opt {
|
||||
display: grid;
|
||||
grid-template-columns: 1.1rem 1fr;
|
||||
align-items: center;
|
||||
gap: 0 .55rem;
|
||||
min-height: 2.2rem;
|
||||
padding: .15rem 0;
|
||||
cursor: pointer;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__meta {
|
||||
grid-column: 2;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 0 .45rem;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__opt input {
|
||||
grid-row: 1 / span 2;
|
||||
width: 1.1rem;
|
||||
height: 1.1rem;
|
||||
margin: 0;
|
||||
accent-color: var(--md-typeset-a-color);
|
||||
}
|
||||
.md-typeset .nj-integration-ns__opt input:focus-visible {
|
||||
outline: 2px solid var(--md-accent-fg-color);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__opt code {
|
||||
font-size: .64rem;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__hint {
|
||||
color: var(--md-typeset-a-color);
|
||||
font-family: var(--md-code-font-family);
|
||||
font-size: .64rem;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__since {
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-size: .6rem;
|
||||
}
|
||||
.md-typeset .nj-integration-ns__opt.is-unavailable {
|
||||
cursor: not-allowed;
|
||||
opacity: .5;
|
||||
}
|
||||
@media screen and (max-width: 44.984375em) {
|
||||
.md-typeset .nj-integration-ns__opt {
|
||||
min-height: 2.75rem;
|
||||
}
|
||||
}
|
||||
|
||||
/* roadmap lanes and release timeline (scripts/figures/integration.py, release_timeline.py) */
|
||||
.md-typeset svg.nj-fig--lanes { min-width: 44rem; max-width: 46rem; }
|
||||
.md-typeset svg.nj-fig--timeline { min-width: 44rem; max-width: 52rem; }
|
||||
.nj-fig .nj-int-lane { fill: color-mix(in srgb, var(--md-typeset-a-color) 10%, var(--md-default-bg-color)); stroke: var(--md-typeset-a-color); stroke-width: 1.5; }
|
||||
.nj-fig .nj-int-lane--future { fill: none; stroke-dasharray: 6 4; }
|
||||
.nj-fig .nj-int-lanetext { fill: var(--md-typeset-a-color); font-size: 15px; font-weight: 700; }
|
||||
.nj-fig .nj-int-text { fill: currentColor; font-size: 13px; }
|
||||
.nj-fig .nj-int-mute { fill: currentColor; fill-opacity: .7; font-size: 12.5px; }
|
||||
.nj-fig .nj-int-macro { fill: currentColor; font-family: var(--md-code-font-family), monospace; font-size: 12.5px; }
|
||||
.nj-fig .nj-int-val { fill: currentColor; font-family: var(--md-code-font-family), monospace; font-size: 13px; font-weight: 600; }
|
||||
.nj-fig .nj-int-row { fill: color-mix(in srgb, currentColor 4%, var(--md-default-bg-color)); }
|
||||
.nj-fig .nj-int-track { fill: color-mix(in srgb, currentColor 14%, var(--md-default-bg-color)); stroke: color-mix(in srgb, currentColor 45%, var(--md-default-bg-color)); stroke-width: 1.2; }
|
||||
.nj-fig .nj-int-track--on { fill: var(--md-typeset-a-color); stroke: var(--md-typeset-a-color); }
|
||||
.nj-fig .nj-int-knob { fill: var(--md-default-bg-color); stroke: color-mix(in srgb, currentColor 45%, var(--md-default-bg-color)); stroke-width: 1.2; }
|
||||
.nj-fig .nj-int-knob--on { stroke: var(--md-typeset-a-color); }
|
||||
.nj-fig .nj-int-axis { stroke: color-mix(in srgb, currentColor 45%, var(--md-default-bg-color)); stroke-width: 1.5; }
|
||||
.nj-fig .nj-int-grid { stroke: color-mix(in srgb, currentColor 14%, var(--md-default-bg-color)); stroke-width: 1; }
|
||||
.nj-fig .nj-int-minor { fill: var(--md-typeset-a-color); stroke: var(--md-default-bg-color); stroke-width: 1.5; }
|
||||
.nj-fig .nj-int-patch { fill: var(--md-default-bg-color); stroke: var(--md-typeset-a-color); stroke-width: 1.5; }
|
||||
.nj-fig .nj-int-major { fill: currentColor; fill-opacity: .7; font-size: 13px; font-weight: 600; }
|
||||
.nj-fig .nj-int-label { fill: currentColor; font-size: 12px; font-weight: 600; text-anchor: middle; }
|
||||
.nj-fig .nj-int-year { fill: currentColor; fill-opacity: .7; font-size: 12px; text-anchor: middle; }
|
||||
.nj-fig .nj-int-leader { stroke: color-mix(in srgb, currentColor 30%, var(--md-default-bg-color)); stroke-width: 1; }
|
||||
.nj-fig .nj-int-hit { fill: transparent; }
|
||||
|
||||
/* roadmap: value pills (3.x default -> 4.0 value) */
|
||||
.nj-fig .nj-int-pill { fill: color-mix(in srgb, currentColor 8%, var(--md-default-bg-color)); stroke: color-mix(in srgb, currentColor 35%, var(--md-default-bg-color)); stroke-width: 1.2; }
|
||||
.nj-fig .nj-int-pill--v4 { fill: var(--md-typeset-a-color); stroke: var(--md-typeset-a-color); }
|
||||
.nj-fig .nj-int-val--v4 { fill: var(--md-default-bg-color); }
|
||||
@@ -1,107 +0,0 @@
|
||||
/* figures: jsonview (features/json_view.md; SVGs from scripts/figures/json_view_layout.py, stepper in js/fig-jsonview.js) */
|
||||
|
||||
/* one colour per concept, the same in every figure: structure (object/array, views) blue, keys navy, strings green,
|
||||
numbers orange, decoded strings purple, owned edit storage teal, dangling/invalid red */
|
||||
.nj-jsonview, .nj-jsonview-cmp {
|
||||
--jv-struct: var(--nj-blue);
|
||||
--jv-key: var(--nj-hl-key);
|
||||
--jv-str: var(--nj-hl-string);
|
||||
--jv-num: var(--nj-hl-number);
|
||||
--jv-dec: var(--nj-hl-function);
|
||||
--jv-own: var(--nj-hl-type);
|
||||
--jv-bad: var(--nj-red);
|
||||
--jv-line: color-mix(in srgb, currentColor 55%, var(--md-default-bg-color));
|
||||
}
|
||||
.md-typeset svg.nj-jsonview { min-width: 34rem; max-width: 42rem; }
|
||||
.nj-jsonview .nj-jsonview-c-struct { --c: var(--jv-struct); }
|
||||
.nj-jsonview .nj-jsonview-c-key { --c: var(--jv-key); }
|
||||
.nj-jsonview .nj-jsonview-c-str { --c: var(--jv-str); }
|
||||
.nj-jsonview .nj-jsonview-c-num { --c: var(--jv-num); }
|
||||
.nj-jsonview .nj-jsonview-c-dec { --c: var(--jv-dec); }
|
||||
.nj-jsonview .nj-jsonview-c-own { --c: var(--jv-own); }
|
||||
.nj-jsonview .nj-jsonview-c-bad { --c: var(--jv-bad); }
|
||||
.nj-jsonview .nj-jsonview-c-line { --c: var(--jv-line); }
|
||||
|
||||
.nj-jsonview text { fill: currentColor; font-size: 13px; }
|
||||
.nj-jsonview text[class*="nj-jsonview-c-"] { fill: var(--c); }
|
||||
.nj-jsonview .nj-jsonview-h { font-size: 15px; font-weight: 600; fill-opacity: .85; }
|
||||
.nj-jsonview .nj-jsonview-sm2 { font-size: 14px; }
|
||||
.nj-jsonview .nj-jsonview-note { font-size: 13px; fill-opacity: .75; }
|
||||
.nj-jsonview .nj-jsonview-strong { font-weight: 600; fill-opacity: 1; }
|
||||
.nj-jsonview .nj-jsonview-tiny { font-size: 10.5px; fill-opacity: .7; }
|
||||
.nj-jsonview .nj-jsonview-mono { font-family: var(--md-code-font-family), monospace; font-size: 13px; }
|
||||
.nj-jsonview .nj-jsonview-sm { font-size: 12px; }
|
||||
.nj-jsonview .nj-jsonview-xs { font-size: 11px; }
|
||||
.nj-jsonview .nj-jsonview-muted { fill-opacity: .75; }
|
||||
.nj-jsonview .nj-jsonview-byte { font-size: 12px; }
|
||||
.nj-jsonview .nj-jsonview-kind { font-size: 12.5px; font-weight: 700; }
|
||||
|
||||
.nj-jsonview .nj-jsonview-box { fill: var(--md-default-bg-color); stroke: var(--jv-line); stroke-width: 1.5; }
|
||||
.nj-jsonview .nj-jsonview-heap { fill: color-mix(in srgb, currentColor 7%, var(--md-default-bg-color)); stroke: var(--jv-line); stroke-width: 1.5; stroke-dasharray: 5 3; }
|
||||
.nj-jsonview .nj-jsonview-ribbon { fill: color-mix(in srgb, currentColor 4%, var(--md-default-bg-color)); stroke: var(--jv-line); stroke-width: 1.2; }
|
||||
.nj-jsonview .nj-jsonview-span { fill: color-mix(in srgb, var(--c) 18%, var(--md-default-bg-color)); }
|
||||
.nj-jsonview .nj-jsonview-frame { fill: none; stroke: var(--jv-line); stroke-width: 1.2; stroke-dasharray: 6 4; }
|
||||
.nj-jsonview .nj-jsonview-store { fill: color-mix(in srgb, var(--jv-own) 6%, var(--md-default-bg-color)); stroke: color-mix(in srgb, var(--jv-own) 55%, var(--md-default-bg-color)); stroke-width: 1.2; stroke-dasharray: 6 4; }
|
||||
.nj-jsonview .nj-jsonview-node { fill: color-mix(in srgb, var(--c) 12%, var(--md-default-bg-color)); stroke: var(--c); stroke-width: 1.5; }
|
||||
.nj-jsonview .nj-jsonview-node.nj-jsonview-hot { stroke-width: 3; }
|
||||
.nj-jsonview .nj-jsonview-node.nj-jsonview-gap { fill: var(--md-default-bg-color); stroke: var(--jv-bad); stroke-dasharray: 4 3; }
|
||||
.nj-jsonview .nj-jsonview-node.nj-jsonview-free { fill: none; stroke-dasharray: 3 3; }
|
||||
.nj-jsonview .nj-jsonview-sep { stroke: var(--jv-line); stroke-width: 1; fill: none; }
|
||||
.nj-jsonview .nj-jsonview-arr { stroke: var(--c); stroke-width: 1.5; fill: none; }
|
||||
.nj-jsonview .nj-jsonview-dash { stroke-dasharray: 4 3; }
|
||||
.nj-jsonview .nj-jsonview-head { fill: var(--c); }
|
||||
.nj-jsonview .nj-jsonview-bar { fill: color-mix(in srgb, var(--jv-struct) 30%, var(--md-default-bg-color)); stroke: var(--jv-struct); stroke-width: 1.2; }
|
||||
.nj-jsonview .nj-jsonview-bad {
|
||||
fill: color-mix(in srgb, var(--jv-bad) 20%, var(--md-default-bg-color));
|
||||
stroke: var(--jv-bad); stroke-width: 1.2; stroke-dasharray: 4 2;
|
||||
}
|
||||
.nj-jsonview .nj-jsonview-evt { stroke: var(--jv-bad); stroke-width: 2; fill: none; }
|
||||
.nj-jsonview .nj-jsonview-evt--ok { stroke: var(--jv-struct); stroke-dasharray: 4 3; }
|
||||
.nj-jsonview .nj-jsonview-onbad, .nj-jsonview .nj-jsonview-onok { font-size: 11.5px; fill-opacity: 1; }
|
||||
|
||||
/* the edit stepper: without JS all frames are shown one below the other */
|
||||
.nj-jsonview-steps { margin: 1.5rem 0; }
|
||||
.md-typeset .nj-jsonview-step { display: block; width: 100%; max-width: none; margin: 0 0 1.5rem; }
|
||||
.nj-jsonview-step > figcaption {
|
||||
margin: .25rem 0 0; font-size: .75rem; color: var(--md-default-fg-color--light); text-align: left;
|
||||
max-width: none;
|
||||
}
|
||||
.nj-jsonview-step > figcaption code { font-size: .95em; }
|
||||
.nj-jsonview-step .nj-jsonview-scroll { overflow-x: auto; }
|
||||
.md-typeset .nj-jsonview-steps.is-enhanced .nj-jsonview-step { display: none; margin: 0; }
|
||||
.md-typeset .nj-jsonview-steps.is-enhanced .nj-jsonview-step.is-current { display: block; }
|
||||
.nj-jsonview-controls { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; margin: 0 0 .6rem; }
|
||||
.nj-jsonview-controls button {
|
||||
min-height: 2.2rem; min-width: 2.2rem; padding: 0 .8rem;
|
||||
font: inherit; font-size: .7rem; font-weight: 600; cursor: pointer;
|
||||
color: var(--md-typeset-a-color); background: var(--md-default-bg-color);
|
||||
border: 1.5px solid var(--md-typeset-a-color); border-radius: .4rem;
|
||||
}
|
||||
.nj-jsonview-controls button:hover:not(:disabled) { background: color-mix(in srgb, var(--md-typeset-a-color) 10%, var(--md-default-bg-color)); }
|
||||
.nj-jsonview-controls button:focus-visible { outline: 2px solid var(--md-accent-fg-color); outline-offset: 2px; }
|
||||
.nj-jsonview-controls button:disabled { opacity: .45; cursor: default; }
|
||||
.nj-jsonview-controls button[aria-current="step"], .nj-jsonview-controls button[aria-current="step"]:hover { color: var(--md-default-bg-color); background: var(--md-typeset-a-color); }
|
||||
.nj-jsonview-controls .nj-jsonview-status { font-size: .7rem; color: var(--md-default-fg-color--light); margin-left: .25rem; }
|
||||
@media (max-width: 44.9375em) {
|
||||
.nj-jsonview-controls button { min-height: 44px; min-width: 44px; }
|
||||
}
|
||||
@media (prefers-reduced-motion: no-preference) {
|
||||
.nj-jsonview-steps.is-enhanced .nj-jsonview-step.is-current { animation: nj-jsonview-fade .25s ease-out; }
|
||||
}
|
||||
@keyframes nj-jsonview-fade { from { opacity: .3; } to { opacity: 1; } }
|
||||
|
||||
/* json vs ordered_json vs editable document */
|
||||
.nj-jsonview-cmp { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: .6rem; margin: 1.2rem 0; }
|
||||
.nj-jsonview-cmp > div {
|
||||
border: 1px solid var(--md-default-fg-color--lightest); border-radius: .4rem; padding: .5rem .6rem .6rem;
|
||||
background: var(--md-code-bg-color); min-width: 0;
|
||||
}
|
||||
.nj-jsonview-cmp > div.nj-jsonview-cmp--best { border-color: var(--jv-struct); }
|
||||
.nj-jsonview-cmp .nj-jsonview-cmp-h { font-size: .7rem; font-weight: 600; margin: 0 0 .1rem; }
|
||||
.nj-jsonview-cmp .nj-jsonview-cmp-v { font-size: .64rem; color: var(--md-default-fg-color--light); margin: 0 0 .4rem; }
|
||||
.md-typeset .nj-jsonview-cmp pre { margin: 0; font-family: var(--md-code-font-family), monospace; font-size: .68rem; line-height: 1.5; white-space: pre; overflow-x: auto; background: none; color: var(--md-code-fg-color); }
|
||||
.nj-jsonview-cmp .nj-jsonview-bad { color: var(--jv-bad); font-weight: 600; text-decoration: underline wavy; text-underline-offset: 3px; }
|
||||
.nj-jsonview-cmp .nj-jsonview-ok { color: var(--jv-own); font-weight: 600; }
|
||||
@media (max-width: 44.9375em) {
|
||||
.nj-jsonview-cmp { grid-template-columns: minmax(0, 1fr); }
|
||||
}
|
||||
@@ -1,98 +0,0 @@
|
||||
/* figures: macro chooser (js/fig-macros.js) on features/arbitrary_types.md; colours come from the brand
|
||||
variables in brand.css, which switch with the light/slate scheme */
|
||||
.nj-macro-chooser {
|
||||
--nj-mc-line: color-mix(in srgb, currentColor 18%, var(--md-default-bg-color));
|
||||
--nj-mc-panel: color-mix(in srgb, currentColor 3%, var(--md-default-bg-color));
|
||||
--nj-mc-ink2: var(--md-default-fg-color--light);
|
||||
margin: 1.2em 0 1.6em;
|
||||
font-size: .74rem;
|
||||
}
|
||||
.md-typeset .nj-macro-chooser .nj-mc-fallback > :first-child { margin-top: 0; }
|
||||
|
||||
.nj-mc-app { border: 1px solid var(--nj-mc-line); border-radius: .3rem; background: var(--nj-mc-panel);
|
||||
padding: .9rem; display: grid; grid-template-columns: minmax(0, 1fr); gap: 1rem; }
|
||||
.nj-mc-form, .nj-mc-out, .nj-mc-editor, .nj-mc-members, .nj-mc-mbody { grid-template-columns: minmax(0, 1fr); }
|
||||
.nj-mc-form { display: grid; gap: 1rem; margin: 0; }
|
||||
|
||||
/* questions as segmented radio groups */
|
||||
.nj-mc-questions { display: grid; grid-template-columns: repeat(auto-fill, minmax(min(14.5rem, 100%), 1fr)); gap: .7rem .9rem; }
|
||||
.nj-mc-q { border: 0; margin: 0; padding: 0; min-width: 0; }
|
||||
.nj-mc-q legend { font-weight: 600; padding: 0; margin-bottom: .3rem; font-size: .7rem; }
|
||||
.nj-mc-seg { display: flex; border: 1px solid var(--nj-mc-line); border-radius: .25rem; overflow: hidden;
|
||||
background: var(--md-default-bg-color); }
|
||||
.nj-mc-seg input { position: absolute; opacity: 0; width: 1px; height: 1px; margin: 0; pointer-events: none; }
|
||||
.nj-mc-seg label { flex: 1 1 0; display: flex; align-items: center; justify-content: center; text-align: center;
|
||||
min-height: 2.1rem; padding: .25rem .5rem; cursor: pointer; line-height: 1.25; font-size: .7rem;
|
||||
color: var(--md-default-fg-color); transition: background-color .15s, color .15s; }
|
||||
.nj-mc-seg label + input + label { border-left: 1px solid var(--nj-mc-line); }
|
||||
.nj-mc-seg label:hover { background: var(--nj-blue-soft); }
|
||||
.nj-mc-seg input:checked + label { background: var(--nj-blue); color: var(--md-default-bg-color); font-weight: 600; }
|
||||
.nj-mc-seg input:focus-visible + label { outline: 2px solid var(--md-accent-fg-color); outline-offset: -3px; }
|
||||
.nj-mc-q:disabled .nj-mc-seg { opacity: .45; }
|
||||
.nj-mc-q:disabled label { cursor: not-allowed; }
|
||||
.nj-mc-q:disabled label:hover { background: transparent; }
|
||||
.md-typeset .nj-mc-qnote { margin: .3rem 0 0; font-size: .64rem; line-height: 1.4; color: var(--nj-mc-ink2); }
|
||||
|
||||
/* type editor */
|
||||
.nj-mc-editor { display: grid; gap: .6rem; border-top: 1px solid var(--nj-mc-line); padding-top: .9rem; }
|
||||
.nj-mc-names { display: grid; grid-template-columns: repeat(auto-fill, minmax(min(11rem, 100%), 1fr)); gap: .6rem .9rem; }
|
||||
.nj-mc-field { display: grid; gap: .2rem; }
|
||||
.nj-mc-field label { font-weight: 600; font-size: .7rem; }
|
||||
.nj-mc-field[hidden] { display: none; }
|
||||
.nj-macro-chooser input[type="text"] { font-family: var(--md-code-font-family), monospace; font-size: .7rem;
|
||||
min-height: 2.1rem; padding: .2rem .45rem; min-width: 0; width: 100%; box-sizing: border-box;
|
||||
border: 1px solid var(--nj-mc-line); border-radius: .2rem; background: var(--md-default-bg-color);
|
||||
color: var(--md-default-fg-color); }
|
||||
.nj-macro-chooser input[type="text"]:focus { outline: 2px solid var(--md-accent-fg-color); outline-offset: 0; border-color: transparent; }
|
||||
|
||||
.nj-mc-members { display: grid; gap: .35rem; }
|
||||
.nj-mc-mbody { display: grid; gap: .35rem; }
|
||||
.nj-mc-mrow { display: grid; grid-template-columns: minmax(0, 1.3fr) minmax(0, 1fr) 2.2rem; gap: .4rem; align-items: center; }
|
||||
.nj-mc-custom .nj-mc-mrow { grid-template-columns: minmax(0, 1.3fr) minmax(0, 1fr) minmax(0, 1fr) 2.2rem; }
|
||||
.nj-mc-mrow .nj-mc-keycol { display: none; }
|
||||
.nj-mc-custom .nj-mc-mrow .nj-mc-keycol { display: block; }
|
||||
.nj-mc-mhead { font-weight: 600; font-size: .66rem; color: var(--nj-mc-ink2); }
|
||||
.nj-mc-mhead .nj-mc-keycol[hidden] { display: none; }
|
||||
|
||||
.nj-macro-chooser button { font: inherit; cursor: pointer; border-radius: .2rem; }
|
||||
.nj-macro-chooser button:focus-visible { outline: 2px solid var(--md-accent-fg-color); outline-offset: 2px; }
|
||||
.nj-mc-rm { width: 2.2rem; height: 2.1rem; border: 1px solid var(--nj-mc-line); background: var(--md-default-bg-color);
|
||||
color: var(--nj-mc-ink2); font-size: 1rem; line-height: 1; padding: 0; }
|
||||
.nj-mc-rm:hover { color: var(--nj-red); border-color: var(--nj-red); }
|
||||
.nj-mc-add, .nj-mc-copy { justify-self: start; min-height: 2.1rem; padding: .2rem .8rem; font-size: .7rem; font-weight: 600;
|
||||
border: 1px solid var(--nj-blue); background: var(--md-default-bg-color); color: var(--nj-blue); }
|
||||
.nj-mc-add:hover, .nj-mc-copy:hover { background: var(--nj-blue-soft); }
|
||||
|
||||
/* output */
|
||||
.nj-mc-out { display: grid; gap: .7rem; }
|
||||
.nj-mc-result { border-left: .2rem solid var(--nj-blue); background: var(--nj-blue-soft); border-radius: 0 .2rem .2rem 0;
|
||||
padding: .55rem .8rem; }
|
||||
.nj-mc-result.nj-mc-bad { border-left-color: var(--nj-red); background: var(--nj-red-soft); }
|
||||
.md-typeset .nj-mc-result p { margin: 0; }
|
||||
.md-typeset .nj-mc-result p + p { margin-top: .3rem; }
|
||||
.md-typeset .nj-mc-label { font-size: .64rem; font-weight: 600; text-transform: uppercase; letter-spacing: .04em; color: var(--nj-mc-ink2); }
|
||||
.md-typeset .nj-mc-macro code { font-size: .8rem; font-weight: 600; background: transparent; padding: 0;
|
||||
overflow-wrap: anywhere; color: var(--md-default-fg-color); }
|
||||
.md-typeset .nj-mc-why { line-height: 1.5; }
|
||||
.md-typeset .nj-mc-hints { margin: 0; padding-left: 1.1rem; font-size: .68rem; color: var(--nj-mc-ink2); }
|
||||
.md-typeset .nj-mc-hints li { margin: 0; }
|
||||
.nj-mc-hints[hidden], .nj-mc-code[hidden] { display: none; }
|
||||
|
||||
.nj-mc-codebar { display: flex; align-items: center; gap: .6rem; margin-bottom: .3rem; }
|
||||
.nj-mc-codetitle { font-weight: 600; font-size: .7rem; margin-right: auto; }
|
||||
.nj-mc-copystatus { font-size: .66rem; color: var(--nj-mc-ink2); }
|
||||
.md-typeset .nj-mc-code .highlight { margin: 0; }
|
||||
.md-typeset .nj-mc-code pre { margin: 0; }
|
||||
.md-typeset .nj-mc-code pre > code { max-height: 34rem; }
|
||||
|
||||
@media (max-width: 44.9375em) {
|
||||
.nj-mc-app { padding: .7rem; }
|
||||
.nj-mc-seg label, .nj-macro-chooser input[type="text"], .nj-mc-add, .nj-mc-copy { min-height: 2.75rem; }
|
||||
.nj-mc-rm { width: 2.75rem; height: 2.75rem; }
|
||||
.nj-mc-mrow, .nj-mc-custom .nj-mc-mrow { grid-template-columns: minmax(0, 1fr) minmax(0, 1fr) 2.75rem; }
|
||||
.nj-mc-custom .nj-mc-mrow .nj-mc-keycol { grid-column: 1 / 3; }
|
||||
.nj-mc-custom .nj-mc-mhead { display: none; }
|
||||
}
|
||||
@media (prefers-reduced-motion: reduce) {
|
||||
.nj-mc-seg label { transition: none; }
|
||||
}
|
||||
@@ -1,459 +0,0 @@
|
||||
/* figures: pointer (features/json_pointer.md, json_patch.md, merge_patch.md; widgets in js/fig-pointer.js) */
|
||||
|
||||
/* value types: the colours of the code highlighting (brand.css), so a string looks the same everywhere */
|
||||
.nj-pointer-walk, .nj-pointer-fl, .nj-patch {
|
||||
--nj-pointer-s: var(--nj-hl-string);
|
||||
--nj-pointer-n: var(--nj-hl-number);
|
||||
--nj-pointer-b: var(--nj-hl-function);
|
||||
--nj-pointer-line: color-mix(in srgb, var(--md-default-fg-color) 28%, var(--md-default-bg-color));
|
||||
--nj-pointer-ok: #23793a;
|
||||
--nj-pointer-ok-soft: #e6f4ea;
|
||||
}
|
||||
[data-md-color-scheme="slate"] :is(.nj-pointer-walk, .nj-pointer-fl, .nj-patch) {
|
||||
--nj-pointer-ok: #7ed491;
|
||||
--nj-pointer-ok-soft: #14301d;
|
||||
}
|
||||
|
||||
/* ---------- pointer walker ---------- */
|
||||
.md-typeset .nj-pointer-walk {
|
||||
display: grid;
|
||||
grid-template-columns: minmax(0, 1fr);
|
||||
gap: 1rem 1.6rem;
|
||||
margin: 1.5rem 0;
|
||||
padding: 1rem 1.1rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 6px;
|
||||
font-size: .75rem;
|
||||
}
|
||||
@media screen and (min-width: 45em) {
|
||||
.md-typeset .nj-pointer-walk--js {
|
||||
grid-template-columns: minmax(0, 1fr) minmax(0, 1.1fr);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk--js .nj-pointer-panel { order: 2; }
|
||||
}
|
||||
.md-typeset .nj-pointer-static {
|
||||
margin: 0;
|
||||
color: var(--md-default-fg-color--light);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk code {
|
||||
font-size: .95em;
|
||||
}
|
||||
|
||||
/* tree: elbow lines drawn by each item (::before up to its row, ::after down to the next sibling) */
|
||||
.md-typeset .nj-pointer-walk ul.nj-pointer-tree,
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree ul {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree ul {
|
||||
padding-left: 1.5rem;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree li {
|
||||
position: relative;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
--nj-pointer-mid: .95rem;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree li::before,
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree li::after {
|
||||
content: none;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree ul > li::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: -1rem;
|
||||
width: .8rem;
|
||||
height: var(--nj-pointer-mid);
|
||||
border: 0 solid var(--nj-pointer-line);
|
||||
border-width: 0 0 2px 2px;
|
||||
border-bottom-left-radius: 4px;
|
||||
background: none;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree ul > li:not(:last-child)::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
left: -1rem;
|
||||
border-left: 2px solid var(--nj-pointer-line);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree ul > li.is-on::before {
|
||||
z-index: 1;
|
||||
border-color: var(--md-typeset-a-color);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-tree ul > li.is-pass::after {
|
||||
z-index: 1;
|
||||
border-left-color: var(--md-typeset-a-color);
|
||||
}
|
||||
|
||||
.md-typeset .nj-pointer-walk .nj-pointer-n {
|
||||
display: inline-block;
|
||||
margin: .15rem 0;
|
||||
padding: .2rem .5rem;
|
||||
border: 1px solid transparent;
|
||||
border-radius: 6px;
|
||||
background: none;
|
||||
color: var(--md-default-fg-color);
|
||||
font: inherit;
|
||||
font-family: var(--md-code-font-family), monospace;
|
||||
font-size: .95em;
|
||||
line-height: 1.5;
|
||||
text-align: left;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk button.nj-pointer-n {
|
||||
cursor: pointer;
|
||||
}
|
||||
.md-typeset .nj-pointer-walk button.nj-pointer-n:hover {
|
||||
border-color: var(--md-default-fg-color--lightest);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk :is(button):focus-visible {
|
||||
outline: 2px solid var(--md-typeset-a-color);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
.nj-pointer-k { color: var(--nj-hl-key); }
|
||||
.nj-pointer-t {
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-family: var(--md-text-font-family), sans-serif;
|
||||
font-size: .88em;
|
||||
font-style: italic;
|
||||
}
|
||||
.nj-pointer-v--s { color: var(--nj-pointer-s); }
|
||||
.nj-pointer-v--n { color: var(--nj-pointer-n); }
|
||||
.nj-pointer-v--b { color: var(--nj-pointer-b); }
|
||||
|
||||
.md-typeset .nj-pointer-walk li.is-on > .nj-pointer-n {
|
||||
border-color: color-mix(in srgb, var(--md-typeset-a-color) 45%, transparent);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk li.is-target > .nj-pointer-n {
|
||||
border-color: var(--md-typeset-a-color);
|
||||
background-color: var(--nj-blue-soft);
|
||||
box-shadow: 0 0 0 1px var(--md-typeset-a-color);
|
||||
}
|
||||
/* the value a container pointer identifies includes its subtree */
|
||||
.md-typeset .nj-pointer-walk li.is-target li > .nj-pointer-n {
|
||||
background-color: var(--nj-blue-soft);
|
||||
}
|
||||
.md-typeset .nj-pointer-walk li.is-miss > .nj-pointer-n {
|
||||
border-color: var(--nj-red);
|
||||
border-style: dashed;
|
||||
}
|
||||
|
||||
/* panel: pointer bar, result, example pointers */
|
||||
.nj-pointer-lbl {
|
||||
margin: 0 0 .35rem;
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-size: .62rem;
|
||||
font-weight: 600;
|
||||
letter-spacing: .04em;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
.nj-pointer-lbl span {
|
||||
font-weight: 500;
|
||||
letter-spacing: 0;
|
||||
text-transform: none;
|
||||
}
|
||||
.nj-pointer-bar {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
margin-bottom: .6rem;
|
||||
}
|
||||
.md-typeset .nj-pointer-seg {
|
||||
margin: 0 -1px 0 0;
|
||||
padding: .3rem .55rem;
|
||||
border: 1px solid var(--md-typeset-a-color);
|
||||
background-color: var(--md-default-bg-color);
|
||||
color: var(--md-typeset-a-color);
|
||||
cursor: pointer;
|
||||
font: inherit;
|
||||
}
|
||||
.md-typeset .nj-pointer-seg:first-child { border-radius: 6px 0 0 6px; }
|
||||
.md-typeset .nj-pointer-seg:last-child { border-radius: 0 6px 6px 0; }
|
||||
.md-typeset .nj-pointer-seg:only-child { border-radius: 6px; }
|
||||
.md-typeset .nj-pointer-seg code { color: inherit; font-size: 1em; }
|
||||
.md-typeset .nj-pointer-seg--root code { color: var(--md-default-fg-color--light); }
|
||||
.md-typeset .nj-pointer-seg.is-after {
|
||||
border-color: var(--md-default-fg-color--lighter);
|
||||
color: var(--md-default-fg-color--light);
|
||||
border-style: dashed;
|
||||
}
|
||||
.md-typeset .nj-pointer-seg[aria-pressed="true"] {
|
||||
position: relative;
|
||||
background-color: var(--md-typeset-a-color);
|
||||
color: var(--md-default-bg-color);
|
||||
}
|
||||
.md-typeset .nj-pointer-seg--root[aria-pressed="true"] code { color: inherit; }
|
||||
.nj-pointer-out {
|
||||
min-height: 3.2em;
|
||||
margin-bottom: .9rem;
|
||||
padding: .5rem .7rem;
|
||||
border-left: 3px solid var(--md-typeset-a-color);
|
||||
border-radius: 0 6px 6px 0;
|
||||
background-color: var(--md-code-bg-color);
|
||||
line-height: 1.6;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.md-typeset .nj-pointer-out .nj-pointer-val { color: var(--md-typeset-a-color); font-weight: 600; }
|
||||
.nj-pointer-out .nj-pointer-note { color: var(--md-default-fg-color--light); }
|
||||
.nj-pointer-out .nj-pointer-err { color: var(--nj-red); font-weight: 600; }
|
||||
.nj-pointer-presets {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: .35rem;
|
||||
}
|
||||
.md-typeset .nj-pointer-chip {
|
||||
padding: .2rem .5rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 6px;
|
||||
background-color: var(--md-default-bg-color);
|
||||
color: var(--md-default-fg-color);
|
||||
cursor: pointer;
|
||||
font: inherit;
|
||||
}
|
||||
.md-typeset .nj-pointer-chip:hover { border-color: var(--md-typeset-a-color); }
|
||||
.md-typeset .nj-pointer-chip[aria-pressed="true"] {
|
||||
border-color: var(--md-typeset-a-color);
|
||||
background-color: var(--nj-blue-soft);
|
||||
color: var(--md-typeset-a-color);
|
||||
}
|
||||
.md-typeset .nj-pointer-chip code { color: inherit; font-size: 1em; }
|
||||
@media (pointer: coarse), screen and (max-width: 44.984375em) {
|
||||
.md-typeset :is(.nj-pointer-seg, .nj-pointer-chip, .nj-patch-btn) { min-height: 44px; min-width: 44px; }
|
||||
.md-typeset .nj-pointer-walk button.nj-pointer-n { min-height: 40px; }
|
||||
}
|
||||
|
||||
/* ---------- flatten / unflatten figure (scripts/figures/json_pointer_flatten.py) ---------- */
|
||||
.md-typeset svg.nj-pointer-fl { min-width: 28rem; max-width: 44rem; }
|
||||
.nj-pointer-fl .nj-pointer-fl-edge { fill: none; stroke: var(--fg-line); stroke-width: 1.5; }
|
||||
.nj-pointer-fl .nj-pointer-fl-link { fill: none; stroke-width: 1.5; stroke-opacity: .75; }
|
||||
.nj-pointer-fl .nj-pointer-fl-link.nj-pointer-fl--s, .nj-pointer-fl .nj-pointer-fl-dot.nj-pointer-fl--s { stroke: var(--nj-pointer-s); }
|
||||
.nj-pointer-fl .nj-pointer-fl-link.nj-pointer-fl--n, .nj-pointer-fl .nj-pointer-fl-dot.nj-pointer-fl--n { stroke: var(--nj-pointer-n); }
|
||||
.nj-pointer-fl .nj-pointer-fl-link.nj-pointer-fl--b, .nj-pointer-fl .nj-pointer-fl-dot.nj-pointer-fl--b { stroke: var(--nj-pointer-b); }
|
||||
.nj-pointer-fl .nj-pointer-fl-dot { fill: var(--md-default-bg-color); stroke-width: 2; }
|
||||
.nj-pointer-fl tspan.nj-pointer-fl--s { fill: var(--nj-pointer-s); }
|
||||
.nj-pointer-fl tspan.nj-pointer-fl--n { fill: var(--nj-pointer-n); }
|
||||
.nj-pointer-fl tspan.nj-pointer-fl--b { fill: var(--nj-pointer-b); }
|
||||
.nj-pointer-fl .nj-pointer-fl-k, .nj-pointer-fl .nj-pointer-fl-inner, .nj-pointer-fl .nj-pointer-fl-key { fill: var(--nj-hl-key); }
|
||||
.nj-pointer-fl .nj-pointer-fl-op {
|
||||
fill: var(--md-typeset-a-color);
|
||||
font-family: var(--md-code-font-family), monospace;
|
||||
font-size: 15px;
|
||||
font-weight: 600;
|
||||
text-anchor: middle;
|
||||
}
|
||||
|
||||
/* ---------- JSON Patch stepper ---------- */
|
||||
.md-typeset .nj-patch--js .md-typeset__scrollwrap,
|
||||
.md-typeset .nj-patch--js > .md-typeset__table,
|
||||
.md-typeset .nj-patch--js > table {
|
||||
display: none;
|
||||
}
|
||||
.md-typeset .nj-patch-stage {
|
||||
margin: 1.5rem 0;
|
||||
padding: 1rem 1.1rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 6px;
|
||||
font-size: .75rem;
|
||||
}
|
||||
.nj-patch-cols {
|
||||
display: grid;
|
||||
grid-template-columns: minmax(0, 1fr);
|
||||
gap: 1rem 1.4rem;
|
||||
}
|
||||
@media screen and (min-width: 50em) {
|
||||
.nj-patch-cols { grid-template-columns: minmax(0, .8fr) minmax(0, 1.2fr); }
|
||||
}
|
||||
.nj-patch-h {
|
||||
margin: 0 0 .35rem;
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-size: .62rem;
|
||||
font-weight: 600;
|
||||
letter-spacing: .04em;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
.nj-patch-doc {
|
||||
--nj-patch-lh: 1.9rem;
|
||||
--nj-patch-pad: .5rem;
|
||||
position: relative;
|
||||
padding: var(--nj-patch-pad) .6rem var(--nj-patch-pad) 2rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 6px;
|
||||
background-color: var(--md-code-bg-color);
|
||||
font-family: var(--md-code-font-family), monospace;
|
||||
font-size: .95em;
|
||||
}
|
||||
.nj-patch-line {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
align-items: center;
|
||||
gap: 0 .6rem;
|
||||
min-height: var(--nj-patch-lh);
|
||||
margin: 0 -.3rem;
|
||||
padding: 0 .3rem;
|
||||
border-radius: 4px;
|
||||
white-space: pre;
|
||||
}
|
||||
.nj-patch-code { white-space: pre; }
|
||||
.nj-patch-k { color: var(--nj-hl-key); }
|
||||
.nj-patch-s { color: var(--nj-pointer-s); }
|
||||
.nj-patch-note {
|
||||
padding: 0 .4rem;
|
||||
border-radius: 4px;
|
||||
font-family: var(--md-text-font-family), sans-serif;
|
||||
font-size: .82em;
|
||||
font-weight: 600;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.nj-patch-line--add { background-color: var(--nj-pointer-ok-soft); box-shadow: inset 3px 0 0 var(--nj-pointer-ok); }
|
||||
.nj-patch-line--add .nj-patch-note { color: var(--nj-pointer-ok); }
|
||||
.nj-patch-line--del { background-color: var(--nj-red-soft); box-shadow: inset 3px 0 0 var(--nj-red); }
|
||||
.nj-patch-line--del .nj-patch-code { text-decoration: line-through; text-decoration-color: var(--nj-red); text-decoration-thickness: 2px; opacity: .75; }
|
||||
.nj-patch-line--del .nj-patch-note { color: var(--nj-red); }
|
||||
.nj-patch-line--mod .nj-patch-note { color: var(--nj-pointer-ok); }
|
||||
.nj-patch-line--test { background-color: var(--nj-blue-soft); box-shadow: inset 3px 0 0 var(--md-typeset-a-color); }
|
||||
.nj-patch-line--test .nj-patch-note { color: var(--md-typeset-a-color); }
|
||||
.nj-patch-ins { padding: .05rem .15rem; border-radius: 3px; background-color: var(--nj-pointer-ok-soft); box-shadow: 0 0 0 1.5px var(--nj-pointer-ok); }
|
||||
.nj-patch-src { padding: .05rem .15rem; border-radius: 3px; box-shadow: 0 0 0 1.5px var(--md-typeset-a-color); }
|
||||
|
||||
/* move/copy connector in the left gutter: a bracket from the source line to the target line */
|
||||
.nj-patch-arc {
|
||||
position: absolute;
|
||||
left: .55rem;
|
||||
width: .8rem;
|
||||
border: 2px solid var(--md-typeset-a-color);
|
||||
border-right: 0;
|
||||
border-radius: 6px 0 0 6px;
|
||||
}
|
||||
.nj-patch-arc::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
right: -2px;
|
||||
border: 5px solid transparent;
|
||||
border-left: 7px solid var(--md-typeset-a-color);
|
||||
}
|
||||
.nj-patch-arc--down::after { bottom: -6px; }
|
||||
.nj-patch-arc--up::after { top: -6px; }
|
||||
|
||||
.md-typeset .nj-patch-ops {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
counter-reset: nj-patch;
|
||||
}
|
||||
.md-typeset .nj-patch-ops > li {
|
||||
position: relative;
|
||||
margin: 0 0 .3rem;
|
||||
padding: .35rem .5rem .35rem 2rem;
|
||||
border: 1px solid transparent;
|
||||
border-radius: 6px;
|
||||
counter-increment: nj-patch;
|
||||
line-height: 1.5;
|
||||
}
|
||||
.md-typeset .nj-patch-ops > li::before {
|
||||
content: counter(nj-patch);
|
||||
position: absolute;
|
||||
top: .35rem;
|
||||
left: .6rem;
|
||||
color: var(--md-default-fg-color--lighter);
|
||||
font-weight: 600;
|
||||
font-variant-numeric: tabular-nums;
|
||||
}
|
||||
.md-typeset .nj-patch-ops code { font-size: .9em; overflow-wrap: anywhere; }
|
||||
.md-typeset .nj-patch-ops > li.is-done { opacity: .6; }
|
||||
.md-typeset .nj-patch-ops > li.is-cur {
|
||||
border-color: var(--md-typeset-a-color);
|
||||
background-color: var(--nj-blue-soft);
|
||||
}
|
||||
.md-typeset .nj-patch-ops > li.is-cur::before { color: var(--md-typeset-a-color); }
|
||||
.nj-patch-op { color: var(--nj-hl-keyword); font-weight: 600; }
|
||||
.nj-patch-path { color: var(--nj-pointer-s); }
|
||||
.md-typeset .nj-patch-ops > li.is-cur .nj-patch-path {
|
||||
padding: 0 .15rem;
|
||||
border-radius: 3px;
|
||||
background-color: var(--md-typeset-a-color);
|
||||
color: var(--md-default-bg-color);
|
||||
}
|
||||
.nj-patch-ctrl {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
align-items: center;
|
||||
gap: .4rem;
|
||||
margin-top: .9rem;
|
||||
}
|
||||
.md-typeset .nj-patch-btn {
|
||||
padding: .3rem .9rem;
|
||||
border: 1px solid var(--md-default-fg-color--lighter);
|
||||
border-radius: 6px;
|
||||
background-color: var(--md-default-bg-color);
|
||||
color: var(--md-default-fg-color);
|
||||
cursor: pointer;
|
||||
font: inherit;
|
||||
font-weight: 600;
|
||||
}
|
||||
.md-typeset .nj-patch-btn--primary {
|
||||
border-color: var(--md-typeset-a-color);
|
||||
background-color: var(--md-typeset-a-color);
|
||||
color: var(--md-default-bg-color);
|
||||
}
|
||||
.md-typeset .nj-patch-btn:disabled { opacity: .45; cursor: default; }
|
||||
.md-typeset .nj-patch-btn:focus-visible { outline: 2px solid var(--md-typeset-a-color); outline-offset: 2px; }
|
||||
.nj-patch-count {
|
||||
margin-left: auto;
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-variant-numeric: tabular-nums;
|
||||
}
|
||||
.md-typeset .nj-patch-status {
|
||||
min-height: 3.2em;
|
||||
margin: .6rem 0 0;
|
||||
color: var(--md-default-fg-color--light);
|
||||
}
|
||||
@media (prefers-reduced-motion: no-preference) {
|
||||
.nj-patch-doc--anim :is(.nj-patch-line--add, .nj-patch-line--del, .nj-patch-line--test, .nj-patch-ins, .nj-patch-arc) {
|
||||
animation: nj-patch-in 450ms ease-out;
|
||||
}
|
||||
}
|
||||
@keyframes nj-patch-in {
|
||||
from { opacity: 0; transform: translateX(-.4rem); }
|
||||
to { opacity: 1; transform: none; }
|
||||
}
|
||||
|
||||
/* ---------- merge patch table ---------- */
|
||||
.nj-pointer-mpt {
|
||||
--nj-pointer-mp-set: var(--nj-hl-keyword);
|
||||
--nj-pointer-mp-add: #23793a;
|
||||
--nj-pointer-mp-del: var(--nj-red);
|
||||
--nj-pointer-mp-rec: var(--nj-hl-function);
|
||||
--nj-pointer-mp-arr: var(--nj-hl-number);
|
||||
--nj-pointer-mp-keep: var(--md-default-fg-color--light);
|
||||
}
|
||||
[data-md-color-scheme="slate"] .nj-pointer-mpt { --nj-pointer-mp-add: #7ed491; }
|
||||
.md-typeset .nj-pointer-mpt td { vertical-align: top; }
|
||||
.md-typeset .nj-pointer-mpt td:first-child { white-space: nowrap; }
|
||||
.nj-pointer-mp {
|
||||
display: inline-block;
|
||||
padding: .05rem .5rem;
|
||||
border: 1px solid currentColor;
|
||||
border-radius: 999px;
|
||||
background-color: color-mix(in srgb, currentColor 10%, var(--md-default-bg-color));
|
||||
font-size: .92em;
|
||||
font-weight: 600;
|
||||
line-height: 1.5;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.nj-pointer-mp--set { color: var(--nj-pointer-mp-set); }
|
||||
.nj-pointer-mp--add { color: var(--nj-pointer-mp-add); }
|
||||
.nj-pointer-mp--del { color: var(--nj-pointer-mp-del); }
|
||||
.nj-pointer-mp--rec { color: var(--nj-pointer-mp-rec); }
|
||||
.nj-pointer-mp--arr { color: var(--nj-pointer-mp-arr); }
|
||||
.nj-pointer-mp--keep { color: var(--nj-pointer-mp-keep); }
|
||||
.nj-pointer-mp-none { color: var(--md-default-fg-color--light); font-style: italic; }
|
||||
.md-typeset .nj-pointer-mpt table:not([class]) td code { white-space: normal; }
|
||||
.md-typeset .nj-pointer-mpt table:not([class]) td:nth-child(-n+2) code { white-space: nowrap; }
|
||||
/* the result cell takes a tint of the rule's colour */
|
||||
.md-typeset .nj-pointer-mpt tr:has(.nj-pointer-mp--set) td:last-child { background-color: color-mix(in srgb, var(--nj-pointer-mp-set) 8%, transparent); }
|
||||
.md-typeset .nj-pointer-mpt tr:has(.nj-pointer-mp--add) td:last-child { background-color: color-mix(in srgb, var(--nj-pointer-mp-add) 8%, transparent); }
|
||||
.md-typeset .nj-pointer-mpt tr:has(.nj-pointer-mp--del) td:last-child { background-color: color-mix(in srgb, var(--nj-pointer-mp-del) 8%, transparent); }
|
||||
.md-typeset .nj-pointer-mpt tr:has(.nj-pointer-mp--rec) td:last-child { background-color: color-mix(in srgb, var(--nj-pointer-mp-rec) 8%, transparent); }
|
||||
.md-typeset .nj-pointer-mpt tr:has(.nj-pointer-mp--arr) td:last-child { background-color: color-mix(in srgb, var(--nj-pointer-mp-arr) 8%, transparent); }
|
||||
@@ -1,207 +0,0 @@
|
||||
/* figures: sax (SAX event stepper on features/parsing/sax_interface.md, js/fig-sax.js; memory_over_time.svg and
|
||||
chunk_buffering.svg on features/parsing/large_and_partial_input.md). Event colours are the --cb-* variables of the
|
||||
parser-callback figure in brand.css, which .nj-fig provides. */
|
||||
|
||||
/* ---------- stepper ---------- */
|
||||
.md-typeset .nj-sax {
|
||||
display: grid;
|
||||
grid-template-columns: minmax(0, 1fr);
|
||||
gap: .9rem 1.4rem;
|
||||
margin: 1.5rem 0;
|
||||
padding: 1rem 1.1rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-radius: 8px;
|
||||
background: var(--md-default-bg-color);
|
||||
font-size: .74rem;
|
||||
}
|
||||
@media screen and (min-width: 45em) {
|
||||
.md-typeset .nj-sax {
|
||||
grid-template-columns: minmax(0, 1fr) minmax(0, 1.15fr);
|
||||
grid-template-areas: "ctl ctl" "text text" "ev state" "status status";
|
||||
}
|
||||
.md-typeset .nj-sax > .nj-sax__controls { grid-area: ctl; }
|
||||
.md-typeset .nj-sax > .nj-sax__lane--text { grid-area: text; }
|
||||
.md-typeset .nj-sax > .nj-sax__lane--events { grid-area: ev; }
|
||||
.md-typeset .nj-sax > .nj-sax__lane--state { grid-area: state; }
|
||||
.md-typeset .nj-sax > .nj-sax__status { grid-area: status; }
|
||||
}
|
||||
.md-typeset .nj-sax p { margin: 0; }
|
||||
.md-typeset .nj-sax .nj-sax__h {
|
||||
margin: 0 0 .45rem;
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-size: .68rem;
|
||||
font-weight: 600;
|
||||
letter-spacing: .02em;
|
||||
}
|
||||
.md-typeset .nj-sax .nj-sax__h code { font-size: .95em; }
|
||||
.md-typeset .nj-sax .nj-sax__text code {
|
||||
display: inline-block;
|
||||
max-width: 100%;
|
||||
overflow-x: auto;
|
||||
padding: .35rem .6rem;
|
||||
font-size: .95rem;
|
||||
white-space: pre;
|
||||
word-break: normal;
|
||||
}
|
||||
.nj-sax .nj-sax-unread { color: var(--md-default-fg-color--light); }
|
||||
.nj-sax .nj-sax-unread--never { color: var(--md-default-fg-color--lighter); text-decoration: line-through; text-decoration-color: var(--md-default-fg-color--lighter); }
|
||||
.nj-sax .nj-sax-read { color: var(--md-code-fg-color); }
|
||||
.nj-sax .nj-sax-tok { border-radius: 3px; box-shadow: inset 0 -3px 0 var(--nj-sax-ev, var(--cb-v)); background: color-mix(in srgb, var(--nj-sax-ev, var(--cb-v)) 22%, transparent); }
|
||||
.nj-sax .nj-sax-tok--os, .nj-sax .nj-sax-ev--os { --nj-sax-ev: var(--cb-os); }
|
||||
.nj-sax .nj-sax-tok--oe, .nj-sax .nj-sax-ev--oe { --nj-sax-ev: var(--cb-oe); }
|
||||
.nj-sax .nj-sax-tok--k, .nj-sax .nj-sax-ev--k { --nj-sax-ev: var(--cb-k); }
|
||||
.nj-sax .nj-sax-tok--as, .nj-sax .nj-sax-ev--as { --nj-sax-ev: var(--cb-as); }
|
||||
.nj-sax .nj-sax-tok--ae, .nj-sax .nj-sax-ev--ae { --nj-sax-ev: var(--cb-ae); }
|
||||
.nj-sax .nj-sax-tok--v, .nj-sax .nj-sax-ev--v { --nj-sax-ev: var(--cb-v); }
|
||||
|
||||
/* event ticker */
|
||||
.md-typeset .nj-sax ol.nj-sax__events {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
counter-reset: nj-sax;
|
||||
}
|
||||
.md-typeset .nj-sax ol.nj-sax__events > li {
|
||||
position: relative;
|
||||
margin: 0 0 .2rem;
|
||||
padding: .12rem .4rem .12rem 2.6rem;
|
||||
border-radius: 5px;
|
||||
counter-increment: nj-sax;
|
||||
line-height: 1.5;
|
||||
}
|
||||
.md-typeset .nj-sax ol.nj-sax__events > li::before {
|
||||
content: counter(nj-sax);
|
||||
position: absolute;
|
||||
left: .35rem;
|
||||
top: .2rem;
|
||||
width: 1.1rem;
|
||||
color: var(--md-default-fg-color--lighter);
|
||||
font-size: .64rem;
|
||||
font-variant-numeric: tabular-nums;
|
||||
text-align: right;
|
||||
}
|
||||
.md-typeset .nj-sax ol.nj-sax__events > li::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
left: 1.75rem;
|
||||
top: 50%;
|
||||
width: .55rem;
|
||||
height: .55rem;
|
||||
margin-top: -.275rem;
|
||||
border-radius: 50%;
|
||||
background: var(--nj-sax-ev);
|
||||
}
|
||||
.md-typeset .nj-sax ol.nj-sax__events code { background: none; padding: 0; font-size: .8rem; }
|
||||
.nj-sax .nj-sax-ev--todo { opacity: .42; }
|
||||
.nj-sax .nj-sax-ev--skip { opacity: .42; text-decoration: line-through; }
|
||||
.nj-sax .nj-sax-ev--skip::after { background: var(--md-default-fg-color--lighter) !important; }
|
||||
.nj-sax .nj-sax-ev--cur { background: color-mix(in srgb, var(--nj-sax-ev) 16%, transparent); }
|
||||
.md-typeset .nj-sax .nj-sax-ev--false > code::after {
|
||||
content: " \2192 false";
|
||||
color: var(--nj-red);
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
/* handler state */
|
||||
.md-typeset .nj-sax pre.nj-sax__tree { margin: 0 0 .6rem; }
|
||||
.md-typeset .nj-sax pre.nj-sax__tree > code { padding: .5rem .7rem; font-size: .76rem; line-height: 1.45; }
|
||||
.nj-sax .nj-sax-hit { border-radius: 3px; background: color-mix(in srgb, var(--nj-blue) 22%, transparent); box-shadow: 0 0 0 1px color-mix(in srgb, var(--nj-blue) 55%, transparent); }
|
||||
.nj-sax .nj-sax-dim { color: var(--md-default-fg-color--lighter); }
|
||||
.md-typeset .nj-sax .nj-sax__stackh { margin: 0 0 .3rem; color: var(--md-default-fg-color--light); font-size: .66rem; font-weight: 600; }
|
||||
.md-typeset .nj-sax ol.nj-sax__stack {
|
||||
display: flex;
|
||||
flex-direction: column-reverse;
|
||||
gap: .25rem;
|
||||
margin: 0 0 .6rem;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
.md-typeset .nj-sax ol.nj-sax__stack > li {
|
||||
margin: 0;
|
||||
padding: .2rem .5rem;
|
||||
border: 1px solid var(--md-default-fg-color--lightest);
|
||||
border-left: 3px solid var(--nj-blue);
|
||||
border-radius: 4px;
|
||||
}
|
||||
.md-typeset .nj-sax ol.nj-sax__stack > li.nj-sax-dim { border-left-color: var(--md-default-fg-color--lightest); }
|
||||
.md-typeset .nj-sax ol.nj-sax__stack code { background: none; padding: 0; }
|
||||
.md-typeset .nj-sax .nj-sax__note { color: var(--md-default-fg-color--light); font-size: .75rem; line-height: 1.5; }
|
||||
.md-typeset .nj-sax dl.nj-sax__kv {
|
||||
display: grid;
|
||||
grid-template-columns: auto minmax(0, 1fr);
|
||||
gap: .35rem .8rem;
|
||||
margin: 0 0 .6rem;
|
||||
}
|
||||
.md-typeset .nj-sax dl.nj-sax__kv dt { color: var(--md-default-fg-color--light); font-weight: 600; }
|
||||
.md-typeset .nj-sax dl.nj-sax__kv dd { margin: 0; }
|
||||
|
||||
/* controls */
|
||||
.nj-sax .nj-sax__controls { display: flex; flex-wrap: wrap; gap: .5rem 1rem; align-items: center; }
|
||||
.nj-sax .nj-sax__btns, .nj-sax .nj-sax__modes { display: flex; flex-wrap: wrap; gap: .35rem; }
|
||||
.nj-sax .nj-sax__modes { margin-left: auto; }
|
||||
.md-typeset .nj-sax .nj-sax-btn {
|
||||
min-height: 2.2rem;
|
||||
padding: .3rem .8rem;
|
||||
border: 1px solid color-mix(in srgb, var(--nj-blue) 55%, var(--md-default-bg-color));
|
||||
border-radius: 6px;
|
||||
background: var(--md-default-bg-color);
|
||||
color: var(--nj-blue);
|
||||
font: inherit;
|
||||
font-weight: 600;
|
||||
cursor: pointer;
|
||||
}
|
||||
.md-typeset .nj-sax .nj-sax-btn:hover:not(:disabled) { background: color-mix(in srgb, var(--nj-blue) 10%, var(--md-default-bg-color)); }
|
||||
.md-typeset .nj-sax .nj-sax-btn--main, .md-typeset .nj-sax .nj-sax-btn[aria-pressed="true"] {
|
||||
border-color: var(--nj-band);
|
||||
background: var(--nj-band);
|
||||
color: #fff;
|
||||
}
|
||||
.md-typeset .nj-sax .nj-sax-btn--main:hover:not(:disabled), .md-typeset .nj-sax .nj-sax-btn[aria-pressed="true"]:hover {
|
||||
background: var(--md-primary-fg-color--light);
|
||||
}
|
||||
.md-typeset .nj-sax .nj-sax-btn:disabled { opacity: .4; cursor: default; }
|
||||
.md-typeset .nj-sax .nj-sax-btn:focus-visible, .nj-sax .nj-sax__stop input:focus-visible {
|
||||
outline: 2px solid var(--nj-blue);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
.nj-sax .nj-sax__stop { display: inline-flex; gap: .45rem; align-items: center; min-height: 2.2rem; cursor: pointer; }
|
||||
.nj-sax .nj-sax__stop input { width: 1.05rem; height: 1.05rem; margin: 0; accent-color: var(--nj-red); }
|
||||
.nj-sax .nj-sax__stop:has(input:disabled) { opacity: .45; cursor: default; }
|
||||
.md-typeset .nj-sax .nj-sax__status {
|
||||
padding-top: .6rem;
|
||||
border-top: 1px solid var(--md-default-fg-color--lightest);
|
||||
color: var(--md-default-fg-color--light);
|
||||
font-size: .72rem;
|
||||
min-height: 2.6em;
|
||||
}
|
||||
@media screen and (max-width: 44.984375em) {
|
||||
.md-typeset .nj-sax { padding: .8rem; }
|
||||
.md-typeset .nj-sax .nj-sax-btn { min-height: 44px; min-width: 44px; }
|
||||
.nj-sax .nj-sax__stop { min-height: 44px; }
|
||||
.nj-sax .nj-sax__modes { margin-left: 0; }
|
||||
}
|
||||
@media (prefers-reduced-motion: no-preference) {
|
||||
.nj-sax .nj-sax__events > li { transition: opacity .2s, background-color .2s; }
|
||||
}
|
||||
|
||||
/* ---------- static SVG figures ---------- */
|
||||
.md-typeset svg.nj-fig--sax-mem { min-width: 34rem; max-width: 40rem; }
|
||||
.md-typeset svg.nj-fig--sax-buf { min-width: 36rem; max-width: 42rem; }
|
||||
.nj-fig .nj-sax-axis { fill: none; stroke: var(--fg-line); stroke-width: 1.5; }
|
||||
.nj-fig .nj-sax-illus { font-style: italic; }
|
||||
.nj-fig .nj-sax-curve { fill: none; stroke-width: 3; stroke-linecap: round; stroke-linejoin: round; }
|
||||
.nj-fig .nj-sax-c-dom { --nj-sax-c: var(--nj-red); }
|
||||
.nj-fig .nj-sax-c-doc { --nj-sax-c: var(--nj-hl-type); }
|
||||
.nj-fig .nj-sax-c-cb { --nj-sax-c: var(--nj-hl-number); }
|
||||
.nj-fig .nj-sax-c-sax { --nj-sax-c: var(--nj-blue); }
|
||||
.nj-fig .nj-sax-curve.nj-sax-c-doc { stroke-dasharray: 9 5; }
|
||||
.nj-fig .nj-sax-curve { stroke: var(--nj-sax-c); }
|
||||
.nj-fig .nj-sax-lab { fill: var(--nj-sax-c); font-size: 14.5px; font-weight: 700; }
|
||||
.nj-fig .nj-sax-old { fill: color-mix(in srgb, currentColor 10%, var(--md-default-bg-color)); }
|
||||
.nj-fig .nj-sax-new { fill: color-mix(in srgb, var(--md-typeset-a-color) 18%, var(--md-default-bg-color)); stroke: var(--md-typeset-a-color); stroke-width: 1; }
|
||||
.nj-fig .nj-sax-buf { fill: currentColor; font-family: var(--md-code-font-family), monospace; font-size: 14px; white-space: pre; }
|
||||
.nj-fig .nj-sax-sep { stroke: var(--fg-line); stroke-width: 1; stroke-dasharray: 3 3; }
|
||||
.nj-fig .nj-sax-status { font-size: 14px; font-weight: 600; }
|
||||
.nj-fig .nj-sax-s-wait { fill: var(--nj-blue); }
|
||||
.nj-fig .nj-sax-s-ok { fill: var(--nj-hl-string); }
|
||||
.nj-fig .nj-sax-s-err { fill: var(--nj-red); }
|
||||
@@ -1 +0,0 @@
|
||||
<svg xmlns='http://www.w3.org/2000/svg' width='160' height='160'><g font-family='Menlo,monospace' font-size='26' font-weight='600' fill='#ffffff' fill-opacity='0.10'><text x='14' y='34'>{</text><text x='92' y='22'>]</text><text x='136' y='60'>:</text><text x='52' y='82'>[</text><text x='118' y='112'>,</text><text x='20' y='140'>}</text><text x='78' y='150'>:</text><text x='140' y='158'>{</text></g></svg>
|
||||
|
Before Width: | Height: | Size: 408 B |
@@ -124,28 +124,26 @@ For all the macros, the first parameter is the name of the class/struct. The `DE
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A["choosing a NLOHMANN_DEFINE_* macro"] --> B{{"adding fields to a base class?"}}
|
||||
A["choosing a NLOHMANN_DEFINE_* macro"] --> B{"adding fields to a base class?"}
|
||||
B -->|"yes"| C["...DERIVED_TYPE..."]
|
||||
B -->|"no"| D["...TYPE..."]
|
||||
C --> E{{"need access to private members?"}}
|
||||
C --> E{"need access to private members?"}
|
||||
D --> E
|
||||
E -->|"yes"| F["...INTRUSIVE... (used inside the class)"]
|
||||
E -->|"no"| G["...NON_INTRUSIVE... (used in the namespace)"]
|
||||
F --> H{{"only serializing, never parsing back?"}}
|
||||
F --> H{"only serializing, never parsing back?"}
|
||||
G --> H
|
||||
H -->|"yes"| I["...ONLY_SERIALIZE"]
|
||||
H -->|"no"| J{{"allow missing keys when parsing?"}}
|
||||
H -->|"no"| J{"allow missing keys when parsing?"}
|
||||
J -->|"yes"| K["...WITH_DEFAULT"]
|
||||
J -->|"no"| L["plain (missing keys throw)"]
|
||||
I --> M{{"need custom JSON key names?"}}
|
||||
I --> M{"need custom JSON key names?"}
|
||||
K --> M
|
||||
L --> M
|
||||
M -->|"yes"| N["...WITH_NAMES"]
|
||||
M -->|"no"| O["done"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Decision tree for choosing a `NLOHMANN_DEFINE_*` macro: answer the questions from top to bottom; each answer picks one part of the macro name, and the parts are combined in this order. The table below lists the resulting macros.</p>
|
||||
|
||||
| Need access to private members | Need only serialization | Allow missing values when de-serializing | macro |
|
||||
|------------------------------------------------------------------|------------------------------------------------------------------|------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------|
|
||||
| <div style="color: green;">:octicons-check-circle-fill-24:</div> | <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: red;">:octicons-x-circle-fill-24:</div> | [**NLOHMANN_DEFINE_TYPE_INTRUSIVE**](../api/macros/nlohmann_define_type_intrusive.md) |
|
||||
@@ -155,8 +153,6 @@ flowchart TD
|
||||
| <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: green;">:octicons-check-circle-fill-24:</div> | [**NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT**](../api/macros/nlohmann_define_type_non_intrusive.md) |
|
||||
| <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: green;">:octicons-check-circle-fill-24:</div> | <div style="color: grey;">:octicons-skip-fill-24:</div> | [**NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_ONLY_SERIALIZE**](../api/macros/nlohmann_define_type_non_intrusive.md) |
|
||||
|
||||
<p class="nj-table-caption" markdown>Macros for classes and structs without a base class. A green check means yes, a red cross means no, and a grey skip sign means the column does not apply, as a macro that only serializes never reads values.</p>
|
||||
|
||||
For _derived_ classes and structs, use the following macros
|
||||
|
||||
| Need access to private members | Need only serialization | Allow missing values when de-serializing | macro |
|
||||
@@ -168,33 +164,12 @@ For _derived_ classes and structs, use the following macros
|
||||
| <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: green;">:octicons-check-circle-fill-24:</div> | [**NLOHMANN_DEFINE_DERIVED_TYPE_NON_INTRUSIVE_WITH_DEFAULT**](../api/macros/nlohmann_define_derived_type.md) |
|
||||
| <div style="color: red;">:octicons-x-circle-fill-24:</div> | <div style="color: green;">:octicons-check-circle-fill-24:</div> | <div style="color: grey;">:octicons-skip-fill-24:</div> | [**NLOHMANN_DEFINE_DERIVED_TYPE_NON_INTRUSIVE_ONLY_SERIALIZE**](../api/macros/nlohmann_define_derived_type.md) |
|
||||
|
||||
<p class="nj-table-caption" markdown>Macros for derived classes and structs, read as Table 1.</p>
|
||||
|
||||
!!! info "Implementation limits"
|
||||
|
||||
- The current macro implementations are limited to at most 63 member variables. If you want to serialize/deserialize
|
||||
types with more than 63 member variables, you need to define the `to_json`/`from_json` functions manually.
|
||||
- For the `WITH_NAMES` variants the limit is halved to 31 member variables.
|
||||
|
||||
To pick the macro for your own type and get code to start from, answer the questions below.
|
||||
|
||||
<div class="nj-macro-chooser" data-variant="full" markdown>
|
||||
<div class="nj-mc-fallback" markdown>
|
||||
|
||||
- Members are private: use an `INTRUSIVE` macro inside the class ([reference](../api/macros/nlohmann_define_type_intrusive.md){ data-nj-mc="intrusive" }).
|
||||
- All members are public, or you cannot edit the class: use a `NON_INTRUSIVE` macro in the class's namespace ([reference](../api/macros/nlohmann_define_type_non_intrusive.md){ data-nj-mc="non_intrusive" }).
|
||||
- The class adds members to a serializable base class: use a `DERIVED_TYPE` macro with the base class as second argument ([reference](../api/macros/nlohmann_define_derived_type.md){ data-nj-mc="derived" }).
|
||||
- Missing keys should keep their default values: append `_WITH_DEFAULT`; otherwise a missing key throws.
|
||||
- You only convert to JSON: append `_ONLY_SERIALIZE` instead.
|
||||
- JSON keys differ from the member names: append `_WITH_NAMES` and write `"key", member` pairs ([reference](../api/macros/nlohmann_define_type_with_names.md){ data-nj-mc="with_names" }).
|
||||
- Private members of a class you cannot edit: no macro works; write the conversion by hand ([third-party types](#how-do-i-convert-third-party-types){ data-nj-mc="third_party" }).
|
||||
- The type is not default constructible and is converted in both directions: no macro works; specialize `adl_serializer` with a `from_json` that returns the value, or append `_ONLY_SERIALIZE` if you only convert to JSON ([non-default-constructible types](#how-can-i-use-get-for-non-default-constructiblenon-copyable-types){ data-nj-mc="non_default" }).
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Macro chooser: each answer selects one part of the macro name; the generated program defines the type, calls the macro and converts a value to JSON and back. Combinations that no macro supports show the alternative instead of code.</p>
|
||||
|
||||
??? example "Example: using the `NLOHMANN_DEFINE_TYPE_*` macros"
|
||||
|
||||
The `to_json`/`from_json` functions for the `person` struct above can be created with:
|
||||
@@ -324,8 +299,6 @@ flowchart LR
|
||||
B -->|"user specialization replaces the default"| E["user's adl_serializer specialization for T"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>How a conversion between `json` and a type `T` is dispatched: the default `adl_serializer` calls the free `to_json`/`from_json` functions found by argument-dependent lookup, while a user specialization of `adl_serializer` replaces this path.</p>
|
||||
|
||||
The library uses **JSON Serializers** to convert types to JSON.
|
||||
The default serializer for `nlohmann::json` is `nlohmann::adl_serializer` (ADL means [Argument-Dependent Lookup](https://en.cppreference.com/w/cpp/language/adl)).
|
||||
|
||||
|
||||
@@ -53,25 +53,7 @@ See [binary values](../binary_values.md) for more information.
|
||||
| UBJSON (size) | 58.6 % | 92.3 % | 86.8 % | 97.4 % |
|
||||
| UBJSON (size+type) | 55.9 % | 92.3 % | 85.0 % | 95.0 % |
|
||||
|
||||
<p class="nj-table-caption" markdown>Size of each test file in each format, in percent of the minified JSON value; the smallest size per file is printed in bold. The (size) and (size+type) rows are written with the `use_size` and `use_type` options of [`to_bjdata`](../../api/basic_json/to_bjdata.md) and [`to_ubjson`](../../api/basic_json/to_ubjson.md).</p>
|
||||
|
||||
<div class="nj-charts-grid-wrap" markdown>
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/binary_sizes_canada.svg"
|
||||
</div>
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/binary_sizes_twitter.svg"
|
||||
</div>
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/binary_sizes_citm_catalog.svg"
|
||||
</div>
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/binary_sizes_jeopardy.svg"
|
||||
</div>
|
||||
</div>
|
||||
<p class="nj-charts-caption" markdown>The table above as charts: size per base format relative to minified JSON (vertical line at
|
||||
100 %); the smallest format per file is drawn in a stronger colour than the others. The size and size+type variants of BJData and UBJSON are
|
||||
omitted here; see the table.</p>
|
||||
Sizes compared to minified JSON value; the smallest size per file is printed in bold.
|
||||
|
||||
## See also
|
||||
|
||||
|
||||
@@ -25,8 +25,6 @@ class vector ["std::vector<uint8_t>"]
|
||||
vector <|-- binary_t
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Class diagram of `json::binary_t`: it derives from `std::vector<uint8_t>` and adds functions to set, clear, query, and test an optional subtype.</p>
|
||||
|
||||
By default, binary values are stored as `std::vector<std::uint8_t>`. This type can be changed by providing a template
|
||||
parameter to the `basic_json` type. To store binary subtypes, the storage type is extended and exposed as
|
||||
[`json::binary_t`](../api/basic_json/binary_t.md):
|
||||
|
||||
@@ -89,5 +89,3 @@ non-existing, an exception is thrown.
|
||||
| access to valid array index | reference to existing value is returned | const reference to existing value is returned |
|
||||
| access to non-existing object key | `basic_json::out_of_range` exception is thrown | `basic_json::out_of_range` exception is thrown |
|
||||
| access to invalid array index | `basic_json::out_of_range` exception is thrown | `basic_json::out_of_range` exception is thrown |
|
||||
|
||||
<p class="nj-table-caption" markdown>Result of [`at`](../../api/basic_json/at.md) in each scenario, for a non-const and a const value.</p>
|
||||
@@ -12,23 +12,16 @@ Testing whether a key or index exists before accessing it is also possible, with
|
||||
[`contains`](../../api/basic_json/contains.md) or [`find`](../../api/basic_json/find.md) (which returns an iterator to
|
||||
the value, or `end()` if it is not found).
|
||||
|
||||
How do I get a value out? Start at the top and follow the first question that applies:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A["getting a value out"] --> P{{"nested path such as /server/port?"}}
|
||||
P -->|"yes"| JP["JSON Pointer: at(ptr), value(ptr, default), contains(ptr)"]
|
||||
P -->|"no, one key or index"| T{{"only testing whether it exists?"}}
|
||||
T -->|"yes"| CF["contains() / find()"]
|
||||
T -->|"no"| M{{"may it be missing?"}}
|
||||
M -->|"yes, a fallback is fine"| V["value(key, default)"]
|
||||
M -->|"yes, and missing is an error"| AT["at(): throws out_of_range"]
|
||||
M -->|"no, it exists and its type is known"| OP["operator[] and get#lt;T#gt;()"]
|
||||
OP -.- W["non-const operator[] inserts null for a missing key"]
|
||||
A["accessing a value"] --> B{"must it exist?"}
|
||||
B -->|"yes, missing is an error"| C["at() -- throws"]
|
||||
B -->|"yes, but checking is my job"| D["operator[] -- unchecked"]
|
||||
B -->|"no, a fallback is fine"| E["value() -- default value"]
|
||||
A --> F{"just testing first?"}
|
||||
F -->|"yes"| G["contains() / find()"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Decision tree for reading a value: the labels on the arrows are the answers to the questions, and the boxes name the functions to use. The dashed line marks a side effect of the non-const `operator[]`.</p>
|
||||
|
||||
## Does this key exist?
|
||||
|
||||
Use [`contains`](../../api/basic_json/contains.md) to test for a key; it does not modify the value and does not throw:
|
||||
|
||||
@@ -125,5 +125,3 @@ for (int i = 0; i < 1000; ++i) {
|
||||
| access to valid array index | reference to existing value is returned | const reference to existing value is returned |
|
||||
| access to non-existing object key | reference to newly inserted `#!json null` value is returned | **undefined behavior**; [runtime assertion](../assertions.md) in debug mode |
|
||||
| access to invalid array index | reference to newly inserted `#!json null` value is returned; any index between previous maximal index and passed index are filled with `#!json null` | **undefined behavior**; [runtime assertion](../assertions.md) in debug mode |
|
||||
|
||||
<p class="nj-table-caption" markdown>Result of [`operator[]`](../../api/basic_json/operator%5B%5D.md) in each scenario, for a non-const and a const value.</p>
|
||||
@@ -9,11 +9,7 @@ As for other containers, [`begin()`](../api/basic_json/begin.md) returns an iter
|
||||
placeholder and cannot be dereferenced. In case of null values, empty arrays, or empty objects, `begin()` will return
|
||||
`end()`.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-begin-end.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>The range of `begin()` and `end()`: `begin()` refers to the first element, `end()` to the position after the last element, which must not be dereferenced.</p>
|
||||

|
||||
|
||||
### Iteration order for objects
|
||||
|
||||
@@ -116,11 +112,7 @@ for (auto& [key, val] : j_object.items())
|
||||
[`rbegin()`](../api/basic_json/rbegin.md) and [`rend()`](../api/basic_json/rend.md) return iterators in the reverse
|
||||
sequence.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/range-rbegin-rend.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>The range of `rbegin()` and `rend()` over the same elements: `rbegin()` refers to the last element and `rend()` to the position before the first one. Each reverse iterator stores an iterator to the element after the one it refers to.</p>
|
||||

|
||||
|
||||
??? example "Example: reverse iteration with `rbegin()` and `rend()`"
|
||||
|
||||
|
||||
@@ -7,24 +7,6 @@ of operations to apply to a JSON document. Operations address locations in the d
|
||||
[JSON Pointer](json_pointer.md) paths. With the [`patch`](../api/basic_json/patch.md) function, a JSON Patch is applied
|
||||
to the current JSON value by executing all operations from the patch, yielding the patched document as a new value.
|
||||
|
||||
The following steps through one operation of each kind. The first three operations are those of the example below; the
|
||||
other three continue on its result.
|
||||
|
||||
<div class="nj-patch" data-nj-patch markdown>
|
||||
|
||||
| Operation | Before | After |
|
||||
|-------------------------------------------------------------|------------------------------------------------|-------------------------------------------------|
|
||||
| `{"op": "replace", "path": "/baz", "value": "boo"}` | `{"baz": "qux", "foo": "bar"}` | `{"baz": "boo", "foo": "bar"}` |
|
||||
| `{"op": "add", "path": "/hello", "value": ["world"]}` | `{"baz": "boo", "foo": "bar"}` | `{"baz": "boo", "foo": "bar", "hello": ["world"]}` |
|
||||
| `{"op": "remove", "path": "/foo"}` | `{"baz": "boo", "foo": "bar", "hello": ["world"]}` | `{"baz": "boo", "hello": ["world"]}` |
|
||||
| `{"op": "move", "from": "/baz", "path": "/hello/1"}` | `{"baz": "boo", "hello": ["world"]}` | `{"hello": ["world", "boo"]}` |
|
||||
| `{"op": "copy", "from": "/hello/0", "path": "/greeting"}` | `{"hello": ["world", "boo"]}` | `{"greeting": "world", "hello": ["world", "boo"]}` |
|
||||
| `{"op": "test", "path": "/greeting", "value": "world"}` | `{"greeting": "world", "hello": ["world", "boo"]}` | unchanged (a failed test throws) |
|
||||
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Stepper through the six operations: *Next* applies the next operation, *Back* undoes it, and *Reset* returns to the original document. The current operation is highlighted in the patch list, and the lines it changes are marked in the document.</p>
|
||||
|
||||
!!! tip "Applying a patch without copying"
|
||||
|
||||
[`patch`](../api/basic_json/patch.md) leaves the original value unchanged and returns the patched result as a copy.
|
||||
@@ -57,8 +39,6 @@ flowchart LR
|
||||
P -.->|"applied to source, yields"| T
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>How `diff` and `patch` relate: `diff(source, target)` yields a patch, and applying that patch to the source yields the target.</p>
|
||||
|
||||
!!! success "Invariant"
|
||||
|
||||
For two JSON values *source* and *target*, the following code yields always true:
|
||||
|
||||
@@ -18,40 +18,6 @@ Consider the following JSON document
|
||||
}
|
||||
```
|
||||
|
||||
Select a pointer (or a node of the tree) to walk it through this document; each segment of the pointer goes one level
|
||||
deeper. The table below lists the same pointers.
|
||||
|
||||
<div class="nj-pointer-walk" data-nj-pointer-walk data-doc="{"array":["A","B","C"],"nested":{"one":1,"two":2,"three":[true,false]}}" role="group" aria-label="Pointer walker for the example document">
|
||||
<p class="nj-pointer-static">Highlighted: the path of the pointer <code>/nested/three/1</code>, which identifies <code>false</code>.</p>
|
||||
<ul class="nj-pointer-tree">
|
||||
<li data-p="" class="is-on"><span class="nj-pointer-n"><span class="nj-pointer-k">root</span> <span class="nj-pointer-t">object</span></span>
|
||||
<ul>
|
||||
<li data-p="/array" class="is-pass"><span class="nj-pointer-n"><span class="nj-pointer-k">"array"</span> <span class="nj-pointer-t">array</span></span>
|
||||
<ul>
|
||||
<li data-p="/array/0"><span class="nj-pointer-n"><span class="nj-pointer-k">0</span>: <span class="nj-pointer-v nj-pointer-v--s">"A"</span></span></li>
|
||||
<li data-p="/array/1"><span class="nj-pointer-n"><span class="nj-pointer-k">1</span>: <span class="nj-pointer-v nj-pointer-v--s">"B"</span></span></li>
|
||||
<li data-p="/array/2"><span class="nj-pointer-n"><span class="nj-pointer-k">2</span>: <span class="nj-pointer-v nj-pointer-v--s">"C"</span></span></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li data-p="/nested" class="is-on"><span class="nj-pointer-n"><span class="nj-pointer-k">"nested"</span> <span class="nj-pointer-t">object</span></span>
|
||||
<ul>
|
||||
<li data-p="/nested/one" class="is-pass"><span class="nj-pointer-n"><span class="nj-pointer-k">"one"</span>: <span class="nj-pointer-v nj-pointer-v--n">1</span></span></li>
|
||||
<li data-p="/nested/two" class="is-pass"><span class="nj-pointer-n"><span class="nj-pointer-k">"two"</span>: <span class="nj-pointer-v nj-pointer-v--n">2</span></span></li>
|
||||
<li data-p="/nested/three" class="is-on"><span class="nj-pointer-n"><span class="nj-pointer-k">"three"</span> <span class="nj-pointer-t">array</span></span>
|
||||
<ul>
|
||||
<li data-p="/nested/three/0" class="is-pass"><span class="nj-pointer-n"><span class="nj-pointer-k">0</span>: <span class="nj-pointer-v nj-pointer-v--b">true</span></span></li>
|
||||
<li data-p="/nested/three/1" class="is-on is-target"><span class="nj-pointer-n"><span class="nj-pointer-k">1</span>: <span class="nj-pointer-v nj-pointer-v--b">false</span></span></li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>The highlighted nodes are the path from the root to the selected level, and the line below the tree shows the value the pointer resolves to. Select a segment in the pointer bar to stop at a shallower level, or a node of the tree to select its pointer.</p>
|
||||
|
||||
Then every value inside the JSON document can be identified as follows:
|
||||
|
||||
| JSON Pointer | JSON value |
|
||||
@@ -161,14 +127,6 @@ The reverse function, [`unflatten`](../api/basic_json/unflatten.md) recreates th
|
||||
auto j_original = j_flat.unflatten();
|
||||
```
|
||||
|
||||
Each leaf of the document becomes one key of the flat object, and `unflatten()` reverses the mapping:
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/json_pointer_flatten.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Left: the example document as a tree; right: the flat object it becomes. `flatten()` converts from left to right, `unflatten()` from right to left.</p>
|
||||
|
||||
## See also
|
||||
|
||||
- Class [`json_pointer`](../api/json_pointer/index.md)
|
||||
|
||||
@@ -33,14 +33,6 @@ index. It gives you the read-only, type-inspection part of the `basic_json` inte
|
||||
actual `basic_json` value for a subtree, [`materialize()`](../api/basic_json_view/materialize.md) builds exactly the
|
||||
one [`parse()`](../api/basic_json/parse.md) would have produced for it.
|
||||
|
||||
The same small text, parsed both ways:
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/json_view_layout.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Top: the tree of separate heap allocations that `basic_json::parse()` builds. Bottom: `json_document::parse()` keeps the source text and builds one flat index of 16-byte nodes that point back into it, plus a buffer of decoded strings.</p>
|
||||
|
||||
## How to use it
|
||||
|
||||
Include `<nlohmann/json_view.hpp>` in addition to (or instead of) `<nlohmann/json.hpp>`. Parse into a
|
||||
@@ -92,12 +84,6 @@ Moving the `basic_json_document<>` itself is fine and does **not** invalidate it
|
||||
allocation that keeps its address across the move. Take a fresh view from [`root()`](../api/basic_json_document/root.md)
|
||||
whenever any of the other conditions above was not met.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/json_view_lifetime.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Four timelines of a document and its views, each bar showing when an object is alive or valid and when it dangles. Destroying the borrowed text, re-parsing, or shrinking the document invalidates the views taken before; moving the document does not.</p>
|
||||
|
||||
A view can dangle, exactly like a `#!cpp std::string_view`: nothing stops you from using it after its document is
|
||||
gone. This is deliberate. A view is two pointers and trivially copyable; making it safe (a `#!cpp std::shared_ptr` in
|
||||
the document and a `#!cpp std::weak_ptr` in each view) would make it larger, add reference counting to every copy,
|
||||
@@ -288,26 +274,6 @@ or `ordered_json` value in place lossy. Say you parse a configuration file, patc
|
||||
- **`ordered_json`** keeps the key order, but still rewrites every number the same way: parsing has already reduced
|
||||
it to a `#!cpp double`/`#!cpp int64_t`, and there is no way back to how it was spelled in the source text.
|
||||
|
||||
The patch of the example below (set `"host"`, add `"retries"`) written back by each of them:
|
||||
|
||||
<div class="nj-jsonview-cmp" role="group" aria-label="The same patch written back by json, ordered_json, and json_editable_document">
|
||||
<div><p class="nj-jsonview-cmp-h"><code>json</code></p><p class="nj-jsonview-cmp-v">keys sorted, numbers rewritten</p><pre>{<span class="nj-jsonview-bad">"host"</span>:"db2",
|
||||
"name":"cache",
|
||||
"port":6379,
|
||||
"price":<span class="nj-jsonview-bad">19.9</span>,
|
||||
"retries":3}</pre></div>
|
||||
<div><p class="nj-jsonview-cmp-h"><code>ordered_json</code></p><p class="nj-jsonview-cmp-v">key order kept, numbers rewritten</p><pre>{"name":"cache",
|
||||
"host":"db2",
|
||||
"port":6379,
|
||||
"price":<span class="nj-jsonview-bad">19.9</span>,
|
||||
"retries":3}</pre></div>
|
||||
<div class="nj-jsonview-cmp--best"><p class="nj-jsonview-cmp-h"><code>json_editable_document</code></p><p class="nj-jsonview-cmp-v">order and spelling kept</p><pre>{"name":"cache",
|
||||
"host":"db2",
|
||||
"port":6379,
|
||||
"price":<span class="nj-jsonview-ok">19.90</span>,
|
||||
"retries":3}</pre></div>
|
||||
</div>
|
||||
|
||||
An editable document keeps both. [`dump()`](../api/basic_json_view/dump.md) of an edited document writes members in
|
||||
document order -- a member [`set`](../api/basic_json_document/set.md) added goes at the end, exactly where it was
|
||||
inserted, and an [`erase`](../api/basic_json_document/erase.md)d member simply leaves a gap: everything around it
|
||||
@@ -335,8 +301,8 @@ parsed into for as long as it is not itself replaced. So every [view](../api/bas
|
||||
an edit, including a previously obtained [`root()`](../api/basic_json_document/root.md), stays valid and, if it
|
||||
still refers to the edited value, sees the edit; a view of a value a later edit drops or replaces just keeps showing
|
||||
what it last held. New values go to storage the document allocates and owns on demand. The one thing an edit does
|
||||
invalidate is the **iterators** taken over an edited array or object: the first time an element is added to it,
|
||||
inserted into it, erased from it, or replaced by a value that spans a different number of nodes, its elements move from the parsed, fixed layout to a growable block of links
|
||||
invalidate is the **iterators** taken over an edited array or object: the first time one of its elements is set,
|
||||
appended to, inserted into, or erased, its elements move from the parsed, fixed layout to a growable block of links
|
||||
so that [`push_back`](../api/basic_json_document/push_back.md) can later grow it in amortized constant time --
|
||||
existing elements are not touched, but an iterator that was walking the old layout no longer matches. A string
|
||||
obtained with
|
||||
@@ -346,43 +312,6 @@ edits. See [`basic_json_document`'s Edits](../api/basic_json_document/index.md#e
|
||||
throws (the *basic* guarantee, not the strong one `dump()` and the read-only functions provide). How edits are kept in
|
||||
the index is described in the [architecture overview](../home/architecture.md#node-index-of-json-views).
|
||||
|
||||
Step through the edits of a small document (the node fields follow the [architecture overview](../home/architecture.md#node-index-of-json-views)):
|
||||
|
||||
<div class="nj-jsonview-steps" data-nj-jsonview-steps>
|
||||
<figure class="nj-jsonview-step" data-label="After parsing">
|
||||
<div class="nj-jsonview-scroll">
|
||||
--8<-- "images/json_view_edit_0.svg"
|
||||
</div>
|
||||
<figcaption>Step 1 of 5. After parsing: nine nodes in the parsed index, no owned storage yet.</figcaption>
|
||||
</figure>
|
||||
<figure class="nj-jsonview-step" data-label="set an existing member">
|
||||
<div class="nj-jsonview-scroll">
|
||||
--8<-- "images/json_view_edit_1.svg"
|
||||
</div>
|
||||
<figcaption>Step 2 of 5. <code>doc.set(doc.root(), "port", 6380)</code> overwrites the node of the integer in place; no member is added or removed, so the object keeps its parsed layout.</figcaption>
|
||||
</figure>
|
||||
<figure class="nj-jsonview-step" data-label="erase an array element">
|
||||
<div class="nj-jsonview-scroll">
|
||||
--8<-- "images/json_view_edit_2.svg"
|
||||
</div>
|
||||
<figcaption>Step 3 of 5. <code>doc.erase(doc.root()["tags"], 0)</code>: the array is edited for the first time, so its elements move to a block of links in owned storage. The node of <code>"eu"</code> stays in the index, but nothing refers to it any more; iterators over the array taken before are invalid.</figcaption>
|
||||
</figure>
|
||||
<figure class="nj-jsonview-step" data-label="push_back onto the array">
|
||||
<div class="nj-jsonview-scroll">
|
||||
--8<-- "images/json_view_edit_3.svg"
|
||||
</div>
|
||||
<figcaption>Step 4 of 5. <code>doc.push_back(doc.root()["tags"], "new")</code>: the new string gets its own node, its text goes to the buffer of edited text, and a link to it is appended to the block of the array.</figcaption>
|
||||
</figure>
|
||||
<figure class="nj-jsonview-step" data-label="set a new member">
|
||||
<div class="nj-jsonview-scroll">
|
||||
--8<-- "images/json_view_edit_4.svg"
|
||||
</div>
|
||||
<figcaption>Step 5 of 5. <code>doc.set(doc.root(), "retries", 3)</code>: a new member, so the object moves to a block too: copies of its keys, links to the values it already had, then the new key and a link to the new integer.</figcaption>
|
||||
</figure>
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>The node index and the owned storage of the document after each of five edits. Use *Back*, *Next*, or the numbered buttons to switch between the steps; without JavaScript all steps are shown one below the other.</p>
|
||||
|
||||
## Images
|
||||
|
||||
[`save()`](../api/basic_json_document/save.md) writes a document as an *image*: a byte buffer that
|
||||
@@ -444,8 +373,6 @@ either.
|
||||
| **Typical use** | general-purpose JSON handling: config, request/response bodies you build or modify, anything you hold onto | validating or projecting a text into your own data structure without ever holding the whole thing as JSON | large or high-volume input where you only need part of it, or need it repeatedly, and can keep the source text (or a copy) alive for as long as the document lives | a document you read, patch a few fields of, and write back -- a configuration file, for instance -- where the rest of it should come back exactly as it was |
|
||||
| **Caching/reload** | not applicable -- re-parse, or roll your own serialization | not applicable | [`save()`](../api/basic_json_document/save.md)/[`load()`](../api/basic_json_document/load.md): cache the parsed index as an image and reload it without parsing | same, saving the document's current -- possibly edited -- state |
|
||||
|
||||
<p class="nj-table-caption" markdown>Each column is one way to work with JSON in this library, and each row compares one property of them.</p>
|
||||
|
||||
## Version history
|
||||
|
||||
- Added in version 3.13.0.
|
||||
@@ -12,35 +12,6 @@ easier to read and write for object-shaped documents.
|
||||
The function [`merge_diff`](../api/basic_json/merge_diff.md) creates a merge patch that changes one JSON value into
|
||||
another.
|
||||
|
||||
The example below shows every rule in one patch, member by member:
|
||||
|
||||
<div class="nj-pointer-mpt" markdown>
|
||||
|
||||
| Rule | Key | Target | Patch | Result |
|
||||
|------|-----|--------|-------|--------|
|
||||
| <span class="nj-pointer-mp nj-pointer-mp--set">change value</span> | `title` | `#!json "Goodbye!"` | `#!json "Hello!"` | `#!json "Hello!"` |
|
||||
| <span class="nj-pointer-mp nj-pointer-mp--add">add key</span> | `phoneNumber` | <span class="nj-pointer-mp-none">(no key)</span> | `#!json "+01-123-456-7890"` | `#!json "+01-123-456-7890"` |
|
||||
| <span class="nj-pointer-mp nj-pointer-mp--del">null removes key</span> | `author.familyName` | `#!json "Doe"` | `#!json null` | <span class="nj-pointer-mp-none">(removed)</span> |
|
||||
| <span class="nj-pointer-mp nj-pointer-mp--rec">object merges recursively</span> | `author` | `#!json {"givenName": "John", "familyName": "Doe"}` | `#!json {"familyName": null}` | `#!json {"givenName": "John"}` |
|
||||
| <span class="nj-pointer-mp nj-pointer-mp--arr">array replaced whole</span> | `tags` | `#!json ["example", "sample"]` | `#!json ["example"]` | `#!json ["example"]` |
|
||||
| <span class="nj-pointer-mp nj-pointer-mp--keep">unchanged key</span> | `content` | `#!json "This will be unchanged"` | <span class="nj-pointer-mp-none">(no key)</span> | `#!json "This will be unchanged"` |
|
||||
|
||||
</div>
|
||||
|
||||
An array in the patch replaces the array in the target, so a merge patch cannot change a single element. Each member of
|
||||
the patch is applied like this; a patch that is not an object replaces the whole target.
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
M["member of the patch"] --> N{{"value null?"}}
|
||||
N -->|yes| D["delete the key"]
|
||||
N -->|no| O{{"value an object?"}}
|
||||
O -->|yes| R["merge recursively into the target's value"]
|
||||
O -->|no| S["set the key to the value"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>How one member of a merge patch is applied: a `null` value deletes the key, an object is merged recursively, and any other value replaces the value of the key.</p>
|
||||
|
||||
!!! tip "Not a general deep merge"
|
||||
|
||||
A merge patch is not a general deep merge: a `#!json null` value in the patch deletes the key from the target.
|
||||
|
||||
@@ -4,8 +4,6 @@ This library has experimental support for C++ modules, introduced in C++20. The
|
||||
|
||||
Please be aware that the module is experimental and a full test is outstanding, and the exported symbols are subject to change.
|
||||
|
||||
Importing the module instead of including the header reduces the compile time of every translation unit that uses the library, at the price of building the module once. The [Compile times](../integration/compile_times.md#use-c20-modules) page has measurements and the one-off cost.
|
||||
|
||||
## Requirements
|
||||
The `nlohmann.json` module requires that the build system is configured to build and resolve modules when imported. Obviously, as modules were introduced in C++20, this feature can only be used in C++20 and subsequent versions.
|
||||
|
||||
|
||||
@@ -40,22 +40,6 @@ For example, the namespace name for version 3.11.2 with `JSON_DIAGNOSTICS` defin
|
||||
nlohmann::json_abi_diag_v3_11_2
|
||||
```
|
||||
|
||||
The name is assembled from these segments; pick a version and macros to see the resulting name:
|
||||
|
||||
<figure class="nj-integration-ns" data-nj-integration-ns aria-label="How the inline namespace name is assembled from its segments">
|
||||
<div class="nj-integration-ns__strip" aria-live="polite">
|
||||
<span class="nj-integration-ns__seg nj-integration-ns__seg--root"><code>nlohmann</code><small>root namespace</small></span>
|
||||
<span class="nj-integration-ns__seg nj-integration-ns__seg--sep"><code>::</code><small> </small></span>
|
||||
<span class="nj-integration-ns__seg nj-integration-ns__seg--abi"><code>json_abi</code><small>always</small></span>
|
||||
<span class="nj-integration-ns__seg nj-integration-ns__seg--tag"><code>_diag</code><small>JSON_DIAGNOSTICS=1</small></span>
|
||||
<span class="nj-integration-ns__seg nj-integration-ns__seg--ver"><code>_v3_11_2</code><small>version 3.11.2</small></span>
|
||||
</div>
|
||||
<figcaption>Version 3.11.2 with <code>JSON_DIAGNOSTICS</code> defined to <code>1</code>. ABI tags are appended in the order of the
|
||||
list above, the version suffix comes last.</figcaption>
|
||||
</figure>
|
||||
|
||||
<p class="nj-caption" markdown>The name of the inline namespace, assembled from its segments. Select a version and macros to see which ABI tags appear; a tag the chosen version does not have is disabled.</p>
|
||||
|
||||
## Purpose
|
||||
|
||||
Several incompatibilities have been observed. Amongst the most common ones is linking code compiled with different
|
||||
@@ -73,8 +57,6 @@ graph
|
||||
app --> library
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The application uses the library with `JSON_DIAGNOSTICS=1` and links `some library`, which uses the same library version with `JSON_DIAGNOSTICS=0`. Arrows point from a component to what it uses.</p>
|
||||
|
||||
In releases prior to 3.11.0, mixing any version of the JSON library with different `JSON_DIAGNOSTICS` settings would
|
||||
result in a crashing application. If `some_library` never passes instances of JSON library types to the application,
|
||||
this scenario became safe in version 3.11.0 and above due to the inline namespace yielding distinct symbol names.
|
||||
|
||||
@@ -13,8 +13,6 @@ flowchart LR
|
||||
A --> V["bool: is the input valid JSON?"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The three entry points for parsing: `parse()` builds a `basic_json` value, optionally filtered by a parser callback, `sax_parse()` delivers events to a SAX handler, and `accept()` only checks whether the input is valid.</p>
|
||||
|
||||
## Input
|
||||
|
||||
The [`parse`](../../api/basic_json/parse.md) function reads a JSON value from an input. The input can be
|
||||
|
||||
@@ -17,8 +17,6 @@ flowchart TD
|
||||
H -->|"yes"| I["stop early with SAX, or read through a view"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Questions about the input and the approach this page describes for each; an input can match more than one question.</p>
|
||||
|
||||
## Several values in one stream
|
||||
|
||||
For newline-delimited input, read line by line and parse each line, as described in [JSON Lines](json_lines.md). For
|
||||
@@ -82,14 +80,6 @@ exception is one past the buffer size in the first case:
|
||||
The example feeds a document in five chunks. The first four are reported as incomplete, and a syntax error is reported as
|
||||
such, not as missing data.
|
||||
|
||||
The chunks of the example, and the bytes each attempt parses again:
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/chunk_buffering.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Each row is one parse attempt on the growing buffer: an error at the byte after the end of the buffer means the value is incomplete, an error before the end is a real syntax error. The last line adds up the bytes parsed over all attempts.</p>
|
||||
|
||||
!!! warning "Limits of buffering"
|
||||
|
||||
- The buffer must contain exactly one value. Data that belongs to the next value is a syntax error. Use framing if
|
||||
@@ -103,14 +93,6 @@ The chunks of the example, and the bytes each attempt parses again:
|
||||
|
||||
The input does not have to become one huge `json` value. The two tools below process it piece by piece.
|
||||
|
||||
How the memory use develops while a large array of records is parsed (illustrative, not a measurement):
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/memory_over_time.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Memory use over the number of records parsed: `parse()` keeps the whole tree, `json_document` the text plus its index, a discarding callback one record at a time, and SAX only what the handler keeps.</p>
|
||||
|
||||
### Handle and discard elements with a callback
|
||||
|
||||
A [parser callback](parser_callbacks.md) is called for every finished value. If it returns `#!cpp false`, the value is
|
||||
|
||||
@@ -29,8 +29,6 @@ class sax_t ["json::sax_t"] {
|
||||
}
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The interface `json::sax_t`: one function per event, each returning `bool`; the functions marked with `*` are pure virtual.</p>
|
||||
|
||||
```cpp
|
||||
// called when null is parsed
|
||||
bool null();
|
||||
@@ -64,34 +62,6 @@ bool parse_error(std::size_t position, const std::string& last_token, const json
|
||||
|
||||
The return value of each function determines whether parsing should proceed.
|
||||
|
||||
## Stepping through the events
|
||||
|
||||
The events for a small input, step by step, and what two different handlers do with them. Press *Play* or step with *Next*:
|
||||
|
||||
<div class="nj-sax nj-fig" id="sax-event-stepper" data-nj-sax role="group" aria-label="SAX events for the input {"a":[1,true],"b":"x"}, and the state of a handler after each event">
|
||||
<div class="nj-sax__lane nj-sax__lane--text"><p class="nj-sax__h">input</p><p class="nj-sax__text"><code class="nj-sax__src">{"a":[1,true],"b":"x"}</code></p></div>
|
||||
<div class="nj-sax__lane nj-sax__lane--events"><p class="nj-sax__h">events, in the order the parser calls them</p><ol class="nj-sax__events">
|
||||
<li class="nj-sax-ev nj-sax-ev--os"><code>start_object(-1)</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--k"><code>key("a")</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--as"><code>start_array(-1)</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--v"><code>number_unsigned(1)</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--v"><code>boolean(true)</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--ae"><code>end_array()</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--k"><code>key("b")</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--v"><code>string("x")</code></li>
|
||||
<li class="nj-sax-ev nj-sax-ev--oe"><code>end_object()</code></li>
|
||||
</ol></div>
|
||||
<div class="nj-sax__lane nj-sax__lane--state"><p class="nj-sax__h">handler: build a value tree, as <code>parse</code> does</p><div class="nj-sax__state"><pre class="nj-sax__tree"><code>{
|
||||
"a": [
|
||||
1,
|
||||
true
|
||||
],
|
||||
"b": "x"
|
||||
}</code></pre><p class="nj-sax__note">After <code>end_object()</code> the tree is complete and no container is open. The number of elements is passed as -1: the parser does not know it in advance.</p></div></div>
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>The three lanes show the input consumed so far, the events called so far, and the state of the selected handler (*build a tree* or *keep only /b*). Check *return false at this event* to stop the parse at the current event and see which events are no longer called.</p>
|
||||
|
||||
To implement your own SAX handler, proceed as follows:
|
||||
|
||||
1. Implement the SAX interface in a class. You can use class `nlohmann::json_sax<json>` as base class, but you can also use any class where the functions described above are implemented and public.
|
||||
|
||||
@@ -96,17 +96,6 @@ comparison for text-heavy documents (63.5%-87.5%), at the cost of an
|
||||
whether it is worth the loss of human readability at all -- depends on the actual data; see the
|
||||
[comparison tables](binary_formats/index.md#comparison) before choosing one.
|
||||
|
||||
<div class="nj-charts-grid-wrap" markdown>
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/binary_sizes_canada.svg"
|
||||
</div>
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/binary_sizes_jeopardy.svg"
|
||||
</div>
|
||||
</div>
|
||||
<p class="nj-charts-caption" markdown>Two of the four panels from the [size comparison](binary_formats/index.md#sizes);
|
||||
the smallest format per file is drawn in a stronger colour than the others.</p>
|
||||
|
||||
## Object type: `json` vs. `ordered_json`
|
||||
|
||||
The default [`json`](../api/json.md) type stores object keys in a `#!cpp std::map`, giving logarithmic-time lookup,
|
||||
@@ -119,13 +108,6 @@ read. The [measurements on the `ordered_map` page](../api/ordered_map.md#complex
|
||||
negligible at typical object sizes (2000 keys: 0.7 ms for `json` vs. 3.6 ms for `ordered_json`, a 5x factor) but grows
|
||||
steeply for large, machine-generated objects (16 000 keys: 3.3 ms vs. 181.6 ms, a 54x factor).
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/ordered_json_scaling.svg"
|
||||
</div>
|
||||
<p class="nj-charts-caption" markdown>Parsing a flat object of `n` keys, measured with `-O2 -DNDEBUG`; all
|
||||
four sizes from the [table on the `ordered_map` page](../api/ordered_map.md#complexity), both
|
||||
axes logarithmic.</p>
|
||||
|
||||
If insertion order matters *and* an object routinely has many thousands of keys, `ordered_json`'s quadratic build cost
|
||||
may not be acceptable. The library's [`ObjectType` template parameter](types/template_parameters.md#objecttype) can be
|
||||
set to a different container instead: `#!cpp nlohmann::fifo_map` keeps insertion order with a real lookup index
|
||||
|
||||
@@ -64,8 +64,6 @@ basic_json .. json_value
|
||||
basic_json .. value_t
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Storage of a `basic_json` value: the enumeration `value_t` holds the type, and the union `json_value` holds the value, as a pointer for objects, arrays, strings, and binary values and directly for booleans and numbers.</p>
|
||||
|
||||
## Template arguments
|
||||
|
||||
The data types to store a JSON value are derived from the template arguments passed to class `basic_json`:
|
||||
|
||||
@@ -27,11 +27,7 @@ JSON defines the syntax of numbers as follows:
|
||||
|
||||
The following railroad diagram from [json.org](https://json.org) visualizes the number syntax:
|
||||
|
||||
<div class="railroad-wrap" markdown>
|
||||
--8<-- "images/json_syntax_number.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Read the diagram from left to right: every path along the lines spells a valid number, made of an optional minus sign, an integer part, an optional fraction, and an optional exponent.</p>
|
||||

|
||||
|
||||
### Number interoperability
|
||||
|
||||
@@ -73,17 +69,15 @@ otherwise, it uses unsigned integer storage.
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A["number literal"] --> B{{"has a fraction (.) or exponent (e/E)?"}}
|
||||
A["number literal"] --> B{"has a fraction (.) or exponent (e/E)?"}
|
||||
B -->|"yes"| F["number_float_t"]
|
||||
B -->|"no"| C{{"has a leading minus sign?"}}
|
||||
B -->|"no"| C{"has a leading minus sign?"}
|
||||
C -->|"yes"| D["try number_integer_t"]
|
||||
C -->|"no"| E["try number_unsigned_t"]
|
||||
D -->|"overflow"| F
|
||||
E -->|"overflow"| F
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>How the parser picks the storage type of a number literal: a fraction or exponent always gives `number_float_t`; otherwise the sign selects the signed or unsigned integer type, and a value that overflows it is stored as `number_float_t`.</p>
|
||||
|
||||
!!! info "Notes"
|
||||
|
||||
- Numbers with a decimal digit or scientific notation are always stored as `#!c double`.
|
||||
@@ -137,32 +131,6 @@ The JSON number grammar allows for different ways to express zero, and this libr
|
||||
|
||||
That is, `-0` is stored as a signed integer, but the serialization does not reproduce the `-`.
|
||||
|
||||
The literals mentioned on this page, parsed with `json::parse` and serialized with `dump()` (checked against the
|
||||
library; pick one or type it to see the row):
|
||||
|
||||
<div class="nj-charts-num" markdown>
|
||||
|
||||
| Literal | Stored as (`type()`) | `dump()` |
|
||||
|---------|----------------------|----------|
|
||||
| `0` | `number_unsigned` (`std::uint64_t`) | `0` |
|
||||
| `-0` | `number_integer` (`std::int64_t`) | `0` |
|
||||
| `-0.0` | `number_float` (`double`) | `-0.0` |
|
||||
| `1E3` | `number_float` (`double`) | `1000.0` |
|
||||
| `-12345678912345789123456789` | `number_float` (`double`) | `-1.2345678912345788e+25` |
|
||||
| `18446744073709551615` | `number_unsigned` (`std::uint64_t`) | `18446744073709551615` |
|
||||
| `18446744073709551616` | `number_float` (`double`) | `1.8446744073709552e+19` |
|
||||
| `-9223372036854775808` | `number_integer` (`std::int64_t`) | `-9223372036854775808` |
|
||||
| `1E400` | exception `out_of_range.406` | (nothing, parsing fails) |
|
||||
| `1E-400` | `number_float` (`double`) | `0.0` |
|
||||
| `3.141592653589793238462643383279` | `number_float` (`double`) | `3.141592653589793` |
|
||||
| `2555.5599999999999` | `number_float` (`double`) | `2555.56` |
|
||||
| `0.0000972439793401814` | `number_float` (`double`) | `9.72439793401814e-05` |
|
||||
| `12345E-5` | `number_float` (`double`) | `0.12345` |
|
||||
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Each row shows how a literal is stored and how `dump()` writes it back. The explorer only knows the literals in this list; other input is reported as not in the verified list.</p>
|
||||
|
||||
### Number serialization
|
||||
|
||||
- Integer numbers are serialized as is; that is, no scientific notation is used.
|
||||
@@ -361,8 +329,6 @@ the stored number:
|
||||
| [`type_name()`](../../api/basic_json/type_name.md) | `#!c "number"` | `#!c "number"` | `#!c "number"` | `#!c "string"` |
|
||||
| [`type()`](../../api/basic_json/type.md) | `number_unsigned` | `number_integer` | `number_float` | `string` |
|
||||
|
||||
<p class="nj-table-caption" markdown>Return value of each function for a value that stores an unsigned integer, a signed integer, or a floating-point number, and for a string for comparison.</p>
|
||||
|
||||
### Template number types
|
||||
|
||||
The number types can be changed with template parameters.
|
||||
|
||||
@@ -32,8 +32,6 @@ flowchart LR
|
||||
oa --> output
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Data flow through the library: input runs left to right through an input adapter and the lexer and parser (JSON text) or the `binary_reader` (binary formats) into SAX events, which build the value tree; the `serializer` or the `binary_writer` writes the tree to an output adapter.</p>
|
||||
|
||||
- **JSON text** is read by an [input adapter](#input-adapters), tokenized by the lexer, and turned into SAX events by
|
||||
the parser.
|
||||
- **Binary formats** (BJData, BON8, BSON, CBOR, MessagePack, UBJSON) are read by an input adapter and turned into the same SAX
|
||||
@@ -194,8 +192,6 @@ packet-beta
|
||||
96-127: "next"
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Layout of one 16-byte node of a JSON view index. Each row is 32 bits wide, and the numbers are the bit offsets of the fields `kind`, `flags`, `extra`, `off`, `len`, and `next`.</p>
|
||||
|
||||
| Bytes | Field | Type | Contents |
|
||||
|-------|---------|------------|-------------------------------------------------------------------------------------------------------------------------------|
|
||||
| 0 | `kind` | `uint8_t` | the type, numbered as [`value_t`](../api/basic_json/value_t.md): 0 null, 1 object, 2 array, 3 string, 4 boolean, 5 signed integer, 6 unsigned integer, 7 float; 10 for a link (see below). There is no node for a discarded value: a [discarded](../api/basic_json_view/is_discarded.md) view has none |
|
||||
@@ -205,8 +201,6 @@ packet-beta
|
||||
| 8-11 | `len` | `uint32_t` | strings: the length after decoding; floats and literals: the length of the token; arrays and objects: the number of elements |
|
||||
| 12-15 | `next` | `uint32_t` | arrays and objects: the number of nodes of the subtree, including the node itself |
|
||||
|
||||
<p class="nj-table-caption" markdown>Fields of a node, by their byte offset within the 16-byte node. Integers use bytes 8-15 differently, see below.</p>
|
||||
|
||||
- **Integers** keep their converted value in bytes 8-15 instead of `len` and `next`; the length of their token follows
|
||||
from the number of digits in `extra` (and the sign). Non-negative integers are unsigned integers, as with
|
||||
[`parse`](../api/basic_json/parse.md).
|
||||
@@ -240,8 +234,6 @@ flowchart LR
|
||||
n2 -. next .-> e
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The five nodes of `#!json {"a": [1, 2.5]}` in document order. Solid arrows lead from each node to the one after it; dotted arrows show where `next` leads from the object and the array, past their subtrees.</p>
|
||||
|
||||
| Node | `kind` | `extra` | `off` | `len` | `next` |
|
||||
|------|----------------------|---------|-------|-------|--------|
|
||||
| 0 | 1 (object) | 0 | 0 | 1 | 5 |
|
||||
@@ -250,8 +242,6 @@ flowchart LR
|
||||
| 3 | 6 (unsigned integer) | 0x0001 | 7 | - | - |
|
||||
| 4 | 7 (float) | 0x0101 | 10 | 3 | 0 |
|
||||
|
||||
<p class="nj-table-caption" markdown>Fields of the five nodes of `#!json {"a": [1, 2.5]}`. `off` is the byte offset in the text, and - marks the bytes 8-15 that hold the integer's value instead of `len` and `next`.</p>
|
||||
|
||||
All `flags` are 0. The integer's bytes 8-15 hold its value, 1; its `extra` says it has one digit. The float's `extra`
|
||||
says it has one integer and one fraction digit, and its `len` is that of the token `2.5`.
|
||||
|
||||
@@ -297,9 +287,8 @@ template<class T>
|
||||
std::size_t get_elements(T* dest, std::size_t count = 1);
|
||||
```
|
||||
|
||||
The lexer detects two optional extensions at compile time. `iterator_input_adapter` provides both, and only for
|
||||
random-access input of single-byte characters. `input_stream_adapter` provides the second one (as a window onto the
|
||||
streambuf's buffer) unless `JSON_DISABLE_STREAM_BULK_SCAN` is defined:
|
||||
The lexer detects two optional extensions at compile time. Only `iterator_input_adapter` provides them, and only for
|
||||
random-access input of single-byte characters:
|
||||
|
||||
- `supports_seek`, `get_consumed_count()`, and `copy_consumed_range()` let the lexer reconstruct already consumed input
|
||||
for error messages instead of copying every character it reads. With `get_read_count()` and
|
||||
@@ -317,40 +306,6 @@ The function `input_adapter` picks the right adapter for the argument passed to
|
||||
- `input_stream_adapter` reads from a `std::istream`.
|
||||
- `file_input_adapter` reads from a `std::FILE*`.
|
||||
|
||||
The adapters have no common base class: the lexer and the parser are templates on the adapter type, and
|
||||
`wide_string_input_adapter` wraps an `iterator_input_adapter`:
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class input_adapter ["input adapter"] {
|
||||
<<concept>>
|
||||
+char_type
|
||||
+get_character() int_type
|
||||
+get_elements(T* dest, size_t count) size_t
|
||||
}
|
||||
class iterator_input_adapter {
|
||||
-IteratorType current
|
||||
-SentinelType end
|
||||
}
|
||||
class wide_string_input_adapter {
|
||||
-BaseInputAdapter base_adapter
|
||||
}
|
||||
class input_stream_adapter {
|
||||
-std::istream* is
|
||||
-std::streambuf* sb
|
||||
}
|
||||
class file_input_adapter {
|
||||
-std::FILE* m_file
|
||||
}
|
||||
input_adapter <|.. iterator_input_adapter
|
||||
input_adapter <|.. wide_string_input_adapter
|
||||
input_adapter <|.. input_stream_adapter
|
||||
input_adapter <|.. file_input_adapter
|
||||
wide_string_input_adapter o-- iterator_input_adapter : converts to UTF-8
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The input adapters as a class diagram. The dotted arrows mean that each adapter implements the input adapter concept; the diamond shows that `wide_string_input_adapter` holds an `iterator_input_adapter`.</p>
|
||||
|
||||
## SAX interface
|
||||
|
||||
The parser does not build values itself. It reports what it reads as events to a [SAX](../features/parsing/sax_interface.md)
|
||||
@@ -366,7 +321,6 @@ The library comes with two consumers in `detail/input/json_sax.hpp`:
|
||||
|
||||
The `binary_reader` emits the same events for binary formats, so [`sax_parse`](../api/basic_json/sax_parse.md) works
|
||||
with a user-defined consumer for JSON and for all binary formats alike.
|
||||
The [SAX event stepper](../features/parsing/sax_interface.md#sax-event-stepper) shows the events for a small input.
|
||||
|
||||
## Output adapters
|
||||
|
||||
@@ -385,36 +339,6 @@ The `serializer` (used by [`dump`](../api/basic_json/dump.md) and [`operator<<`]
|
||||
- `output_stream_adapter` writes to a `std::ostream`.
|
||||
- `output_string_adapter` appends to a string.
|
||||
|
||||
They implement the abstract class `output_adapter_protocol`. The class `output_adapter` creates the one that matches
|
||||
its argument and holds it in a `std::shared_ptr` (`output_adapter_t`):
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class output_adapter_protocol~CharType~ {
|
||||
<<interface>>
|
||||
+write_character(CharType c)*
|
||||
+write_characters(const CharType* s, size_t length)*
|
||||
}
|
||||
class output_vector_adapter {
|
||||
-std::vector& v
|
||||
}
|
||||
class output_stream_adapter {
|
||||
-std::basic_ostream& stream
|
||||
}
|
||||
class output_string_adapter {
|
||||
-StringType& str
|
||||
}
|
||||
class output_adapter {
|
||||
-output_adapter_t oa
|
||||
}
|
||||
output_adapter_protocol <|-- output_vector_adapter
|
||||
output_adapter_protocol <|-- output_stream_adapter
|
||||
output_adapter_protocol <|-- output_string_adapter
|
||||
output_adapter o-- output_adapter_protocol : shared_ptr
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The output adapters as a class diagram. The three adapters derive from `output_adapter_protocol` (solid arrows), and `output_adapter` holds one of them through a `shared_ptr` (diamond).</p>
|
||||
|
||||
The `binary_writer` does not call an adapter for every byte. The `to_*` functions that return a `std::vector` write
|
||||
into the vector through a sink (`output_vector_sink`) that is not virtual. The functions that take an output adapter
|
||||
write through a sink (`output_adapter_sink`) that collects the output in a buffer of one kibibyte and passes it to the
|
||||
|
||||
@@ -6,35 +6,35 @@
|
||||
|
||||
All exceptions inherit from class `json::exception` (which in turn inherits from `std::exception`). It is used as the base class for all exceptions thrown by the `basic_json` class. This class can hence be used as "wildcard" to catch exceptions.
|
||||
|
||||
The map shows the class tree and every exception id documented on this page; click an id to jump to its section.
|
||||
``` mermaid
|
||||
classDiagram
|
||||
direction LR
|
||||
class `std::exception` {
|
||||
<<interface>>
|
||||
}
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/exception_map.svg"
|
||||
</div>
|
||||
class `json::exception` {
|
||||
+const int id
|
||||
+const char* what() const
|
||||
}
|
||||
|
||||
<p class="nj-caption" markdown>The exception classes from `std::exception` down to the five families, each with the ids it can throw. Every id chip links to the section that describes it.</p>
|
||||
class `json::parse_error` {
|
||||
+const std::size_t byte
|
||||
}
|
||||
|
||||
Which exception an element access throws depends on the function and on the type of the value:
|
||||
class `json::invalid_iterator`
|
||||
class `json::type_error`
|
||||
class `json::out_of_range`
|
||||
class `json::other_error`
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
S{{"which call?"}} -->|"at(key)"| A{{"j is"}}
|
||||
A -->|"object, key missing"| A1["out_of_range.403"]
|
||||
A -->|"array or null"| A2["type_error.304"]
|
||||
S -->|"at(index)"| B{{"j is"}}
|
||||
B -->|"array, index >= size()"| B1["out_of_range.401"]
|
||||
B -->|"object or null"| B2["type_error.304"]
|
||||
S -->|"non-const operator[](key)"| C{{"j is"}}
|
||||
C -->|"object or null"| C1["no exception: a missing key is inserted as null"]
|
||||
C -->|"array"| C2["type_error.305"]
|
||||
S -->|"value(key, default)"| D{{"j is"}}
|
||||
D -->|"object, key missing"| D1["no exception: returns the default"]
|
||||
D -->|"object, incompatible value type"| D2["type_error.302"]
|
||||
D -->|"array or null"| D3["type_error.306"]
|
||||
`std::exception` <|-- `json::exception`
|
||||
`json::exception` <|-- `json::parse_error`
|
||||
`json::exception` <|-- `json::invalid_iterator`
|
||||
`json::exception` <|-- `json::type_error`
|
||||
`json::exception` <|-- `json::out_of_range`
|
||||
`json::exception` <|-- `json::other_error`
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Exceptions thrown by element access. Start at the call on the left, follow the edge that matches the type of `j`, and read the exception id (or "no exception") in the box at the end.</p>
|
||||
|
||||
### Switch off exceptions
|
||||
|
||||
Exceptions are used widely within the library. They can, however, be switched off with either using the compiler flag `-fno-exceptions` or by defining the symbol [`JSON_NOEXCEPTION`](../api/macros/json_noexception.md). In this case, exceptions are replaced by `abort()` calls. You can further control this behavior by defining `JSON_THROW_USER` (overriding `#!cpp throw`), `JSON_TRY_USER` (overriding `#!cpp try`), and `JSON_CATCH_USER` (overriding `#!cpp catch`).
|
||||
|
||||
@@ -192,8 +192,6 @@ The value is a `json`, and printing it produces JSON text. Convert it first: `#!
|
||||
|
||||
Use `contains` or `find`. Do not test with the non-const `operator[]`: like `std::map::operator[]`, it inserts a `null`
|
||||
value for a missing key. See [Does this key exist?](../features/element_access/index.md#does-this-key-exist).
|
||||
For choosing between `value`, `contains`/`find`, `at`, `operator[]`, and JSON Pointer, see the decision flow in
|
||||
[Element access](../features/element_access/index.md).
|
||||
|
||||
### Reading a value with a fallback
|
||||
|
||||
|
||||
@@ -14,14 +14,6 @@ changed in it. The API overview is generated from the "Version history" section
|
||||
[API pages](../../api/basic_json/index.md); it is not a change log, but helps to see whether a feature is available in
|
||||
the version you use.
|
||||
|
||||
All releases at a glance (hover a marker for its version and date):
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/release_timeline.svg"
|
||||
</div>
|
||||
|
||||
<p class="nj-caption" markdown>Releases from 1.0.0 to the latest one, on a time axis by year. Filled dots with a version label are minor or major releases, rings are patch releases.</p>
|
||||
|
||||
## Unreleased
|
||||
|
||||
| Release | Date | Summary |
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--sizes" viewBox="0 0 340 220" role="img" aria-labelledby="nj-charts-bs-canada nj-charts-bs-canada-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-bs-canada">Size of canada.json in each binary format relative to minified J​SON</title>
|
||||
<desc id="nj-charts-bs-canada-d">B​JData 53.2 %; B​ON8 50.5 %; B​SON 85.8 %; C​BOR 50.5 %; MessagePack 50.5 %; U​BJSON 53.2 %. Smallest: B​ON8 and C​BOR and MessagePack.</desc>
|
||||
<text class="nj-charts-panel" x="8" y="18">canada.json</text>
|
||||
<line class="nj-charts-grid" x1="104" y1="40" x2="104" y2="196"/>
|
||||
<text class="nj-charts-tick" x="104" y="211">0 %</text>
|
||||
<line class="nj-charts-grid" x1="186.727" y1="40" x2="186.727" y2="196"/>
|
||||
<text class="nj-charts-tick" x="186.727" y="211">50 %</text>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="58.5">B​JData</text>
|
||||
<path class="nj-charts-c1 nj-charts-dim" d="M104 46 H188.022 Q192.022 46 192.022 50 V58 Q192.022 62 188.022 62 H104 Z"><title>canada.json, B​JData: 53.2 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt nj-charts-best" x="96" y="84.5">B​ON8</text>
|
||||
<path class="nj-charts-c2" d="M104 72 H183.555 Q187.555 72 187.555 76 V84 Q187.555 88 183.555 88 H104 Z"><title>canada.json, B​ON8: 50.5 % of minified J​SON (smallest)</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="110.5">B​SON</text>
|
||||
<path class="nj-charts-c3 nj-charts-dim" d="M104 98 H241.96 Q245.96 98 245.96 102 V110 Q245.96 114 241.96 114 H104 Z"><title>canada.json, B​SON: 85.8 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt nj-charts-best" x="96" y="136.5">C​BOR</text>
|
||||
<path class="nj-charts-c4" d="M104 124 H183.555 Q187.555 124 187.555 128 V136 Q187.555 140 183.555 140 H104 Z"><title>canada.json, C​BOR: 50.5 % of minified J​SON (smallest)</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt nj-charts-best" x="96" y="162.5">MessagePack</text>
|
||||
<path class="nj-charts-c5" d="M104 150 H183.555 Q187.555 150 187.555 154 V162 Q187.555 166 183.555 166 H104 Z"><title>canada.json, MessagePack: 50.5 % of minified J​SON (smallest)</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="188.5">U​BJSON</text>
|
||||
<path class="nj-charts-c6 nj-charts-dim" d="M104 176 H188.022 Q192.022 176 192.022 180 V188 Q192.022 192 188.022 192 H104 Z"><title>canada.json, U​BJSON: 53.2 % of minified J​SON</title></path>
|
||||
<line class="nj-charts-ref" x1="269.455" y1="36" x2="269.455" y2="196"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="271.455" y="32">minified J​SON = 100 %</text>
|
||||
<text class="nj-charts-tick" x="269.455" y="211">100 %</text>
|
||||
<text class="nj-charts-val" x="197.022" y="58.5">53.2 %</text>
|
||||
<text class="nj-charts-val nj-charts-best" x="192.555" y="84.5">50.5 %</text>
|
||||
<text class="nj-charts-val" x="250.96" y="110.5">85.8 %</text>
|
||||
<text class="nj-charts-val nj-charts-best" x="192.555" y="136.5">50.5 %</text>
|
||||
<text class="nj-charts-val nj-charts-best" x="192.555" y="162.5">50.5 %</text>
|
||||
<text class="nj-charts-val" x="197.022" y="188.5">53.2 %</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.2 KiB |
@@ -1,30 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--sizes" viewBox="0 0 340 220" role="img" aria-labelledby="nj-charts-bs-citm_catalog nj-charts-bs-citm_catalog-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-bs-citm_catalog">Size of citm_catalog.json in each binary format relative to minified J​SON</title>
|
||||
<desc id="nj-charts-bs-citm_catalog-d">B​JData 78.1 %; B​ON8 63.5 %; B​SON 95.8 %; C​BOR 68.4 %; MessagePack 68.5 %; U​BJSON 78.2 %. Smallest: B​ON8.</desc>
|
||||
<text class="nj-charts-panel" x="8" y="18">citm_catalog.json</text>
|
||||
<line class="nj-charts-grid" x1="104" y1="40" x2="104" y2="196"/>
|
||||
<text class="nj-charts-tick" x="104" y="211">0 %</text>
|
||||
<line class="nj-charts-grid" x1="186.727" y1="40" x2="186.727" y2="196"/>
|
||||
<text class="nj-charts-tick" x="186.727" y="211">50 %</text>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="58.5">B​JData</text>
|
||||
<path class="nj-charts-c1 nj-charts-dim" d="M104 46 H229.22 Q233.22 46 233.22 50 V58 Q233.22 62 229.22 62 H104 Z"><title>citm_catalog.json, B​JData: 78.1 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt nj-charts-best" x="96" y="84.5">B​ON8</text>
|
||||
<path class="nj-charts-c2" d="M104 72 H205.064 Q209.064 72 209.064 76 V84 Q209.064 88 205.064 88 H104 Z"><title>citm_catalog.json, B​ON8: 63.5 % of minified J​SON (smallest)</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="110.5">B​SON</text>
|
||||
<path class="nj-charts-c3 nj-charts-dim" d="M104 98 H258.505 Q262.505 98 262.505 102 V110 Q262.505 114 258.505 114 H104 Z"><title>citm_catalog.json, B​SON: 95.8 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="136.5">C​BOR</text>
|
||||
<path class="nj-charts-c4 nj-charts-dim" d="M104 124 H213.171 Q217.171 124 217.171 128 V136 Q217.171 140 213.171 140 H104 Z"><title>citm_catalog.json, C​BOR: 68.4 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="162.5">MessagePack</text>
|
||||
<path class="nj-charts-c5 nj-charts-dim" d="M104 150 H213.336 Q217.336 150 217.336 154 V162 Q217.336 166 213.336 166 H104 Z"><title>citm_catalog.json, MessagePack: 68.5 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="188.5">U​BJSON</text>
|
||||
<path class="nj-charts-c6 nj-charts-dim" d="M104 176 H229.385 Q233.385 176 233.385 180 V188 Q233.385 192 229.385 192 H104 Z"><title>citm_catalog.json, U​BJSON: 78.2 % of minified J​SON</title></path>
|
||||
<line class="nj-charts-ref" x1="269.455" y1="36" x2="269.455" y2="196"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="271.455" y="32">minified J​SON = 100 %</text>
|
||||
<text class="nj-charts-tick" x="269.455" y="211">100 %</text>
|
||||
<text class="nj-charts-val" x="238.22" y="58.5">78.1 %</text>
|
||||
<text class="nj-charts-val nj-charts-best" x="214.064" y="84.5">63.5 %</text>
|
||||
<text class="nj-charts-val" x="267.505" y="110.5">95.8 %</text>
|
||||
<text class="nj-charts-val" x="222.171" y="136.5">68.4 %</text>
|
||||
<text class="nj-charts-val" x="222.336" y="162.5">68.5 %</text>
|
||||
<text class="nj-charts-val" x="238.385" y="188.5">78.2 %</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.2 KiB |
@@ -1,30 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--sizes" viewBox="0 0 340 220" role="img" aria-labelledby="nj-charts-bs-jeopardy nj-charts-bs-jeopardy-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-bs-jeopardy">Size of jeopardy.json in each binary format relative to minified J​SON</title>
|
||||
<desc id="nj-charts-bs-jeopardy-d">B​JData 96.6 %; B​ON8 87.5 %; B​SON 106.7 %; C​BOR 88 %; MessagePack 87.9 %; U​BJSON 96.6 %. Smallest: B​ON8.</desc>
|
||||
<text class="nj-charts-panel" x="8" y="18">jeopardy.json</text>
|
||||
<line class="nj-charts-grid" x1="104" y1="40" x2="104" y2="196"/>
|
||||
<text class="nj-charts-tick" x="104" y="211">0 %</text>
|
||||
<line class="nj-charts-grid" x1="186.727" y1="40" x2="186.727" y2="196"/>
|
||||
<text class="nj-charts-tick" x="186.727" y="211">50 %</text>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="58.5">B​JData</text>
|
||||
<path class="nj-charts-c1 nj-charts-dim" d="M104 46 H259.829 Q263.829 46 263.829 50 V58 Q263.829 62 259.829 62 H104 Z"><title>jeopardy.json, B​JData: 96.6 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt nj-charts-best" x="96" y="84.5">B​ON8</text>
|
||||
<path class="nj-charts-c2" d="M104 72 H244.773 Q248.773 72 248.773 76 V84 Q248.773 88 244.773 88 H104 Z"><title>jeopardy.json, B​ON8: 87.5 % of minified J​SON (smallest)</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="110.5">B​SON</text>
|
||||
<path class="nj-charts-c3 nj-charts-dim" d="M104 98 H276.54 Q280.54 98 280.54 102 V110 Q280.54 114 276.54 114 H104 Z"><title>jeopardy.json, B​SON: 106.7 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="136.5">C​BOR</text>
|
||||
<path class="nj-charts-c4 nj-charts-dim" d="M104 124 H245.6 Q249.6 124 249.6 128 V136 Q249.6 140 245.6 140 H104 Z"><title>jeopardy.json, C​BOR: 88 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="162.5">MessagePack</text>
|
||||
<path class="nj-charts-c5 nj-charts-dim" d="M104 150 H245.435 Q249.435 150 249.435 154 V162 Q249.435 166 245.435 166 H104 Z"><title>jeopardy.json, MessagePack: 87.9 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="188.5">U​BJSON</text>
|
||||
<path class="nj-charts-c6 nj-charts-dim" d="M104 176 H259.829 Q263.829 176 263.829 180 V188 Q263.829 192 259.829 192 H104 Z"><title>jeopardy.json, U​BJSON: 96.6 % of minified J​SON</title></path>
|
||||
<line class="nj-charts-ref" x1="269.455" y1="36" x2="269.455" y2="196"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="271.455" y="32">minified J​SON = 100 %</text>
|
||||
<text class="nj-charts-tick" x="269.455" y="211">100 %</text>
|
||||
<text class="nj-charts-val" x="268.829" y="58.5">96.6 %</text>
|
||||
<text class="nj-charts-val nj-charts-best" x="253.773" y="84.5">87.5 %</text>
|
||||
<text class="nj-charts-val" x="285.54" y="110.5">106.7 %</text>
|
||||
<text class="nj-charts-val" x="254.6" y="136.5">88.0 %</text>
|
||||
<text class="nj-charts-val" x="254.435" y="162.5">87.9 %</text>
|
||||
<text class="nj-charts-val" x="268.829" y="188.5">96.6 %</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.1 KiB |
@@ -1,30 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--sizes" viewBox="0 0 340 220" role="img" aria-labelledby="nj-charts-bs-twitter nj-charts-bs-twitter-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-bs-twitter">Size of twitter.json in each binary format relative to minified J​SON</title>
|
||||
<desc id="nj-charts-bs-twitter-d">B​JData 91.1 %; B​ON8 83.8 %; B​SON 95.2 %; C​BOR 86.3 %; MessagePack 86 %; U​BJSON 91.3 %. Smallest: B​ON8.</desc>
|
||||
<text class="nj-charts-panel" x="8" y="18">twitter.json</text>
|
||||
<line class="nj-charts-grid" x1="104" y1="40" x2="104" y2="196"/>
|
||||
<text class="nj-charts-tick" x="104" y="211">0 %</text>
|
||||
<line class="nj-charts-grid" x1="186.727" y1="40" x2="186.727" y2="196"/>
|
||||
<text class="nj-charts-tick" x="186.727" y="211">50 %</text>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="58.5">B​JData</text>
|
||||
<path class="nj-charts-c1 nj-charts-dim" d="M104 46 H250.729 Q254.729 46 254.729 50 V58 Q254.729 62 250.729 62 H104 Z"><title>twitter.json, B​JData: 91.1 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt nj-charts-best" x="96" y="84.5">B​ON8</text>
|
||||
<path class="nj-charts-c2" d="M104 72 H238.651 Q242.651 72 242.651 76 V84 Q242.651 88 238.651 88 H104 Z"><title>twitter.json, B​ON8: 83.8 % of minified J​SON (smallest)</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="110.5">B​SON</text>
|
||||
<path class="nj-charts-c3 nj-charts-dim" d="M104 98 H257.513 Q261.513 98 261.513 102 V110 Q261.513 114 257.513 114 H104 Z"><title>twitter.json, B​SON: 95.2 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="136.5">C​BOR</text>
|
||||
<path class="nj-charts-c4 nj-charts-dim" d="M104 124 H242.787 Q246.787 124 246.787 128 V136 Q246.787 140 242.787 140 H104 Z"><title>twitter.json, C​BOR: 86.3 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="162.5">MessagePack</text>
|
||||
<path class="nj-charts-c5 nj-charts-dim" d="M104 150 H242.291 Q246.291 150 246.291 154 V162 Q246.291 166 242.291 166 H104 Z"><title>twitter.json, MessagePack: 86 % of minified J​SON</title></path>
|
||||
<text class="nj-charts-rowlabel nj-charts-fmt" x="96" y="188.5">U​BJSON</text>
|
||||
<path class="nj-charts-c6 nj-charts-dim" d="M104 176 H251.06 Q255.06 176 255.06 180 V188 Q255.06 192 251.06 192 H104 Z"><title>twitter.json, U​BJSON: 91.3 % of minified J​SON</title></path>
|
||||
<line class="nj-charts-ref" x1="269.455" y1="36" x2="269.455" y2="196"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="271.455" y="32">minified J​SON = 100 %</text>
|
||||
<text class="nj-charts-tick" x="269.455" y="211">100 %</text>
|
||||
<text class="nj-charts-val" x="259.729" y="58.5">91.1 %</text>
|
||||
<text class="nj-charts-val nj-charts-best" x="247.651" y="84.5">83.8 %</text>
|
||||
<text class="nj-charts-val" x="266.513" y="110.5">95.2 %</text>
|
||||
<text class="nj-charts-val" x="251.787" y="136.5">86.3 %</text>
|
||||
<text class="nj-charts-val" x="251.291" y="162.5">86.0 %</text>
|
||||
<text class="nj-charts-val" x="260.06" y="188.5">91.3 %</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.1 KiB |
|
After Width: | Height: | Size: 45 KiB |
@@ -1,39 +0,0 @@
|
||||
<svg class="nj-fig nj-fig--cb" viewBox="0 0 480 262" role="img" aria-labelledby="fig-cb-title" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-cb-title">Example of the parse events a callback sees for the J​SON text {"name": "Berlin", "location": [52.519444, 13.406667]}: object_start after the opening brace, key after each key, array_start after the opening bracket, value after each value, array_end after the closing bracket, and object_end after the closing brace. Every array and object also produces a value event when it is complete.</title>
|
||||
<text class="fg-h" x="16" y="28">J​SON to parse</text>
|
||||
<text class="fg-h" x="320" y="28">callback events</text>
|
||||
<text class="fg-code" x="16" y="74" xml:space="preserve">{</text>
|
||||
<circle class="cb-os" cx="35.6" cy="69" r="5.5"/>
|
||||
<text class="fg-code" x="35.2" y="102" xml:space="preserve">"name"</text>
|
||||
<circle class="cb-k" cx="102.8" cy="97" r="5.5"/>
|
||||
<text class="fg-code" x="112.8" y="102" xml:space="preserve">: "Berlin"</text>
|
||||
<circle class="cb-v" cx="218.8" cy="97" r="5.5"/>
|
||||
<text class="fg-code" x="228.8" y="102" xml:space="preserve">,</text>
|
||||
<text class="fg-code" x="35.2" y="130" xml:space="preserve">"location"</text>
|
||||
<circle class="cb-k" cx="141.2" cy="125" r="5.5"/>
|
||||
<text class="fg-code" x="151.2" y="130" xml:space="preserve">: [</text>
|
||||
<circle class="cb-as" cx="190" cy="125" r="5.5"/>
|
||||
<text class="fg-code" x="54.4" y="158" xml:space="preserve">52.519444</text>
|
||||
<circle class="cb-v" cx="150.8" cy="153" r="5.5"/>
|
||||
<text class="fg-code" x="160.8" y="158" xml:space="preserve">,</text>
|
||||
<text class="fg-code" x="54.4" y="186" xml:space="preserve">13.406667</text>
|
||||
<circle class="cb-v" cx="150.8" cy="181" r="5.5"/>
|
||||
<text class="fg-code" x="35.2" y="214" xml:space="preserve">]</text>
|
||||
<circle class="cb-ae" cx="54.8" cy="209" r="5.5"/>
|
||||
<circle class="cb-v" cx="74.8" cy="209" r="5.5"/>
|
||||
<text class="fg-code" x="16" y="242" xml:space="preserve">}</text>
|
||||
<circle class="cb-oe" cx="35.6" cy="237" r="5.5"/>
|
||||
<circle class="cb-v" cx="55.6" cy="237" r="5.5"/>
|
||||
<circle class="cb-os" cx="327" cy="69" r="6"/>
|
||||
<text class="fg-code fg-leg" x="344" y="74">object_start</text>
|
||||
<circle class="cb-k" cx="327" cy="99" r="6"/>
|
||||
<text class="fg-code fg-leg" x="344" y="104">key</text>
|
||||
<circle class="cb-oe" cx="327" cy="129" r="6"/>
|
||||
<text class="fg-code fg-leg" x="344" y="134">object_end</text>
|
||||
<circle class="cb-as" cx="327" cy="159" r="6"/>
|
||||
<text class="fg-code fg-leg" x="344" y="164">array_start</text>
|
||||
<circle class="cb-ae" cx="327" cy="189" r="6"/>
|
||||
<text class="fg-code fg-leg" x="344" y="194">array_end</text>
|
||||
<circle class="cb-v" cx="327" cy="219" r="6"/>
|
||||
<text class="fg-code fg-leg" x="344" y="224">value</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 2.7 KiB |
@@ -1,50 +0,0 @@
|
||||
<svg class="nj-fig nj-fig--sax-buf" viewBox="0 0 700 442" role="img" aria-labelledby="fig-sax-buf-title fig-sax-buf-desc" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-sax-buf-title">Buffering chunks until the value is complete: five chunks of {"name": "Mary", "list": [1, 2, 3]} appended to a buffer.</title>
|
||||
<desc id="fig-sax-buf-desc">After chunks 1 to 4 the buffer has 4, 12, 19, and 30 bytes, and parsing it fails at byte 5, 13, 20, and 31: one past the end, so the input is incomplete and the program waits for more. After chunk 5 the buffer of 35 bytes parses as one complete value. For the input [1, ] of 5 bytes the error is at byte 5, before the end, so it is a real syntax error. Every attempt parses the buffer from byte 1, so 4 + 12 + 19 + 30 + 35 = 100 bytes are parsed for a 35-byte value, and the work grows quadratically.</desc>
|
||||
<text class="fg-h" x="16" y="24">chunk</text>
|
||||
<text class="fg-h" x="96" y="24">buffer, parsed from byte 1 each time</text>
|
||||
<text class="fg-h" x="420" y="24">result</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="67">chunk 1</text>
|
||||
<rect class="nj-sax-new" x="96" y="50" width="36.6" height="24" rx="4"/>
|
||||
<text class="nj-sax-buf" x="96" y="67" xml:space="preserve">{"na</text>
|
||||
<path class="nj-sax-caret nj-sax-s-wait" d="M133.8 76 l-5 8 h10 z"/>
|
||||
<text class="nj-sax-status nj-sax-s-wait" x="420" y="61">error at byte 5 = size + 1</text>
|
||||
<text class="fg-note fg-note--l" x="420" y="77">incomplete: wait for more</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="117">chunk 2</text>
|
||||
<rect class="nj-sax-old" x="93" y="100" width="36.6" height="24" rx="4"/>
|
||||
<rect class="nj-sax-new" x="129.6" y="100" width="70.2" height="24" rx="4"/>
|
||||
<text class="nj-sax-buf" x="96" y="117" xml:space="preserve">{"name": "Ma</text>
|
||||
<path class="nj-sax-caret nj-sax-s-wait" d="M201 126 l-5 8 h10 z"/>
|
||||
<text class="nj-sax-status nj-sax-s-wait" x="420" y="111">error at byte 13 = size + 1</text>
|
||||
<text class="fg-note fg-note--l" x="420" y="127">incomplete: wait for more</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="167">chunk 3</text>
|
||||
<rect class="nj-sax-old" x="93" y="150" width="103.8" height="24" rx="4"/>
|
||||
<rect class="nj-sax-new" x="196.8" y="150" width="61.8" height="24" rx="4"/>
|
||||
<text class="nj-sax-buf" x="96" y="167" xml:space="preserve">{"name": "Mary", "l</text>
|
||||
<path class="nj-sax-caret nj-sax-s-wait" d="M259.8 176 l-5 8 h10 z"/>
|
||||
<text class="nj-sax-status nj-sax-s-wait" x="420" y="161">error at byte 20 = size + 1</text>
|
||||
<text class="fg-note fg-note--l" x="420" y="177">incomplete: wait for more</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="217">chunk 4</text>
|
||||
<rect class="nj-sax-old" x="93" y="200" width="162.6" height="24" rx="4"/>
|
||||
<rect class="nj-sax-new" x="255.6" y="200" width="95.4" height="24" rx="4"/>
|
||||
<text class="nj-sax-buf" x="96" y="217" xml:space="preserve">{"name": "Mary", "list": [1, 2</text>
|
||||
<path class="nj-sax-caret nj-sax-s-wait" d="M352.2 226 l-5 8 h10 z"/>
|
||||
<text class="nj-sax-status nj-sax-s-wait" x="420" y="211">error at byte 31 = size + 1</text>
|
||||
<text class="fg-note fg-note--l" x="420" y="227">incomplete: wait for more</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="267">chunk 5</text>
|
||||
<rect class="nj-sax-old" x="93" y="250" width="255" height="24" rx="4"/>
|
||||
<rect class="nj-sax-new" x="348" y="250" width="45" height="24" rx="4"/>
|
||||
<text class="nj-sax-buf" x="96" y="267" xml:space="preserve">{"name": "Mary", "list": [1, 2, 3]}</text>
|
||||
<text class="nj-sax-status nj-sax-s-ok" x="420" y="261">parsed, size 35</text>
|
||||
<text class="fg-note fg-note--l" x="420" y="277">complete: one value</text>
|
||||
<path class="nj-sax-sep" d="M16 290 H684"/>
|
||||
<text class="fg-note fg-note--l" x="16" y="325">other input</text>
|
||||
<rect class="nj-sax-new" x="96" y="308" width="45" height="24" rx="4"/>
|
||||
<text class="nj-sax-buf" x="96" y="325" xml:space="preserve">[1, ]</text>
|
||||
<path class="nj-sax-caret nj-sax-s-err" d="M133.8 334 l-5 8 h10 z"/>
|
||||
<text class="nj-sax-status nj-sax-s-err" x="420" y="319">error at byte 5, size 5</text>
|
||||
<text class="fg-note fg-note--l" x="420" y="335">before the end: a real error</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="366">Bytes parsed: 4 + 12 + 19 + 30 + 35 = 100 for a value of 35 bytes.</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="386">Every attempt starts again at byte 1, so the total work grows</text>
|
||||
<text class="fg-note fg-note--l" x="16" y="406">quadratically with the size of the value.</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 4.5 KiB |
@@ -1,60 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--compile" viewBox="0 0 470 516" role="img" aria-labelledby="nj-charts-ct nj-charts-ct-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-ct">Change in compile time against the default configuration at -O0, Apple clang and G​CC 16</title>
|
||||
<desc id="nj-charts-ct-d">Grouped horizontal bars, negative is faster. json_fwd.hpp instead of json.hpp on a header-only translation unit: Apple clang -62 %, G​CC 16 -82 %; extern template on a parsing translation unit: Apple clang -7 %, G​CC 16 -21 %; JSON_NO_AUTOMATIC_UDLS on a model translation unit: Apple clang -11 %, G​CC 16 -11 %; JSON_NO_AUTOMATIC_UDLS on a parsing translation unit: Apple clang -1 %, G​CC 16 -2 %; JSON_HAS_FILESYSTEM=0 + JSON_NO_IO on a model translation unit: Apple clang -8 %, G​CC 16 -11 %; JSON_HAS_FILESYSTEM=0 on a model translation unit: Apple clang -5 %, G​CC 16 -9 %; JSON_NO_IO on a model translation unit: Apple clang -2 %, G​CC 16 -2 %; JSON_USE_GLOBAL_UDLS=0 on a model translation unit: Apple clang 0 %, G​CC 16 -1 %.</desc>
|
||||
<rect class="nj-charts-clang" x="8" y="10" width="12" height="12" rx="3"/>
|
||||
<text class="nj-charts-leg" x="26" y="20.5">Apple clang</text>
|
||||
<rect class="nj-charts-gcc" x="126" y="10" width="12" height="12" rx="3"/>
|
||||
<text class="nj-charts-leg" x="144" y="20.5">G​CC 16</text>
|
||||
<line class="nj-charts-grid" x1="47.4" y1="58" x2="47.4" y2="472"/>
|
||||
<text class="nj-charts-tick" x="47.4" y="488">−80 %</text>
|
||||
<line class="nj-charts-grid" x1="126.2" y1="58" x2="126.2" y2="472"/>
|
||||
<text class="nj-charts-tick" x="126.2" y="488">−60 %</text>
|
||||
<line class="nj-charts-grid" x1="205" y1="58" x2="205" y2="472"/>
|
||||
<text class="nj-charts-tick" x="205" y="488">−40 %</text>
|
||||
<line class="nj-charts-grid" x1="283.8" y1="58" x2="283.8" y2="472"/>
|
||||
<text class="nj-charts-tick" x="283.8" y="488">−20 %</text>
|
||||
<text class="nj-charts-tick" x="362.6" y="488">0 %</text>
|
||||
<text class="nj-charts-tick nj-charts-tick--l" x="8" y="506">← faster</text>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="462" y="506">slower →</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="62"><tspan class="nj-charts-code">json_fwd.hpp instead of json.hpp</tspan><tspan class="nj-charts-sub"> · header-only TU</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 70 H122.32 Q118.32 70 118.32 74 V78 Q118.32 82 122.32 82 H362.6 Z"><title>json_fwd.hpp instead of json.hpp, header-only TU (Apple clang): −62 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="80.5">−62 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 84 H43.52 Q39.52 84 39.52 88 V92 Q39.52 96 43.52 96 H362.6 Z"><title>json_fwd.hpp instead of json.hpp, header-only TU (G​CC 16): −82 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="94.5">−82 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="114"><tspan class="nj-charts-code">extern template</tspan><tspan class="nj-charts-sub"> · parsing TU</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 122 H339.02 Q335.02 122 335.02 126 V130 Q335.02 134 339.02 134 H362.6 Z"><title>extern template, parsing TU (Apple clang): −7 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="132.5">−7 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 136 H283.86 Q279.86 136 279.86 140 V144 Q279.86 148 283.86 148 H362.6 Z"><title>extern template, parsing TU (G​CC 16): −21 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="146.5">−21 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="166"><tspan class="nj-charts-code">JSON_NO_AUTOMATIC_UDLS</tspan><tspan class="nj-charts-sub"> · model TU</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 174 H323.26 Q319.26 174 319.26 178 V182 Q319.26 186 323.26 186 H362.6 Z"><title>JSON_NO_AUTOMATIC_UDLS, model TU (Apple clang): −11 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="184.5">−11 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 188 H323.26 Q319.26 188 319.26 192 V196 Q319.26 200 323.26 200 H362.6 Z"><title>JSON_NO_AUTOMATIC_UDLS, model TU (G​CC 16): −11 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="198.5">−11 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="218"><tspan class="nj-charts-code">JSON_NO_AUTOMATIC_UDLS</tspan><tspan class="nj-charts-sub"> · parsing TU</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 226 H362.6 Q358.66 226 358.66 229.94 V234.06 Q358.66 238 362.6 238 H362.6 Z"><title>JSON_NO_AUTOMATIC_UDLS, parsing TU (Apple clang): −1 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="236.5">−1 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 240 H358.72 Q354.72 240 354.72 244 V248 Q354.72 252 358.72 252 H362.6 Z"><title>JSON_NO_AUTOMATIC_UDLS, parsing TU (G​CC 16): −2 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="250.5">−2 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="270"><tspan class="nj-charts-code">JSON_HAS_FILESYSTEM=0 + JSON_NO_IO</tspan><tspan class="nj-charts-sub"> · model TU</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 278 H335.08 Q331.08 278 331.08 282 V286 Q331.08 290 335.08 290 H362.6 Z"><title>JSON_HAS_FILESYSTEM=0 + JSON_NO_IO, model TU (Apple clang): −8 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="288.5">−8 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 292 H323.26 Q319.26 292 319.26 296 V300 Q319.26 304 323.26 304 H362.6 Z"><title>JSON_HAS_FILESYSTEM=0 + JSON_NO_IO, model TU (G​CC 16): −11 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="302.5">−11 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="322"><tspan class="nj-charts-code">JSON_HAS_FILESYSTEM=0</tspan><tspan class="nj-charts-sub"> · model TU</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 330 H346.9 Q342.9 330 342.9 334 V338 Q342.9 342 346.9 342 H362.6 Z"><title>JSON_HAS_FILESYSTEM=0, model TU (Apple clang): −5 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="340.5">−5 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 344 H331.14 Q327.14 344 327.14 348 V352 Q327.14 356 331.14 356 H362.6 Z"><title>JSON_HAS_FILESYSTEM=0, model TU (G​CC 16): −9 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="354.5">−9 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="374"><tspan class="nj-charts-code">JSON_NO_IO</tspan><tspan class="nj-charts-sub"> · model TU*</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 382 H358.72 Q354.72 382 354.72 386 V390 Q354.72 394 358.72 394 H362.6 Z"><title>JSON_NO_IO, model TU (Apple clang): −2 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="392.5">−2 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 396 H358.72 Q354.72 396 354.72 400 V404 Q354.72 408 358.72 408 H362.6 Z"><title>JSON_NO_IO, model TU (G​CC 16): −2 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="406.5">−2 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="426"><tspan class="nj-charts-code">JSON_USE_GLOBAL_UDLS=0</tspan><tspan class="nj-charts-sub"> · model TU*</tspan></text>
|
||||
<path class="nj-charts-clang" d="M362.6 434 h0.5 v12 h-0.5 Z"><title>JSON_USE_GLOBAL_UDLS=0, model TU (Apple clang): 0 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="444.5">0 %</text>
|
||||
<path class="nj-charts-gcc" d="M362.6 448 H362.6 Q358.66 448 358.66 451.94 V456.06 Q358.66 460 362.6 460 H362.6 Z"><title>JSON_USE_GLOBAL_UDLS=0, model TU (G​CC 16): −1 %</title></path>
|
||||
<text class="nj-charts-val" x="367.6" y="458.5">−1 %</text>
|
||||
<line class="nj-charts-zero" x1="362.6" y1="58" x2="362.6" y2="472"/>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 7.5 KiB |
@@ -1,30 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--compile" viewBox="0 0 440 282" role="img" aria-labelledby="nj-charts-mod nj-charts-mod-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-mod">Compile time per translation unit with import nlohmann.json at -O0, and the one-off cost of the module</title>
|
||||
<desc id="nj-charts-mod-d">Horizontal bars, negative is faster, medians of nine runs, -std=c++20 for both. model TU, Apple clang: -48 % (1311 ms to 680 ms); model TU, G​CC 16: -47 % (2156 ms to 1153 ms); parsing TU, Apple clang: -42 % (1387 ms to 800 ms); parsing TU, G​CC 16: -36 % (2838 ms to 1810 ms); one-off build, Apple clang: 1630 ms; one-off build, G​CC 16: 2538 ms.</desc>
|
||||
<rect class="nj-charts-clang" x="8" y="10" width="12" height="12" rx="3"/>
|
||||
<text class="nj-charts-leg" x="26" y="20.5">Apple clang</text>
|
||||
<rect class="nj-charts-gcc" x="126" y="10" width="12" height="12" rx="3"/>
|
||||
<text class="nj-charts-leg" x="144" y="20.5">G​CC 16</text>
|
||||
<line class="nj-charts-grid" x1="68.6667" y1="58" x2="68.6667" y2="160"/>
|
||||
<text class="nj-charts-tick" x="68.6667" y="176">−50 %</text>
|
||||
<line class="nj-charts-grid" x1="220.333" y1="58" x2="220.333" y2="160"/>
|
||||
<text class="nj-charts-tick" x="220.333" y="176">−25 %</text>
|
||||
<text class="nj-charts-tick" x="372" y="176">0 %</text>
|
||||
<text class="nj-charts-tick nj-charts-tick--l" x="8" y="194">← faster per TU</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="62">model TU<tspan class="nj-charts-sub"> · import nlohmann.json</tspan></text>
|
||||
<path class="nj-charts-clang" d="M372 70 H84.8 Q80.8 70 80.8 74 V78 Q80.8 82 84.8 82 H372 Z"><title>model TU, Apple clang: 1311 ms by default, 680 ms import nlohmann.json (−48 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="80.5">−48 %</text>
|
||||
<path class="nj-charts-gcc" d="M372 84 H90.8667 Q86.8667 84 86.8667 88 V92 Q86.8667 96 90.8667 96 H372 Z"><title>model TU, G​CC 16: 2156 ms by default, 1153 ms import nlohmann.json (−47 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="94.5">−47 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="114">parsing TU<tspan class="nj-charts-sub"> · import nlohmann.json</tspan></text>
|
||||
<path class="nj-charts-clang" d="M372 122 H121.2 Q117.2 122 117.2 126 V130 Q117.2 134 121.2 134 H372 Z"><title>parsing TU, Apple clang: 1387 ms by default, 800 ms import nlohmann.json (−42 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="132.5">−42 %</text>
|
||||
<path class="nj-charts-gcc" d="M372 136 H157.6 Q153.6 136 153.6 140 V144 Q153.6 148 157.6 148 H372 Z"><title>parsing TU, G​CC 16: 2838 ms by default, 1810 ms import nlohmann.json (−36 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="146.5">−36 %</text>
|
||||
<line class="nj-charts-zero" x1="372" y1="58" x2="372" y2="160"/>
|
||||
<text class="nj-charts-rowlabel" x="8" y="222">One-off cost<tspan class="nj-charts-sub"> · built once, reused by every TU</tspan></text>
|
||||
<rect class="nj-charts-clang" x="8" y="232.5" width="10" height="10" rx="2.5"/>
|
||||
<text class="nj-charts-val" x="24" y="242">Apple clang: 1630 ms once, saves 587 to 631 ms per TU</text>
|
||||
<rect class="nj-charts-gcc" x="8" y="252.5" width="10" height="10" rx="2.5"/>
|
||||
<text class="nj-charts-val" x="24" y="262">G​CC 16: 2538 ms once, saves 1003 to 1028 ms per TU</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.3 KiB |
@@ -1,30 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--compile" viewBox="0 0 440 282" role="img" aria-labelledby="nj-charts-pch nj-charts-pch-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-pch">Compile time per translation unit with a precompiled json.hpp at -O0, and the one-off cost of the PCH</title>
|
||||
<desc id="nj-charts-pch-d">Horizontal bars, negative is faster, medians of nine runs, -std=c++17. model TU, Apple clang: -43 % (1045 ms to 594 ms); model TU, G​CC 16: -41 % (1789 ms to 1060 ms); parsing TU, Apple clang: -38 % (1148 ms to 714 ms); parsing TU, G​CC 16: -25 % (2498 ms to 1884 ms); one-off build, Apple clang: 771 ms; one-off build, G​CC 16: 2254 ms.</desc>
|
||||
<rect class="nj-charts-clang" x="8" y="10" width="12" height="12" rx="3"/>
|
||||
<text class="nj-charts-leg" x="26" y="20.5">Apple clang</text>
|
||||
<rect class="nj-charts-gcc" x="126" y="10" width="12" height="12" rx="3"/>
|
||||
<text class="nj-charts-leg" x="144" y="20.5">G​CC 16</text>
|
||||
<line class="nj-charts-grid" x1="68.6667" y1="58" x2="68.6667" y2="160"/>
|
||||
<text class="nj-charts-tick" x="68.6667" y="176">−50 %</text>
|
||||
<line class="nj-charts-grid" x1="220.333" y1="58" x2="220.333" y2="160"/>
|
||||
<text class="nj-charts-tick" x="220.333" y="176">−25 %</text>
|
||||
<text class="nj-charts-tick" x="372" y="176">0 %</text>
|
||||
<text class="nj-charts-tick nj-charts-tick--l" x="8" y="194">← faster per TU</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="62">model TU<tspan class="nj-charts-sub"> · with PCH</tspan></text>
|
||||
<path class="nj-charts-clang" d="M372 70 H115.133 Q111.133 70 111.133 74 V78 Q111.133 82 115.133 82 H372 Z"><title>model TU, Apple clang: 1045 ms by default, 594 ms with PCH (−43 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="80.5">−43 %</text>
|
||||
<path class="nj-charts-gcc" d="M372 84 H127.267 Q123.267 84 123.267 88 V92 Q123.267 96 127.267 96 H372 Z"><title>model TU, G​CC 16: 1789 ms by default, 1060 ms with PCH (−41 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="94.5">−41 %</text>
|
||||
<text class="nj-charts-rowlabel" x="8" y="114">parsing TU<tspan class="nj-charts-sub"> · with PCH</tspan></text>
|
||||
<path class="nj-charts-clang" d="M372 122 H145.467 Q141.467 122 141.467 126 V130 Q141.467 134 145.467 134 H372 Z"><title>parsing TU, Apple clang: 1148 ms by default, 714 ms with PCH (−38 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="132.5">−38 %</text>
|
||||
<path class="nj-charts-gcc" d="M372 136 H224.333 Q220.333 136 220.333 140 V144 Q220.333 148 224.333 148 H372 Z"><title>parsing TU, G​CC 16: 2498 ms by default, 1884 ms with PCH (−25 %)</title></path>
|
||||
<text class="nj-charts-val" x="377" y="146.5">−25 %</text>
|
||||
<line class="nj-charts-zero" x1="372" y1="58" x2="372" y2="160"/>
|
||||
<text class="nj-charts-rowlabel" x="8" y="222">One-off cost<tspan class="nj-charts-sub"> · built once, reused by every TU</tspan></text>
|
||||
<rect class="nj-charts-clang" x="8" y="232.5" width="10" height="10" rx="2.5"/>
|
||||
<text class="nj-charts-val" x="24" y="242">Apple clang: 771 ms once, saves 434 to 451 ms per TU</text>
|
||||
<rect class="nj-charts-gcc" x="8" y="252.5" width="10" height="10" rx="2.5"/>
|
||||
<text class="nj-charts-val" x="24" y="262">G​CC 16: 2254 ms once, saves 614 to 729 ms per TU</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.2 KiB |
@@ -1,174 +0,0 @@
|
||||
<svg class="nj-fig nj-exceptions-map nj-exceptions-map--wide" viewBox="0 0 760 694" aria-labelledby="nj-exc-map-title-w nj-exc-map-desc-w" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<title id="nj-exc-map-title-w">Exception id map</title>
|
||||
<desc id="nj-exc-map-desc-w">Class tree: std::exception is the base of json::exception, which is the base of the five exception families parse_error (ids 1xx), invalid_iterator (2xx), type_error (3xx), out_of_range (4xx) and other_error (5xx). Each family lists the ids documented on this page, 68 in total; every id links to its section.</desc>
|
||||
<defs><marker id="nj-exc-tri-w" viewBox="0 0 12 12" refX="11" refY="6" markerWidth="11" markerHeight="11" orient="auto"><path class="nj-exceptions-tri" d="M1 1 L11 6 L1 11 z"/></marker></defs>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="656" x2="34" y2="158" marker-end="url(#nj-exc-tri-w)"/>
|
||||
<rect class="nj-exceptions-box" x="12" y="12" width="200" height="52" rx="7"/><text class="nj-exceptions-name" x="24" y="34">std::exception</text><text class="nj-exceptions-sub" x="24" y="53">C++ standard library base</text>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="104" x2="34" y2="66" marker-end="url(#nj-exc-tri-w)"/>
|
||||
<rect class="nj-exceptions-box" x="12" y="104" width="300" height="52" rx="7"/><text class="nj-exceptions-name" x="24" y="126">json::exception</text><text class="nj-exceptions-sub" x="24" y="145">id, what() · catch-all</text>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="222" x2="64" y2="222"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#parse-errors" aria-label="json::parse_error, 1xx · 15 ids · adds member byte"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="196" width="214" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="218">json::parse_error</text><text class="nj-exceptions-sub" x="76" y="237">1xx · 15 ids · adds member byte</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error101" aria-label="json.exception.parse_error.101"><rect x="294" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="226.5">101</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error102" aria-label="json.exception.parse_error.102"><rect x="341.7" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="226.5">102</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error103" aria-label="json.exception.parse_error.103"><rect x="389.4" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="226.5">103</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error104" aria-label="json.exception.parse_error.104"><rect x="437.1" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="226.5">104</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error105" aria-label="json.exception.parse_error.105"><rect x="484.8" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="226.5">105</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error106" aria-label="json.exception.parse_error.106"><rect x="532.5" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="226.5">106</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error107" aria-label="json.exception.parse_error.107"><rect x="580.2" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="589.2" y="226.5">107</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error108" aria-label="json.exception.parse_error.108"><rect x="627.9" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="636.9" y="226.5">108</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error109" aria-label="json.exception.parse_error.109"><rect x="675.6" y="208" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="684.6" y="226.5">109</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error110" aria-label="json.exception.parse_error.110"><rect x="294" y="242" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="260.5">110</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error112" aria-label="json.exception.parse_error.112"><rect x="341.7" y="242" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="260.5">112</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error113" aria-label="json.exception.parse_error.113"><rect x="389.4" y="242" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="260.5">113</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error114" aria-label="json.exception.parse_error.114"><rect x="437.1" y="242" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="260.5">114</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error115" aria-label="json.exception.parse_error.115"><rect x="484.8" y="242" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="260.5">115</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error116" aria-label="json.exception.parse_error.116"><rect x="532.5" y="242" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="260.5">116</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="322" x2="64" y2="322"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#iterator-errors" aria-label="json::invalid_iterator, 2xx · 14 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="296" width="214" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="318">json::invalid_iterator</text><text class="nj-exceptions-sub" x="76" y="337">2xx · 14 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator201" aria-label="json.exception.invalid_iterator.201"><rect x="294" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="326.5">201</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator202" aria-label="json.exception.invalid_iterator.202"><rect x="341.7" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="326.5">202</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator203" aria-label="json.exception.invalid_iterator.203"><rect x="389.4" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="326.5">203</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator204" aria-label="json.exception.invalid_iterator.204"><rect x="437.1" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="326.5">204</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator205" aria-label="json.exception.invalid_iterator.205"><rect x="484.8" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="326.5">205</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator206" aria-label="json.exception.invalid_iterator.206"><rect x="532.5" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="326.5">206</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator207" aria-label="json.exception.invalid_iterator.207"><rect x="580.2" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="589.2" y="326.5">207</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator208" aria-label="json.exception.invalid_iterator.208"><rect x="627.9" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="636.9" y="326.5">208</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator209" aria-label="json.exception.invalid_iterator.209"><rect x="675.6" y="308" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="684.6" y="326.5">209</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator210" aria-label="json.exception.invalid_iterator.210"><rect x="294" y="342" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="360.5">210</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator211" aria-label="json.exception.invalid_iterator.211"><rect x="341.7" y="342" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="360.5">211</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator212" aria-label="json.exception.invalid_iterator.212"><rect x="389.4" y="342" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="360.5">212</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator213" aria-label="json.exception.invalid_iterator.213"><rect x="437.1" y="342" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="360.5">213</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator214" aria-label="json.exception.invalid_iterator.214"><rect x="484.8" y="342" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="360.5">214</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="422" x2="64" y2="422"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#type-errors" aria-label="json::type_error, 3xx · 21 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="396" width="214" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="418">json::type_error</text><text class="nj-exceptions-sub" x="76" y="437">3xx · 21 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error301" aria-label="json.exception.type_error.301"><rect x="294" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="426.5">301</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error302" aria-label="json.exception.type_error.302"><rect x="341.7" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="426.5">302</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error303" aria-label="json.exception.type_error.303"><rect x="389.4" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="426.5">303</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error304" aria-label="json.exception.type_error.304"><rect x="437.1" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="426.5">304</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error305" aria-label="json.exception.type_error.305"><rect x="484.8" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="426.5">305</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error306" aria-label="json.exception.type_error.306"><rect x="532.5" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="426.5">306</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error307" aria-label="json.exception.type_error.307"><rect x="580.2" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="589.2" y="426.5">307</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error308" aria-label="json.exception.type_error.308"><rect x="627.9" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="636.9" y="426.5">308</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error309" aria-label="json.exception.type_error.309"><rect x="675.6" y="408" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="684.6" y="426.5">309</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error310" aria-label="json.exception.type_error.310"><rect x="294" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="460.5">310</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error311" aria-label="json.exception.type_error.311"><rect x="341.7" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="460.5">311</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error312" aria-label="json.exception.type_error.312"><rect x="389.4" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="460.5">312</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error313" aria-label="json.exception.type_error.313"><rect x="437.1" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="460.5">313</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error314" aria-label="json.exception.type_error.314"><rect x="484.8" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="460.5">314</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error315" aria-label="json.exception.type_error.315"><rect x="532.5" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="460.5">315</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error316" aria-label="json.exception.type_error.316"><rect x="580.2" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="589.2" y="460.5">316</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error317" aria-label="json.exception.type_error.317"><rect x="627.9" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="636.9" y="460.5">317</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error318" aria-label="json.exception.type_error.318"><rect x="675.6" y="442" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="684.6" y="460.5">318</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error319" aria-label="json.exception.type_error.319"><rect x="294" y="476" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="494.5">319</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error320" aria-label="json.exception.type_error.320"><rect x="341.7" y="476" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="494.5">320</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error321" aria-label="json.exception.type_error.321"><rect x="389.4" y="476" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="494.5">321</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="556" x2="64" y2="556"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#out-of-range" aria-label="json::out_of_range, 4xx · 16 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="530" width="214" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="552">json::out_of_range</text><text class="nj-exceptions-sub" x="76" y="571">4xx · 16 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range401" aria-label="json.exception.out_of_range.401"><rect x="294" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="560.5">401</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range402" aria-label="json.exception.out_of_range.402"><rect x="341.7" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="560.5">402</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range403" aria-label="json.exception.out_of_range.403"><rect x="389.4" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="560.5">403</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range404" aria-label="json.exception.out_of_range.404"><rect x="437.1" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="560.5">404</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range405" aria-label="json.exception.out_of_range.405"><rect x="484.8" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="560.5">405</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range406" aria-label="json.exception.out_of_range.406"><rect x="532.5" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="560.5">406</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range407" aria-label="json.exception.out_of_range.407"><rect x="580.2" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="589.2" y="560.5">407</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range408" aria-label="json.exception.out_of_range.408"><rect x="627.9" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="636.9" y="560.5">408</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range409" aria-label="json.exception.out_of_range.409"><rect x="675.6" y="542" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="684.6" y="560.5">409</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range410" aria-label="json.exception.out_of_range.410"><rect x="294" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="594.5">410</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range411" aria-label="json.exception.out_of_range.411"><rect x="341.7" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="594.5">411</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range412" aria-label="json.exception.out_of_range.412"><rect x="389.4" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="398.4" y="594.5">412</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range413" aria-label="json.exception.out_of_range.413"><rect x="437.1" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="446.1" y="594.5">413</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range414" aria-label="json.exception.out_of_range.414"><rect x="484.8" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="493.8" y="594.5">414</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range415" aria-label="json.exception.out_of_range.415"><rect x="532.5" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="541.5" y="594.5">415</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range416" aria-label="json.exception.out_of_range.416"><rect x="580.2" y="576" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="589.2" y="594.5">416</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="656" x2="64" y2="656"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#further-exceptions" aria-label="json::other_error, 5xx · 2 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="630" width="214" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="652">json::other_error</text><text class="nj-exceptions-sub" x="76" y="671">5xx · 2 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionother_error501" aria-label="json.exception.other_error.501"><rect x="294" y="642" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="303" y="660.5">501</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionother_error502" aria-label="json.exception.other_error.502"><rect x="341.7" y="642" width="41.7" height="28" rx="6"/><text class="nj-exceptions-id" x="350.7" y="660.5">502</text></a>
|
||||
</svg>
|
||||
<svg class="nj-fig nj-exceptions-map nj-exceptions-map--narrow" viewBox="0 0 360 1152" aria-labelledby="nj-exc-map-title-n nj-exc-map-desc-n" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<title id="nj-exc-map-title-n">Exception id map</title>
|
||||
<desc id="nj-exc-map-desc-n">Class tree: std::exception is the base of json::exception, which is the base of the five exception families parse_error (ids 1xx), invalid_iterator (2xx), type_error (3xx), out_of_range (4xx) and other_error (5xx). Each family lists the ids documented on this page, 68 in total; every id links to its section.</desc>
|
||||
<defs><marker id="nj-exc-tri-n" viewBox="0 0 12 12" refX="11" refY="6" markerWidth="11" markerHeight="11" orient="auto"><path class="nj-exceptions-tri" d="M1 1 L11 6 L1 11 z"/></marker></defs>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="1070" x2="34" y2="158" marker-end="url(#nj-exc-tri-n)"/>
|
||||
<rect class="nj-exceptions-box" x="12" y="12" width="190" height="52" rx="7"/><text class="nj-exceptions-name" x="24" y="34">std::exception</text><text class="nj-exceptions-sub" x="24" y="53">C++ standard library base</text>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="104" x2="34" y2="66" marker-end="url(#nj-exc-tri-n)"/>
|
||||
<rect class="nj-exceptions-box" x="12" y="104" width="250" height="52" rx="7"/><text class="nj-exceptions-name" x="24" y="126">json::exception</text><text class="nj-exceptions-sub" x="24" y="145">id, what() · catch-all</text>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="222" x2="64" y2="222"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#parse-errors" aria-label="json::parse_error, 1xx · 15 ids · adds member byte"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="196" width="284" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="218">json::parse_error</text><text class="nj-exceptions-sub" x="76" y="237">1xx · 15 ids · adds member byte</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error101" aria-label="json.exception.parse_error.101"><rect x="64" y="258" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="279.5">101</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error102" aria-label="json.exception.parse_error.102"><rect x="111.7" y="258" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="279.5">102</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error103" aria-label="json.exception.parse_error.103"><rect x="159.4" y="258" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="279.5">103</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error104" aria-label="json.exception.parse_error.104"><rect x="207.1" y="258" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="279.5">104</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error105" aria-label="json.exception.parse_error.105"><rect x="254.8" y="258" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="279.5">105</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error106" aria-label="json.exception.parse_error.106"><rect x="302.5" y="258" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="279.5">106</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error107" aria-label="json.exception.parse_error.107"><rect x="64" y="298" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="319.5">107</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error108" aria-label="json.exception.parse_error.108"><rect x="111.7" y="298" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="319.5">108</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error109" aria-label="json.exception.parse_error.109"><rect x="159.4" y="298" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="319.5">109</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error110" aria-label="json.exception.parse_error.110"><rect x="207.1" y="298" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="319.5">110</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error112" aria-label="json.exception.parse_error.112"><rect x="254.8" y="298" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="319.5">112</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error113" aria-label="json.exception.parse_error.113"><rect x="302.5" y="298" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="319.5">113</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error114" aria-label="json.exception.parse_error.114"><rect x="64" y="338" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="359.5">114</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error115" aria-label="json.exception.parse_error.115"><rect x="111.7" y="338" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="359.5">115</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionparse_error116" aria-label="json.exception.parse_error.116"><rect x="159.4" y="338" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="359.5">116</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="424" x2="64" y2="424"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#iterator-errors" aria-label="json::invalid_iterator, 2xx · 14 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="398" width="284" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="420">json::invalid_iterator</text><text class="nj-exceptions-sub" x="76" y="439">2xx · 14 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator201" aria-label="json.exception.invalid_iterator.201"><rect x="64" y="460" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="481.5">201</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator202" aria-label="json.exception.invalid_iterator.202"><rect x="111.7" y="460" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="481.5">202</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator203" aria-label="json.exception.invalid_iterator.203"><rect x="159.4" y="460" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="481.5">203</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator204" aria-label="json.exception.invalid_iterator.204"><rect x="207.1" y="460" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="481.5">204</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator205" aria-label="json.exception.invalid_iterator.205"><rect x="254.8" y="460" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="481.5">205</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator206" aria-label="json.exception.invalid_iterator.206"><rect x="302.5" y="460" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="481.5">206</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator207" aria-label="json.exception.invalid_iterator.207"><rect x="64" y="500" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="521.5">207</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator208" aria-label="json.exception.invalid_iterator.208"><rect x="111.7" y="500" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="521.5">208</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator209" aria-label="json.exception.invalid_iterator.209"><rect x="159.4" y="500" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="521.5">209</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator210" aria-label="json.exception.invalid_iterator.210"><rect x="207.1" y="500" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="521.5">210</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator211" aria-label="json.exception.invalid_iterator.211"><rect x="254.8" y="500" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="521.5">211</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator212" aria-label="json.exception.invalid_iterator.212"><rect x="302.5" y="500" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="521.5">212</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator213" aria-label="json.exception.invalid_iterator.213"><rect x="64" y="540" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="561.5">213</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptioninvalid_iterator214" aria-label="json.exception.invalid_iterator.214"><rect x="111.7" y="540" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="561.5">214</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="626" x2="64" y2="626"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#type-errors" aria-label="json::type_error, 3xx · 21 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="600" width="284" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="622">json::type_error</text><text class="nj-exceptions-sub" x="76" y="641">3xx · 21 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error301" aria-label="json.exception.type_error.301"><rect x="64" y="662" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="683.5">301</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error302" aria-label="json.exception.type_error.302"><rect x="111.7" y="662" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="683.5">302</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error303" aria-label="json.exception.type_error.303"><rect x="159.4" y="662" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="683.5">303</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error304" aria-label="json.exception.type_error.304"><rect x="207.1" y="662" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="683.5">304</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error305" aria-label="json.exception.type_error.305"><rect x="254.8" y="662" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="683.5">305</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error306" aria-label="json.exception.type_error.306"><rect x="302.5" y="662" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="683.5">306</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error307" aria-label="json.exception.type_error.307"><rect x="64" y="702" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="723.5">307</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error308" aria-label="json.exception.type_error.308"><rect x="111.7" y="702" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="723.5">308</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error309" aria-label="json.exception.type_error.309"><rect x="159.4" y="702" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="723.5">309</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error310" aria-label="json.exception.type_error.310"><rect x="207.1" y="702" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="723.5">310</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error311" aria-label="json.exception.type_error.311"><rect x="254.8" y="702" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="723.5">311</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error312" aria-label="json.exception.type_error.312"><rect x="302.5" y="702" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="723.5">312</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error313" aria-label="json.exception.type_error.313"><rect x="64" y="742" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="763.5">313</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error314" aria-label="json.exception.type_error.314"><rect x="111.7" y="742" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="763.5">314</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error315" aria-label="json.exception.type_error.315"><rect x="159.4" y="742" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="763.5">315</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error316" aria-label="json.exception.type_error.316"><rect x="207.1" y="742" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="763.5">316</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error317" aria-label="json.exception.type_error.317"><rect x="254.8" y="742" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="763.5">317</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error318" aria-label="json.exception.type_error.318"><rect x="302.5" y="742" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="763.5">318</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error319" aria-label="json.exception.type_error.319"><rect x="64" y="782" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="803.5">319</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error320" aria-label="json.exception.type_error.320"><rect x="111.7" y="782" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="803.5">320</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptiontype_error321" aria-label="json.exception.type_error.321"><rect x="159.4" y="782" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="803.5">321</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="868" x2="64" y2="868"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#out-of-range" aria-label="json::out_of_range, 4xx · 16 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="842" width="284" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="864">json::out_of_range</text><text class="nj-exceptions-sub" x="76" y="883">4xx · 16 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range401" aria-label="json.exception.out_of_range.401"><rect x="64" y="904" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="925.5">401</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range402" aria-label="json.exception.out_of_range.402"><rect x="111.7" y="904" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="925.5">402</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range403" aria-label="json.exception.out_of_range.403"><rect x="159.4" y="904" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="925.5">403</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range404" aria-label="json.exception.out_of_range.404"><rect x="207.1" y="904" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="925.5">404</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range405" aria-label="json.exception.out_of_range.405"><rect x="254.8" y="904" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="925.5">405</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range406" aria-label="json.exception.out_of_range.406"><rect x="302.5" y="904" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="925.5">406</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range407" aria-label="json.exception.out_of_range.407"><rect x="64" y="944" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="965.5">407</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range408" aria-label="json.exception.out_of_range.408"><rect x="111.7" y="944" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="965.5">408</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range409" aria-label="json.exception.out_of_range.409"><rect x="159.4" y="944" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="965.5">409</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range410" aria-label="json.exception.out_of_range.410"><rect x="207.1" y="944" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="965.5">410</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range411" aria-label="json.exception.out_of_range.411"><rect x="254.8" y="944" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="263.8" y="965.5">411</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range412" aria-label="json.exception.out_of_range.412"><rect x="302.5" y="944" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="311.5" y="965.5">412</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range413" aria-label="json.exception.out_of_range.413"><rect x="64" y="984" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="1005.5">413</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range414" aria-label="json.exception.out_of_range.414"><rect x="111.7" y="984" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="1005.5">414</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range415" aria-label="json.exception.out_of_range.415"><rect x="159.4" y="984" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="168.4" y="1005.5">415</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionout_of_range416" aria-label="json.exception.out_of_range.416"><rect x="207.1" y="984" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="216.1" y="1005.5">416</text></a>
|
||||
<line class="nj-exceptions-edge" x1="34" y1="1070" x2="64" y2="1070"/>
|
||||
<a class="nj-exceptions-fam" xlink:href="#further-exceptions" aria-label="json::other_error, 5xx · 2 ids"><rect class="nj-exceptions-box nj-exceptions-box--fam" x="64" y="1044" width="284" height="52" rx="7"/><text class="nj-exceptions-name" x="76" y="1066">json::other_error</text><text class="nj-exceptions-sub" x="76" y="1085">5xx · 2 ids</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionother_error501" aria-label="json.exception.other_error.501"><rect x="64" y="1106" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="73" y="1127.5">501</text></a>
|
||||
<a class="nj-exceptions-chip" xlink:href="#jsonexceptionother_error502" aria-label="json.exception.other_error.502"><rect x="111.7" y="1106" width="41.7" height="34" rx="6"/><text class="nj-exceptions-id" x="120.7" y="1127.5">502</text></a>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 39 KiB |
@@ -1 +0,0 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 1200 675" width="1200" height="675" role="img"><title>JSON for Modern C++: feature slideshow (animated, 20 slides, 15 s each)</title><style>.bg{fill:#fff} .tx{fill:#0f1419} .tx2{fill:#3d444f} .tx3{fill:#8a919c} .com{fill:#646d7a}.bl{fill:#1747a6} .blk{fill:#1747a6} .kw{fill:#1747a6} .ty{fill:#0d6e72} .fn{fill:#6b3fb8} .str{fill:#23793a} .num{fill:#b04a07} .pp{fill:#a3247a}.panel{fill:#f5f7fa;stroke:#e3e6eb;stroke-width:1} .rule{stroke:#e3e6eb;stroke-width:1}.wm-a{fill:#0f1419} .wm-s{fill:#1747a6}.on-a,.on-tx{fill:#fff} .red{fill:#d93a3f} .on-panel{fill:#fff;fill-opacity:.08;stroke:#fff;stroke-opacity:.16} .on-s{fill:#bcd3fb} .w70{fill:#fff;fill-opacity:.7} .on-tx2{fill:#dbe6fb} .chip{fill:#fff;fill-opacity:.14}.pat{fill:#fff;fill-opacity:.09}.h1{stop-color:#1d55c4} .h2{stop-color:#123a8a}.seg{fill:#e3e6eb} .seg-on{fill:#1747a6}.seg.on-band{fill:#fff;fill-opacity:.25} .seg-on.on-band{fill:#fff;fill-opacity:1}.bg{fill:#0f1218} .tx,.wm-a{fill:#f2f4f7} .tx2{fill:#c3c8d1} .tx3{fill:#7b828e} .com{fill:#8b929e}.bl,.blk,.wm-s,.seg-on,.kw{fill:#7aa7f5} .ty{fill:#4fd1c5} .fn{fill:#c4a3ff} .str{fill:#7ed491} .num{fill:#f5a65b} .pp{fill:#f48fc8}.panel{fill:#171b23;stroke:#272c36} .rule{stroke:#272c36} .seg{fill:#272c36}.red{fill:#c8383d} .h1{stop-color:#163f93} .h2{stop-color:#0c2556}.s{opacity:0;animation:show 300s linear infinite backwards}.fill{transform-box:fill-box;transform-origin:left;animation:fill 300s linear infinite backwards;animation-delay:inherit}.s0{animation-name:show0} .sl{animation-name:showl}@keyframes show{0%{opacity:0;animation-timing-function:cubic-bezier(.2,.6,.2,1)} 0.2000%{opacity:1} 5.2000%{opacity:1} 5.2100%{opacity:0} 100%{opacity:0}}@keyframes show0{0%{opacity:1} 5.2000%{opacity:1} 5.2100%{opacity:0} 100%{opacity:0}}@keyframes showl{0%{opacity:0;animation-timing-function:cubic-bezier(.2,.6,.2,1)} 0.2000%{opacity:1} 5.0000%{opacity:1} 5.2000%{opacity:0} 100%{opacity:0}}@keyframes fill{0%{transform:scaleX(0)} 5.0000%{transform:scaleX(1)} 100%{transform:scaleX(1)}}@media (prefers-reduced-motion:reduce){.s,.fill{animation:none} .s:first-of-type{opacity:1}}</style><defs><path id="g0" d="M233 0 46 730H148L269 238Q281 191 289 148Q298 105 302 81Q306 105 315 148Q324 191 335 239L452 730H554L366 0H233Z"/><path id="g1" d="M97 0V730H522V641H195V424H487V337H195V89H522V0H97Z"/><path id="g2" d="M89 0V730H315Q382 730 432 703Q483 677 510 629Q538 582 538 518Q538 445 501 391Q463 338 401 316L548 0H439L300 305H187V0H89ZM187 393H315Q370 393 403 427Q436 461 436 517Q436 574 403 608Q370 642 315 642H187V393Z"/><path id="g3" d="M304 -10Q233 -10 179 15Q126 41 97 88Q68 136 68 202H167Q167 144 204 111Q242 78 304 78Q364 78 399 112Q435 146 435 201Q435 243 412 274Q390 306 347 317L239 346Q168 366 126 419Q85 471 85 543Q85 602 112 646Q138 691 186 715Q234 740 297 740Q361 740 409 715Q457 691 485 647Q512 603 512 545H414Q414 593 381 623Q348 653 297 653Q245 653 214 623Q182 593 182 545Q182 507 203 480Q224 453 262 442L373 412Q448 392 490 336Q532 279 532 201Q532 137 504 89Q476 42 424 16Q373 -10 304 -10Z"/><path id="g4" d="M101 0V90H250V640H101V730H499V640H350V90H499V0H101Z"/><path id="g5" d="M300 -10Q200 -10 142 48Q84 106 84 212V518Q84 625 142 682Q200 740 300 740Q400 740 458 682Q516 625 516 519V212Q516 106 458 48Q400 -10 300 -10ZM300 78Q357 78 387 110Q417 142 417 202V528Q417 588 387 620Q357 652 300 652Q244 652 213 620Q183 588 183 528V202Q183 142 213 110Q244 78 300 78Z"/><path id="g6" d="M85 0V730H214L432 114Q429 141 427 179Q424 217 422 259Q421 301 421 337V730H515V0H386L170 616Q172 591 174 553Q176 516 178 474Q179 433 179 396V0H85Z"/><path id="g8" d="M290 -10Q187 -10 127 46Q67 103 67 200H166Q166 143 200 110Q233 78 291 78Q348 78 382 110Q415 143 415 200V251Q415 308 382 341Q349 375 291 375H209V458L385 641H89V730H496V640L291 428L293 462Q395 462 455 405Q515 349 515 251V200Q515 103 454 46Q394 -10 290 -10Z"/><path id="g9" d="M300 -10Q262 -10 238 13Q215 36 215 72Q215 111 238 134Q262 158 300 158Q338 158 362 134Q385 111 385 72Q385 36 362 13Q338 -10 300 -10Z"/><path id="ga" d="M88 0V90H284V641L88 495V607L254 730H383V90H543V0H88Z"/><path id="gb" d="M300 -10Q232 -10 182 17Q132 43 104 92Q77 141 77 206V524Q77 590 104 638Q132 687 182 713Q232 740 300 740Q369 740 419 713Q468 687 496 638Q523 590 523 524V206Q523 141 496 92Q468 43 418 17Q368 -10 300 -10ZM300 75Q358 75 393 111Q428 148 428 206V524Q428 582 393 619Q358 655 300 655Q242 655 207 619Q172 582 172 524V206Q172 148 207 111Q242 75 300 75ZM300 309Q272 309 255 324Q238 339 238 368Q238 396 255 411Q272 425 300 425Q328 425 345 411Q362 396 362 368Q362 339 345 324Q328 309 300 309Z"/><path id="gc" d="M180 688V0H134V1056H180V816H168Q204 944 310 1008Q417 1072 544 1072Q659 1072 746 1024Q834 975 884 889Q934 803 934 688V0H888V688Q888 840 792 933Q696 1026 544 1026Q440 1026 358 982Q275 939 228 862Q180 786 180 688Z"/><path id="gd" d="M180 1490V0H134V1490H180Z"/><path id="ge" d="M530 -16Q394 -16 289 54Q184 125 125 248Q66 371 6Line truncated
|
||||
|
Before Width: | Height: | Size: 395 KiB |
@@ -1 +0,0 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 1200 675" width="1200" height="675" role="img"><title>JSON for Modern C++: feature slideshow (animated, 20 slides, 15 s each)</title><style>.bg{fill:#fff} .tx{fill:#0f1419} .tx2{fill:#3d444f} .tx3{fill:#8a919c} .com{fill:#646d7a}.bl{fill:#1747a6} .blk{fill:#1747a6} .kw{fill:#1747a6} .ty{fill:#0d6e72} .fn{fill:#6b3fb8} .str{fill:#23793a} .num{fill:#b04a07} .pp{fill:#a3247a}.panel{fill:#f5f7fa;stroke:#e3e6eb;stroke-width:1} .rule{stroke:#e3e6eb;stroke-width:1}.wm-a{fill:#0f1419} .wm-s{fill:#1747a6}.on-a,.on-tx{fill:#fff} .red{fill:#d93a3f} .on-panel{fill:#fff;fill-opacity:.08;stroke:#fff;stroke-opacity:.16} .on-s{fill:#bcd3fb} .w70{fill:#fff;fill-opacity:.7} .on-tx2{fill:#dbe6fb} .chip{fill:#fff;fill-opacity:.14}.pat{fill:#fff;fill-opacity:.09}.h1{stop-color:#1d55c4} .h2{stop-color:#123a8a}.seg{fill:#e3e6eb} .seg-on{fill:#1747a6}.seg.on-band{fill:#fff;fill-opacity:.25} .seg-on.on-band{fill:#fff;fill-opacity:1}.s{opacity:0;animation:show 300s linear infinite backwards}.fill{transform-box:fill-box;transform-origin:left;animation:fill 300s linear infinite backwards;animation-delay:inherit}.s0{animation-name:show0} .sl{animation-name:showl}@keyframes show{0%{opacity:0;animation-timing-function:cubic-bezier(.2,.6,.2,1)} 0.2000%{opacity:1} 5.2000%{opacity:1} 5.2100%{opacity:0} 100%{opacity:0}}@keyframes show0{0%{opacity:1} 5.2000%{opacity:1} 5.2100%{opacity:0} 100%{opacity:0}}@keyframes showl{0%{opacity:0;animation-timing-function:cubic-bezier(.2,.6,.2,1)} 0.2000%{opacity:1} 5.0000%{opacity:1} 5.2000%{opacity:0} 100%{opacity:0}}@keyframes fill{0%{transform:scaleX(0)} 5.0000%{transform:scaleX(1)} 100%{transform:scaleX(1)}}@media (prefers-reduced-motion:reduce){.s,.fill{animation:none} .s:first-of-type{opacity:1}}</style><defs><path id="g0" d="M233 0 46 730H148L269 238Q281 191 289 148Q298 105 302 81Q306 105 315 148Q324 191 335 239L452 730H554L366 0H233Z"/><path id="g1" d="M97 0V730H522V641H195V424H487V337H195V89H522V0H97Z"/><path id="g2" d="M89 0V730H315Q382 730 432 703Q483 677 510 629Q538 582 538 518Q538 445 501 391Q463 338 401 316L548 0H439L300 305H187V0H89ZM187 393H315Q370 393 403 427Q436 461 436 517Q436 574 403 608Q370 642 315 642H187V393Z"/><path id="g3" d="M304 -10Q233 -10 179 15Q126 41 97 88Q68 136 68 202H167Q167 144 204 111Q242 78 304 78Q364 78 399 112Q435 146 435 201Q435 243 412 274Q390 306 347 317L239 346Q168 366 126 419Q85 471 85 543Q85 602 112 646Q138 691 186 715Q234 740 297 740Q361 740 409 715Q457 691 485 647Q512 603 512 545H414Q414 593 381 623Q348 653 297 653Q245 653 214 623Q182 593 182 545Q182 507 203 480Q224 453 262 442L373 412Q448 392 490 336Q532 279 532 201Q532 137 504 89Q476 42 424 16Q373 -10 304 -10Z"/><path id="g4" d="M101 0V90H250V640H101V730H499V640H350V90H499V0H101Z"/><path id="g5" d="M300 -10Q200 -10 142 48Q84 106 84 212V518Q84 625 142 682Q200 740 300 740Q400 740 458 682Q516 625 516 519V212Q516 106 458 48Q400 -10 300 -10ZM300 78Q357 78 387 110Q417 142 417 202V528Q417 588 387 620Q357 652 300 652Q244 652 213 620Q183 588 183 528V202Q183 142 213 110Q244 78 300 78Z"/><path id="g6" d="M85 0V730H214L432 114Q429 141 427 179Q424 217 422 259Q421 301 421 337V730H515V0H386L170 616Q172 591 174 553Q176 516 178 474Q179 433 179 396V0H85Z"/><path id="g8" d="M290 -10Q187 -10 127 46Q67 103 67 200H166Q166 143 200 110Q233 78 291 78Q348 78 382 110Q415 143 415 200V251Q415 308 382 341Q349 375 291 375H209V458L385 641H89V730H496V640L291 428L293 462Q395 462 455 405Q515 349 515 251V200Q515 103 454 46Q394 -10 290 -10Z"/><path id="g9" d="M300 -10Q262 -10 238 13Q215 36 215 72Q215 111 238 134Q262 158 300 158Q338 158 362 134Q385 111 385 72Q385 36 362 13Q338 -10 300 -10Z"/><path id="ga" d="M88 0V90H284V641L88 495V607L254 730H383V90H543V0H88Z"/><path id="gb" d="M300 -10Q232 -10 182 17Q132 43 104 92Q77 141 77 206V524Q77 590 104 638Q132 687 182 713Q232 740 300 740Q369 740 419 713Q468 687 496 638Q523 590 523 524V206Q523 141 496 92Q468 43 418 17Q368 -10 300 -10ZM300 75Q358 75 393 111Q428 148 428 206V524Q428 582 393 619Q358 655 300 655Q242 655 207 619Q172 582 172 524V206Q172 148 207 111Q242 75 300 75ZM300 309Q272 309 255 324Q238 339 238 368Q238 396 255 411Q272 425 300 425Q328 425 345 411Q362 396 362 368Q362 339 345 324Q328 309 300 309Z"/><path id="gc" d="M180 688V0H134V1056H180V816H168Q204 944 310 1008Q417 1072 544 1072Q659 1072 746 1024Q834 975 884 889Q934 803 934 688V0H888V688Q888 840 792 933Q696 1026 544 1026Q440 1026 358 982Q275 939 228 862Q180 786 180 688Z"/><path id="gd" d="M180 1490V0H134V1490H180Z"/><path id="ge" d="M530 -16Q394 -16 289 54Q184 125 125 248Q66 371 66 528Q66 686 125 808Q184 931 289 1002Q394 1072 530 1072Q666 1072 770 1002Q874 931 933 808Q992 686 992 528Q992 371 933 248Q874 125 770 54Q666 -16 530 -16ZM530 30Q652 30 746 94Q840 157 893 270Q946 382 946 528Q946 674 893 786Q840 899 746 962Q652 1026 530 1026Q408 1026 314 962Q219 899 166 786Q112 674 112 528Q112 382 166 270Q219 157 314 94Q408 30 530 30Z"/><path id="gf" d="MLine truncated
|
||||
|
Before Width: | Height: | Size: 394 KiB |
@@ -1,52 +0,0 @@
|
||||
<svg class="nj-fig nj-pointer-fl" viewBox="0 0 760 442" role="img" aria-labelledby="fig-flat-title" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-flat-title">flatten() turns the nested example document into a flat object, and unflatten() turns it back. Left, the document as a tree: array with the elements A, B, C, and nested with one = 1, two = 2, and three with the elements true and false. Right, the flat object with one key per leaf: /array/0 = A, /array/1 = B, /array/2 = C, /nested/one = 1, /nested/two = 2, /nested/three/0 = true, /nested/three/1 = false. Each leaf is joined to its key by a line.</title>
|
||||
<defs><marker id="fig-flat-arrow" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto"><path class="fg-head" d="M0 1 L10 5 L0 9 z"/></marker></defs>
|
||||
<text class="fg-h" x="20" y="26">nested value</text>
|
||||
<text class="fg-h" x="470" y="26">flat object: key = J​SON Pointer</text>
|
||||
<line class="fg-arrow" x1="250" y1="52" x2="450" y2="52" marker-end="url(#fig-flat-arrow)"/>
|
||||
<text class="nj-pointer-fl-op" x="350" y="44">flatten()</text>
|
||||
<line class="fg-arrow" x1="450" y1="420" x2="250" y2="420" marker-end="url(#fig-flat-arrow)"/>
|
||||
<text class="nj-pointer-fl-op" x="350" y="412">unflatten()</text>
|
||||
<path class="nj-pointer-fl-edge" d="M25 99 V115 H42"/>
|
||||
<path class="nj-pointer-fl-edge" d="M51 127 V143 H68"/>
|
||||
<path class="nj-pointer-fl-edge" d="M51 127 V171 H68"/>
|
||||
<path class="nj-pointer-fl-edge" d="M51 127 V199 H68"/>
|
||||
<path class="nj-pointer-fl-edge" d="M25 99 V227 H42"/>
|
||||
<path class="nj-pointer-fl-edge" d="M51 239 V255 H68"/>
|
||||
<path class="nj-pointer-fl-edge" d="M51 239 V283 H68"/>
|
||||
<path class="nj-pointer-fl-edge" d="M51 239 V311 H68"/>
|
||||
<path class="nj-pointer-fl-edge" d="M77 323 V339 H94"/>
|
||||
<path class="nj-pointer-fl-edge" d="M77 323 V367 H94"/>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--s" d="M139.6 143 C259.6 143 340 171 460 171"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--s" cx="139.6" cy="143" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="176" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/array/0"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--s">"A"</tspan></text>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--s" d="M139.6 171 C259.6 171 340 199 460 199"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--s" cx="139.6" cy="171" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="204" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/array/1"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--s">"B"</tspan></text>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--s" d="M139.6 199 C259.6 199 340 227 460 227"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--s" cx="139.6" cy="199" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="232" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/array/2"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--s">"C"</tspan></text>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--n" d="M158.8 255 C278.8 255 340 255 460 255"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--n" cx="158.8" cy="255" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="260" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/nested/one"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--n">1</tspan></text>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--n" d="M158.8 283 C278.8 283 340 283 460 283"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--n" cx="158.8" cy="283" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="288" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/nested/two"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--n">2</tspan></text>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--b" d="M175.2 339 C295.2 339 340 311 460 311"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--b" cx="175.2" cy="339" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="316" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/nested/three/0"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--b">true</tspan></text>
|
||||
<path class="nj-pointer-fl-link nj-pointer-fl--b" d="M184.8 367 C304.8 367 340 339 460 339"/>
|
||||
<circle class="nj-pointer-fl-dot nj-pointer-fl--b" cx="184.8" cy="367" r="3.5"/>
|
||||
<text class="fg-code" x="470" y="344" xml:space="preserve"><tspan class="nj-pointer-fl-key">"/nested/three/1"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--b">false</tspan></text>
|
||||
<text class="fg-h" x="20" y="92">root</text>
|
||||
<text class="fg-code nj-pointer-fl-inner" x="46" y="120">"array"</text>
|
||||
<text class="fg-code" x="72" y="148" xml:space="preserve"><tspan class="nj-pointer-fl-k">0</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--s">"A"</tspan></text>
|
||||
<text class="fg-code" x="72" y="176" xml:space="preserve"><tspan class="nj-pointer-fl-k">1</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--s">"B"</tspan></text>
|
||||
<text class="fg-code" x="72" y="204" xml:space="preserve"><tspan class="nj-pointer-fl-k">2</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--s">"C"</tspan></text>
|
||||
<text class="fg-code nj-pointer-fl-inner" x="46" y="232">"nested"</text>
|
||||
<text class="fg-code" x="72" y="260" xml:space="preserve"><tspan class="nj-pointer-fl-k">"one"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--n">1</tspan></text>
|
||||
<text class="fg-code" x="72" y="288" xml:space="preserve"><tspan class="nj-pointer-fl-k">"two"</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--n">2</tspan></text>
|
||||
<text class="fg-code nj-pointer-fl-inner" x="72" y="316">"three"</text>
|
||||
<text class="fg-code" x="98" y="344" xml:space="preserve"><tspan class="nj-pointer-fl-k">0</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--b">true</tspan></text>
|
||||
<text class="fg-code" x="98" y="372" xml:space="preserve"><tspan class="nj-pointer-fl-k">1</tspan>: <tspan class="nj-pointer-fl-v nj-pointer-fl--b">false</tspan></text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 5.6 KiB |
|
After Width: | Height: | Size: 36 KiB |
@@ -1,66 +0,0 @@
|
||||
<svg class="railroad" viewBox="0 0 860 214" role="img" aria-labelledby="rr-title" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="rr-title">Railroad diagram of the J​SON number syntax: optional minus, then 0 or a digit from 1 to 9 followed by digits, then an optional fraction (a dot and digits) and an optional exponent (e or E, an optional sign, and digits).</title>
|
||||
<g class="rr-track" fill="none" stroke="currentColor" stroke-opacity=".6" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||||
<path d="M8 44 L850 44"/>
|
||||
<path d="M24 44 L31 44 Q38 44 38 51 L38 82 Q38 92 48 92 L59 92"/>
|
||||
<path d="M85 92 L96 92 Q106 92 106 82 L106 51 Q106 44 113 44 L120 44"/>
|
||||
<path d="M120 44 L127 44 Q134 44 134 51 L134 82 Q134 92 144 92 L160 92"/>
|
||||
<path d="M242 92 L370 92 Q380 92 380 82 L380 52 Q380 44 388 44 L396 44"/>
|
||||
<path d="M242 92 L250 92 Q258 92 258 100 L258 126 Q258 136 268 136 L278 136"/>
|
||||
<path d="M332 136 L340 136 Q348 136 348 128 L348 92"/>
|
||||
<path d="M340 136 L340 160 Q340 170 330 170 L280 170 Q270 170 270 160 L270 136"/>
|
||||
<path d="M396 44 L403 44 Q410 44 410 51 L410 84.5 Q410 92 417.5 92 L425 92"/>
|
||||
<path d="M451 92 L462 92"/>
|
||||
<path d="M524 92 L524 116 Q524 126 514 126 L466 126 Q456 126 456 116 L456 92"/>
|
||||
<path d="M516 92 L523 92 Q530 92 530 85 L530 52 Q530 44 538 44 L546 44"/>
|
||||
<path d="M546 44 L553 44 Q560 44 560 51 L560 83.5 Q560 92 568.5 92 L577 92"/>
|
||||
<path d="M546 44 L553 44 Q560 44 560 51 L560 127.5 Q560 136 568.5 136 L577 136"/>
|
||||
<path d="M603 92 L728 92"/>
|
||||
<path d="M603 136 L611.5 136 Q620 136 620 127.5 L620 92"/>
|
||||
<path d="M640 92 L647 92 Q654 92 654 99 L654 128 Q654 136 662 136 L670 136"/>
|
||||
<path d="M640 92 L647 92 Q654 92 654 99 L654 172 Q654 180 662 180 L670 180"/>
|
||||
<path d="M696 136 L704 136 Q712 136 712 128 L712 92"/>
|
||||
<path d="M696 180 L704 180 Q712 180 712 172 L712 92"/>
|
||||
<path d="M728 92 L746 92"/>
|
||||
<path d="M808 92 L808 116 Q808 126 798 126 L748 126 Q738 126 738 116 L738 92"/>
|
||||
<path d="M800 92 L808 92 Q816 92 816 84 L816 52 Q816 44 824 44 L832 44"/>
|
||||
</g>
|
||||
<polygon class="rr-arrow" points="2,38 12,44 2,50"/>
|
||||
<polygon class="rr-arrow" points="846,38 858,44 846,50"/>
|
||||
<circle class="rr-bg" cx="72" cy="92" r="13"/>
|
||||
<circle class="rr-t" cx="72" cy="92" r="13"/>
|
||||
<circle class="rr-bg" cx="257" cy="44" r="13"/>
|
||||
<circle class="rr-t" cx="257" cy="44" r="13"/>
|
||||
<rect class="rr-bg" x="160" y="78" width="82" height="28" rx="6"/>
|
||||
<rect class="rr-n" x="160" y="78" width="82" height="28" rx="6"/>
|
||||
<rect class="rr-bg" x="278" y="122" width="54" height="28" rx="6"/>
|
||||
<rect class="rr-n" x="278" y="122" width="54" height="28" rx="6"/>
|
||||
<circle class="rr-bg" cx="438" cy="92" r="13"/>
|
||||
<circle class="rr-t" cx="438" cy="92" r="13"/>
|
||||
<rect class="rr-bg" x="462" y="78" width="54" height="28" rx="6"/>
|
||||
<rect class="rr-n" x="462" y="78" width="54" height="28" rx="6"/>
|
||||
<circle class="rr-bg" cx="590" cy="92" r="13"/>
|
||||
<circle class="rr-t" cx="590" cy="92" r="13"/>
|
||||
<circle class="rr-bg" cx="590" cy="136" r="13"/>
|
||||
<circle class="rr-t" cx="590" cy="136" r="13"/>
|
||||
<circle class="rr-bg" cx="683" cy="136" r="13"/>
|
||||
<circle class="rr-t" cx="683" cy="136" r="13"/>
|
||||
<circle class="rr-bg" cx="683" cy="180" r="13"/>
|
||||
<circle class="rr-t" cx="683" cy="180" r="13"/>
|
||||
<rect class="rr-bg" x="746" y="78" width="54" height="28" rx="6"/>
|
||||
<rect class="rr-n" x="746" y="78" width="54" height="28" rx="6"/>
|
||||
<text class="rr-c" x="72" y="97">−</text>
|
||||
<text class="rr-c" x="257" y="49">0</text>
|
||||
<text class="rr-b" x="201" y="97">digit 1–9</text>
|
||||
<text class="rr-b" x="305" y="141">digit</text>
|
||||
<text class="rr-c" x="438" y="97">.</text>
|
||||
<text class="rr-b" x="489" y="97">digit</text>
|
||||
<text class="rr-c" x="590" y="97">e</text>
|
||||
<text class="rr-c" x="590" y="141">E</text>
|
||||
<text class="rr-c" x="683" y="141">−</text>
|
||||
<text class="rr-c" x="683" y="185">+</text>
|
||||
<text class="rr-b" x="773" y="97">digit</text>
|
||||
<text class="rr-l rr-name" x="24" y="32">number</text>
|
||||
<text class="rr-l" x="420" y="32">fraction</text>
|
||||
<text class="rr-l" x="580" y="32">exponent</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 3.9 KiB |
@@ -1,57 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview nj-jsonview-editfig" viewBox="0 0 840 372" role="img" aria-labelledby="fig-jve0-title fig-jve0-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jve0-title">Step 1 of 5: parsed</title>
|
||||
<desc id="fig-jve0-title-d">After parse: nine nodes, nothing owned yet. The dump with number_format::source is {"port":6379,"price":19.90,"tags":["eu","a\"b"]}.</desc>
|
||||
<defs>
|
||||
<marker id="jve0-line" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-line nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve0-own" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-own nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve0-struct" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-struct nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve0-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong" x="16" y="22" xml:space="preserve">parsed index: fixed, never moves</text>
|
||||
<text class="nj-jsonview-note" x="824" y="22" text-anchor="end" xml:space="preserve">the source text is never written</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="36" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="42" y="47" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="78" y="61" text-anchor="middle" xml:space="preserve">object</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="78" y="77" text-anchor="middle" xml:space="preserve">{ } 3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="124" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="130" y="47" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="166" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="166" y="77" text-anchor="middle" xml:space="preserve">port</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="212" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="218" y="47" xml:space="preserve">2</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="254" y="61" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="254" y="77" text-anchor="middle" xml:space="preserve">6379</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="300" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="306" y="47" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="342" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="342" y="77" text-anchor="middle" xml:space="preserve">price</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="388" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="394" y="47" xml:space="preserve">4</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="430" y="61" text-anchor="middle" xml:space="preserve">float</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="430" y="77" text-anchor="middle" xml:space="preserve">19.90</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="476" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="482" y="47" xml:space="preserve">5</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="518" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="518" y="77" text-anchor="middle" xml:space="preserve">tags</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="564" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="570" y="47" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="606" y="61" text-anchor="middle" xml:space="preserve">array</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="606" y="77" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-str" x="652" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="658" y="47" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="694" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="694" y="77" text-anchor="middle" xml:space="preserve">"eu"</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="746" y="47" xml:space="preserve">8</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-dec" x="782" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="782" y="77" text-anchor="middle" xml:space="preserve">a"b</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong nj-jsonview-c-own" x="16" y="288" xml:space="preserve">owned storage: allocated on demand, never moves</text>
|
||||
<rect class="nj-jsonview-store" x="10" y="192" width="820" height="54" rx="8"/>
|
||||
<text class="nj-jsonview-note" x="26" y="224" xml:space="preserve">empty: a read-only json_document has none of this</text>
|
||||
<path class="nj-jsonview-sep" d="M16 300 H824"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="318" xml:space="preserve">view v = root()["tags"] (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="318" xml:space="preserve">valid, sees every edit</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="338" xml:space="preserve">iterator over tags (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="338" xml:space="preserve">valid</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs nj-jsonview-muted" x="16" y="360" xml:space="preserve">dump(): {"port":6379,"price":19.90,"tags":["eu","a\"b"]}</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 6.4 KiB |
@@ -1,57 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview nj-jsonview-editfig" viewBox="0 0 840 372" role="img" aria-labelledby="fig-jve1-title fig-jve1-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jve1-title">Step 2 of 5: doc.set(doc.root(), "port", 6380)</title>
|
||||
<desc id="fig-jve1-title-d">set: the node of the integer is overwritten in place. The dump with number_format::source is {"port":6380,"price":19.90,"tags":["eu","a\"b"]}.</desc>
|
||||
<defs>
|
||||
<marker id="jve1-line" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-line nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve1-own" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-own nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve1-struct" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-struct nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve1-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong" x="16" y="22" xml:space="preserve">parsed index: fixed, never moves</text>
|
||||
<text class="nj-jsonview-note" x="824" y="22" text-anchor="end" xml:space="preserve">the source text is never written</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="36" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="42" y="47" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="78" y="61" text-anchor="middle" xml:space="preserve">object</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="78" y="77" text-anchor="middle" xml:space="preserve">{ } 3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="124" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="130" y="47" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="166" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="166" y="77" text-anchor="middle" xml:space="preserve">port</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-num" x="212" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="218" y="47" xml:space="preserve">2</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="254" y="61" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="254" y="77" text-anchor="middle" xml:space="preserve">6380</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="300" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="306" y="47" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="342" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="342" y="77" text-anchor="middle" xml:space="preserve">price</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="388" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="394" y="47" xml:space="preserve">4</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="430" y="61" text-anchor="middle" xml:space="preserve">float</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="430" y="77" text-anchor="middle" xml:space="preserve">19.90</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="476" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="482" y="47" xml:space="preserve">5</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="518" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="518" y="77" text-anchor="middle" xml:space="preserve">tags</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="564" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="570" y="47" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="606" y="61" text-anchor="middle" xml:space="preserve">array</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="606" y="77" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-str" x="652" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="658" y="47" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="694" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="694" y="77" text-anchor="middle" xml:space="preserve">"eu"</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="746" y="47" xml:space="preserve">8</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-dec" x="782" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="782" y="77" text-anchor="middle" xml:space="preserve">a"b</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong nj-jsonview-c-own" x="16" y="288" xml:space="preserve">owned storage: allocated on demand, never moves</text>
|
||||
<rect class="nj-jsonview-store" x="10" y="192" width="820" height="54" rx="8"/>
|
||||
<text class="nj-jsonview-note" x="26" y="224" xml:space="preserve">empty: a read-only json_document has none of this</text>
|
||||
<path class="nj-jsonview-sep" d="M16 300 H824"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="318" xml:space="preserve">view v = root()["tags"] (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="318" xml:space="preserve">valid, sees every edit</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="338" xml:space="preserve">iterator over tags (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="338" xml:space="preserve">valid</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs nj-jsonview-muted" x="16" y="360" xml:space="preserve">dump(): {"port":6380,"price":19.90,"tags":["eu","a\"b"]}</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 6.4 KiB |
@@ -1,70 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview nj-jsonview-editfig" viewBox="0 0 840 372" role="img" aria-labelledby="fig-jve2-title fig-jve2-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jve2-title">Step 3 of 5: doc.erase(doc.root()["tags"], 0)</title>
|
||||
<desc id="fig-jve2-title-d">erase: the array moves to a block of links in owned storage. The dump with number_format::source is {"port":6380,"price":19.90,"tags":["a\"b"]}.</desc>
|
||||
<defs>
|
||||
<marker id="jve2-line" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-line nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve2-own" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-own nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve2-struct" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-struct nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve2-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong" x="16" y="22" xml:space="preserve">parsed index: fixed, never moves</text>
|
||||
<text class="nj-jsonview-note" x="824" y="22" text-anchor="end" xml:space="preserve">the source text is never written</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="36" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="42" y="47" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="78" y="61" text-anchor="middle" xml:space="preserve">object</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="78" y="77" text-anchor="middle" xml:space="preserve">{ } 3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="124" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="130" y="47" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="166" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="166" y="77" text-anchor="middle" xml:space="preserve">port</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="212" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="218" y="47" xml:space="preserve">2</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="254" y="61" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="254" y="77" text-anchor="middle" xml:space="preserve">6380</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="300" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="306" y="47" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="342" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="342" y="77" text-anchor="middle" xml:space="preserve">price</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="388" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="394" y="47" xml:space="preserve">4</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="430" y="61" text-anchor="middle" xml:space="preserve">float</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="430" y="77" text-anchor="middle" xml:space="preserve">19.90</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="476" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="482" y="47" xml:space="preserve">5</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="518" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="518" y="77" text-anchor="middle" xml:space="preserve">tags</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="564" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="570" y="47" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="606" y="61" text-anchor="middle" xml:space="preserve">array</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-struct nj-jsonview-strong" x="643" y="47" text-anchor="end" xml:space="preserve">moved</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="606" y="77" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-gap nj-jsonview-c-str" x="652" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="658" y="47" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="694" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="694" y="77" text-anchor="middle" xml:space="preserve">"eu"</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="694" y="98" text-anchor="middle" xml:space="preserve">unreferenced</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="746" y="47" xml:space="preserve">8</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-dec" x="782" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="782" y="77" text-anchor="middle" xml:space="preserve">a"b</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong nj-jsonview-c-own" x="16" y="288" xml:space="preserve">owned storage: allocated on demand, never moves</text>
|
||||
<rect class="nj-jsonview-store" x="10" y="192" width="820" height="54" rx="8"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-struct" x="16" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="66" y="207" text-anchor="end" xml:space="preserve">0'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="43" y="220" text-anchor="middle" xml:space="preserve">header</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="43" y="235" text-anchor="middle" xml:space="preserve">[ ] 1</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-own" x="73" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="123" y="207" text-anchor="end" xml:space="preserve">1'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="100" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="100" y="235" text-anchor="middle" xml:space="preserve">→ 8</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M100 196 C100 140 782 140 782 84" marker-end="url(#jve2-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-free nj-jsonview-c-own" x="130" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="157" y="224" text-anchor="middle" xml:space="preserve">free</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-struct nj-jsonview-dash" d="M598 84 C598 140 43 140 43 196" marker-end="url(#jve2-struct)"/>
|
||||
<path class="nj-jsonview-sep" d="M16 300 H824"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="318" xml:space="preserve">view v = root()["tags"] (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="318" xml:space="preserve">valid, sees every edit</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="338" xml:space="preserve">iterator over tags (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-bad nj-jsonview-strong" x="320" y="338" xml:space="preserve">invalid: tags no longer uses the parsed layout</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs nj-jsonview-muted" x="16" y="360" xml:space="preserve">dump(): {"port":6380,"price":19.90,"tags":["a\"b"]}</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 8.0 KiB |
@@ -1,80 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview nj-jsonview-editfig" viewBox="0 0 840 372" role="img" aria-labelledby="fig-jve3-title fig-jve3-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jve3-title">Step 4 of 5: doc.push_back(doc.root()["tags"], "new")</title>
|
||||
<desc id="fig-jve3-title-d">push_back: a new node, and a link appended to the block. The dump with number_format::source is {"port":6380,"price":19.90,"tags":["a\"b","new"]}.</desc>
|
||||
<defs>
|
||||
<marker id="jve3-line" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-line nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve3-own" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-own nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve3-struct" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-struct nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve3-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong" x="16" y="22" xml:space="preserve">parsed index: fixed, never moves</text>
|
||||
<text class="nj-jsonview-note" x="824" y="22" text-anchor="end" xml:space="preserve">the source text is never written</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="36" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="42" y="47" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="78" y="61" text-anchor="middle" xml:space="preserve">object</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="78" y="77" text-anchor="middle" xml:space="preserve">{ } 3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="124" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="130" y="47" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="166" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="166" y="77" text-anchor="middle" xml:space="preserve">port</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="212" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="218" y="47" xml:space="preserve">2</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="254" y="61" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="254" y="77" text-anchor="middle" xml:space="preserve">6380</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="300" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="306" y="47" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="342" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="342" y="77" text-anchor="middle" xml:space="preserve">price</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="388" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="394" y="47" xml:space="preserve">4</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="430" y="61" text-anchor="middle" xml:space="preserve">float</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="430" y="77" text-anchor="middle" xml:space="preserve">19.90</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="476" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="482" y="47" xml:space="preserve">5</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="518" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="518" y="77" text-anchor="middle" xml:space="preserve">tags</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="564" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="570" y="47" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="606" y="61" text-anchor="middle" xml:space="preserve">array</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-struct nj-jsonview-strong" x="643" y="47" text-anchor="end" xml:space="preserve">moved</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="606" y="77" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-gap nj-jsonview-c-str" x="652" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="658" y="47" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="694" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="694" y="77" text-anchor="middle" xml:space="preserve">"eu"</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="694" y="98" text-anchor="middle" xml:space="preserve">unreferenced</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="746" y="47" xml:space="preserve">8</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-dec" x="782" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="782" y="77" text-anchor="middle" xml:space="preserve">a"b</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong nj-jsonview-c-own" x="16" y="288" xml:space="preserve">owned storage: allocated on demand, never moves</text>
|
||||
<rect class="nj-jsonview-store" x="10" y="192" width="820" height="54" rx="8"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="16" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="66" y="207" text-anchor="end" xml:space="preserve">0'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="43" y="220" text-anchor="middle" xml:space="preserve">header</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="43" y="235" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-own" x="73" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="123" y="207" text-anchor="end" xml:space="preserve">1'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="100" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="100" y="235" text-anchor="middle" xml:space="preserve">→ 8</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M100 196 C100 140 782 140 782 84" marker-end="url(#jve3-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-own" x="130" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="180" y="207" text-anchor="end" xml:space="preserve">2'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="157" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="157" y="235" text-anchor="middle" xml:space="preserve">→ 3'</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M157 242 C157 268 214 268 214 244" marker-end="url(#jve3-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-str" x="187" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="237" y="207" text-anchor="end" xml:space="preserve">3'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="214" y="220" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="214" y="235" text-anchor="middle" xml:space="preserve">"new"</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-struct nj-jsonview-dash" d="M598 84 C598 140 43 140 43 196" marker-end="url(#jve3-struct)"/>
|
||||
<text class="nj-jsonview-note" x="588" y="282" text-anchor="end" xml:space="preserve">edited text</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-str" x="596" y="264" width="42" height="26" rx="4"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="602" y="282" xml:space="preserve">new</text>
|
||||
<path class="nj-jsonview-sep" d="M16 300 H824"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="318" xml:space="preserve">view v = root()["tags"] (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="318" xml:space="preserve">valid, sees every edit</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="338" xml:space="preserve">iterator over tags (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-bad nj-jsonview-strong" x="320" y="338" xml:space="preserve">invalid: tags no longer uses the parsed layout</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs nj-jsonview-muted" x="16" y="360" xml:space="preserve">dump(): {"port":6380,"price":19.90,"tags":["a\"b","new"]}</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 9.1 KiB |
@@ -1,126 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview nj-jsonview-editfig" viewBox="0 0 840 372" role="img" aria-labelledby="fig-jve4-title fig-jve4-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jve4-title">Step 5 of 5: doc.set(doc.root(), "retries", 3)</title>
|
||||
<desc id="fig-jve4-title-d">set of a new member: the object moves to a block as well. The dump with number_format::source is {"port":6380,"price":19.90,"tags":["a\"b","new"],"retries":3}.</desc>
|
||||
<defs>
|
||||
<marker id="jve4-line" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-line nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve4-own" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-own nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve4-struct" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-struct nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jve4-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong" x="16" y="22" xml:space="preserve">parsed index: fixed, never moves</text>
|
||||
<text class="nj-jsonview-note" x="824" y="22" text-anchor="end" xml:space="preserve">the source text is never written</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="36" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="42" y="47" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="78" y="61" text-anchor="middle" xml:space="preserve">object</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-struct nj-jsonview-strong" x="115" y="47" text-anchor="end" xml:space="preserve">moved</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="78" y="77" text-anchor="middle" xml:space="preserve">{ } 3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="124" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="130" y="47" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="166" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="166" y="77" text-anchor="middle" xml:space="preserve">port</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="212" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="218" y="47" xml:space="preserve">2</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="254" y="61" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="254" y="77" text-anchor="middle" xml:space="preserve">6380</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="300" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="306" y="47" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="342" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="342" y="77" text-anchor="middle" xml:space="preserve">price</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="388" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="394" y="47" xml:space="preserve">4</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="430" y="61" text-anchor="middle" xml:space="preserve">float</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="430" y="77" text-anchor="middle" xml:space="preserve">19.90</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="476" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="482" y="47" xml:space="preserve">5</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="518" y="61" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="518" y="77" text-anchor="middle" xml:space="preserve">tags</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="564" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="570" y="47" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="606" y="61" text-anchor="middle" xml:space="preserve">array</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-struct nj-jsonview-strong" x="643" y="47" text-anchor="end" xml:space="preserve">moved</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="606" y="77" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-gap nj-jsonview-c-str" x="652" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="658" y="47" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="694" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="694" y="77" text-anchor="middle" xml:space="preserve">"eu"</text>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="694" y="98" text-anchor="middle" xml:space="preserve">unreferenced</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="34" width="84" height="50" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="746" y="47" xml:space="preserve">8</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-dec" x="782" y="61" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="782" y="77" text-anchor="middle" xml:space="preserve">a"b</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong nj-jsonview-c-own" x="16" y="288" xml:space="preserve">owned storage: allocated on demand, never moves</text>
|
||||
<rect class="nj-jsonview-store" x="10" y="192" width="820" height="54" rx="8"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="16" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="66" y="207" text-anchor="end" xml:space="preserve">0'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="43" y="220" text-anchor="middle" xml:space="preserve">header</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="43" y="235" text-anchor="middle" xml:space="preserve">[ ] 2</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-own" x="73" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="123" y="207" text-anchor="end" xml:space="preserve">1'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="100" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="100" y="235" text-anchor="middle" xml:space="preserve">→ 8</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M100 196 C100 140 782 140 782 84" marker-end="url(#jve4-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-own" x="130" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="180" y="207" text-anchor="end" xml:space="preserve">2'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="157" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="157" y="235" text-anchor="middle" xml:space="preserve">→ 3'</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M157 242 C157 268 214 268 214 244" marker-end="url(#jve4-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-str" x="187" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="237" y="207" text-anchor="end" xml:space="preserve">3'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-str" x="214" y="220" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="214" y="235" text-anchor="middle" xml:space="preserve">"new"</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-num" x="244" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="294" y="207" text-anchor="end" xml:space="preserve">4'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-num" x="271" y="220" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="271" y="235" text-anchor="middle" xml:space="preserve">3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-struct" x="301" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="351" y="207" text-anchor="end" xml:space="preserve">5'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-struct" x="328" y="220" text-anchor="middle" xml:space="preserve">header</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="328" y="235" text-anchor="middle" xml:space="preserve">{ } 4</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-key" x="358" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="408" y="207" text-anchor="end" xml:space="preserve">6'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="385" y="220" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="385" y="235" text-anchor="middle" xml:space="preserve">port</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-own" x="415" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="465" y="207" text-anchor="end" xml:space="preserve">7'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="442" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="442" y="235" text-anchor="middle" xml:space="preserve">→ 2</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M442 196 C442 140 254 140 254 84" marker-end="url(#jve4-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-key" x="472" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="522" y="207" text-anchor="end" xml:space="preserve">8'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="499" y="220" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="499" y="235" text-anchor="middle" xml:space="preserve">price</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-own" x="529" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="579" y="207" text-anchor="end" xml:space="preserve">9'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="556" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="556" y="235" text-anchor="middle" xml:space="preserve">→ 4</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M556 196 C556 140 430 140 430 84" marker-end="url(#jve4-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-key" x="586" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="636" y="207" text-anchor="end" xml:space="preserve">10'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="613" y="220" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="613" y="235" text-anchor="middle" xml:space="preserve">tags</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-own" x="643" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="693" y="207" text-anchor="end" xml:space="preserve">11'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="670" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="670" y="235" text-anchor="middle" xml:space="preserve">→ 6</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M670 196 C670 140 614 140 614 84" marker-end="url(#jve4-own)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-key" x="700" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="750" y="207" text-anchor="end" xml:space="preserve">12'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-key" x="727" y="220" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="727" y="235" text-anchor="middle" xml:space="preserve">retries</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-hot nj-jsonview-c-own" x="757" y="196" width="54" height="46" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="807" y="207" text-anchor="end" xml:space="preserve">13'</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-xs nj-jsonview-c-own" x="784" y="220" text-anchor="middle" xml:space="preserve">link</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="784" y="235" text-anchor="middle" xml:space="preserve">→ 4'</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-own" d="M784 242 C784 268 271 268 271 244" marker-end="url(#jve4-own)"/>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-struct nj-jsonview-dash" d="M598 84 C598 140 43 140 43 196" marker-end="url(#jve4-struct)"/>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-struct nj-jsonview-dash" d="M70 84 C70 140 328 140 328 196" marker-end="url(#jve4-struct)"/>
|
||||
<text class="nj-jsonview-note" x="588" y="282" text-anchor="end" xml:space="preserve">edited text</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-str" x="596" y="264" width="112" height="26" rx="4"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="602" y="282" xml:space="preserve">newretries</text>
|
||||
<path class="nj-jsonview-sep" d="M16 300 H824"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="318" xml:space="preserve">view v = root()["tags"] (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-struct nj-jsonview-strong" x="320" y="318" xml:space="preserve">valid, sees every edit</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="16" y="338" xml:space="preserve">iterator over tags (taken after parse):</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-c-bad nj-jsonview-strong" x="320" y="338" xml:space="preserve">invalid: tags no longer uses the parsed layout</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs nj-jsonview-muted" x="16" y="360" xml:space="preserve">dump(): {"port":6380,"price":19.90,"tags":["a\"b","new"],"retries":3}</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 14 KiB |
@@ -1,182 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview " viewBox="0 0 840 692" role="img" aria-labelledby="fig-jvl-title fig-jvl-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jvl-title">The same J​SON text parsed by basic_json::parse() and by json_document::parse()</title>
|
||||
<desc id="fig-jvl-title-d">The text {"port": 6379, "price": 19.90, "tags": ["eu", "a\"b"]}. Top: basic_json::parse() builds a tree: the root json value points to a std::map whose three nodes are separate heap allocations; the price is stored as the double 19.9; the tags array is a std::vector of two json values, each pointing to its own std::string. Bottom: json_document::parse() keeps the 54 bytes of source text and builds a flat index of nine 16-byte nodes in document order: object, key port, unsigned integer 6379 (the converted value is in the node), key price, float, key tags, array, string eu, and an escaped string. Keys, the float, and the plain string point back into the source text; the escaped string points into the document's buffer of decoded strings. A json_view is two pointers: one to the document and one to a node, here the array.</desc>
|
||||
<defs>
|
||||
<marker id="jvl-line" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-line nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-str" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-str nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-key" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-key nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-num" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-num nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-dec" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-dec nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-own" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-own nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-struct" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-struct nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
<marker id="jvl-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<text class="nj-jsonview-h" x="16" y="26" xml:space="preserve">basic_json::parse(): a tree, every array, object, and string in its own heap allocation</text>
|
||||
<rect class="nj-jsonview-box" x="16" y="98" width="60" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono" x="46" y="120" text-anchor="middle" xml:space="preserve">json</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M76 115 L106 115" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="108" y="98" width="84" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono" x="150" y="120" text-anchor="middle" xml:space="preserve">std::map</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M192 115 C192 115 226 67 226 67" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="228" y="50" width="180" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-c-key" x="240" y="72" xml:space="preserve">"port"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-c-num" x="396" y="72" text-anchor="end" xml:space="preserve">6379</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M192 115 C192 115 226 115 226 115" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="228" y="98" width="180" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-c-key" x="240" y="120" xml:space="preserve">"price"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-c-num" x="396" y="120" text-anchor="end" xml:space="preserve">19.9</text>
|
||||
<text class="nj-jsonview-note" x="418" y="120" xml:space="preserve">double: 19.90 is gone</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M192 115 C192 115 226 163 226 163" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="228" y="146" width="180" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-c-key" x="240" y="168" xml:space="preserve">"tags"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-c-line" x="396" y="168" text-anchor="end" xml:space="preserve">•</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M408 163 L442 163" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="444" y="146" width="104" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono" x="496" y="168" text-anchor="middle" xml:space="preserve">std::vector</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M548 163 L576 163" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="578" y="146" width="92" height="34" rx="5"/>
|
||||
<path class="nj-jsonview-sep" d="M624 146 V180"/>
|
||||
<text class="nj-jsonview-mono" x="601" y="168" text-anchor="middle" xml:space="preserve">json</text>
|
||||
<text class="nj-jsonview-mono" x="647" y="168" text-anchor="middle" xml:space="preserve">json</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M601 146 C601 126 706 150 706 130" marker-end="url(#jvl-line)"/>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M647 180 C647 200 706 176 706 196" marker-end="url(#jvl-line)"/>
|
||||
<rect class="nj-jsonview-heap" x="708" y="113" width="126" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm nj-jsonview-c-str" x="771" y="135" text-anchor="middle" xml:space="preserve">std::string eu</text>
|
||||
<rect class="nj-jsonview-heap" x="708" y="179" width="126" height="34" rx="5"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm nj-jsonview-c-str" x="771" y="201" text-anchor="middle" xml:space="preserve">std::string a"b</text>
|
||||
<rect class="nj-jsonview-heap" x="16" y="186" width="18" height="14" rx="3"/>
|
||||
<text class="nj-jsonview-note" x="42" y="198" xml:space="preserve">a separate heap allocation</text>
|
||||
<path class="nj-jsonview-sep" d="M16 234 H824"/>
|
||||
<text class="nj-jsonview-h" x="16" y="262" xml:space="preserve">json_document::parse(): the source text stays where it is; one flat index of 16-byte nodes</text>
|
||||
<text class="nj-jsonview-note" x="16" y="290" xml:space="preserve">source text, 54 bytes (borrowed, or owned by the document)</text>
|
||||
<rect class="nj-jsonview-ribbon" x="42" y="300" width="756" height="26" rx="4"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-key" x="71" y="302" width="54" height="22" rx="3"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-num" x="169" y="302" width="54" height="22" rx="3"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-key" x="267" y="302" width="68" height="22" rx="3"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-num" x="379" y="302" width="68" height="22" rx="3"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-key" x="491" y="302" width="54" height="22" rx="3"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-str" x="617" y="302" width="26" height="22" rx="3"/>
|
||||
<rect class="nj-jsonview-span nj-jsonview-c-dec" x="701" y="302" width="54" height="22" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="49" y="317.5" text-anchor="middle" xml:space="preserve">{</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="63" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="77" y="317.5" text-anchor="middle" xml:space="preserve">p</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="91" y="317.5" text-anchor="middle" xml:space="preserve">o</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="105" y="317.5" text-anchor="middle" xml:space="preserve">r</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="119" y="317.5" text-anchor="middle" xml:space="preserve">t</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="133" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="147" y="317.5" text-anchor="middle" xml:space="preserve">:</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="175" y="317.5" text-anchor="middle" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="189" y="317.5" text-anchor="middle" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="203" y="317.5" text-anchor="middle" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="217" y="317.5" text-anchor="middle" xml:space="preserve">9</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="231" y="317.5" text-anchor="middle" xml:space="preserve">,</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="259" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="273" y="317.5" text-anchor="middle" xml:space="preserve">p</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="287" y="317.5" text-anchor="middle" xml:space="preserve">r</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="301" y="317.5" text-anchor="middle" xml:space="preserve">i</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="315" y="317.5" text-anchor="middle" xml:space="preserve">c</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="329" y="317.5" text-anchor="middle" xml:space="preserve">e</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="343" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="357" y="317.5" text-anchor="middle" xml:space="preserve">:</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="385" y="317.5" text-anchor="middle" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="399" y="317.5" text-anchor="middle" xml:space="preserve">9</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="413" y="317.5" text-anchor="middle" xml:space="preserve">.</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="427" y="317.5" text-anchor="middle" xml:space="preserve">9</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="441" y="317.5" text-anchor="middle" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="455" y="317.5" text-anchor="middle" xml:space="preserve">,</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="483" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="497" y="317.5" text-anchor="middle" xml:space="preserve">t</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="511" y="317.5" text-anchor="middle" xml:space="preserve">a</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="525" y="317.5" text-anchor="middle" xml:space="preserve">g</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="539" y="317.5" text-anchor="middle" xml:space="preserve">s</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="553" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="567" y="317.5" text-anchor="middle" xml:space="preserve">:</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="595" y="317.5" text-anchor="middle" xml:space="preserve">[</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="609" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="623" y="317.5" text-anchor="middle" xml:space="preserve">e</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="637" y="317.5" text-anchor="middle" xml:space="preserve">u</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="651" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="665" y="317.5" text-anchor="middle" xml:space="preserve">,</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="693" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="707" y="317.5" text-anchor="middle" xml:space="preserve">a</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="721" y="317.5" text-anchor="middle" xml:space="preserve">\</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="735" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="749" y="317.5" text-anchor="middle" xml:space="preserve">b</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="763" y="317.5" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="777" y="317.5" text-anchor="middle" xml:space="preserve">]</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-byte" x="791" y="317.5" text-anchor="middle" xml:space="preserve">}</text>
|
||||
<text class="nj-jsonview-tiny" x="49" y="340" text-anchor="middle" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-tiny" x="189" y="340" text-anchor="middle" xml:space="preserve">10</text>
|
||||
<text class="nj-jsonview-tiny" x="329" y="340" text-anchor="middle" xml:space="preserve">20</text>
|
||||
<text class="nj-jsonview-tiny" x="469" y="340" text-anchor="middle" xml:space="preserve">30</text>
|
||||
<text class="nj-jsonview-tiny" x="609" y="340" text-anchor="middle" xml:space="preserve">40</text>
|
||||
<text class="nj-jsonview-tiny" x="749" y="340" text-anchor="middle" xml:space="preserve">50</text>
|
||||
<rect class="nj-jsonview-frame" x="16" y="366" width="808" height="254" rx="10"/>
|
||||
<text class="nj-jsonview-note nj-jsonview-strong" x="30" y="602" xml:space="preserve">json_document: owns the node index and the buffer of decoded strings</text>
|
||||
<text class="nj-jsonview-note" x="30" y="500" xml:space="preserve">node index: 9 nodes × 16 bytes = 144 bytes, in document order</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="36" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="42" y="420" xml:space="preserve">0</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-struct" x="78" y="434" text-anchor="middle" xml:space="preserve">object</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="78" y="451" text-anchor="middle" xml:space="preserve">len 3</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="78" y="465" text-anchor="middle" xml:space="preserve">next 9</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="124" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="130" y="420" xml:space="preserve">1</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-key" x="166" y="434" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="166" y="451" text-anchor="middle" xml:space="preserve">off 2</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="166" y="465" text-anchor="middle" xml:space="preserve">len 4</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-key" d="M166 406 C166 367 98 367 98 328" marker-end="url(#jvl-key)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="212" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="218" y="420" xml:space="preserve">2</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-num" x="254" y="434" text-anchor="middle" xml:space="preserve">uint</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="254" y="451" text-anchor="middle" xml:space="preserve">6379</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="254" y="465" text-anchor="middle" xml:space="preserve">(converted)</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="300" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="306" y="420" xml:space="preserve">3</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-key" x="342" y="434" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="342" y="451" text-anchor="middle" xml:space="preserve">off 16</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="342" y="465" text-anchor="middle" xml:space="preserve">len 5</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-key" d="M342 406 C342 367 301 367 301 328" marker-end="url(#jvl-key)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-num" x="388" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="394" y="420" xml:space="preserve">4</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-num" x="430" y="434" text-anchor="middle" xml:space="preserve">float</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="430" y="451" text-anchor="middle" xml:space="preserve">off 24</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="430" y="465" text-anchor="middle" xml:space="preserve">len 5</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-num" d="M430 406 C430 367 413 367 413 328" marker-end="url(#jvl-num)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-key" x="476" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="482" y="420" xml:space="preserve">5</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-key" x="518" y="434" text-anchor="middle" xml:space="preserve">key</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="518" y="451" text-anchor="middle" xml:space="preserve">off 32</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="518" y="465" text-anchor="middle" xml:space="preserve">len 4</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-key" d="M518 406 C518 367 518 367 518 328" marker-end="url(#jvl-key)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="564" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="570" y="420" xml:space="preserve">6</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-struct" x="606" y="434" text-anchor="middle" xml:space="preserve">array</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="606" y="451" text-anchor="middle" xml:space="preserve">len 2</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="606" y="465" text-anchor="middle" xml:space="preserve">next 3</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-str" x="652" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="658" y="420" xml:space="preserve">7</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-str" x="694" y="434" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="694" y="451" text-anchor="middle" xml:space="preserve">off 41</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="694" y="465" text-anchor="middle" xml:space="preserve">len 2</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-str" d="M694 406 C694 367 630 367 630 328" marker-end="url(#jvl-str)"/>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="406" width="84" height="68" rx="5"/>
|
||||
<text class="nj-jsonview-tiny" x="746" y="420" xml:space="preserve">8</text>
|
||||
<text class="nj-jsonview-kind nj-jsonview-c-dec" x="782" y="434" text-anchor="middle" xml:space="preserve">string</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="782" y="451" text-anchor="middle" xml:space="preserve">escaped</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-xs" x="782" y="465" text-anchor="middle" xml:space="preserve">len 3</text>
|
||||
<text class="nj-jsonview-note" x="773" y="568" text-anchor="middle" xml:space="preserve">decoded strings</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-dec" x="740" y="518" width="66" height="30" rx="4"/>
|
||||
<text class="nj-jsonview-mono" x="751" y="538" text-anchor="middle" xml:space="preserve">a</text>
|
||||
<text class="nj-jsonview-mono" x="773" y="538" text-anchor="middle" xml:space="preserve">"</text>
|
||||
<text class="nj-jsonview-mono" x="795" y="538" text-anchor="middle" xml:space="preserve">b</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-dec" d="M782 474 C782 496 773 496 773 518" marker-end="url(#jvl-dec)"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="470" y="670" text-anchor="end" xml:space="preserve">json_view v = doc.root()["tags"]</text>
|
||||
<rect class="nj-jsonview-node nj-jsonview-c-struct" x="480" y="648" width="140" height="34" rx="6"/>
|
||||
<path class="nj-jsonview-sep" d="M550 648 V682"/>
|
||||
<text class="nj-jsonview-mono" x="515" y="670" text-anchor="middle" xml:space="preserve">doc*</text>
|
||||
<text class="nj-jsonview-mono" x="585" y="670" text-anchor="middle" xml:space="preserve">node*</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-struct" d="M515 648 L515 622" marker-end="url(#jvl-struct)"/>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-struct" d="M585 648 C585 561 606 561 606 474" marker-end="url(#jvl-struct)"/>
|
||||
<text class="nj-jsonview-note" x="30" y="524" xml:space="preserve">integers are converted while parsing and kept in their node;</text>
|
||||
<text class="nj-jsonview-note" x="30" y="542" xml:space="preserve">floats and strings point back into the text</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 21 KiB |
@@ -1,61 +0,0 @@
|
||||
<svg class="nj-fig nj-jsonview " viewBox="0 0 840 572" role="img" aria-labelledby="fig-jvt-title fig-jvt-title-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-jvt-title">When a json_view becomes invalid</title>
|
||||
<desc id="fig-jvt-title-d">Four timelines. First: a document borrows a std::string; when the string is destroyed, the document and every view taken from it dangle. Second: doc.read() re-parses the document; views taken before are invalid, a fresh view from root() is valid. Third: doc.shrink_to_fit() has the same effect. Fourth: moving the document does not invalidate its views; destroying the moved-to document does.</desc>
|
||||
<defs>
|
||||
<marker id="jvt-bad" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="6.5" markerHeight="6.5" orient="auto-start-reverse"><path class="nj-jsonview-c-bad nj-jsonview-head" d="M0 1 L10 5 L0 9 z"/></marker>
|
||||
</defs>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="210" y="12" width="34" height="12" rx="3"/>
|
||||
<text class="nj-jsonview-note" x="252" y="23" xml:space="preserve">alive / valid</text>
|
||||
<rect class="nj-jsonview-bad" x="370" y="12" width="34" height="12" rx="3"/>
|
||||
<text class="nj-jsonview-note" x="412" y="23" xml:space="preserve">dangling: using it is undefined behavior</text>
|
||||
<path class="nj-jsonview-arr nj-jsonview-c-line" d="M210 44 L820 44"/>
|
||||
<text class="nj-jsonview-tiny" x="820" y="38" text-anchor="end" xml:space="preserve">time →</text>
|
||||
<text class="nj-jsonview-h nj-jsonview-sm2" x="16" y="74" xml:space="preserve">The borrowed text is destroyed</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="99" text-anchor="end" xml:space="preserve">std::string text</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="210" y="87" width="260" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="127" text-anchor="end" xml:space="preserve">json_document doc</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="270" y="115" width="200" height="16" rx="3"/>
|
||||
<rect class="nj-jsonview-bad" x="470" y="115" width="350" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="155" text-anchor="end" xml:space="preserve">json_view v</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="330" y="143" width="140" height="16" rx="3"/>
|
||||
<rect class="nj-jsonview-bad" x="470" y="143" width="350" height="16" rx="3"/>
|
||||
<path class="nj-jsonview-evt" d="M470 82 V168"/>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="474" y="80" xml:space="preserve">text destroyed</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-onbad" x="476" y="155" xml:space="preserve">every view, and the document itself</text>
|
||||
<text class="nj-jsonview-h nj-jsonview-sm2" x="16" y="202" xml:space="preserve">The document is re-parsed</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="227" text-anchor="end" xml:space="preserve">json_document doc</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="210" y="215" width="610" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="255" text-anchor="end" xml:space="preserve">json_view v</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="270" y="243" width="200" height="16" rx="3"/>
|
||||
<rect class="nj-jsonview-bad" x="470" y="243" width="350" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="283" text-anchor="end" xml:space="preserve">v = doc.root()</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="530" y="271" width="290" height="16" rx="3"/>
|
||||
<path class="nj-jsonview-evt" d="M470 210 V296"/>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="474" y="208" xml:space="preserve">doc.read(other)</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-onbad" x="476" y="255" xml:space="preserve">views taken before</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-onok" x="536" y="283" xml:space="preserve">a fresh view is valid again</text>
|
||||
<text class="nj-jsonview-h nj-jsonview-sm2" x="16" y="330" xml:space="preserve">The document is shrunk</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="355" text-anchor="end" xml:space="preserve">json_document doc</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="210" y="343" width="610" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="383" text-anchor="end" xml:space="preserve">json_view v</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="270" y="371" width="200" height="16" rx="3"/>
|
||||
<rect class="nj-jsonview-bad" x="470" y="371" width="350" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="411" text-anchor="end" xml:space="preserve">v = doc.root()</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="530" y="399" width="290" height="16" rx="3"/>
|
||||
<path class="nj-jsonview-evt" d="M470 338 V424"/>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="474" y="336" xml:space="preserve">doc.shrink_to_fit()</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-onbad" x="476" y="383" xml:space="preserve">views taken before</text>
|
||||
<text class="nj-jsonview-note nj-jsonview-onok" x="536" y="411" xml:space="preserve">a fresh view is valid again</text>
|
||||
<text class="nj-jsonview-h nj-jsonview-sm2" x="16" y="458" xml:space="preserve">The document is moved, then destroyed</text>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="483" text-anchor="end" xml:space="preserve">json_document doc</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="210" y="471" width="210" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="511" text-anchor="end" xml:space="preserve">moved = std::move(doc)</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="420" y="499" width="260" height="16" rx="3"/>
|
||||
<text class="nj-jsonview-mono nj-jsonview-sm" x="198" y="539" text-anchor="end" xml:space="preserve">json_view v</text>
|
||||
<rect class="nj-jsonview-bar nj-jsonview-c-struct" x="270" y="527" width="410" height="16" rx="3"/>
|
||||
<rect class="nj-jsonview-bad" x="680" y="527" width="140" height="16" rx="3"/>
|
||||
<path class="nj-jsonview-evt nj-jsonview-evt--ok" d="M420 466 V552"/>
|
||||
<text class="nj-jsonview-tiny" x="424" y="464" xml:space="preserve">std::move: views stay valid</text>
|
||||
<path class="nj-jsonview-evt" d="M680 466 V552"/>
|
||||
<text class="nj-jsonview-tiny nj-jsonview-c-bad" x="684" y="464" xml:space="preserve">moved is destroyed</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 6.2 KiB |
@@ -1,20 +0,0 @@
|
||||
<svg class="nj-fig nj-fig--sax-mem" viewBox="0 0 660 312" role="img" aria-labelledby="fig-sax-mem-title fig-sax-mem-desc" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-sax-mem-title">Illustrative memory use over time while a large array of records is parsed, not a measurement.</title>
|
||||
<desc id="fig-sax-mem-desc">Four curves. D​OM, parse(): rises steadily until the whole tree is in memory. json_document: starts at about the size of the text, which it keeps, and grows a little while its index is built. Parser callback that discards every record: stays flat at the size of one record. S​AX: stays flat and lowest, because no value is built and only what the handler keeps is in memory.</desc>
|
||||
<path class="nj-sax-axis" d="M56 36 V272 H448"/>
|
||||
<text class="fg-h" x="16" y="24">memory</text>
|
||||
<text class="fg-note fg-note--l" x="56" y="294">time: records parsed</text>
|
||||
<text class="fg-note fg-note--r nj-sax-illus" x="648" y="24">illustrative, not a measurement</text>
|
||||
<path class="nj-sax-curve nj-sax-c-dom" d="M56 268 L440 52"/>
|
||||
<path class="nj-sax-curve nj-sax-c-doc" d="M56 168 L440 146"/>
|
||||
<path class="nj-sax-curve nj-sax-c-cb" d="M56 250 L88 238 L88 250 L120 238 L120 250 L152 238 L152 250 L184 238 L184 250 L216 238 L216 250 L248 238 L248 250 L280 238 L280 250 L312 238 L312 250 L344 238 L344 250 L376 238 L376 250 L408 238 L408 250 L440 238 L440 250"/>
|
||||
<path class="nj-sax-curve nj-sax-c-sax" d="M56 264 H440"/>
|
||||
<text class="nj-sax-lab nj-sax-c-dom" x="456" y="48">D​OM: parse()</text>
|
||||
<text class="fg-note fg-note--l" x="456" y="65">the whole tree</text>
|
||||
<text class="nj-sax-lab nj-sax-c-doc" x="456" y="142">json_document</text>
|
||||
<text class="fg-note fg-note--l" x="456" y="159">the text plus its index</text>
|
||||
<text class="nj-sax-lab nj-sax-c-cb" x="456" y="227">callback, discard</text>
|
||||
<text class="fg-note fg-note--l" x="456" y="244">one record at a time</text>
|
||||
<text class="nj-sax-lab nj-sax-c-sax" x="456" y="269">S​AX</text>
|
||||
<text class="fg-note fg-note--l" x="456" y="286">only what the handler keeps</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 2.0 KiB |
@@ -1,31 +0,0 @@
|
||||
<svg class="nj-fig nj-charts nj-charts--scaling" viewBox="0 0 440 238" role="img" aria-labelledby="nj-charts-sc nj-charts-sc-d" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-charts-sc">Time to parse a flat object of n keys, json against ordered_json, logarithmic axes</title>
|
||||
<desc id="nj-charts-sc-d">2000 keys: json 0.7 ms, ordered_json 3.6 ms (5x). 4000 keys: 0.8 ms and 14.0 ms (19x). 8000 keys: 1.6 ms and 67.8 ms (43x). 16000 keys: 3.3 ms and 181.6 ms (54x).</desc>
|
||||
<line class="nj-charts-grid" x1="66" y1="176.187" x2="330" y2="176.187"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="60" y="180.187">1 ms</text>
|
||||
<line class="nj-charts-grid" x1="66" y1="111.521" x2="330" y2="111.521"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="60" y="115.521">10 ms</text>
|
||||
<line class="nj-charts-grid" x1="66" y1="46.8538" x2="330" y2="46.8538"/>
|
||||
<text class="nj-charts-tick nj-charts-tick--r" x="60" y="50.8538">100 ms</text>
|
||||
<line class="nj-charts-axis" x1="66" y1="210" x2="330" y2="210"/>
|
||||
<text class="nj-charts-tick" x="66" y="226">2 000</text>
|
||||
<text class="nj-charts-tick" x="154" y="226">4 000</text>
|
||||
<text class="nj-charts-tick" x="242" y="226">8 000</text>
|
||||
<text class="nj-charts-tick" x="330" y="226">16 000</text>
|
||||
<polyline class="nj-charts-json" points="66,186.204 154,182.454 242,162.987 330,142.657"/>
|
||||
<circle class="nj-charts-json-dot" cx="66" cy="186.204" r="4.5"><title>json, 2000 keys: 0.7 ms</title></circle>
|
||||
<circle class="nj-charts-json-dot" cx="154" cy="182.454" r="4.5"><title>json, 4000 keys: 0.8 ms</title></circle>
|
||||
<circle class="nj-charts-json-dot" cx="242" cy="162.987" r="4.5"><title>json, 8000 keys: 1.6 ms</title></circle>
|
||||
<circle class="nj-charts-json-dot" cx="330" cy="142.657" r="4.5"><title>json, 16000 keys: 3.3 ms</title></circle>
|
||||
<text class="nj-charts-val nj-charts-name-json" x="340" y="140.657">json</text>
|
||||
<text class="nj-charts-val" x="340" y="155.657">3.3 ms</text>
|
||||
<text class="nj-charts-val" x="72" y="202.204">0.7 ms</text>
|
||||
<polyline class="nj-charts-ojson" points="66,140.213 154,102.071 242,57.7677 330,30.0977"/>
|
||||
<circle class="nj-charts-ojson-dot" cx="66" cy="140.213" r="4.5"><title>ordered_json, 2000 keys: 3.6 ms</title></circle>
|
||||
<circle class="nj-charts-ojson-dot" cx="154" cy="102.071" r="4.5"><title>ordered_json, 4000 keys: 14 ms</title></circle>
|
||||
<circle class="nj-charts-ojson-dot" cx="242" cy="57.7677" r="4.5"><title>ordered_json, 8000 keys: 67.8 ms</title></circle>
|
||||
<circle class="nj-charts-ojson-dot" cx="330" cy="30.0977" r="4.5"><title>ordered_json, 16000 keys: 181.6 ms</title></circle>
|
||||
<text class="nj-charts-val nj-charts-name-ojson" x="340" y="28.0977">ordered_json</text>
|
||||
<text class="nj-charts-val" x="340" y="43.0977">181.6 ms</text>
|
||||
<text class="nj-charts-val" x="72" y="160.213">3.6 ms</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 2.7 KiB |
@@ -1,240 +0,0 @@
|
||||
<svg class="nj-fig nj-exceptions-qa nj-exceptions-qa--wide" viewBox="0 0 760 808" role="img" aria-labelledby="nj-qa-title-w nj-qa-desc-w" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-qa-title-w">Quality assurance pipeline</title>
|
||||
<desc id="nj-qa-desc-w">Every push or pull request starts these checks in parallel: Build matrix (every push / PR): 50+ compilers: G​CC, Clang, M​SVC, AppleClang, Intel, NVIDIA, ... C++11, 14, 17, 20, 23, and 26 libc++ and libstdc++ warnings: Clang -Weverything, G​CC 300+ warnings; Unit tests (doctest) (every push / PR): every public A​PI function every exception id and message all Unicode code points single header and split headers custom number, string, array, and object types; Coverage (every push / PR): unit tests cover all lines of the code base; Static analysis (every push / PR, scheduled): Clang-Tidy, Cppcheck, Infer Clang Static Analyzer (52 checkers), I​WYU, Codacy CodeQL, Semgrep, Flawfinder (also scheduled); Dynamic analysis (every push / PR): runtime assertions Valgrind (Memcheck) address and undefined behavior sanitizers, integer overflow, nullability violations; Fuzzing (every PR, continuous): CIFuzz on every pull request OSS-Fuzz: billions of inputs every crash fixed with a reproducing unit test; Style (every push / PR): Artistic Style (astyle), enforced in the C​I cpplint with 61 rules; Docs and examples (every push / PR, scheduled): every documentation example is tested; changed output fails site built with warnings as errors; links checked regularly (scheduled); Integration, supply chain (every push / PR, scheduled): CMake 3.5, 3.31.6, and 4.0.0 Meson, Swift Package Manager dependency review on every PR Dependabot daily, OpenSSF Scorecard, R​EUSE. When they pass, the change is merged into develop; a release is made only when no vulnerability alert is open.</desc>
|
||||
<defs><marker id="nj-qa-arrow-w" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto"><path class="fg-head" d="M0 1 L10 5 L0 9 z"/></marker></defs>
|
||||
<rect class="nj-exceptions-groupbox" x="12" y="70" width="736" height="594" rx="12"/>
|
||||
<rect class="nj-exceptions-stage" x="265" y="8" width="230" height="34" rx="17"/>
|
||||
<text class="nj-exceptions-stagetext" x="380" y="30">push or pull request</text>
|
||||
<line class="nj-exceptions-edge" x1="380" y1="42" x2="380" y2="68" marker-end="url(#nj-qa-arrow-w)"/>
|
||||
<text class="nj-exceptions-group" x="26" y="94">checks, run in parallel on GitHub Actions and AppVeyor</text>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="110" width="228" height="184" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="135">Build matrix</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="146" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="160">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="188">50+ compilers: G​CC, Clang, M​SVC,</text>
|
||||
<text class="nj-exceptions-line" x="40" y="206">AppleClang, Intel, NVIDIA, ...</text>
|
||||
<text class="nj-exceptions-line" x="40" y="224">C++11, 14, 17, 20, 23, and 26</text>
|
||||
<text class="nj-exceptions-line" x="40" y="242">libc++ and libstdc++</text>
|
||||
<text class="nj-exceptions-line" x="40" y="260">warnings: Clang -Weverything,</text>
|
||||
<text class="nj-exceptions-line" x="40" y="278">G​CC 300+ warnings</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="266" y="110" width="228" height="184" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="280" y="135">Unit tests (doctest)</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="280" y="146" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="335.25" y="160">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="280" y="188">every public A​PI function</text>
|
||||
<text class="nj-exceptions-line" x="280" y="206">every exception id and message</text>
|
||||
<text class="nj-exceptions-line" x="280" y="224">all Unicode code points</text>
|
||||
<text class="nj-exceptions-line" x="280" y="242">single header and split headers</text>
|
||||
<text class="nj-exceptions-line" x="280" y="260">custom number, string, array,</text>
|
||||
<text class="nj-exceptions-line" x="280" y="278">and object types</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="506" y="110" width="228" height="184" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="520" y="135">Coverage</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="520" y="146" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="575.25" y="160">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="520" y="188">unit tests cover all lines</text>
|
||||
<text class="nj-exceptions-line" x="520" y="206">of the code base</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="306" width="228" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="331">Static analysis</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="342" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="356">every push / PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--sched" x="156.5" y="342" width="72.7" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--sched" x="192.85" y="356">scheduled</text>
|
||||
<text class="nj-exceptions-line" x="40" y="384">Clang-Tidy, Cppcheck, Infer</text>
|
||||
<text class="nj-exceptions-line" x="40" y="402">Clang Static Analyzer (52</text>
|
||||
<text class="nj-exceptions-line" x="40" y="420">checkers), I​WYU, Codacy</text>
|
||||
<text class="nj-exceptions-line" x="40" y="438">CodeQL, Semgrep, Flawfinder</text>
|
||||
<text class="nj-exceptions-line" x="40" y="456">(also scheduled)</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="266" y="306" width="228" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="280" y="331">Dynamic analysis</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="280" y="342" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="335.25" y="356">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="280" y="384">runtime assertions</text>
|
||||
<text class="nj-exceptions-line" x="280" y="402">Valgrind (Memcheck)</text>
|
||||
<text class="nj-exceptions-line" x="280" y="420">address and undefined behavior</text>
|
||||
<text class="nj-exceptions-line" x="280" y="438">sanitizers, integer overflow,</text>
|
||||
<text class="nj-exceptions-line" x="280" y="456">nullability violations</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="506" y="306" width="228" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="520" y="331">Fuzzing</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="520" y="342" width="66.4" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="553.2" y="356">every PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--cont" x="592.4" y="342" width="79" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--cont" x="631.9" y="356">continuous</text>
|
||||
<text class="nj-exceptions-line" x="520" y="384">CIFuzz on every pull request</text>
|
||||
<text class="nj-exceptions-line" x="520" y="402">OSS-Fuzz: billions of inputs</text>
|
||||
<text class="nj-exceptions-line" x="520" y="420">every crash fixed with a</text>
|
||||
<text class="nj-exceptions-line" x="520" y="438">reproducing unit test</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="484" width="228" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="509">Style</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="520" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="534">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="562">Artistic Style (astyle),</text>
|
||||
<text class="nj-exceptions-line" x="40" y="580">enforced in the C​I</text>
|
||||
<text class="nj-exceptions-line" x="40" y="598">cpplint with 61 rules</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="266" y="484" width="228" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="280" y="509">Docs and examples</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="280" y="520" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="335.25" y="534">every push / PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--sched" x="396.5" y="520" width="72.7" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--sched" x="432.85" y="534">scheduled</text>
|
||||
<text class="nj-exceptions-line" x="280" y="562">every documentation example is</text>
|
||||
<text class="nj-exceptions-line" x="280" y="580">tested; changed output fails</text>
|
||||
<text class="nj-exceptions-line" x="280" y="598">site built with warnings</text>
|
||||
<text class="nj-exceptions-line" x="280" y="616">as errors; links checked</text>
|
||||
<text class="nj-exceptions-line" x="280" y="634">regularly (scheduled)</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="506" y="484" width="228" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="520" y="509">Integration, supply chain</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="520" y="520" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="575.25" y="534">every push / PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--sched" x="636.5" y="520" width="72.7" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--sched" x="672.85" y="534">scheduled</text>
|
||||
<text class="nj-exceptions-line" x="520" y="562">CMake 3.5, 3.31.6, and 4.0.0</text>
|
||||
<text class="nj-exceptions-line" x="520" y="580">Meson, Swift Package Manager</text>
|
||||
<text class="nj-exceptions-line" x="520" y="598">dependency review on every PR</text>
|
||||
<text class="nj-exceptions-line" x="520" y="616">Dependabot daily, OpenSSF</text>
|
||||
<text class="nj-exceptions-line" x="520" y="634">Scorecard, R​EUSE</text>
|
||||
</g>
|
||||
<line class="nj-exceptions-edge" x1="380" y1="664" x2="380" y2="690" marker-end="url(#nj-qa-arrow-w)"/>
|
||||
<rect class="nj-exceptions-stage nj-exceptions-stage--merge" x="265" y="692" width="230" height="34" rx="17"/>
|
||||
<text class="nj-exceptions-stagetext" x="380" y="714">merge into develop</text>
|
||||
<line class="nj-exceptions-edge" x1="380" y1="726" x2="380" y2="752" marker-end="url(#nj-qa-arrow-w)"/>
|
||||
<rect class="nj-exceptions-stage nj-exceptions-stage--merge" x="230" y="754" width="300" height="46" rx="23"/>
|
||||
<text class="nj-exceptions-stagetext" x="380" y="776">release</text>
|
||||
<text class="nj-exceptions-stagesub" x="380" y="792">no open vulnerability alert</text>
|
||||
</svg>
|
||||
<svg class="nj-fig nj-exceptions-qa nj-exceptions-qa--narrow" viewBox="0 0 360 1786" role="img" aria-labelledby="nj-qa-title-n nj-qa-desc-n" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-qa-title-n">Quality assurance pipeline</title>
|
||||
<desc id="nj-qa-desc-n">Every push or pull request starts these checks in parallel: Build matrix (every push / PR): 50+ compilers: G​CC, Clang, M​SVC, AppleClang, Intel, NVIDIA, ... C++11, 14, 17, 20, 23, and 26 libc++ and libstdc++ warnings: Clang -Weverything, G​CC 300+ warnings; Unit tests (doctest) (every push / PR): every public A​PI function every exception id and message all Unicode code points single header and split headers custom number, string, array, and object types; Coverage (every push / PR): unit tests cover all lines of the code base; Static analysis (every push / PR, scheduled): Clang-Tidy, Cppcheck, Infer Clang Static Analyzer (52 checkers), I​WYU, Codacy CodeQL, Semgrep, Flawfinder (also scheduled); Dynamic analysis (every push / PR): runtime assertions Valgrind (Memcheck) address and undefined behavior sanitizers, integer overflow, nullability violations; Fuzzing (every PR, continuous): CIFuzz on every pull request OSS-Fuzz: billions of inputs every crash fixed with a reproducing unit test; Style (every push / PR): Artistic Style (astyle), enforced in the C​I cpplint with 61 rules; Docs and examples (every push / PR, scheduled): every documentation example is tested; changed output fails site built with warnings as errors; links checked regularly (scheduled); Integration, supply chain (every push / PR, scheduled): CMake 3.5, 3.31.6, and 4.0.0 Meson, Swift Package Manager dependency review on every PR Dependabot daily, OpenSSF Scorecard, R​EUSE. When they pass, the change is merged into develop; a release is made only when no vulnerability alert is open.</desc>
|
||||
<defs><marker id="nj-qa-arrow-n" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto"><path class="fg-head" d="M0 1 L10 5 L0 9 z"/></marker></defs>
|
||||
<rect class="nj-exceptions-groupbox" x="12" y="70" width="336" height="1572" rx="12"/>
|
||||
<rect class="nj-exceptions-stage" x="65" y="8" width="230" height="34" rx="17"/>
|
||||
<text class="nj-exceptions-stagetext" x="180" y="30">push or pull request</text>
|
||||
<line class="nj-exceptions-edge" x1="180" y1="42" x2="180" y2="68" marker-end="url(#nj-qa-arrow-n)"/>
|
||||
<text class="nj-exceptions-group" x="26" y="94">checks, run in parallel</text>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="110" width="308" height="184" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="135">Build matrix</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="146" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="160">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="188">50+ compilers: G​CC, Clang, M​SVC,</text>
|
||||
<text class="nj-exceptions-line" x="40" y="206">AppleClang, Intel, NVIDIA, ...</text>
|
||||
<text class="nj-exceptions-line" x="40" y="224">C++11, 14, 17, 20, 23, and 26</text>
|
||||
<text class="nj-exceptions-line" x="40" y="242">libc++ and libstdc++</text>
|
||||
<text class="nj-exceptions-line" x="40" y="260">warnings: Clang -Weverything,</text>
|
||||
<text class="nj-exceptions-line" x="40" y="278">G​CC 300+ warnings</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="306" width="308" height="184" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="331">Unit tests (doctest)</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="342" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="356">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="384">every public A​PI function</text>
|
||||
<text class="nj-exceptions-line" x="40" y="402">every exception id and message</text>
|
||||
<text class="nj-exceptions-line" x="40" y="420">all Unicode code points</text>
|
||||
<text class="nj-exceptions-line" x="40" y="438">single header and split headers</text>
|
||||
<text class="nj-exceptions-line" x="40" y="456">custom number, string, array,</text>
|
||||
<text class="nj-exceptions-line" x="40" y="474">and object types</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="502" width="308" height="112" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="527">Coverage</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="538" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="552">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="580">unit tests cover all lines</text>
|
||||
<text class="nj-exceptions-line" x="40" y="598">of the code base</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="626" width="308" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="651">Static analysis</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="662" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="676">every push / PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--sched" x="156.5" y="662" width="72.7" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--sched" x="192.85" y="676">scheduled</text>
|
||||
<text class="nj-exceptions-line" x="40" y="704">Clang-Tidy, Cppcheck, Infer</text>
|
||||
<text class="nj-exceptions-line" x="40" y="722">Clang Static Analyzer (52</text>
|
||||
<text class="nj-exceptions-line" x="40" y="740">checkers), I​WYU, Codacy</text>
|
||||
<text class="nj-exceptions-line" x="40" y="758">CodeQL, Semgrep, Flawfinder</text>
|
||||
<text class="nj-exceptions-line" x="40" y="776">(also scheduled)</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="804" width="308" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="829">Dynamic analysis</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="840" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="854">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="882">runtime assertions</text>
|
||||
<text class="nj-exceptions-line" x="40" y="900">Valgrind (Memcheck)</text>
|
||||
<text class="nj-exceptions-line" x="40" y="918">address and undefined behavior</text>
|
||||
<text class="nj-exceptions-line" x="40" y="936">sanitizers, integer overflow,</text>
|
||||
<text class="nj-exceptions-line" x="40" y="954">nullability violations</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="982" width="308" height="148" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="1007">Fuzzing</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="1018" width="66.4" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="73.2" y="1032">every PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--cont" x="112.4" y="1018" width="79" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--cont" x="151.9" y="1032">continuous</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1060">CIFuzz on every pull request</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1078">OSS-Fuzz: billions of inputs</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1096">every crash fixed with a</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1114">reproducing unit test</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="1142" width="308" height="130" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="1167">Style</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="1178" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="1192">every push / PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1220">Artistic Style (astyle),</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1238">enforced in the C​I</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1256">cpplint with 61 rules</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="1284" width="308" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="1309">Docs and examples</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="1320" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="1334">every push / PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--sched" x="156.5" y="1320" width="72.7" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--sched" x="192.85" y="1334">scheduled</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1362">every documentation example is</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1380">tested; changed output fails</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1398">site built with warnings</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1416">as errors; links checked</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1434">regularly (scheduled)</text>
|
||||
</g>
|
||||
<g class="nj-exceptions-card">
|
||||
<rect class="nj-exceptions-box" x="26" y="1462" width="308" height="166" rx="8"/>
|
||||
<text class="nj-exceptions-ctitle" x="40" y="1487">Integration, supply chain</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--push" x="40" y="1498" width="110.5" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--push" x="95.25" y="1512">every push / PR</text>
|
||||
<rect class="nj-exceptions-badge nj-exceptions-badge--sched" x="156.5" y="1498" width="72.7" height="20" rx="10"/>
|
||||
<text class="nj-exceptions-badgetext nj-exceptions-badgetext--sched" x="192.85" y="1512">scheduled</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1540">CMake 3.5, 3.31.6, and 4.0.0</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1558">Meson, Swift Package Manager</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1576">dependency review on every PR</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1594">Dependabot daily, OpenSSF</text>
|
||||
<text class="nj-exceptions-line" x="40" y="1612">Scorecard, R​EUSE</text>
|
||||
</g>
|
||||
<line class="nj-exceptions-edge" x1="180" y1="1642" x2="180" y2="1668" marker-end="url(#nj-qa-arrow-n)"/>
|
||||
<rect class="nj-exceptions-stage nj-exceptions-stage--merge" x="65" y="1670" width="230" height="34" rx="17"/>
|
||||
<text class="nj-exceptions-stagetext" x="180" y="1692">merge into develop</text>
|
||||
<line class="nj-exceptions-edge" x1="180" y1="1704" x2="180" y2="1730" marker-end="url(#nj-qa-arrow-n)"/>
|
||||
<rect class="nj-exceptions-stage nj-exceptions-stage--merge" x="30" y="1732" width="300" height="46" rx="23"/>
|
||||
<text class="nj-exceptions-stagetext" x="180" y="1754">release</text>
|
||||
<text class="nj-exceptions-stagesub" x="180" y="1770">no open vulnerability alert</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 22 KiB |
@@ -1,28 +1,447 @@
|
||||
<svg class="nj-fig nj-fig--range" viewBox="0 0 600 150" role="img" aria-labelledby="fig-be-title" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="fig-be-title">A row of fifteen elements followed by a dashed past-the-last position. begin() points to the first element and end() points to the past-the-last position.</title>
|
||||
<defs><marker id="fig-be-arrow" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto"><path class="fg-head" d="M0 1 L10 5 L0 9 z"/></marker></defs>
|
||||
<rect class="fg-cell" x="30" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="64" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="98" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="132" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="166" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="200" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="234" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="268" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="302" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="336" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="370" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="404" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="438" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="472" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell" x="506" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-cell fg-cell--end" x="540" y="62" width="30" height="30" rx="5"/>
|
||||
<rect class="fg-pill" x="15" y="8" width="60" height="24" rx="6"/>
|
||||
<text class="fg-pilltext" x="45" y="24">begin</text>
|
||||
<line class="fg-arrow" x1="45" y1="32" x2="45" y2="60" marker-end="url(#fig-be-arrow)"/>
|
||||
<rect class="fg-pill" x="531" y="8" width="48" height="24" rx="6"/>
|
||||
<text class="fg-pilltext" x="555" y="24">end</text>
|
||||
<line class="fg-arrow" x1="555" y1="32" x2="555" y2="60" marker-end="url(#fig-be-arrow)"/>
|
||||
<text class="fg-note fg-note--r" x="537" y="132">Past-the-last element</text>
|
||||
<line class="fg-arrow" x1="555" y1="124" x2="555" y2="96" marker-end="url(#fig-be-arrow)"/>
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="545.89282"
|
||||
height="156.9409"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.4 r9939"
|
||||
sodipodi:docname="range-begin-end.svg">
|
||||
<style type="text/css">
|
||||
@media (prefers-color-scheme: dark) {
|
||||
[style*="stroke:#000000"] { stroke: #e6e6e6 !important; }
|
||||
[style*="fill:#000000"] { fill: #e6e6e6 !important; }
|
||||
[style*="fill:#ffffff"] { fill: #1e1e1e !important; }
|
||||
[style*="fill:#0000ff"] { fill: #7aa2ff !important; }
|
||||
marker path { fill: #e6e6e6 !important; stroke: #e6e6e6 !important; }
|
||||
stop[style*="#c1b1b1"] { stop-color: #5a5a5a !important; }
|
||||
stop[style*="#b6b6b6"] { stop-color: #4a4a4a !important; }
|
||||
stop[style*="#e3e3e3"] { stop-color: #2a2a2a !important; }
|
||||
}
|
||||
</style>
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path6525"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt"
|
||||
transform="matrix(-0.4,0,0,-0.4,-4,0)"
|
||||
inkscape:connector-curvature="0" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path6519"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt"
|
||||
transform="matrix(-0.8,0,0,-0.8,-10,0)"
|
||||
inkscape:connector-curvature="0" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
id="linearGradient5488">
|
||||
<stop
|
||||
style="stop-color:#c1b1b1;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5490" />
|
||||
<stop
|
||||
style="stop-color:#e3e3e3;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5492" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient4040">
|
||||
<stop
|
||||
style="stop-color:#b6b6b6;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop4042" />
|
||||
<stop
|
||||
style="stop-color:#e3e3e3;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop4044" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5488"
|
||||
id="linearGradient6284"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
x1="81"
|
||||
y1="1001.3622"
|
||||
x2="81"
|
||||
y2="971.36218" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5488-2"
|
||||
id="linearGradient6284-3"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
x1="81"
|
||||
y1="1001.3622"
|
||||
x2="81"
|
||||
y2="971.36218" />
|
||||
<linearGradient
|
||||
id="linearGradient5488-2">
|
||||
<stop
|
||||
style="stop-color:#c1b1b1;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5490-5" />
|
||||
<stop
|
||||
style="stop-color:#e3e3e3;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5492-8" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5488-0"
|
||||
id="linearGradient6284-5"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
x1="81"
|
||||
y1="1001.3622"
|
||||
x2="81"
|
||||
y2="971.36218" />
|
||||
<linearGradient
|
||||
id="linearGradient5488-0">
|
||||
<stop
|
||||
style="stop-color:#c1b1b1;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5490-1" />
|
||||
<stop
|
||||
style="stop-color:#e3e3e3;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5492-3" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1Mend-8"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6525-3"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt"
|
||||
transform="matrix(-0.4,0,0,-0.4,-4,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5488"
|
||||
id="linearGradient9026"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
x1="81"
|
||||
y1="1001.3622"
|
||||
x2="81"
|
||||
y2="971.36218" />
|
||||
</defs>
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="1.4"
|
||||
inkscape:cx="332.80082"
|
||||
inkscape:cy="165.04542"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1680"
|
||||
inkscape:window-height="993"
|
||||
inkscape:window-x="0"
|
||||
inkscape:window-y="34"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:snap-bbox="true"
|
||||
inkscape:object-nodes="true"
|
||||
inkscape:snap-smooth-nodes="false"
|
||||
inkscape:bbox-nodes="false"
|
||||
inkscape:snap-bbox-edge-midpoints="false"
|
||||
inkscape:object-paths="true"
|
||||
fit-margin-top="10"
|
||||
fit-margin-right="10"
|
||||
fit-margin-bottom="10"
|
||||
fit-margin-left="10" />
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title />
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(-26.107143,-893.4807)">
|
||||
<g
|
||||
id="g7184">
|
||||
<path
|
||||
inkscape:tile-y0="219"
|
||||
inkscape:tile-x0="51"
|
||||
inkscape:tile-h="30.00002"
|
||||
inkscape:tile-w="29.999997"
|
||||
inkscape:tile-cy="234.00001"
|
||||
inkscape:tile-cx="65.999998"
|
||||
sodipodi:nodetypes="ccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path3006"
|
||||
d="m 80.999997,1001.3622 -29.999997,0 0,-30.00002 29.999997,0 z"
|
||||
style="fill:url(#linearGradient9026);fill-opacity:1;stroke:#000000;stroke-width:2;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
|
||||
<use
|
||||
height="300"
|
||||
width="600"
|
||||
style="fill:none"
|
||||
id="use4010"
|
||||
transform="translate(29.999997,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0" />
|
||||
<use
|
||||
id="use4012"
|
||||
transform="translate(59.999994,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4014"
|
||||
transform="translate(89.999991,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4016"
|
||||
transform="translate(119.99999,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4018"
|
||||
transform="translate(149.99998,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4020"
|
||||
transform="translate(179.99998,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4022"
|
||||
transform="translate(209.99998,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4024"
|
||||
transform="translate(239.99998,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4026"
|
||||
transform="translate(269.99997,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4028"
|
||||
transform="translate(299.99997,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4030"
|
||||
transform="translate(329.99997,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4032"
|
||||
transform="translate(359.99996,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4034"
|
||||
transform="translate(389.99996,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4036"
|
||||
transform="translate(419.99996,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<use
|
||||
id="use4038"
|
||||
transform="translate(449.99995,0)"
|
||||
xlink:href="#path3006"
|
||||
inkscape:tiled-clone-of="#path3006"
|
||||
y="0"
|
||||
x="0"
|
||||
width="600"
|
||||
height="300" />
|
||||
<path
|
||||
inkscape:tile-y0="219"
|
||||
inkscape:tile-x0="51"
|
||||
inkscape:tile-h="30.00002"
|
||||
inkscape:tile-w="29.999997"
|
||||
inkscape:tile-cy="234.00001"
|
||||
inkscape:tile-cx="65.999998"
|
||||
sodipodi:nodetypes="ccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path3006-3"
|
||||
d="m 560.99995,1001.3622 -30,0 0,-30.00002 30,0 z"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2, 2;stroke-dashoffset:0;marker-start:none" />
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:10px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;line-height:55.00000119%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;fill:#000000;fill-opacity:1;stroke:none;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
|
||||
x="392.94931"
|
||||
y="1040.2404"
|
||||
id="text6504"
|
||||
sodipodi:linespacing="55.000001%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6506"
|
||||
x="392.94931"
|
||||
y="1040.2404"
|
||||
rotate="0 0 0 0 0 0 0 0 0.50000191 0 0 0 0 0 0 0 0 0 0 0 0 0"
|
||||
dy="0"
|
||||
dx="0"
|
||||
style="font-size:12.80000019px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:DejaVu Sans;-inkscape-font-specification:DejaVu Sans">Past-the-last element</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-end:url(#Arrow1Mend)"
|
||||
d="m 531.84531,279.29187 c 14.75083,-11.1311 12.86656,-14.42379 15.15229,-29.29442"
|
||||
id="path6510"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,752.36218)"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<g
|
||||
id="g7203"
|
||||
transform="translate(-40,-18.482143)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:1;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 128.39286,947.36218 -51.785717,0 0,-21.51786 51.785717,0 z"
|
||||
id="use6288-9"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccccc"
|
||||
inkscape:tile-x0="51"
|
||||
inkscape:tile-y0="219" />
|
||||
<text
|
||||
transform="translate(0,752.36218)"
|
||||
sodipodi:linespacing="55.000001%"
|
||||
id="text7176"
|
||||
y="189.10715"
|
||||
x="80.535713"
|
||||
style="font-size:15px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;line-height:55.00000119%;letter-spacing:0px;word-spacing:0px;fill:#0000ff;fill-opacity:1;stroke:none;font-family:DejaVu Sans;-inkscape-font-specification:DejaVu Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="189.10715"
|
||||
x="80.535713"
|
||||
id="tspan7178"
|
||||
sodipodi:role="line">begin</tspan></text>
|
||||
</g>
|
||||
<g
|
||||
id="g7238"
|
||||
transform="translate(20.035895,11.306019)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:1;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 538.39286,914.19254 -37.50001,0 0,-21.51786 37.50001,0 z"
|
||||
id="use6288-9-7"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccccc"
|
||||
inkscape:tile-x0="51"
|
||||
inkscape:tile-y0="219" />
|
||||
<text
|
||||
sodipodi:linespacing="55.000001%"
|
||||
id="text7176-3"
|
||||
y="908.29968"
|
||||
x="504.82141"
|
||||
style="font-size:15px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;line-height:55.00000119%;letter-spacing:0px;word-spacing:0px;fill:#0000ff;fill-opacity:1;stroke:none;font-family:DejaVu Sans;-inkscape-font-specification:DejaVu Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="908.29968"
|
||||
x="504.82141"
|
||||
id="tspan7178-7"
|
||||
sodipodi:role="line">end</tspan></text>
|
||||
</g>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-mid:none;marker-end:url(#Arrow1Mend)"
|
||||
d="M 60.16588,176.51786 C 64.809921,191.17027 67.41717,201.02245 68.196339,219"
|
||||
id="path7243"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,752.36218)"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-mid:none;marker-end:url(#Arrow1Mend)"
|
||||
d="m 540.40821,925.49856 c 2.63474,15.08647 5.72454,31.23577 6.06617,45.86362"
|
||||
id="path7243-8"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
</g>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 14 KiB |
|
Before Width: | Height: | Size: 4.3 KiB After Width: | Height: | Size: 41 KiB |
@@ -1,109 +0,0 @@
|
||||
<svg class="nj-fig nj-fig--timeline" viewBox="0 0 880 147" role="img" aria-labelledby="nj-int-tl-title" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-int-tl-title">Timeline of the 44 releases from v1.0.0 (2015-12-28) to v3.12.0 (2025-04-11): 17 minor or major releases, drawn as filled dots with their version above the axis, and 27 patch releases, drawn as rings.</title>
|
||||
<line class="nj-int-grid" x1="24.0" y1="61" x2="24.0" y2="85"/>
|
||||
<text class="nj-int-year" x="61.5" y="101">2015</text>
|
||||
<line class="nj-int-grid" x1="99.6" y1="61" x2="99.6" y2="85"/>
|
||||
<text class="nj-int-year" x="137.3" y="101">2016</text>
|
||||
<line class="nj-int-grid" x1="175.4" y1="61" x2="175.4" y2="85"/>
|
||||
<text class="nj-int-year" x="212.8" y="101">2017</text>
|
||||
<line class="nj-int-grid" x1="250.9" y1="61" x2="250.9" y2="85"/>
|
||||
<text class="nj-int-year" x="288.4" y="101">2018</text>
|
||||
<line class="nj-int-grid" x1="326.5" y1="61" x2="326.5" y2="85"/>
|
||||
<text class="nj-int-year" x="364.0" y="101">2019</text>
|
||||
<line class="nj-int-grid" x1="402.1" y1="61" x2="402.1" y2="85"/>
|
||||
<text class="nj-int-year" x="439.8" y="101">2020</text>
|
||||
<line class="nj-int-grid" x1="477.9" y1="61" x2="477.9" y2="85"/>
|
||||
<text class="nj-int-year" x="515.4" y="101">2021</text>
|
||||
<line class="nj-int-grid" x1="553.5" y1="61" x2="553.5" y2="85"/>
|
||||
<text class="nj-int-year" x="591.0" y="101">2022</text>
|
||||
<line class="nj-int-grid" x1="629.1" y1="61" x2="629.1" y2="85"/>
|
||||
<text class="nj-int-year" x="666.5" y="101">2023</text>
|
||||
<line class="nj-int-grid" x1="704.6" y1="61" x2="704.6" y2="85"/>
|
||||
<text class="nj-int-year" x="742.3" y="101">2024</text>
|
||||
<line class="nj-int-grid" x1="780.4" y1="61" x2="780.4" y2="85"/>
|
||||
<text class="nj-int-year" x="817.9" y="101">2025</text>
|
||||
<line class="nj-int-grid" x1="856.0" y1="61" x2="856.0" y2="85"/>
|
||||
<line class="nj-int-axis" x1="24" y1="77" x2="856" y2="77"/>
|
||||
<path class="nj-int-axis" fill="none" d="M98.8 114 V119 H104.3 V114"/>
|
||||
<text class="nj-int-major" x="98.8" y="136" text-anchor="start">1.x</text>
|
||||
<path class="nj-int-axis" fill="none" d="M135.8 114 V119 H186.8 V114"/>
|
||||
<text class="nj-int-major" x="161.3" y="136" text-anchor="middle">2.x</text>
|
||||
<path class="nj-int-axis" fill="none" d="M247.8 114 V119 H801.1 V114"/>
|
||||
<text class="nj-int-major" x="524.5" y="136" text-anchor="middle">3.x</text>
|
||||
<line class="nj-int-leader" x1="98.8" y1="68" x2="98.8" y2="70"/>
|
||||
<text class="nj-int-label" x="98.8" y="65">1.0</text>
|
||||
<line class="nj-int-leader" x1="104.3" y1="51" x2="104.3" y2="70"/>
|
||||
<text class="nj-int-label" x="104.3" y="48">1.1</text>
|
||||
<line class="nj-int-leader" x1="135.8" y1="68" x2="135.8" y2="70"/>
|
||||
<text class="nj-int-label" x="135.8" y="65">2.0</text>
|
||||
<line class="nj-int-leader" x1="181.0" y1="68" x2="181.0" y2="70"/>
|
||||
<text class="nj-int-label" x="181.0" y="65">2.1</text>
|
||||
<line class="nj-int-leader" x1="247.8" y1="68" x2="247.8" y2="70"/>
|
||||
<text class="nj-int-label" x="247.8" y="65">3.0</text>
|
||||
<line class="nj-int-leader" x1="257.4" y1="51" x2="257.4" y2="70"/>
|
||||
<text class="nj-int-label" x="257.4" y="48">3.1</text>
|
||||
<line class="nj-int-leader" x1="298.8" y1="68" x2="298.8" y2="70"/>
|
||||
<text class="nj-int-label" x="298.8" y="65">3.2</text>
|
||||
<line class="nj-int-leader" x1="308.3" y1="51" x2="308.3" y2="70"/>
|
||||
<text class="nj-int-label" x="308.3" y="48">3.3</text>
|
||||
<line class="nj-int-leader" x1="313.5" y1="34" x2="313.5" y2="70"/>
|
||||
<text class="nj-int-label" x="313.5" y="31">3.4</text>
|
||||
<line class="nj-int-leader" x1="324.5" y1="68" x2="324.5" y2="70"/>
|
||||
<text class="nj-int-label" x="324.5" y="65">3.5</text>
|
||||
<line class="nj-int-leader" x1="342.7" y1="51" x2="342.7" y2="70"/>
|
||||
<text class="nj-int-label" x="342.7" y="48">3.6</text>
|
||||
<line class="nj-int-leader" x1="369.6" y1="68" x2="369.6" y2="70"/>
|
||||
<text class="nj-int-label" x="369.6" y="65">3.7</text>
|
||||
<line class="nj-int-leader" x1="436.3" y1="68" x2="436.3" y2="70"/>
|
||||
<text class="nj-int-label" x="436.3" y="65">3.8</text>
|
||||
<line class="nj-int-leader" x1="445.2" y1="51" x2="445.2" y2="70"/>
|
||||
<text class="nj-int-label" x="445.2" y="48">3.9</text>
|
||||
<line class="nj-int-leader" x1="525.1" y1="68" x2="525.1" y2="70"/>
|
||||
<text class="nj-int-label" x="525.1" y="65">3.10</text>
|
||||
<line class="nj-int-leader" x1="597.4" y1="68" x2="597.4" y2="70"/>
|
||||
<text class="nj-int-label" x="597.4" y="65">3.11</text>
|
||||
<line class="nj-int-leader" x1="801.1" y1="68" x2="801.1" y2="70"/>
|
||||
<text class="nj-int-label" x="801.1" y="65">3.12</text>
|
||||
<g><title>v2.0.1 released 2016-06-28</title><circle class="nj-int-hit" cx="136.6" cy="77" r="9"/><circle class="nj-int-patch" cx="136.6" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.2 released 2016-07-31</title><circle class="nj-int-hit" cx="143.5" cy="77" r="9"/><circle class="nj-int-patch" cx="143.5" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.3 released 2016-08-31</title><circle class="nj-int-hit" cx="149.9" cy="77" r="9"/><circle class="nj-int-patch" cx="149.9" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.4 released 2016-09-11</title><circle class="nj-int-hit" cx="152.2" cy="77" r="9"/><circle class="nj-int-patch" cx="152.2" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.5 released 2016-09-14</title><circle class="nj-int-hit" cx="152.8" cy="77" r="9"/><circle class="nj-int-patch" cx="152.8" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.6 released 2016-10-15</title><circle class="nj-int-hit" cx="159.2" cy="77" r="9"/><circle class="nj-int-patch" cx="159.2" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.7 released 2016-11-02</title><circle class="nj-int-hit" cx="162.9" cy="77" r="9"/><circle class="nj-int-patch" cx="162.9" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.8 released 2016-12-02</title><circle class="nj-int-hit" cx="169.2" cy="77" r="9"/><circle class="nj-int-patch" cx="169.2" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.9 released 2016-12-16</title><circle class="nj-int-hit" cx="172.1" cy="77" r="9"/><circle class="nj-int-patch" cx="172.1" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.0.10 released 2017-01-02</title><circle class="nj-int-hit" cx="175.6" cy="77" r="9"/><circle class="nj-int-patch" cx="175.6" cy="77" r="3.5"/></g>
|
||||
<g><title>v2.1.1 released 2017-02-25</title><circle class="nj-int-hit" cx="186.8" cy="77" r="9"/><circle class="nj-int-patch" cx="186.8" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.0.1 released 2017-12-29</title><circle class="nj-int-hit" cx="250.3" cy="77" r="9"/><circle class="nj-int-patch" cx="250.3" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.1.1 released 2018-02-13</title><circle class="nj-int-hit" cx="259.9" cy="77" r="9"/><circle class="nj-int-patch" cx="259.9" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.1.2 released 2018-03-14</title><circle class="nj-int-hit" cx="265.9" cy="77" r="9"/><circle class="nj-int-patch" cx="265.9" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.7.1 released 2019-11-06</title><circle class="nj-int-hit" cx="390.5" cy="77" r="9"/><circle class="nj-int-patch" cx="390.5" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.7.2 released 2019-11-10</title><circle class="nj-int-hit" cx="391.3" cy="77" r="9"/><circle class="nj-int-patch" cx="391.3" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.7.3 released 2019-11-17</title><circle class="nj-int-hit" cx="392.8" cy="77" r="9"/><circle class="nj-int-patch" cx="392.8" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.9.1 released 2020-08-06</title><circle class="nj-int-hit" cx="447.2" cy="77" r="9"/><circle class="nj-int-patch" cx="447.2" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.10.1 released 2021-08-24</title><circle class="nj-int-hit" cx="526.6" cy="77" r="9"/><circle class="nj-int-patch" cx="526.6" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.10.2 released 2021-08-26</title><circle class="nj-int-hit" cx="527.0" cy="77" r="9"/><circle class="nj-int-patch" cx="527.0" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.10.3 released 2021-10-08</title><circle class="nj-int-hit" cx="535.9" cy="77" r="9"/><circle class="nj-int-patch" cx="535.9" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.10.4 released 2021-10-16</title><circle class="nj-int-hit" cx="537.5" cy="77" r="9"/><circle class="nj-int-patch" cx="537.5" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.10.5 released 2022-01-03</title><circle class="nj-int-hit" cx="553.9" cy="77" r="9"/><circle class="nj-int-patch" cx="553.9" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.11.2 released 2022-08-12</title><circle class="nj-int-hit" cx="599.6" cy="77" r="9"/><circle class="nj-int-patch" cx="599.6" cy="77" r="3.5"/></g>
|
||||
<g><title>v3.11.3 released 2023-11-28</title><circle class="nj-int-hit" cx="697.6" cy="77" r="9"/><circle class="nj-int-patch" cx="697.6" cy="77" r="3.5"/></g>
|
||||
<g><title>v1.0.0 released 2015-12-28</title><circle class="nj-int-hit" cx="98.8" cy="77" r="9"/><circle class="nj-int-minor" cx="98.8" cy="77" r="6"/></g>
|
||||
<g><title>v1.1.0 released 2016-01-24</title><circle class="nj-int-hit" cx="104.3" cy="77" r="9"/><circle class="nj-int-minor" cx="104.3" cy="77" r="6"/></g>
|
||||
<g><title>v2.0.0 released 2016-06-24</title><circle class="nj-int-hit" cx="135.8" cy="77" r="9"/><circle class="nj-int-minor" cx="135.8" cy="77" r="6"/></g>
|
||||
<g><title>v2.1.0 released 2017-01-28</title><circle class="nj-int-hit" cx="181.0" cy="77" r="9"/><circle class="nj-int-minor" cx="181.0" cy="77" r="6"/></g>
|
||||
<g><title>v3.0.0 released 2017-12-17</title><circle class="nj-int-hit" cx="247.8" cy="77" r="9"/><circle class="nj-int-minor" cx="247.8" cy="77" r="6"/></g>
|
||||
<g><title>v3.1.0 released 2018-02-01</title><circle class="nj-int-hit" cx="257.4" cy="77" r="9"/><circle class="nj-int-minor" cx="257.4" cy="77" r="6"/></g>
|
||||
<g><title>v3.2.0 released 2018-08-20</title><circle class="nj-int-hit" cx="298.8" cy="77" r="9"/><circle class="nj-int-minor" cx="298.8" cy="77" r="6"/></g>
|
||||
<g><title>v3.3.0 released 2018-10-05</title><circle class="nj-int-hit" cx="308.3" cy="77" r="9"/><circle class="nj-int-minor" cx="308.3" cy="77" r="6"/></g>
|
||||
<g><title>v3.4.0 released 2018-10-30</title><circle class="nj-int-hit" cx="313.5" cy="77" r="9"/><circle class="nj-int-minor" cx="313.5" cy="77" r="6"/></g>
|
||||
<g><title>v3.5.0 released 2018-12-22</title><circle class="nj-int-hit" cx="324.5" cy="77" r="9"/><circle class="nj-int-minor" cx="324.5" cy="77" r="6"/></g>
|
||||
<g><title>v3.6.0, v3.6.1 released 2019-03-20</title><circle class="nj-int-hit" cx="342.7" cy="77" r="9"/><circle class="nj-int-minor" cx="342.7" cy="77" r="6"/></g>
|
||||
<g><title>v3.7.0 released 2019-07-28</title><circle class="nj-int-hit" cx="369.6" cy="77" r="9"/><circle class="nj-int-minor" cx="369.6" cy="77" r="6"/></g>
|
||||
<g><title>v3.8.0 released 2020-06-14</title><circle class="nj-int-hit" cx="436.3" cy="77" r="9"/><circle class="nj-int-minor" cx="436.3" cy="77" r="6"/></g>
|
||||
<g><title>v3.9.0 released 2020-07-27</title><circle class="nj-int-hit" cx="445.2" cy="77" r="9"/><circle class="nj-int-minor" cx="445.2" cy="77" r="6"/></g>
|
||||
<g><title>v3.10.0 released 2021-08-17</title><circle class="nj-int-hit" cx="525.1" cy="77" r="9"/><circle class="nj-int-minor" cx="525.1" cy="77" r="6"/></g>
|
||||
<g><title>v3.11.0, v3.11.1 released 2022-08-01</title><circle class="nj-int-hit" cx="597.4" cy="77" r="9"/><circle class="nj-int-minor" cx="597.4" cy="77" r="6"/></g>
|
||||
<g><title>v3.12.0 released 2025-04-11</title><circle class="nj-int-hit" cx="801.1" cy="77" r="9"/><circle class="nj-int-minor" cx="801.1" cy="77" r="6"/></g>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 11 KiB |
@@ -1,98 +0,0 @@
|
||||
<svg class="nj-fig nj-fig--lanes" viewBox="0 0 880 504" role="img" aria-labelledby="nj-int-lanes-title" xmlns="http://www.w3.org/2000/svg">
|
||||
<title id="nj-int-lanes-title">Two lanes: the 3.x release train, whose minor and patch releases do not break code that uses the public A​PI, followed by version 4.0, which has no release date yet. Each breaking change is a macro that is available in 3.x today with its 3.x default and becomes the default in 4.0: JSON_USE_IMPLICIT_CONVERSIONS, added in 3.9.0, 3.x default 1, 4.0 value 0; JSON_USE_GLOBAL_UDLS, added in 3.11.0, 3.x default 1, 4.0 value 0; JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON, added in 3.11.0, 3.x default 0, 4.0 value 0, macro removed; JSON_BRACE_INIT_COPY_SEMANTICS, added in 3.13.0, 3.x default 0, 4.0 value 1; JSON_PRECISE_STREAM_POSITION, added in 3.13.0, 3.x default 0, 4.0 value 1; JSON_STRICT_NUL_HANDLING, added in 3.13.0, 3.x default 0, 4.0 value 1; JSON_STRICT_BINARY_UTF8, added in 3.13.0, 3.x default 0, 4.0 value 1; JSON_DISABLE_TUPLE_REFERENCE_CONVERSION, added in 3.13.0, 3.x default 0, 4.0 value 1; JSON_DELETE_DEPRECATED_FUNCTIONS, added in 3.13.0, 3.x default 0, 4.0 value 1, macro removed.</title>
|
||||
<defs><marker id="nj-int-arrow" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto"><path class="fg-head" d="M0 1 L10 5 L0 9 z"/></marker></defs>
|
||||
<rect class="nj-int-lane" x="16" y="16" width="600" height="56" rx="10"/>
|
||||
<text class="nj-int-lanetext" x="32" y="41">3.x release train</text>
|
||||
<text class="nj-int-mute" x="32" y="60">available today</text>
|
||||
<line class="nj-int-axis" x1="300" y1="30" x2="300" y2="44"/>
|
||||
<text class="nj-int-mute" x="300" y="60" text-anchor="middle">3.9.0</text>
|
||||
<line class="nj-int-axis" x1="445" y1="30" x2="445" y2="44"/>
|
||||
<text class="nj-int-mute" x="445" y="60" text-anchor="middle">3.11.0</text>
|
||||
<line class="nj-int-axis" x1="590" y1="30" x2="590" y2="44"/>
|
||||
<text class="nj-int-mute" x="590" y="60" text-anchor="middle">3.13.0</text>
|
||||
<line class="fg-arrow" x1="210" y1="37" x2="600" y2="37"/>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="618" y1="44" x2="660" y2="44" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-lane nj-int-lane--future" x="664" y="16" width="200" height="56" rx="10"/>
|
||||
<text class="nj-int-lanetext" x="680" y="41">4.0</text>
|
||||
<text class="nj-int-mute" x="680" y="60">no release date yet</text>
|
||||
<text class="nj-int-text" x="16" y="98">A minor or patch release of 3.x does not break code that uses the public A​PI, unless that code opts in with a macro.</text>
|
||||
<text class="nj-int-text" x="16" y="118">4.0 is not developed on a separate branch: it switches the defaults of these macros and removes the macros.</text>
|
||||
<text class="fg-h" x="32" y="150">Macro</text>
|
||||
<text class="fg-h" x="380" y="150">added</text>
|
||||
<text class="fg-h" x="500" y="150" text-anchor="middle">3.x default</text>
|
||||
<text class="nj-int-mute" x="632" y="150" text-anchor="middle">define to try today</text>
|
||||
<text class="fg-h" x="764" y="150" text-anchor="middle">4.0 default</text>
|
||||
<rect class="nj-int-row" x="16" y="170" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="189.5">JSON_USE_IMPLICIT_CONVERSIONS</text>
|
||||
<text class="nj-int-mute" x="380" y="189.5">3.9.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="174" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="189.5" text-anchor="middle">1</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="185" x2="724" y2="185" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="174" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="189.5" text-anchor="middle">0</text>
|
||||
<rect class="nj-int-row" x="16" y="204" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="223.5">JSON_USE_GLOBAL_UDLS</text>
|
||||
<text class="nj-int-mute" x="380" y="223.5">3.11.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="208" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="223.5" text-anchor="middle">1</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="219" x2="724" y2="219" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="208" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="223.5" text-anchor="middle">0</text>
|
||||
<rect class="nj-int-row" x="16" y="238" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="257.5">JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON</text>
|
||||
<text class="nj-int-mute" x="380" y="257.5">3.11.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="242" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="257.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="253" x2="724" y2="253" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="242" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="257.5" text-anchor="middle">removed</text>
|
||||
<rect class="nj-int-row" x="16" y="272" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="291.5">JSON_BRACE_INIT_COPY_SEMANTICS</text>
|
||||
<text class="nj-int-mute" x="380" y="291.5">3.13.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="276" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="291.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="287" x2="724" y2="287" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="276" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="291.5" text-anchor="middle">1</text>
|
||||
<rect class="nj-int-row" x="16" y="306" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="325.5">JSON_PRECISE_STREAM_POSITION</text>
|
||||
<text class="nj-int-mute" x="380" y="325.5">3.13.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="310" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="325.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="321" x2="724" y2="321" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="310" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="325.5" text-anchor="middle">1</text>
|
||||
<rect class="nj-int-row" x="16" y="340" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="359.5">JSON_STRICT_NUL_HANDLING</text>
|
||||
<text class="nj-int-mute" x="380" y="359.5">3.13.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="344" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="359.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="355" x2="724" y2="355" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="344" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="359.5" text-anchor="middle">1</text>
|
||||
<rect class="nj-int-row" x="16" y="374" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="393.5">JSON_STRICT_BINARY_UTF8</text>
|
||||
<text class="nj-int-mute" x="380" y="393.5">3.13.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="378" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="393.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="389" x2="724" y2="389" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="378" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="393.5" text-anchor="middle">1</text>
|
||||
<rect class="nj-int-row" x="16" y="408" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="427.5">JSON_DISABLE_TUPLE_REFERENCE_CONVERSION</text>
|
||||
<text class="nj-int-mute" x="380" y="427.5">3.13.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="412" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="427.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="423" x2="724" y2="423" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="412" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="427.5" text-anchor="middle">1</text>
|
||||
<rect class="nj-int-row" x="16" y="442" width="848" height="30" rx="6"/>
|
||||
<text class="nj-int-macro" x="32" y="461.5">JSON_DELETE_DEPRECATED_FUNCTIONS</text>
|
||||
<text class="nj-int-mute" x="380" y="461.5">3.13.0</text>
|
||||
<rect class="nj-int-pill" x="470" y="446" width="60" height="22" rx="11"/>
|
||||
<text class="nj-int-val" x="500" y="461.5" text-anchor="middle">0</text>
|
||||
<line class="fg-arrow fg-arrow--dash" x1="544" y1="457" x2="724" y2="457" marker-end="url(#nj-int-arrow)"/>
|
||||
<rect class="nj-int-pill nj-int-pill--v4" x="728" y="446" width="72" height="22" rx="11"/>
|
||||
<text class="nj-int-val nj-int-val--v4" x="764" y="461.5" text-anchor="middle">removed</text>
|
||||
<text class="nj-int-mute" x="16" y="496">Versions on the 3.x lane are the ones that added a macro, not to scale. “removed”: see the 4.0 behavior column of the table.</text>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 8.8 KiB |
@@ -1 +0,0 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="-78 -1741 14091 2499" width="495" height="88" role="img" aria-label="nlohmann/json"><title>nlohmann/json</title><g transform="scale(1 -1)"><g fill="#ffffff"><path transform="translate(0.0 0)" d="M279.2 697.3V0H167.3V1104.2H276.1L276.4 850.4H255.4Q299 990.6 399.3 1055.2Q499.6 1119.9 626.3 1119.9Q739.7 1119.9 826.2 1072.4Q912.8 1024.9 962.1 935.2Q1011.4 845.5 1011.4 717.1V0H899.6V709.9Q899.6 851.3 818 933.9Q736.5 1016.6 601.8 1016.6Q510.1 1016.6 437 977.7Q363.8 938.9 321.5 867.2Q279.2 795.6 279.2 697.3Z"/><path transform="translate(1138.0 0)" d="M279.2 1490V0H167.3V1490H279.2Z"/><path transform="translate(1544.1 0)" d="M590.7 -23.1Q448.9 -23.1 339.6 50.3Q230.3 123.7 168.3 252.7Q106.3 381.6 106.3 548Q106.3 715.8 168.3 844.8Q230.3 973.8 339.6 1047.1Q448.9 1120.3 590.7 1120.3Q732.6 1120.3 841.7 1047.1Q950.9 973.8 1012.9 844.6Q1074.9 715.4 1074.9 548Q1074.9 381.6 1013.1 252.7Q951.3 123.7 842.1 50.3Q733 -23.1 590.7 -23.1ZM590.7 79.6Q705.6 79.6 788.9 141.9Q872.2 204.2 917.1 310.4Q962 416.7 962 548Q962 679.6 916.9 786Q871.8 892.4 788.5 955Q705.2 1017.6 590.7 1017.6Q476.7 1017.6 393.5 954.9Q310.3 892.2 265 786.1Q219.6 679.9 219.6 548Q219.6 416.6 264.8 310.4Q309.9 204.2 393.1 141.9Q476.2 79.6 590.7 79.6Z"/><path transform="translate(2684.1 0)" d="M279.2 697.3V0H167.3V1490H279.2V850.4H255.4Q299 990.6 399.3 1055.2Q499.6 1119.9 626.3 1119.9Q739.7 1119.9 826.4 1072.4Q913.2 1024.9 962.5 935.2Q1011.8 845.5 1011.8 717.1V0H899.6V709.9Q899.6 851.3 818 933.9Q736.5 1016.6 601.8 1016.6Q510.1 1016.6 437 977.7Q363.8 938.9 321.5 867.2Q279.2 795.6 279.2 697.3Z"/><path transform="translate(3822.2 0)" d="M167.3 0V1104.2H276.8L277.2 853.7H261.4Q285.1 945.7 337 1004.8Q388.9 1064 457.8 1093.1Q526.7 1122.2 599.7 1122.2Q722.9 1122.2 805.7 1046.7Q888.4 971.2 910.3 844.9H888.1Q907.9 930.7 959.4 992.8Q1011 1054.9 1085.3 1088.6Q1159.6 1122.2 1248.1 1122.2Q1349.1 1122.2 1427 1078Q1505 1033.7 1549.5 948.2Q1594 862.7 1594 738.2V0H1482.1V736.3Q1482.1 878 1408.3 948Q1334.4 1018.1 1221.8 1018.1Q1139.1 1018.1 1074.7 982.6Q1010.3 947 973.4 881.6Q936.6 816.3 936.6 726.7V0H824.7V745.3Q824.7 873 754.3 945.6Q683.9 1018.1 570.7 1018.1Q491.1 1018.1 424.8 981.1Q358.4 944 318.8 875.8Q279.2 807.7 279.2 713.4V0H167.3Z"/><path transform="translate(5542.2 0)" d="M560.3 -22.7Q425.4 -22.7 323.1 49.7Q220.8 122 163.6 251Q106.3 380.1 106.3 549.8Q106.3 718.7 164 847.4Q221.7 976 324.4 1047.9Q427.1 1119.9 561.9 1119.9Q657.4 1119.9 727.7 1085.2Q798.1 1050.6 845.2 994.3Q892.3 938.1 916.4 874.3H924.9V1104.2H1036.2V0H925.3V225.1H916.4Q891.1 161.2 843.7 104.4Q796.3 47.5 725.9 12.4Q655.4 -22.7 560.3 -22.7ZM574.9 79.9Q685.3 79.9 764.2 140.4Q843.1 200.8 885.1 307.1Q927.2 413.4 927.2 550.6Q927.2 687.8 885.1 793Q843.1 898.2 764.2 957.8Q685.3 1017.4 574.9 1017.4Q464.6 1017.4 384.9 957.2Q305.3 897.1 262.4 791.7Q219.6 686.2 219.6 550.6Q219.6 415 262.4 308.6Q305.3 202.3 384.9 141.1Q464.6 79.9 574.9 79.9Z"/><path transform="translate(6705.2 0)" d="M279.2 697.3V0H167.3V1104.2H276.1L276.4 850.4H255.4Q299 990.6 399.3 1055.2Q499.6 1119.9 626.3 1119.9Q739.7 1119.9 826.2 1072.4Q912.8 1024.9 962.1 935.2Q1011.4 845.5 1011.4 717.1V0H899.6V709.9Q899.6 851.3 818 933.9Q736.5 1016.6 601.8 1016.6Q510.1 1016.6 437 977.7Q363.8 938.9 321.5 867.2Q279.2 795.6 279.2 697.3Z"/><path transform="translate(7843.3 0)" d="M279.2 697.3V0H167.3V1104.2H276.1L276.4 850.4H255.4Q299 990.6 399.3 1055.2Q499.6 1119.9 626.3 1119.9Q739.7 1119.9 826.2 1072.4Q912.8 1024.9 962.1 935.2Q1011.4 845.5 1011.4 717.1V0H899.6V709.9Q899.6 851.3 818 933.9Q736.5 1016.6 601.8 1016.6Q510.1 1016.6 437 977.7Q363.8 938.9 321.5 867.2Q279.2 795.6 279.2 697.3Z"/><path transform="translate(9729.7 0)" d="M111.2 1104.2H459.2V-51.7Q459.4 -183.9 406.6 -264.4Q353.7 -344.9 255.5 -381.4Q157.2 -418 21.4 -418H-63.7V-152.7H-14.8Q55.3 -152.7 83.3 -125Q111.2 -97.4 111.2 -39.2V1104.2ZM285.1 1228.6Q208.7 1228.6 155.6 1278Q102.6 1327.5 102.6 1398.2Q102.6 1469.9 155.6 1518.8Q208.7 1567.8 285 1567.8Q361.5 1567.8 414.7 1518.9Q467.8 1470.1 467.8 1398.1Q467.8 1327.4 414.7 1278Q361.5 1228.6 285.1 1228.6Z"/><path transform="translate(10258.7 0)" d="M580.7 -22.1Q436.8 -22.1 326.1 19.4Q215.5 60.9 146.9 138.4Q78.2 215.9 61 323.7L388.3 363.3Q406.3 294.2 455.2 257.5Q504.1 220.8 589.7 220.8Q662.2 220.8 703.6 246.4Q745 271.9 745 313.9Q745 351.2 711.8 374.4Q678.7 397.6 610.3 410.8L416 447.9Q252.5 479.2 170.3 559.5Q88.1 639.9 88.1 767.7Q88.1 878 147.7 956.7Q207.4 1035.5 316.7 1077.7Q426.1 1119.9 575.6 1119.9Q717.4 1119.9 822.1 1080.8Q926.7 1041.7 989.4 969.8Q1052.1 897.9 1067.5 797.8L757.5 759.8Q745.3 815.8 699.4 848.2Q653.5 880.6 583.2 880.6Q518.8 880.6 476.8 855.3Q434.8 829.9 434.8 787.7Q434.8 753.9 462.5 729Q490.3 704.1 557.8 691L771.4 651.3Q937.2 620.2 1017.9 546.8Q1098.7 473.4 1098.7 352.5Q1098.7 239.1 1032.3 154.9Q965.9 70.8 849.2 24.3Q732.5 -22.1 580.7 -22.1Z"/><path transform="translate(11376.8 0)" d="M628.4 -21.6Q455.7 -21.6 329.7 49.8Q203.6 121.3 135.6 249.6Q67.7 378 67.7 548.9Q67.7 720.4 135.6 848.9Q203.6 977.3 329.7Line truncated
|
||||
|
Before Width: | Height: | Size: 5.8 KiB |
@@ -1,11 +1,63 @@
|
||||
---
|
||||
template: home.html
|
||||
hide:
|
||||
- toc
|
||||
---
|
||||
|
||||
# JSON for Modern C++
|
||||
|
||||

|
||||
|
||||
JSON for Modern C++ is a header-only C++11 library that turns JSON into a first-class C++ data type, using the operator
|
||||
magic of modern C++ so that creating, reading, and modifying JSON values feels as natural as it does in languages like
|
||||
Python. The whole library is available as a single header, `json.hpp`, with no dependencies, no subproject, and no
|
||||
complex build system to set up; a companion header, `json_fwd.hpp`, provides forward declarations to keep compile times
|
||||
down, `<nlohmann/json_literals.hpp>` holds the user-defined string literals on their own, and
|
||||
`<nlohmann/json_view.hpp>` adds zero-copy views and editable documents. See
|
||||
[header-only integration](integration/index.md) for details. It is heavily unit-tested with 100% code
|
||||
coverage, checked with Valgrind and the Clang Sanitizers for memory leaks, and continuously fuzz-tested by Google
|
||||
OSS-Fuzz.
|
||||
|
||||
## Quick start
|
||||
|
||||
Add the single header to your project and use the library like this:
|
||||
|
||||
```cpp
|
||||
#include <iostream>
|
||||
#include <nlohmann/json.hpp>
|
||||
|
||||
using nlohmann::json;
|
||||
|
||||
int main()
|
||||
{
|
||||
// parse a JSON string
|
||||
json j = json::parse(R"({"happy": true, "pi": 3.141})");
|
||||
|
||||
// access and modify values
|
||||
j["name"] = "Niels";
|
||||
j["list"] = {1, 0, 2};
|
||||
|
||||
// read a value into a C++ variable and use it
|
||||
double pi = j["pi"].get<double>();
|
||||
std::cout << "2 * pi = " << 2 * pi << '\n';
|
||||
|
||||
// serialize with an indent of 4 spaces
|
||||
std::cout << j.dump(4) << '\n';
|
||||
}
|
||||
```
|
||||
|
||||
Get the library by copying the single header [`json.hpp`](https://github.com/nlohmann/json/releases) from the
|
||||
releases page into a directory `nlohmann` on your include path, or by installing it with a package manager:
|
||||
|
||||
```sh
|
||||
brew install nlohmann-json # Homebrew
|
||||
vcpkg install nlohmann-json # vcpkg
|
||||
```
|
||||
|
||||
```cmake
|
||||
find_package(nlohmann_json 3.12.0 REQUIRED)
|
||||
target_link_libraries(myproject PRIVATE nlohmann_json::nlohmann_json)
|
||||
```
|
||||
|
||||
See [Integration](integration/index.md) for CMake in detail, all supported package managers (Conan, Meson, Bazel,
|
||||
Conda, and more), and pkg-config.
|
||||
|
||||
## Explore the documentation
|
||||
|
||||
<div class="grid cards" markdown>
|
||||
|
||||
- :octicons-rocket-24:{ .lg .middle } __Features__
|
||||
@@ -60,5 +112,11 @@ hide:
|
||||
|
||||
</div>
|
||||
|
||||

|
||||

|
||||
!!! info "Unreleased changes"
|
||||
|
||||
This documentation is built from the `develop` branch and may describe changes that are not part of a release
|
||||
yet. Their version numbers are followed by an <span class="unreleased-version">unreleased</span> badge; see
|
||||
[Releases](home/releases/index.md) for what shipped in each version.
|
||||
|
||||
The library is licensed under the [MIT License](home/license.md). The source code, issue tracker, and discussions
|
||||
are on [GitHub](https://github.com/nlohmann/json).
|
||||
@@ -8,19 +8,6 @@ to point to the appropriate include directories and [`INTERFACE_COMPILE_FEATURES
|
||||
for the necessary C++11 flags. Most [package managers](package_managers.md) that provide a CMake package configuration
|
||||
for this library expose this same target.
|
||||
|
||||
All ways of adding the library described below end at this one target:
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
FP["<b>find_package()</b><br>installed package"] --> T
|
||||
AS["<b>add_subdirectory()</b><br>embedded source tree"] --> T
|
||||
FC["<b>FetchContent</b><br>downloaded at configure time"] --> T
|
||||
PM["<b>Package manager</b><br>its CMake package"] --> T
|
||||
T["<b>nlohmann_json::nlohmann_json</b><br>one INTERFACE target"] --> L["<b>target_link_libraries()</b><br>link it PRIVATE"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>The four ways to add the library in CMake all lead to the same `nlohmann_json::nlohmann_json` interface target, which a project links with `target_link_libraries`. The CMake options below apply to `add_subdirectory()` and `FetchContent`; installed packages have their options fixed at install time.</p>
|
||||
|
||||
### External
|
||||
|
||||
To use this library from a CMake project, you can locate it directly with [`find_package()`](https://cmake.org/cmake/help/latest/command/find_package.html)
|
||||
|
||||
@@ -6,68 +6,9 @@ that cost, ordered by how much they typically save.
|
||||
|
||||
!!! info "Measurements"
|
||||
|
||||
The numbers below are medians of the wall-clock time of nine runs compiling a single translation unit with
|
||||
`-std=c++17 -c` against the single-header version, with Apple clang 21.0.0 (clang-2100.3.34.2) and Homebrew GCC
|
||||
16.2.0 on macOS (Apple M1 Max). All configurations were run interleaved, in alternating order. They show the order
|
||||
of magnitude to expect; measure your own code before and after a change.
|
||||
|
||||
The translation units are listed below. They replace the ones used for earlier versions of this page, whose
|
||||
sources were not published, so the numbers differ from earlier versions.
|
||||
|
||||
??? example "Measured translation units"
|
||||
|
||||
The *model* and *parsing* translation units start with `#include <string>`, `#include <vector>`, and
|
||||
`#include <nlohmann/json.hpp>`; the *header-only* translation unit includes only the library header.
|
||||
|
||||
```cpp title="model translation unit"
|
||||
struct person
|
||||
{
|
||||
std::string name;
|
||||
int age = 0;
|
||||
std::vector<std::string> tags;
|
||||
};
|
||||
|
||||
void to_json(nlohmann::json& j, const person& p)
|
||||
{
|
||||
j = nlohmann::json{{"name", p.name}, {"age", p.age}, {"tags", p.tags}};
|
||||
}
|
||||
|
||||
void from_json(const nlohmann::json& j, person& p)
|
||||
{
|
||||
j.at("name").get_to(p.name);
|
||||
j.at("age").get_to(p.age);
|
||||
j.at("tags").get_to(p.tags);
|
||||
}
|
||||
|
||||
nlohmann::json roundtrip(const person& p)
|
||||
{
|
||||
nlohmann::json j = p;
|
||||
return nlohmann::json(j.get<person>());
|
||||
}
|
||||
```
|
||||
|
||||
```cpp title="parsing translation unit"
|
||||
std::size_t parse_and_dump(const std::string& s)
|
||||
{
|
||||
const nlohmann::json j = nlohmann::json::parse(s);
|
||||
return j.dump(2).size();
|
||||
}
|
||||
```
|
||||
|
||||
```cpp title="header-only translation unit"
|
||||
#include <nlohmann/json.hpp> // or <nlohmann/json_fwd.hpp>
|
||||
|
||||
struct person;
|
||||
void to_json(nlohmann::json& j, const person& p);
|
||||
void from_json(const nlohmann::json& j, person& p);
|
||||
```
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/compile_times.svg"
|
||||
</div>
|
||||
<p class="nj-charts-caption" markdown>Change in compile time at `-O0` against the default configuration of the same
|
||||
translation unit, taken from the tables below (medians of nine runs, see above). * computed from the milliseconds in
|
||||
[Options without effect on compile times](#options-without-effect-on-compile-times).</p>
|
||||
The numbers below are medians of nine runs compiling a single translation unit with `-std=c++17 -c` against the
|
||||
single-header version, with Apple clang and GCC 16 on macOS (Apple silicon). They show the order of magnitude to
|
||||
expect; measure your own code before and after a change.
|
||||
|
||||
## Include `json_fwd.hpp` in headers
|
||||
|
||||
@@ -96,10 +37,8 @@ void from_json(const nlohmann::json& j, person& p) { /* ... */ }
|
||||
|
||||
| Compiler | `json.hpp` (`-O0`) | `json_fwd.hpp` (`-O0`) | Change |
|
||||
|-------------|-------------------:|-----------------------:|-------:|
|
||||
| Apple clang | 868 ms | 332 ms | −62% |
|
||||
| GCC 16 | 1164 ms | 210 ms | −82% |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time of the header-only translation unit at `-O0` with each header, as the median wall-clock time of nine runs (see "Measurements" above). A negative change means a faster build.</p>
|
||||
| Apple clang | 704 ms | 329 ms | −53% |
|
||||
| GCC 16 | 779 ms | 242 ms | −69% |
|
||||
|
||||
This is the most effective option, because it avoids the full header in every translation unit that includes
|
||||
*your* headers.
|
||||
@@ -128,15 +67,13 @@ conversions or only pass `json` values around:
|
||||
|
||||
| Compiler | Translation unit | Default (`-O0` / `-O2`) | `JSON_NO_AUTOMATIC_UDLS` (`-O0` / `-O2`) | Change |
|
||||
|-------------|------------------|------------------------:|-----------------------------------------:|------------:|
|
||||
| Apple clang | model | 1051 ms / 1300 ms | 935 ms / 1170 ms | −11% / −10% |
|
||||
| GCC 16 | model | 1801 ms / 2106 ms | 1598 ms / 1983 ms | −11% / −6% |
|
||||
| Apple clang | parsing | 1157 ms / 2016 ms | 1146 ms / 2006 ms | −1% / 0% |
|
||||
| GCC 16 | parsing | 2529 ms / 4087 ms | 2484 ms / 4059 ms | −2% / −1% |
|
||||
| Apple clang | model | 776 ms / 846 ms | 629 ms / 692 ms | −19% / −18% |
|
||||
| GCC 16 | model | 1022 ms / 1120 ms | 882 ms / 965 ms | −14% / −14% |
|
||||
| Apple clang | parsing | 992 ms / 1815 ms | 1006 ms / 1823 ms | +1% / 0% |
|
||||
| GCC 16 | parsing | 2018 ms / 3420 ms | 1990 ms / 3454 ms | −1% / +1% |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time of the model and parsing translation units without and with `JSON_NO_AUTOMATIC_UDLS`, at `-O0` and `-O2`.</p>
|
||||
|
||||
The model translation unit saves about a tenth. Translation units that parse anyway instantiate the parser regardless
|
||||
and see no difference.
|
||||
Translation units that include only the header save up to a third. Translation units that parse anyway instantiate
|
||||
the parser regardless and see no difference.
|
||||
|
||||
## Instantiate `basic_json` once
|
||||
|
||||
@@ -160,12 +97,10 @@ Include `json_instance.hpp` instead of `<nlohmann/json.hpp>` and compile and lin
|
||||
|
||||
| Compiler | Translation unit | Default (`-O0` / `-O2`) | `extern template` (`-O0` / `-O2`) | Change |
|
||||
|-------------|---------------------|------------------------:|----------------------------------:|------------:|
|
||||
| Apple clang | parsing | 1157 ms / 2016 ms | 1071 ms / 1844 ms | −7% / −9% |
|
||||
| GCC 16 | parsing | 2529 ms / 4087 ms | 1994 ms / 3190 ms | −21% / −22% |
|
||||
| Apple clang | `json_instance.cpp` | — | 2573 ms / 6221 ms | — |
|
||||
| GCC 16 | `json_instance.cpp` | — | 6489 ms / 13759 ms | — |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time of the parsing translation unit without and with the `extern template` declaration, at `-O0` and `-O2`. The `json_instance.cpp` rows are the one-off cost of the translation unit that holds the instantiation.</p>
|
||||
| Apple clang | parsing | 992 ms / 1815 ms | 953 ms / 1625 ms | −4% / −10% |
|
||||
| GCC 16 | parsing | 2018 ms / 3420 ms | 1522 ms / 2728 ms | −25% / −20% |
|
||||
| Apple clang | `json_instance.cpp` | — | 2166 ms / 4660 ms | — |
|
||||
| GCC 16 | `json_instance.cpp` | — | 5085 ms / 10616 ms | — |
|
||||
|
||||
Notes:
|
||||
|
||||
@@ -176,97 +111,12 @@ Notes:
|
||||
- The declaration covers exactly `nlohmann::json`. Add the same lines for `nlohmann::ordered_json`
|
||||
(`nlohmann::basic_json<nlohmann::ordered_map>`) or your own `basic_json` specializations if you use them.
|
||||
|
||||
## Switch off filesystem support
|
||||
|
||||
With C++17, the library includes `<filesystem>` to provide conversions from and to `std::filesystem::path`
|
||||
(see [`JSON_HAS_FILESYSTEM`](../api/macros/json_has_filesystem.md)). Parsing `<filesystem>` is a fixed cost in every
|
||||
translation unit, and it also pulls in `<iomanip>`, `<istream>`, and `<ostream>` (and, with GCC's libstdc++,
|
||||
`<sstream>`). If you do not convert paths, switch the detection off for the whole project:
|
||||
|
||||
```cmake
|
||||
target_compile_definitions(my_target PRIVATE JSON_HAS_FILESYSTEM=0 JSON_HAS_EXPERIMENTAL_FILESYSTEM=0)
|
||||
```
|
||||
|
||||
| Compiler | Translation unit | Default (`-O0` / `-O2`) | Filesystem off (`-O0` / `-O2`) | Change |
|
||||
|-------------|------------------|------------------------:|-------------------------------:|-----------:|
|
||||
| Apple clang | model | 1051 ms / 1300 ms | 998 ms / 1257 ms | −5% / −3% |
|
||||
| GCC 16 | model | 1801 ms / 2106 ms | 1636 ms / 2008 ms | −9% / −5% |
|
||||
| Apple clang | parsing | 1157 ms / 2016 ms | 1107 ms / 1971 ms | −4% / −2% |
|
||||
| GCC 16 | parsing | 2529 ms / 4087 ms | 2405 ms / 4029 ms | −5% / −1% |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time with `JSON_HAS_FILESYSTEM=0` and `JSON_HAS_EXPERIMENTAL_FILESYSTEM=0` against the default configuration, at `-O0` and `-O2`.</p>
|
||||
|
||||
Only with filesystem support switched off does [`JSON_NO_IO`](../api/macros/json_no_io.md) remove the stream headers
|
||||
from the translation unit, so the two macros save most together:
|
||||
|
||||
| Compiler | Translation unit | Default (`-O0` / `-O2`) | Filesystem off and `JSON_NO_IO` (`-O0` / `-O2`) | Change |
|
||||
|-------------|------------------|------------------------:|------------------------------------------------:|-----------:|
|
||||
| Apple clang | model | 1051 ms / 1300 ms | 969 ms / 1219 ms | −8% / −6% |
|
||||
| GCC 16 | model | 1801 ms / 2106 ms | 1605 ms / 1982 ms | −11% / −6% |
|
||||
| Apple clang | parsing | 1157 ms / 2016 ms | 1083 ms / 1947 ms | −6% / −3% |
|
||||
| GCC 16 | parsing | 2529 ms / 4087 ms | 2384 ms / 3972 ms | −6% / −3% |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time with filesystem support switched off and `JSON_NO_IO` defined, against the default configuration, at `-O0` and `-O2`.</p>
|
||||
|
||||
The trade-off: the library's own `to_json`/`from_json` overloads for `std::filesystem::path` (which store the path as
|
||||
UTF-8) are removed. In a test with both compilers on macOS, paths still converted through their implicit conversion
|
||||
from and to `std::string`; whether that fallback exists depends on the platform's native path string type
|
||||
(`std::wstring` on Windows), so check code that converts paths. `JSON_NO_IO` additionally removes all stream
|
||||
functions (see [Options without effect](#options-without-effect-on-compile-times)).
|
||||
|
||||
## Use C++20 modules
|
||||
|
||||
With a toolchain that supports named modules, `import nlohmann.json;` compiles the library once into a module and
|
||||
avoids parsing the header in every translation unit. See [Modules](../features/modules.md) for requirements and known
|
||||
issues. Module support is experimental and currently depends heavily on the compiler version.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/compile_times_modules.svg"
|
||||
</div>
|
||||
<p class="nj-caption" markdown>Change in compile time per translation unit at `-O0` when `#include <nlohmann/json.hpp>` is
|
||||
replaced by `import nlohmann.json;`, both with `-std=c++20`, and the one-off cost of building the module, taken from
|
||||
the table below.</p>
|
||||
|
||||
| Compiler | Translation unit | `#include` (`-O0` / `-O2`) | `import nlohmann.json;` (`-O0` / `-O2`) | Change |
|
||||
|-------------|---------------------------|---------------------------:|----------------------------------------:|------------:|
|
||||
| Apple clang | model | 1311 ms / 1597 ms | 680 ms / 914 ms | −48% / −43% |
|
||||
| GCC 16 | model | 2156 ms / 2588 ms | 1153 ms / 1580 ms | −47% / −39% |
|
||||
| Apple clang | parsing | 1387 ms / 2319 ms | 800 ms / 1676 ms | −42% / −28% |
|
||||
| GCC 16 | parsing | 2838 ms / 4520 ms | 1810 ms / 3476 ms | −36% / −23% |
|
||||
| Apple clang | `json.cppm` (module) | — | 1630 ms / 1642 ms | — |
|
||||
| GCC 16 | `json.cppm` (module) | — | 2538 ms / 2547 ms | — |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time with `#include <nlohmann/json.hpp>` and with `import nlohmann.json;`, both with `-std=c++20`, at `-O0` and `-O2`. The `json.cppm` rows are the one-off cost of building the module.</p>
|
||||
|
||||
Both columns use `-std=c++20`; with `-std=c++17`, the `#include` baseline is 17% to 20% faster (see the next
|
||||
section). The module is built once per set of compiler flags and pays for itself from about the third translation
|
||||
unit that imports it. Notes from the measurement:
|
||||
|
||||
- Apple clang only accepts the module declarations with `-fcxx-modules`; without it, `module;` is a syntax error.
|
||||
- GCC 16 warns with `-Wexpose-global-module-tu-local` about internal constants of the library when building the
|
||||
module. With GCC 16.2, including `<string>` and `<vector>` before `import nlohmann.json;` works, but including
|
||||
them after it fails with redefinition errors ([#5103](https://github.com/nlohmann/json/issues/5103)).
|
||||
|
||||
??? example "How these numbers were measured"
|
||||
|
||||
The model and parsing translation units are the ones listed at the top of this page, with `import nlohmann.json;`
|
||||
in place of `#include <nlohmann/json.hpp>` (after `#include <string>` and `#include <vector>`). Same method as
|
||||
for the other tables, with `-std=c++20`.
|
||||
|
||||
```sh
|
||||
# Apple clang: build the module once, then import it
|
||||
clang++ -std=c++20 -fcxx-modules -O0 -I single_include -c -x c++-module src/modules/json.cppm \
|
||||
-fmodule-output=nlohmann.json.pcm -o json_mod.o
|
||||
clang++ -std=c++20 -fcxx-modules -O0 -fmodule-file=nlohmann.json=nlohmann.json.pcm -c model.cpp
|
||||
|
||||
# GCC 16 (Homebrew on macOS): writes gcm.cache/nlohmann.json.gcm, found by the importing translation unit
|
||||
g++-16 --sysroot=$(xcrun --show-sdk-path) -std=c++20 -fmodules -O0 -I single_include -c src/modules/json.cppm \
|
||||
-o json_mod.o
|
||||
g++-16 --sysroot=$(xcrun --show-sdk-path) -std=c++20 -fmodules -O0 -c model.cpp
|
||||
```
|
||||
|
||||
Link `json_mod.o` into the program.
|
||||
|
||||
## Use precompiled headers
|
||||
|
||||
Build systems can precompile `<nlohmann/json.hpp>` together with other stable headers, for example with CMake's
|
||||
@@ -279,70 +129,21 @@ target_precompile_headers(my_target PRIVATE <nlohmann/json.hpp>)
|
||||
This removes the cost of parsing the header, but not of instantiating templates in each translation unit, so it
|
||||
combines well with the options above.
|
||||
|
||||
<div class="nj-fig-wrap" markdown>
|
||||
--8<-- "images/compile_times_pch.svg"
|
||||
</div>
|
||||
<p class="nj-caption" markdown>Change in compile time per translation unit at `-O0` with a precompiled
|
||||
`<nlohmann/json.hpp>` (`-std=c++17`), and the one-off cost of building the precompiled header, taken from the table
|
||||
below.</p>
|
||||
|
||||
| Compiler | Translation unit | Default (`-O0` / `-O2`) | With PCH (`-O0` / `-O2`) | Change |
|
||||
|-------------|----------------------|------------------------:|-------------------------:|------------:|
|
||||
| Apple clang | model | 1045 ms / 1295 ms | 594 ms / 842 ms | −43% / −35% |
|
||||
| GCC 16 | model | 1789 ms / 2101 ms | 1060 ms / 1376 ms | −41% / −35% |
|
||||
| Apple clang | parsing | 1148 ms / 2008 ms | 714 ms / 1584 ms | −38% / −21% |
|
||||
| GCC 16 | parsing | 2498 ms / 4075 ms | 1884 ms / 3452 ms | −25% / −15% |
|
||||
| Apple clang | building the PCH | — | 771 ms / 760 ms | — |
|
||||
| GCC 16 | building the PCH | — | 2254 ms / 2218 ms | — |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time without and with a precompiled `<nlohmann/json.hpp>`, at `-O0` and `-O2`. The last two rows are the one-off cost of building the precompiled header.</p>
|
||||
|
||||
The saving is largest in translation units that instantiate little, and the PCH pays for itself from the second
|
||||
(Apple clang) or fourth (GCC) translation unit. A precompiled header only works with the flags it was built with:
|
||||
GCC silently ignores a mismatching `.gch` file (for example one built with another `-O` level) unless `-Winvalid-pch`
|
||||
is given.
|
||||
|
||||
??? example "How these numbers were measured"
|
||||
|
||||
`pch.hpp` contains only `#include <nlohmann/json.hpp>`; the translation units are the ones
|
||||
listed at the top of this page.
|
||||
|
||||
```sh
|
||||
# Apple clang
|
||||
clang++ -std=c++17 -O0 -I single_include -x c++-header pch.hpp -o pch.hpp.pch
|
||||
clang++ -std=c++17 -O0 -I single_include -include-pch pch.hpp.pch -include pch.hpp -c model.cpp
|
||||
|
||||
# GCC 16 (Homebrew on macOS): pch.hpp.gch next to pch.hpp is picked up by -include pch.hpp
|
||||
g++-16 --sysroot=$(xcrun --show-sdk-path) -std=c++17 -O0 -I single_include -x c++-header pch.hpp -o pch.hpp.gch
|
||||
g++-16 --sysroot=$(xcrun --show-sdk-path) -std=c++17 -O0 -I single_include -include pch.hpp -Winvalid-pch -c model.cpp
|
||||
```
|
||||
|
||||
## Options without effect on compile times
|
||||
|
||||
Some configuration macros change what the library declares, but do not measurably change compile times:
|
||||
|
||||
| Macro | Apple clang, model (`-O0` / `-O2`) | GCC 16, model (`-O0` / `-O2`) |
|
||||
|------------------------------------------------------------------------|-----------------------------------:|------------------------------:|
|
||||
| default | 1051 ms / 1300 ms | 1801 ms / 2106 ms |
|
||||
| [`JSON_NO_IO`](../api/macros/json_no_io.md) | 1034 ms / 1288 ms | 1756 ms / 2087 ms |
|
||||
| [`JSON_USE_GLOBAL_UDLS`](../api/macros/json_use_global_udls.md)`=0` | 1055 ms / 1298 ms | 1783 ms / 2109 ms |
|
||||
|
||||
<p class="nj-table-caption" markdown>Compile time of the model translation unit with each macro defined; the first row is the default configuration for comparison.</p>
|
||||
|
||||
`JSON_NO_IO` removes the library's stream functions and its `#include`s of `<istream>` and `<ostream>`, but with the
|
||||
default C++17 settings `<filesystem>` includes these headers anyway (and with libc++, `<vector>` already includes
|
||||
`<streambuf>` via `<locale>`), so only a few hundred lines of the library's own stream code go away. It also does not
|
||||
change what the translation unit instantiates. On the parsing translation unit, the change is 0% / 0% (Apple clang)
|
||||
and −2% / 0% (GCC). To get a saving, combine it with
|
||||
[switching off filesystem support](#switch-off-filesystem-support).
|
||||
| default | 776 ms / 846 ms | 1022 ms / 1120 ms |
|
||||
| [`JSON_NO_IO`](../api/macros/json_no_io.md) | 764 ms / 836 ms | 1022 ms / 1117 ms |
|
||||
| [`JSON_USE_GLOBAL_UDLS`](../api/macros/json_use_global_udls.md)`=0` | 763 ms / 852 ms | 1019 ms / 1106 ms |
|
||||
|
||||
`JSON_USE_GLOBAL_UDLS` only controls *where* the literals are declared; to avoid their cost, use
|
||||
`JSON_NO_AUTOMATIC_UDLS` instead.
|
||||
|
||||
## See also
|
||||
|
||||
- [`JSON_HAS_FILESYSTEM`](../api/macros/json_has_filesystem.md) - control the conversions from and to
|
||||
`std::filesystem::path`
|
||||
- [`JSON_NO_AUTOMATIC_UDLS`](../api/macros/json_no_automatic_udls.md) - do not include the user-defined string
|
||||
literals automatically
|
||||
- [Modules](../features/modules.md) - C++20 module support
|
||||
|
||||
@@ -5,31 +5,24 @@ pick one:
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[Add the library to a C++ project] --> B{{Using CMake?}}
|
||||
B -- no --> C{{Package manager available?}}
|
||||
C -- yes --> D["<b>Use a package manager</b><br>see Package Managers"]
|
||||
C -- no --> E["<b>Copy the single header</b><br>see Header only"]
|
||||
B -- yes --> F{{Already installed?}}
|
||||
F -- yes --> G["<b>find_package</b><br>see CMake, External"]
|
||||
F -- no --> H{{CMake 3.14 or later?}}
|
||||
H -- yes --> I["<b>FetchContent</b><br>see CMake, FetchContent"]
|
||||
H -- no --> J["<b>add_subdirectory</b><br>see CMake, Embedded"]
|
||||
G --> T["<code>nlohmann_json::nlohmann_json</code>"]
|
||||
I --> T
|
||||
J --> T
|
||||
A[Add the library to a C++ project] --> B{Already using CMake?}
|
||||
B -- no --> C{Using pkg-config or plain Makefiles?}
|
||||
C -- yes --> D[pkg-config]
|
||||
C -- no --> E[Copy the single header]
|
||||
B -- yes --> F{Library installed system-wide?}
|
||||
F -- yes --> G["find_package()"]
|
||||
F -- no --> H{Use a package manager?}
|
||||
H -- yes --> I[Package manager]
|
||||
H -- no --> J["add_subdirectory() or FetchContent"]
|
||||
```
|
||||
|
||||
<p class="nj-caption" markdown>Choosing an integration method: answer the questions in the hexagons from top to bottom to reach a method. All CMake methods end at the same target, `nlohmann_json::nlohmann_json`; the list below links to each method.</p>
|
||||
|
||||
- **Single header**: copy [`json.hpp`](#header-only) into your project; no build-system integration required.
|
||||
- **CMake**, see [CMake](cmake.md):
|
||||
- [`find_package()`](cmake.md#external) if the library is already installed;
|
||||
- [`FetchContent`](cmake.md#fetchcontent) to download it at configure time (CMake 3.14 or later);
|
||||
- [`add_subdirectory()`](cmake.md#embedded) to embed a vendored copy of the source tree;
|
||||
- or [support both](cmake.md#supporting-both) with an option that selects installed or vendored.
|
||||
- **Package managers**: install the library with Homebrew, Conan, vcpkg, or one of the many others; see
|
||||
[Package Managers](package_managers.md) for the full list.
|
||||
- **pkg-config**: if you use bare Makefiles instead of CMake, [pkg-config](pkg-config.md) supplies the include flags
|
||||
- **Copy the single header**, as described [below](#header-only) — no build-system integration required.
|
||||
- **CMake**: use [`find_package()`](cmake.md#external) if the library is already installed,
|
||||
[`add_subdirectory()`](cmake.md#embedded) to embed the source tree, or [`FetchContent`](cmake.md#fetchcontent) to
|
||||
download it at configure time; see [CMake](cmake.md).
|
||||
- **Package managers**: install the library with a package manager such as Homebrew, Conan, or vcpkg; see
|
||||
[Package Managers](package_managers.md).
|
||||
- **pkg-config**: if you use bare Makefiles instead of CMake, [pkg-config](pkg-config.md) can supply the include flags
|
||||
for an already-installed library.
|
||||
|
||||
Once the library is integrated, see the [Migration Guide](migration_guide.md) for how to keep your code future-proof
|
||||
|
||||
@@ -1,106 +0,0 @@
|
||||
/* figures: charts. Number literal explorer on features/types/number_handling.md.
|
||||
The table in .nj-charts-num is the source and the no-JS fallback; its rows were verified by compiling a program
|
||||
against include/ (json::parse + type() + dump()). The explorer only looks literals up in that table: it does not
|
||||
parse numbers itself, so anything else is reported as "not in the verified list". */
|
||||
(function () {
|
||||
"use strict";
|
||||
|
||||
var WHY = {
|
||||
"0": "No fraction, exponent, or minus sign: stored as unsigned integer.",
|
||||
"-0": "Leading minus sign: stored as signed integer; the serialization does not reproduce the -.",
|
||||
"-0.0": "Has a fraction: stored as double, which keeps the sign of zero.",
|
||||
"1E3": "Has an exponent: always stored as double.",
|
||||
"-12345678912345789123456789": "Smaller than INT64_MIN: does not fit std::int64_t, so it is stored as double.",
|
||||
"18446744073709551615": "2^64-1 is the largest value std::uint64_t can store without loss.",
|
||||
"18446744073709551616": "2^64 does not fit std::uint64_t, so it is stored as double.",
|
||||
"-9223372036854775808": "-2^63 is the smallest value std::int64_t can store.",
|
||||
"1E400": "Its rounded value is not finite as double: parsing throws out_of_range.406.",
|
||||
"1E-400": "Too small for double: becomes zero, with the sign of the number.",
|
||||
"3.141592653589793238462643383279": "Rounded to the nearest double, then printed with the fewest digits that read back.",
|
||||
"2555.5599999999999": "The fewest digits that read back as the same double are 2555.56.",
|
||||
"0.0000972439793401814": "The %g layout switches to scientific notation.",
|
||||
"12345E-5": "The %g layout prints this double without exponent."
|
||||
};
|
||||
|
||||
function init() {
|
||||
var roots = document.querySelectorAll(".nj-charts-num");
|
||||
Array.prototype.forEach.call(roots, setup);
|
||||
}
|
||||
|
||||
function setup(root, idx) {
|
||||
if (root.dataset.njChartsReady) return;
|
||||
var table = root.querySelector("table");
|
||||
if (!table) return;
|
||||
root.dataset.njChartsReady = "1";
|
||||
|
||||
var entries = [];
|
||||
Array.prototype.forEach.call(table.querySelectorAll("tbody tr"), function (tr) {
|
||||
var c = tr.querySelectorAll("td");
|
||||
if (c.length < 3) return;
|
||||
entries.push({ lit: c[0].textContent.trim(), type: c[1].textContent.trim(), dump: c[2].textContent.trim(), row: tr });
|
||||
});
|
||||
if (!entries.length) return;
|
||||
|
||||
var id = "nj-charts-num-" + idx;
|
||||
var ui = document.createElement("div");
|
||||
ui.className = "nj-charts-num-ui";
|
||||
ui.innerHTML =
|
||||
'<ul class="nj-charts-num-chips" aria-label="Literals to show"></ul>' +
|
||||
'<div id="' + id + '-out" aria-live="polite"></div>';
|
||||
root.insertBefore(ui, root.firstChild);
|
||||
|
||||
var list = ui.querySelector("ul");
|
||||
var out = ui.querySelector("#" + id + "-out");
|
||||
var buttons = [];
|
||||
|
||||
entries.forEach(function (e) {
|
||||
var li = document.createElement("li");
|
||||
var b = document.createElement("button");
|
||||
b.type = "button";
|
||||
b.className = "nj-charts-num-chip";
|
||||
b.textContent = e.lit;
|
||||
b.setAttribute("aria-pressed", "false");
|
||||
b.setAttribute("aria-label", "Show literal " + e.lit);
|
||||
b.addEventListener("click", function () { show(e.lit); });
|
||||
li.appendChild(b);
|
||||
list.appendChild(li);
|
||||
buttons.push(b);
|
||||
});
|
||||
|
||||
function show(text) {
|
||||
var lit = text.trim();
|
||||
var hit = null;
|
||||
entries.forEach(function (e, i) {
|
||||
var on = e.lit === lit;
|
||||
if (on) hit = e;
|
||||
buttons[i].setAttribute("aria-pressed", on ? "true" : "false");
|
||||
e.row.classList.toggle("nj-charts-num-hit", on);
|
||||
});
|
||||
out.textContent = "";
|
||||
if (hit) {
|
||||
var dl = document.createElement("dl");
|
||||
dl.className = "nj-charts-num-out";
|
||||
[["literal", hit.lit, true], ["stored as", hit.type, false], ["dump()", hit.dump, true],
|
||||
["why", WHY[hit.lit] || "", false]].forEach(function (p) {
|
||||
if (!p[1]) return;
|
||||
var dt = document.createElement("dt"); dt.textContent = p[0];
|
||||
var dd = document.createElement("dd");
|
||||
if (p[2] && p[1].indexOf("(") !== 0) { var c = document.createElement("code"); c.textContent = p[1]; dd.appendChild(c); }
|
||||
else dd.textContent = p[1];
|
||||
dl.appendChild(dt); dl.appendChild(dd);
|
||||
});
|
||||
out.appendChild(dl);
|
||||
}
|
||||
}
|
||||
|
||||
show(entries[1] ? entries[1].lit : entries[0].lit);
|
||||
}
|
||||
|
||||
if (typeof document$ !== "undefined" && document$ && typeof document$.subscribe === "function") {
|
||||
document$.subscribe(init);
|
||||
} else if (document.readyState === "loading") {
|
||||
document.addEventListener("DOMContentLoaded", init);
|
||||
} else {
|
||||
init();
|
||||
}
|
||||
})();
|
||||
@@ -1 +0,0 @@
|
||||
/* figures: exceptions */
|
||||
@@ -1,130 +0,0 @@
|
||||
/* figures: integration
|
||||
*
|
||||
* Namespace name builder on features/namespace.md. The page ships a static strip for version 3.11.2 with
|
||||
* JSON_DIAGNOSTICS=1; this script adds a version selector and one checkbox per ABI-affecting macro and rebuilds the
|
||||
* strip. Tags, their order, and the versions that know them follow include/nlohmann/detail/abi_macros.hpp and the
|
||||
* "Version history" section of the page; a tag that a version does not have cannot be ticked.
|
||||
*/
|
||||
(function () {
|
||||
"use strict";
|
||||
|
||||
var VERSIONS = ["3.11.2", "3.11.3", "3.12.0", "3.13.0"];
|
||||
// macro, tag, first version with the tag, true if any definition counts (#ifdef) instead of a non-zero value
|
||||
var TAGS = [
|
||||
["JSON_DIAGNOSTICS", "_diag", "3.11.2"],
|
||||
["JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON", "_ldvcmp", "3.11.2"],
|
||||
["JSON_DIAGNOSTIC_POSITIONS", "_dp", "3.12.0"],
|
||||
["JSON_BRACE_INIT_COPY_SEMANTICS", "_bics", "3.13.0"],
|
||||
["JSON_PRECISE_STREAM_POSITION", "_psp", "3.13.0"],
|
||||
["JSON_STRICT_NUL_HANDLING", "_snul", "3.13.0"],
|
||||
["JSON_STRICT_BINARY_UTF8", "_sbu8", "3.13.0"],
|
||||
["JSON_USE_OBJECTS_FOR_ENUM_KEYED_MAPS", "_ekmo", "3.13.0"],
|
||||
["JSON_DISABLE_STREAM_BULK_SCAN", "_dsbs", "3.13.0"],
|
||||
["JSON_DISABLE_UNLOCKED_FILE_IO", "_dufio", "3.13.0"],
|
||||
["JSON_NO_SIMD", "_ns", "3.13.0", true],
|
||||
["JSON_VIEW_NO_SIMD", "_vns", "3.13.0", true],
|
||||
["JSON_VIEW_USE_SSSE3", "_vssse3", "3.13.0", true]
|
||||
];
|
||||
var NO_VERSION = "NLOHMANN_JSON_NAMESPACE_NO_VERSION";
|
||||
|
||||
function el(tag, cls, text) {
|
||||
var node = document.createElement(tag);
|
||||
if (cls) { node.className = cls; }
|
||||
if (text !== undefined) { node.textContent = text; }
|
||||
return node;
|
||||
}
|
||||
|
||||
function seg(kind, code, note) {
|
||||
var span = el("span", "nj-integration-ns__seg nj-integration-ns__seg--" + kind);
|
||||
span.appendChild(el("code", "", code));
|
||||
var small = el("small");
|
||||
// allow line breaks after underscores so that long macro names stay narrow
|
||||
(note || "\u00a0").split("_").forEach(function (part, i, all) {
|
||||
small.appendChild(document.createTextNode(part + (i < all.length - 1 ? "_" : "")));
|
||||
if (i < all.length - 1) { small.appendChild(el("wbr")); }
|
||||
});
|
||||
span.appendChild(small);
|
||||
return span;
|
||||
}
|
||||
|
||||
function setup(fig) {
|
||||
if (fig.getAttribute("data-nj-ready")) { return; }
|
||||
fig.setAttribute("data-nj-ready", "1");
|
||||
var strip = fig.querySelector(".nj-integration-ns__strip");
|
||||
var caption = fig.querySelector("figcaption");
|
||||
var uid = "nj-integration-ns-" + Math.random().toString(36).slice(2, 8);
|
||||
var form = el("form", "nj-integration-ns__controls");
|
||||
form.setAttribute("aria-label", "Namespace name builder");
|
||||
form.addEventListener("submit", function (e) { e.preventDefault(); });
|
||||
|
||||
var vlabel = el("label", "nj-integration-ns__version", "Library version ");
|
||||
var select = el("select");
|
||||
VERSIONS.forEach(function (v) {
|
||||
var option = el("option", "", v);
|
||||
option.value = v;
|
||||
option.selected = v === "3.11.2";
|
||||
select.appendChild(option);
|
||||
});
|
||||
vlabel.appendChild(select);
|
||||
form.appendChild(vlabel);
|
||||
|
||||
var list = el("fieldset", "nj-integration-ns__list");
|
||||
list.appendChild(el("legend", "", "ABI-affecting macros, in tag order"));
|
||||
var boxes = TAGS.concat([[NO_VERSION, "", "3.11.2"]]).map(function (t, i) {
|
||||
var label = el("label", "nj-integration-ns__opt");
|
||||
var box = el("input");
|
||||
box.type = "checkbox";
|
||||
box.id = uid + "-" + i;
|
||||
box.checked = t[0] === "JSON_DIAGNOSTICS";
|
||||
label.htmlFor = box.id;
|
||||
label.appendChild(box);
|
||||
label.appendChild(el("code", "", t[0] + (t[3] ? "" : "=1")));
|
||||
var meta = el("span", "nj-integration-ns__meta");
|
||||
meta.appendChild(el("span", "nj-integration-ns__hint",
|
||||
t[0] === NO_VERSION ? "drops the version" : (t[3] ? "defined: " : "") + t[1]));
|
||||
meta.appendChild(el("span", "nj-integration-ns__since", "since " + t[2]));
|
||||
label.appendChild(meta);
|
||||
list.appendChild(label);
|
||||
return { def: t, box: box, label: label };
|
||||
});
|
||||
form.appendChild(list);
|
||||
fig.insertBefore(form, caption);
|
||||
|
||||
function update() {
|
||||
var version = select.value, index = VERSIONS.indexOf(version);
|
||||
var parts = [seg("root", "nlohmann", "root namespace"), seg("sep", "::"), seg("abi", "json_abi", "always")];
|
||||
var noVersion = false, defs = [];
|
||||
boxes.forEach(function (b) {
|
||||
var available = VERSIONS.indexOf(b.def[2]) <= index;
|
||||
b.box.disabled = !available;
|
||||
if (!available) { b.box.checked = false; }
|
||||
b.label.classList.toggle("is-unavailable", !available);
|
||||
if (!b.box.checked) { return; }
|
||||
defs.push(b.def[0] + (b.def[3] ? "" : "=1"));
|
||||
if (b.def[0] === NO_VERSION) { noVersion = true; } else { parts.push(seg("tag", b.def[1], b.def[0] + (b.def[3] ? "" : "=1"))); }
|
||||
});
|
||||
if (!noVersion) { parts.push(seg("ver", "_v" + version.replace(/\./g, "_"), "version " + version)); }
|
||||
strip.textContent = "";
|
||||
parts.forEach(function (p) { strip.appendChild(p); });
|
||||
strip.setAttribute("aria-label", "Resulting namespace: nlohmann::" + parts.slice(2).map(function (p) {
|
||||
return p.firstChild.textContent;
|
||||
}).join(""));
|
||||
caption.textContent = "Version " + version + (defs.length === 0 ? " with no ABI-affecting macro defined" :
|
||||
defs.length > 3 ? " with " + defs.length + " of the macros defined" : " with " + defs.join(", ")) + ".";
|
||||
}
|
||||
form.addEventListener("change", update);
|
||||
update();
|
||||
}
|
||||
|
||||
function init() {
|
||||
Array.prototype.forEach.call(document.querySelectorAll("[data-nj-integration-ns]"), setup);
|
||||
}
|
||||
|
||||
if (typeof document$ !== "undefined" && document$ && typeof document$.subscribe === "function") {
|
||||
document$.subscribe(init);
|
||||
} else if (document.readyState === "loading") {
|
||||
document.addEventListener("DOMContentLoaded", init);
|
||||
} else {
|
||||
init();
|
||||
}
|
||||
})();
|
||||
@@ -1,78 +0,0 @@
|
||||
/* figures: jsonview -- stepper for the edit frames on features/json_view.md.
|
||||
Without JS the frames (.nj-jsonview-step) show one below the other; with JS one frame at a time, with
|
||||
previous/next and one button per step. Never advances on its own. */
|
||||
(function () {
|
||||
"use strict";
|
||||
|
||||
function njJsonviewInit(root) {
|
||||
if (root.classList.contains("is-enhanced")) return;
|
||||
var steps = Array.prototype.slice.call(root.querySelectorAll(".nj-jsonview-step"));
|
||||
if (steps.length < 2) return;
|
||||
var current = 0;
|
||||
|
||||
var bar = document.createElement("div");
|
||||
bar.className = "nj-jsonview-controls";
|
||||
bar.setAttribute("role", "group");
|
||||
bar.setAttribute("aria-label", "Edit steps");
|
||||
|
||||
function button(label, aria, onClick) {
|
||||
var b = document.createElement("button");
|
||||
b.type = "button";
|
||||
b.textContent = label;
|
||||
b.setAttribute("aria-label", aria);
|
||||
b.addEventListener("click", onClick);
|
||||
bar.appendChild(b);
|
||||
return b;
|
||||
}
|
||||
|
||||
var prev = button("‹ Back", "Previous step", function () { show(current - 1, true); });
|
||||
var dots = steps.map(function (s, i) {
|
||||
return button(String(i + 1), "Step " + (i + 1) + ": " + (s.getAttribute("data-label") || ""), function () { show(i, true); });
|
||||
});
|
||||
var next = button("Next ›", "Next step", function () { show(current + 1, true); });
|
||||
var status = document.createElement("span");
|
||||
status.className = "nj-jsonview-status";
|
||||
status.setAttribute("aria-live", "polite");
|
||||
bar.appendChild(status);
|
||||
|
||||
function show(i, focusKeep) {
|
||||
current = Math.max(0, Math.min(steps.length - 1, i));
|
||||
steps.forEach(function (s, k) {
|
||||
s.classList.toggle("is-current", k === current);
|
||||
s.setAttribute("aria-hidden", k === current ? "false" : "true");
|
||||
});
|
||||
dots.forEach(function (d, k) {
|
||||
if (k === current) d.setAttribute("aria-current", "step"); else d.removeAttribute("aria-current");
|
||||
});
|
||||
prev.disabled = current === 0;
|
||||
next.disabled = current === steps.length - 1;
|
||||
status.textContent = "Step " + (current + 1) + " of " + steps.length;
|
||||
if (focusKeep && document.activeElement && document.activeElement.disabled) {
|
||||
(current === 0 ? next : prev).focus();
|
||||
}
|
||||
}
|
||||
|
||||
root.addEventListener("keydown", function (e) {
|
||||
if (e.target.tagName !== "BUTTON") return;
|
||||
if (e.key === "ArrowRight") { show(current + 1, true); e.preventDefault(); }
|
||||
else if (e.key === "ArrowLeft") { show(current - 1, true); e.preventDefault(); }
|
||||
});
|
||||
|
||||
root.insertBefore(bar, root.firstChild);
|
||||
root.classList.add("is-enhanced");
|
||||
show(0, false);
|
||||
}
|
||||
|
||||
function njJsonviewAll() {
|
||||
var roots = document.querySelectorAll("[data-nj-jsonview-steps]");
|
||||
for (var i = 0; i < roots.length; i++) njJsonviewInit(roots[i]);
|
||||
}
|
||||
|
||||
if (typeof document$ !== "undefined" && document$ && typeof document$.subscribe === "function") {
|
||||
document$.subscribe(njJsonviewAll);
|
||||
} else if (document.readyState === "loading") {
|
||||
document.addEventListener("DOMContentLoaded", njJsonviewAll);
|
||||
} else {
|
||||
njJsonviewAll();
|
||||
}
|
||||
})();
|
||||
@@ -1,585 +0,0 @@
|
||||
/* figures: macro chooser for the NLOHMANN_DEFINE_TYPE_* / NLOHMANN_DEFINE_DERIVED_TYPE_* macros.
|
||||
Usage: <div class="nj-macro-chooser" data-variant="full|compact" data-preset="base=yes,keys=custom" markdown>
|
||||
with a static fallback list inside (shown without JavaScript). Links marked with { data-nj-mc="KEY" } in the
|
||||
fallback are reused for the reference links, so each embedding page resolves its own relative URLs. Keys:
|
||||
intrusive, non_intrusive, derived, with_names, third_party, non_default.
|
||||
The rules follow include/nlohmann/detail/macro_scope.hpp: WITH_NAMES takes "key", member pairs and no empty
|
||||
member list; WITH_DEFAULT and the plain variants default-construct the type in from_json/get; ONLY_SERIALIZE
|
||||
generates to_json only; a type that is not default constructible and converts both ways gets no macro but an
|
||||
adl_serializer specialization whose from_json returns the value; DERIVED_TYPE calls the base type's to_json/from_json first; at most 63 members (31 with
|
||||
WITH_NAMES). The generated programs were compiled and run with clang++ -std=c++11 against include/. */
|
||||
(function () {
|
||||
"use strict";
|
||||
|
||||
var QUESTIONS = [
|
||||
{ id: "edit", legend: "Can you edit the class?", options: [["yes", "Yes"], ["no", "No, it is third-party"]] },
|
||||
{ id: "access", legend: "Member access", options: [["public", "All public"], ["private", "Some private"]] },
|
||||
{ id: "base", legend: "Base class", options: [["no", "None"], ["yes", "Derived from a base"]] },
|
||||
{ id: "dir", legend: "Direction", options: [["both", "To and from JSON"], ["to", "Only to JSON"]] },
|
||||
{ id: "missing", legend: "Missing keys when parsing", options: [["throw", "Throw"], ["default", "Keep defaults"]] },
|
||||
{ id: "keys", legend: "JSON keys", options: [["members", "Member names"], ["custom", "Custom names"]] },
|
||||
{ id: "ctor", legend: "Default constructible?", options: [["yes", "Yes"], ["no", "No"]] }
|
||||
];
|
||||
|
||||
var KEYWORDS = ("alignas alignof and asm auto bool break case catch char class const constexpr continue decltype default " +
|
||||
"delete do double else enum explicit export extern false float for friend goto if inline int long mutable namespace " +
|
||||
"new noexcept not nullptr operator or private protected public register return short signed sizeof static " +
|
||||
"struct switch template this throw true try typedef typeid typename union unsigned using virtual void volatile " +
|
||||
"while").split(" ");
|
||||
var HL_TYPES = ["int", "bool", "double", "float", "char", "void", "auto", "unsigned", "long", "short", "signed"];
|
||||
var HL_CONST = ["true", "false", "nullptr"];
|
||||
var IDENT = /^[A-Za-z_][A-Za-z0-9_]*$/;
|
||||
var MEMBER_TYPE = /^[A-Za-z_][A-Za-z0-9_:<>, ]*$/;
|
||||
|
||||
var counter = 0;
|
||||
|
||||
function el(tag, attrs, text) {
|
||||
var e = document.createElement(tag);
|
||||
if (attrs) {
|
||||
Object.keys(attrs).forEach(function (k) { e.setAttribute(k, attrs[k]); });
|
||||
}
|
||||
if (text !== undefined) e.textContent = text;
|
||||
return e;
|
||||
}
|
||||
|
||||
function esc(s) {
|
||||
return s.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
|
||||
}
|
||||
|
||||
/* small C++ tokenizer emitting the Pygments classes the site already colours */
|
||||
function highlight(code) {
|
||||
var out = "";
|
||||
var re = /(\/\/[^\n]*)|(#include)|(<[a-z_/.]+\.hpp>|<[a-z]+>)|("(?:[^"\\\n]|\\.)*")|(\b\d+\b)|([A-Za-z_][A-Za-z0-9_]*)|(::|<<|==|[=:<>&])|([{}()\[\];,.!])|(\s+)|(.)/g;
|
||||
var m, prev = "";
|
||||
while ((m = re.exec(code)) !== null) {
|
||||
var t = m[0];
|
||||
if (m[1]) out += '<span class="c1">' + esc(t) + "</span>";
|
||||
else if (m[2]) out += '<span class="cp">' + esc(t) + "</span>";
|
||||
else if (m[3] && prev === "#include") out += '<span class="cpf">' + esc(t) + "</span>";
|
||||
else if (m[4]) out += '<span class="s">' + esc(t) + "</span>";
|
||||
else if (m[5]) out += '<span class="mi">' + esc(t) + "</span>";
|
||||
else if (m[6]) {
|
||||
var cls = "n";
|
||||
if (HL_CONST.indexOf(t) >= 0) cls = "kc";
|
||||
else if (HL_TYPES.indexOf(t) >= 0) cls = "kt";
|
||||
else if (KEYWORDS.indexOf(t) >= 0) cls = "k";
|
||||
else if (prev === "namespace") cls = "nn";
|
||||
else if (prev === "struct" || prev === "class") cls = "nc";
|
||||
out += '<span class="' + cls + '">' + esc(t) + "</span>";
|
||||
} else if (m[7]) out += '<span class="o">' + esc(t) + "</span>";
|
||||
else if (m[8]) out += '<span class="p">' + esc(t) + "</span>";
|
||||
else out += esc(t);
|
||||
if (!m[9]) prev = (m[3] && prev === "#include") ? "" : t;
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
function parsePreset(s) {
|
||||
var r = {};
|
||||
(s || "").split(",").forEach(function (kv) {
|
||||
var p = kv.split("=");
|
||||
if (p.length === 2) r[p[0].trim()] = p[1].trim();
|
||||
});
|
||||
return r;
|
||||
}
|
||||
|
||||
/* ---- the decision logic, independent of the DOM ---- */
|
||||
function decide(st) {
|
||||
var res = { errors: [], warnings: [], macro: null, reason: "", place: "", ref: null };
|
||||
var n = st.members.length;
|
||||
var names = st.keys === "custom";
|
||||
|
||||
if (st.edit === "no" && st.access === "private") {
|
||||
res.errors.push({ text: "No macro can reach private members from outside the class. Write to_json/from_json by hand using the public interface, for example in a specialization of adl_serializer.", link: "third_party", linkText: "How do I convert third-party types?" });
|
||||
}
|
||||
var adl = st.dir === "both" && st.ctor === "no";
|
||||
if (!adl && names && n === 0) {
|
||||
res.errors.push({ text: "The WITH_NAMES macros need at least one key and member pair. Without members there is nothing to rename: choose Member names." });
|
||||
}
|
||||
var limit = names ? 31 : 63;
|
||||
if (!adl && n > limit) {
|
||||
res.errors.push({ text: "The macros support at most " + limit + " members" + (names ? " with custom names" : "") + ". Write to_json/from_json by hand for larger types." });
|
||||
}
|
||||
|
||||
/* identifier checks */
|
||||
if (!IDENT.test(st.type) || KEYWORDS.indexOf(st.type) >= 0) res.errors.push({ text: "The type name must be a C++ identifier." });
|
||||
if (st.base === "yes" && (!IDENT.test(st.baseName) || KEYWORDS.indexOf(st.baseName) >= 0)) res.errors.push({ text: "The base class name must be a C++ identifier." });
|
||||
if (st.base === "yes" && st.baseName === st.type) res.errors.push({ text: "The base class needs a different name than the type." });
|
||||
var seenName = {}, seenKey = {};
|
||||
st.members.forEach(function (mb, i) {
|
||||
var label = "Member " + (i + 1);
|
||||
if (!IDENT.test(mb.name) || KEYWORDS.indexOf(mb.name) >= 0) res.errors.push({ text: label + ": the name must be a C++ identifier." });
|
||||
else if (seenName[mb.name]) res.errors.push({ text: label + ": the name " + mb.name + " is used twice." });
|
||||
else if (mb.name === st.type) res.errors.push({ text: label + ": a member cannot have the name of its class." });
|
||||
seenName[mb.name] = true;
|
||||
if (!MEMBER_TYPE.test(mb.mtype.trim())) res.errors.push({ text: label + ": enter a type such as int, std::string or std::vector<int>." });
|
||||
var key = names ? mb.key : mb.name;
|
||||
if (seenKey[key]) res.warnings.push(label + ": the JSON key \"" + key + "\" is used twice; the later member overwrites the earlier one in to_json.");
|
||||
seenKey[key] = true;
|
||||
if (st.base === "yes" && key === "id") res.warnings.push(label + ": the key \"id\" is also written by the example base class; the derived member overwrites it.");
|
||||
});
|
||||
|
||||
if (st.edit === "no" && st.access === "private") return res;
|
||||
|
||||
if (adl) {
|
||||
res.adl = true;
|
||||
res.intrusive = st.access === "private";
|
||||
res.ref = "non_default";
|
||||
res.reason = "Every macro that generates from_json default-constructs the type, so none fits. A specialization of adl_serializer returns the value from from_json instead" +
|
||||
(st.access === "private" ? "; the class befriends it to reach the private members" : "") + ".";
|
||||
res.place = "Write the specialization in namespace nlohmann, after the class.";
|
||||
return res;
|
||||
}
|
||||
|
||||
var intrusive = st.access === "private";
|
||||
var parts = ["NLOHMANN_DEFINE", st.base === "yes" ? "DERIVED_TYPE" : "TYPE", intrusive ? "INTRUSIVE" : "NON_INTRUSIVE"];
|
||||
if (st.dir === "to") parts.push("ONLY_SERIALIZE");
|
||||
else if (st.missing === "default") parts.push("WITH_DEFAULT");
|
||||
if (names) parts.push("WITH_NAMES");
|
||||
res.macro = parts.join("_");
|
||||
res.intrusive = intrusive;
|
||||
res.ref = names ? "with_names" : (st.base === "yes" ? "derived" : (intrusive ? "intrusive" : "non_intrusive"));
|
||||
|
||||
var why = [];
|
||||
if (intrusive) why.push("Private members need the macro inside the class, where its friend functions can access them");
|
||||
else if (st.edit === "no") why.push("You cannot edit the class, so the macro goes next to it in its namespace, which works because all members are public");
|
||||
else why.push("All members are public, so the macro can stay outside the class, in its namespace");
|
||||
if (st.base === "yes") why.push("the conversion of " + (st.baseName || "the base") + " runs first");
|
||||
if (st.dir === "to") why.push("only to_json is generated");
|
||||
else if (st.missing === "default") why.push("missing keys keep the value of a default-constructed " + st.type);
|
||||
else why.push("a missing key throws out_of_range.403");
|
||||
if (names) why.push("each member is preceded by its JSON key");
|
||||
res.reason = why.join("; ") + ".";
|
||||
res.place = intrusive ? "Write the macro inside the class body." : "Write the macro after the class, in the same namespace.";
|
||||
if (st.dir === "to" && st.ctor === "no") res.warnings.push("The type is not default constructible: fine for ONLY_SERIALIZE, but j.get<" + st.type + ">() will not compile.");
|
||||
return res;
|
||||
}
|
||||
|
||||
/* C++ string literal; control characters as three-digit octal escapes, which cannot run into the next character */
|
||||
function cppString(s) {
|
||||
return '"' + s.replace(/[\\"\u0000-\u001f\u007f]/g, function (c) {
|
||||
if (c === "\\" || c === '"') return "\\" + c;
|
||||
var o = c.charCodeAt(0).toString(8);
|
||||
return "\\" + ("00" + o).slice(-3);
|
||||
}) + '"';
|
||||
}
|
||||
|
||||
function macroCall(name, head, pairs, indent) {
|
||||
var one = name + "(" + head.concat(pairs).join(", ") + ")";
|
||||
if (one.length + indent.length <= 88) return indent + one;
|
||||
var lines = [indent + name + "(" + head.join(", ") + (pairs.length ? "," : ")")];
|
||||
pairs.forEach(function (p, i) {
|
||||
lines.push(indent + " " + p + (i === pairs.length - 1 ? ")" : ","));
|
||||
});
|
||||
return lines.join("\n");
|
||||
}
|
||||
|
||||
function generate(st, res) {
|
||||
var ns = "ns";
|
||||
var T = st.type, B = st.baseName;
|
||||
var priv = res.intrusive;
|
||||
var names = st.keys === "custom";
|
||||
var suffix = st.dir === "to" ? "_ONLY_SERIALIZE" : (st.missing === "default" ? "_WITH_DEFAULT" : "");
|
||||
var adl = !!res.adl;
|
||||
var noCtor = st.ctor === "no" && (st.members.length > 0 || st.base === "yes");
|
||||
var L = [];
|
||||
L.push("#include <iostream>");
|
||||
L.push("#include <nlohmann/json.hpp>");
|
||||
L.push("");
|
||||
L.push("using nlohmann::json;");
|
||||
L.push("");
|
||||
L.push("namespace " + ns);
|
||||
L.push("{");
|
||||
if (st.base === "yes") {
|
||||
L.push("// stand-in for your base class: it must be serializable itself");
|
||||
if (priv) {
|
||||
L.push("class " + B);
|
||||
L.push("{");
|
||||
L.push(" private:");
|
||||
L.push(" int id{};");
|
||||
L.push("");
|
||||
L.push(" public:");
|
||||
L.push(" NLOHMANN_DEFINE_TYPE_INTRUSIVE" + suffix + "(" + B + ", id)");
|
||||
L.push("};");
|
||||
} else {
|
||||
L.push("struct " + B);
|
||||
L.push("{");
|
||||
L.push(" int id{};");
|
||||
L.push("};");
|
||||
L.push("NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE" + suffix + "(" + B + ", id)");
|
||||
}
|
||||
L.push("");
|
||||
}
|
||||
var kw = priv ? "class " : "struct ";
|
||||
var inherit = st.base === "yes" ? (priv ? " : public " + B : " : " + B) : "";
|
||||
L.push(kw + T + inherit);
|
||||
L.push("{");
|
||||
if (priv) L.push(" private:");
|
||||
st.members.forEach(function (mb) {
|
||||
L.push(" " + mb.mtype.trim() + " " + mb.name + (noCtor ? ";" : "{};"));
|
||||
});
|
||||
var head = [T];
|
||||
if (st.base === "yes") head.push(B);
|
||||
var pairs = st.members.map(function (mb) {
|
||||
return names ? cppString(mb.key) + ", " + mb.name : mb.name;
|
||||
});
|
||||
if (noCtor || priv) {
|
||||
if (st.members.length) L.push("");
|
||||
if (priv) L.push(" public:");
|
||||
}
|
||||
if (noCtor) {
|
||||
var plist = st.members.map(function (mb) { return mb.mtype.trim() + " " + mb.name + "_"; });
|
||||
var ilist = st.members.map(function (mb) { return mb.name + "(" + mb.name + "_)"; });
|
||||
if (st.base === "yes") {
|
||||
plist.unshift(B + " base_");
|
||||
ilist.unshift(B + "(base_)");
|
||||
}
|
||||
L.push(" " + T + "(" + plist.join(", ") + ")");
|
||||
L.push(" : " + ilist.join(", "));
|
||||
L.push(" {}");
|
||||
if (priv) L.push("");
|
||||
}
|
||||
if (adl) {
|
||||
if (priv) {
|
||||
L.push(" friend struct nlohmann::adl_serializer<" + T + ">;");
|
||||
}
|
||||
L.push("};");
|
||||
L.push("} // namespace " + ns);
|
||||
L.push("");
|
||||
L.push("namespace nlohmann");
|
||||
L.push("{");
|
||||
L.push("template <>");
|
||||
L.push("struct adl_serializer<" + ns + "::" + T + ">");
|
||||
L.push("{");
|
||||
L.push(" // note: the return type is the value, not void, and there is no default construction");
|
||||
L.push(" static " + ns + "::" + T + " from_json(const json& j)");
|
||||
L.push(" {");
|
||||
var args = st.members.map(function (mb) {
|
||||
var key = names ? cppString(mb.key) : cppString(mb.name);
|
||||
var ty = mb.mtype.trim();
|
||||
return st.missing === "default"
|
||||
? "j.value(" + key + ", " + ty + "{})"
|
||||
: "j.at(" + key + ").get<" + ty + ">()";
|
||||
});
|
||||
if (st.base === "yes") args.unshift("j.get<" + ns + "::" + B + ">()");
|
||||
L.push(" return " + ns + "::" + T + "{" + args.join(", ") + "};");
|
||||
L.push(" }");
|
||||
L.push("");
|
||||
L.push(" // you must provide to_json as well: the specialization replaces the default one");
|
||||
L.push(" static void to_json(json& j, const " + ns + "::" + T + "& t)");
|
||||
L.push(" {");
|
||||
if (st.base === "yes") L.push(" j = static_cast<const " + ns + "::" + B + "&>(t);");
|
||||
else L.push(" j = json::object();");
|
||||
st.members.forEach(function (mb) {
|
||||
L.push(" j[" + (names ? cppString(mb.key) : cppString(mb.name)) + "] = t." + mb.name + ";");
|
||||
});
|
||||
L.push(" }");
|
||||
L.push("};");
|
||||
L.push("} // namespace nlohmann");
|
||||
} else if (priv) {
|
||||
L.push(macroCall(res.macro, head, pairs, " "));
|
||||
L.push("};");
|
||||
} else {
|
||||
L.push("};");
|
||||
L.push("");
|
||||
L.push(macroCall(res.macro, head, pairs, ""));
|
||||
}
|
||||
if (!adl) L.push("} // namespace " + ns);
|
||||
L.push("");
|
||||
L.push("int main()");
|
||||
L.push("{");
|
||||
var Q = ns + "::" + T;
|
||||
if (noCtor) {
|
||||
var init = st.members.map(function (mb) { return mb.mtype.trim() + "{}"; });
|
||||
if (st.base === "yes") init.unshift(ns + "::" + B + "{}");
|
||||
L.push(" " + Q + " p{" + init.join(", ") + "};");
|
||||
} else {
|
||||
L.push(" " + Q + " p{};");
|
||||
}
|
||||
L.push(" json j = p; // to_json");
|
||||
L.push(" std::cout << j.dump() << '\\n';");
|
||||
if (st.dir === "both") {
|
||||
L.push("");
|
||||
L.push(" auto p2 = j.get<" + Q + ">(); // from_json");
|
||||
L.push(" std::cout << (json(p2) == j) << '\\n'; // round trip: 1");
|
||||
if (st.missing === "default") {
|
||||
L.push("");
|
||||
L.push(" // missing keys keep the defaults");
|
||||
L.push(" std::cout << json(json::object().get<" + Q + ">()).dump() << '\\n';");
|
||||
} else {
|
||||
L.push(" // a missing key throws json::out_of_range (403)");
|
||||
}
|
||||
}
|
||||
L.push("}");
|
||||
return L.join("\n") + "\n";
|
||||
}
|
||||
|
||||
function copyText(text, done) {
|
||||
function fallback() {
|
||||
var ta = el("textarea", { readonly: "", "aria-hidden": "true" });
|
||||
ta.value = text;
|
||||
ta.style.position = "fixed";
|
||||
ta.style.opacity = "0";
|
||||
document.body.appendChild(ta);
|
||||
ta.select();
|
||||
var ok = false;
|
||||
try { ok = document.execCommand("copy"); } catch (e) { ok = false; }
|
||||
document.body.removeChild(ta);
|
||||
done(ok);
|
||||
}
|
||||
if (navigator.clipboard && window.isSecureContext) {
|
||||
navigator.clipboard.writeText(text).then(function () { done(true); }, fallback);
|
||||
} else {
|
||||
fallback();
|
||||
}
|
||||
}
|
||||
|
||||
/* ---- DOM ---- */
|
||||
function setup(root) {
|
||||
if (root.dataset.njMcReady) return;
|
||||
root.dataset.njMcReady = "1";
|
||||
var uid = "nj-mc-" + (++counter);
|
||||
var variant = root.getAttribute("data-variant") || "full";
|
||||
var preset = parsePreset(root.getAttribute("data-preset"));
|
||||
|
||||
var links = {};
|
||||
Array.prototype.forEach.call(root.querySelectorAll("a[data-nj-mc]"), function (a) {
|
||||
links[a.getAttribute("data-nj-mc")] = a.getAttribute("href");
|
||||
});
|
||||
|
||||
var st = { edit: "yes", access: "public", base: "no", dir: "both", missing: "throw", keys: "members", ctor: "yes",
|
||||
type: "person", baseName: "entity",
|
||||
members: [{ mtype: "std::string", name: "name", key: "name" }, { mtype: "int", name: "age", key: "age" }] };
|
||||
QUESTIONS.forEach(function (q) {
|
||||
if (preset[q.id] && q.options.some(function (o) { return o[0] === preset[q.id]; })) st[q.id] = preset[q.id];
|
||||
});
|
||||
|
||||
var fallback = root.querySelector(".nj-mc-fallback");
|
||||
if (fallback) fallback.hidden = true;
|
||||
|
||||
var app = el("div", { "class": "nj-mc-app" });
|
||||
var form = el("form", { "class": "nj-mc-form", "aria-label": "Macro chooser options" });
|
||||
form.addEventListener("submit", function (e) { e.preventDefault(); });
|
||||
|
||||
var qgrid = el("div", { "class": "nj-mc-questions" });
|
||||
var notes = {};
|
||||
var groups = {};
|
||||
QUESTIONS.forEach(function (q) {
|
||||
var fs = el("fieldset", { "class": "nj-mc-q" });
|
||||
fs.appendChild(el("legend", null, q.legend));
|
||||
var seg = el("div", { "class": "nj-mc-seg" });
|
||||
q.options.forEach(function (o) {
|
||||
var id = uid + "-" + q.id + "-" + o[0];
|
||||
var inp = el("input", { type: "radio", id: id, name: uid + "-" + q.id, value: o[0] });
|
||||
if (st[q.id] === o[0]) inp.checked = true;
|
||||
inp.addEventListener("change", function () { st[q.id] = o[0]; update(); });
|
||||
seg.appendChild(inp);
|
||||
seg.appendChild(el("label", { "for": id }, o[1]));
|
||||
});
|
||||
fs.appendChild(seg);
|
||||
var note = el("p", { "class": "nj-mc-qnote", id: uid + "-" + q.id + "-note" });
|
||||
note.hidden = true;
|
||||
fs.appendChild(note);
|
||||
fs.setAttribute("aria-describedby", note.id);
|
||||
notes[q.id] = note;
|
||||
groups[q.id] = fs;
|
||||
qgrid.appendChild(fs);
|
||||
});
|
||||
form.appendChild(qgrid);
|
||||
|
||||
/* type editor */
|
||||
var editor = el("div", { "class": "nj-mc-editor" });
|
||||
var names = el("div", { "class": "nj-mc-names" });
|
||||
function textField(label, value, onInput, cls) {
|
||||
var id = uid + "-f" + (++counter);
|
||||
var w = el("div", { "class": "nj-mc-field" + (cls ? " " + cls : "") });
|
||||
w.appendChild(el("label", { "for": id }, label));
|
||||
var inp = el("input", { type: "text", id: id, spellcheck: "false", autocomplete: "off", autocapitalize: "off" });
|
||||
inp.value = value;
|
||||
inp.addEventListener("input", function () { onInput(inp.value); update(); });
|
||||
w.appendChild(inp);
|
||||
return w;
|
||||
}
|
||||
names.appendChild(textField("Type name", st.type, function (v) { st.type = v.trim(); }));
|
||||
var baseField = textField("Base class", st.baseName, function (v) { st.baseName = v.trim(); }, "nj-mc-basefield");
|
||||
names.appendChild(baseField);
|
||||
editor.appendChild(names);
|
||||
|
||||
var mtable = el("div", { "class": "nj-mc-members", role: "group", "aria-label": "Member variables" });
|
||||
var mhead = el("div", { "class": "nj-mc-mrow nj-mc-mhead", "aria-hidden": "true" });
|
||||
mhead.appendChild(el("span", null, "Member type"));
|
||||
mhead.appendChild(el("span", null, "Member name"));
|
||||
var keyHead = el("span", { "class": "nj-mc-keycol" }, "JSON key");
|
||||
mhead.appendChild(keyHead);
|
||||
mhead.appendChild(el("span"));
|
||||
mtable.appendChild(mhead);
|
||||
var mbody = el("div", { "class": "nj-mc-mbody" });
|
||||
mtable.appendChild(mbody);
|
||||
var addBtn = el("button", { type: "button", "class": "nj-mc-add" }, "Add member");
|
||||
addBtn.addEventListener("click", function () {
|
||||
var k = st.members.length + 1;
|
||||
var nm = "member" + k;
|
||||
while (st.members.some(function (mb) { return mb.name === nm; })) nm = "member" + (++k);
|
||||
st.members.push({ mtype: "int", name: nm, key: nm });
|
||||
renderMembers();
|
||||
update();
|
||||
var rows = mbody.querySelectorAll(".nj-mc-mrow");
|
||||
var last = rows[rows.length - 1];
|
||||
if (last) last.querySelector("input").focus();
|
||||
});
|
||||
editor.appendChild(mtable);
|
||||
editor.appendChild(addBtn);
|
||||
if (variant === "full") form.appendChild(editor);
|
||||
|
||||
function renderMembers() {
|
||||
mbody.textContent = "";
|
||||
st.members.forEach(function (mb, i) {
|
||||
var row = el("div", { "class": "nj-mc-mrow" });
|
||||
function cell(prop, label, cls) {
|
||||
var inp = el("input", { type: "text", spellcheck: "false", autocomplete: "off", autocapitalize: "off",
|
||||
"aria-label": label + " of member " + (i + 1), placeholder: label, "class": cls || "" });
|
||||
inp.value = mb[prop];
|
||||
inp.addEventListener("input", function () {
|
||||
var keyFollows = prop === "name" && mb.key === mb.name;
|
||||
mb[prop] = prop === "key" ? inp.value : inp.value.trim();
|
||||
if (keyFollows) {
|
||||
mb.key = mb.name;
|
||||
var k = row.querySelector(".nj-mc-keycol");
|
||||
if (k) k.value = mb.key;
|
||||
}
|
||||
update();
|
||||
});
|
||||
row.appendChild(inp);
|
||||
}
|
||||
cell("mtype", "Type");
|
||||
cell("name", "Name");
|
||||
cell("key", "JSON key", "nj-mc-keycol");
|
||||
var rm = el("button", { type: "button", "class": "nj-mc-rm", "aria-label": "Remove member " + (i + 1), title: "Remove member" });
|
||||
rm.appendChild(el("span", { "aria-hidden": "true" }, "\u00d7"));
|
||||
rm.addEventListener("click", function () {
|
||||
st.members.splice(i, 1);
|
||||
renderMembers();
|
||||
update();
|
||||
var btns = mbody.querySelectorAll(".nj-mc-rm");
|
||||
(btns[Math.min(i, btns.length - 1)] || addBtn).focus();
|
||||
});
|
||||
row.appendChild(rm);
|
||||
mbody.appendChild(row);
|
||||
});
|
||||
}
|
||||
renderMembers();
|
||||
app.appendChild(form);
|
||||
|
||||
/* output */
|
||||
var out = el("div", { "class": "nj-mc-out" });
|
||||
var result = el("div", { "class": "nj-mc-result", role: "status", "aria-live": "polite" });
|
||||
out.appendChild(result);
|
||||
var hints = el("ul", { "class": "nj-mc-hints" });
|
||||
out.appendChild(hints);
|
||||
var codeWrap = el("div", { "class": "nj-mc-code" });
|
||||
var bar = el("div", { "class": "nj-mc-codebar" });
|
||||
bar.appendChild(el("span", { "class": "nj-mc-codetitle" }, "Generated code (C++11)"));
|
||||
var copyBtn = el("button", { type: "button", "class": "nj-mc-copy", "aria-label": "Copy generated code" }, "Copy");
|
||||
var copyStatus = el("span", { "class": "nj-mc-copystatus", role: "status", "aria-live": "polite" });
|
||||
bar.appendChild(copyStatus);
|
||||
bar.appendChild(copyBtn);
|
||||
codeWrap.appendChild(bar);
|
||||
var hl = el("div", { "class": "language-cpp highlight" });
|
||||
var pre = el("pre");
|
||||
var code = el("code", { tabindex: "0", "aria-label": "Generated C++ code" });
|
||||
pre.appendChild(code);
|
||||
hl.appendChild(pre);
|
||||
codeWrap.appendChild(hl);
|
||||
if (variant === "full") out.appendChild(codeWrap);
|
||||
app.appendChild(out);
|
||||
root.appendChild(app);
|
||||
|
||||
var currentCode = "";
|
||||
var statusTimer = null;
|
||||
copyBtn.addEventListener("click", function () {
|
||||
copyText(currentCode, function (ok) {
|
||||
copyStatus.textContent = ok ? "Copied" : "Press Ctrl+C / Cmd+C to copy";
|
||||
if (!ok) {
|
||||
var r = document.createRange();
|
||||
r.selectNodeContents(code);
|
||||
var s = window.getSelection();
|
||||
s.removeAllRanges();
|
||||
s.addRange(r);
|
||||
}
|
||||
clearTimeout(statusTimer);
|
||||
statusTimer = setTimeout(function () { copyStatus.textContent = ""; }, 2500);
|
||||
});
|
||||
});
|
||||
|
||||
function setNote(id, text) {
|
||||
notes[id].hidden = !text;
|
||||
notes[id].textContent = text || "";
|
||||
}
|
||||
|
||||
function addLink(parent, key, text) {
|
||||
if (!key || !links[key]) return;
|
||||
parent.appendChild(document.createTextNode(" "));
|
||||
parent.appendChild(el("a", { href: links[key] }, text));
|
||||
}
|
||||
|
||||
function update() {
|
||||
var dirTo = st.dir === "to";
|
||||
groups.missing.disabled = dirTo;
|
||||
groups.missing.classList.toggle("nj-mc-off", dirTo);
|
||||
setNote("missing", dirTo ? "Not applicable: ONLY_SERIALIZE generates no from_json." : "");
|
||||
setNote("access", st.edit === "no" && st.access === "private" ? "Private members of a class you cannot edit are out of reach for every macro." : "");
|
||||
setNote("ctor", st.ctor === "no" && !dirTo ? "The macros default-construct the type when parsing: this gives an adl_serializer specialization instead." : "");
|
||||
baseField.hidden = st.base !== "yes";
|
||||
mtable.classList.toggle("nj-mc-custom", st.keys === "custom");
|
||||
keyHead.hidden = st.keys !== "custom";
|
||||
|
||||
var res = decide(st);
|
||||
result.textContent = "";
|
||||
hints.textContent = "";
|
||||
if ((res.macro || res.adl) && !res.errors.length) {
|
||||
result.className = "nj-mc-result";
|
||||
result.appendChild(el("p", { "class": "nj-mc-label" }, res.adl ? "No macro fits, write a serializer" : "Recommended macro"));
|
||||
var name = el("p", { "class": "nj-mc-macro" });
|
||||
name.appendChild(el("code", null, res.adl ? "adl_serializer<" + st.type + ">" : res.macro));
|
||||
result.appendChild(name);
|
||||
var why = el("p", { "class": "nj-mc-why" }, res.reason + " " + res.place);
|
||||
addLink(why, res.ref, res.adl ? "Details" : "Reference");
|
||||
result.appendChild(why);
|
||||
} else {
|
||||
result.className = "nj-mc-result nj-mc-bad";
|
||||
result.appendChild(el("p", { "class": "nj-mc-label" }, (res.macro || res.adl) ? "Cannot generate this code yet" : "No macro fits"));
|
||||
res.errors.forEach(function (e) {
|
||||
var p = el("p", { "class": "nj-mc-why" }, e.text);
|
||||
addLink(p, e.link, e.linkText);
|
||||
result.appendChild(p);
|
||||
});
|
||||
}
|
||||
res.warnings.forEach(function (w) { hints.appendChild(el("li", null, w)); });
|
||||
hints.hidden = !res.warnings.length;
|
||||
|
||||
var ok = (res.macro || res.adl) && !res.errors.length;
|
||||
codeWrap.hidden = !ok;
|
||||
if (ok) {
|
||||
currentCode = generate(st, res);
|
||||
code.innerHTML = highlight(currentCode);
|
||||
}
|
||||
root.setAttribute("data-nj-mc-macro", ok ? (res.macro || "adl_serializer") : "");
|
||||
}
|
||||
update();
|
||||
}
|
||||
|
||||
function init() {
|
||||
Array.prototype.forEach.call(document.querySelectorAll(".nj-macro-chooser"), setup);
|
||||
}
|
||||
|
||||
if (typeof document$ !== "undefined" && document$ && typeof document$.subscribe === "function") {
|
||||
document$.subscribe(init);
|
||||
} else if (document.readyState === "loading") {
|
||||
document.addEventListener("DOMContentLoaded", init);
|
||||
} else {
|
||||
init();
|
||||
}
|
||||
|
||||
/* exported for the verification scripts */
|
||||
window.njMacroChooser = { decide: decide, generate: generate };
|
||||
})();
|
||||
@@ -1,306 +0,0 @@
|
||||
/* figures: pointer
|
||||
*
|
||||
* Two widgets that enhance static markup (the markup alone is a complete, readable figure):
|
||||
* - [data-nj-pointer-walk] in features/json_pointer.md: a tree of the example document plus a pointer bar whose
|
||||
* segments select a prefix of the pointer; the path down to that level is highlighted and its value is shown.
|
||||
* - [data-nj-patch] in features/json_patch.md: a stepper through six JSON Patch operations; the static table of the
|
||||
* operations is hidden once the stepper is built.
|
||||
* Initialised through Material's document$ (navigation.instant), idempotent per element.
|
||||
*/
|
||||
(function () {
|
||||
"use strict";
|
||||
|
||||
function el(tag, cls, html) {
|
||||
var e = document.createElement(tag);
|
||||
if (cls) e.className = cls;
|
||||
if (html !== undefined) e.innerHTML = html;
|
||||
return e;
|
||||
}
|
||||
function esc(s) {
|
||||
return String(s).replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """);
|
||||
}
|
||||
|
||||
/* ---------- JSON Pointer walker ---------- */
|
||||
|
||||
var PRESETS = ["", "/array", "/array/0", "/array/1", "/array/2", "/nested", "/nested/one", "/nested/two",
|
||||
"/nested/three", "/nested/three/0", "/nested/three/1", "/"];
|
||||
|
||||
function tokens(ptr) {
|
||||
if (ptr === "") return [];
|
||||
return ptr.slice(1).split("/").map(function (t) { return t.replace(/~1/g, "/").replace(/~0/g, "~"); });
|
||||
}
|
||||
function joinTokens(toks) {
|
||||
return toks.map(function (t) { return "/" + t.replace(/~/g, "~0").replace(/\//g, "~1"); }).join("");
|
||||
}
|
||||
// RFC 6901 resolution as json::at() does it; returns {ok, value, depth, error}
|
||||
function resolve(doc, toks) {
|
||||
var v = doc;
|
||||
for (var i = 0; i < toks.length; ++i) {
|
||||
var t = toks[i];
|
||||
if (Array.isArray(v)) {
|
||||
if (!/^(0|[1-9][0-9]*)$/.test(t) || Number(t) >= v.length) {
|
||||
return { ok: false, depth: i, error: "at() throws out_of_range: array index '" + t + "' is out of range" };
|
||||
}
|
||||
v = v[Number(t)];
|
||||
} else if (v !== null && typeof v === "object") {
|
||||
if (!Object.prototype.hasOwnProperty.call(v, t)) {
|
||||
return { ok: false, depth: i, error: "at() throws out_of_range.403: key '" + t + "' not found" };
|
||||
}
|
||||
v = v[t];
|
||||
} else {
|
||||
return { ok: false, depth: i, error: "a primitive value has no children" };
|
||||
}
|
||||
}
|
||||
return { ok: true, value: v, depth: toks.length };
|
||||
}
|
||||
function ptrLabel(p) { return p === "" ? '""' : p; }
|
||||
|
||||
function initWalk(root) {
|
||||
if (root.dataset.njReady) return;
|
||||
var doc;
|
||||
try { doc = JSON.parse(root.getAttribute("data-doc")); } catch (e) { return; }
|
||||
root.dataset.njReady = "1";
|
||||
root.classList.add("nj-pointer-walk--js");
|
||||
|
||||
var tree = root.querySelector(".nj-pointer-tree");
|
||||
var items = Array.prototype.slice.call(tree.querySelectorAll("li[data-p]"));
|
||||
var state = { ptr: "/nested/three/1", level: 3 };
|
||||
|
||||
// tree labels become buttons that select their own pointer
|
||||
items.forEach(function (li) {
|
||||
var span = li.querySelector(":scope > .nj-pointer-n");
|
||||
var b = el("button", "nj-pointer-n", span.innerHTML);
|
||||
b.type = "button";
|
||||
var p = li.getAttribute("data-p");
|
||||
b.setAttribute("aria-label", "Select the pointer " + ptrLabel(p));
|
||||
b.addEventListener("click", function () { set(p, tokens(p).length); });
|
||||
span.replaceWith(b);
|
||||
});
|
||||
|
||||
var panel = el("div", "nj-pointer-panel");
|
||||
panel.appendChild(el("div", "nj-pointer-lbl", "Pointer <span>(select a segment)</span>"));
|
||||
var bar = el("div", "nj-pointer-bar");
|
||||
bar.setAttribute("role", "group");
|
||||
bar.setAttribute("aria-label", "Pointer segments");
|
||||
panel.appendChild(bar);
|
||||
var out = el("div", "nj-pointer-out");
|
||||
out.setAttribute("aria-live", "polite");
|
||||
panel.appendChild(out);
|
||||
panel.appendChild(el("div", "nj-pointer-lbl", "Examples"));
|
||||
var presets = el("div", "nj-pointer-presets");
|
||||
presets.setAttribute("role", "group");
|
||||
presets.setAttribute("aria-label", "Example pointers");
|
||||
PRESETS.forEach(function (p) {
|
||||
var b = el("button", "nj-pointer-chip", "<code>" + esc(ptrLabel(p)) + "</code>");
|
||||
b.type = "button";
|
||||
b.setAttribute("data-p", p);
|
||||
b.setAttribute("aria-label", p === "" ? "Pointer \"\" (the whole document)" : "Pointer " + p);
|
||||
b.addEventListener("click", function () { set(p, tokens(p).length); });
|
||||
presets.appendChild(b);
|
||||
});
|
||||
panel.appendChild(presets);
|
||||
var stat = root.querySelector(".nj-pointer-static");
|
||||
if (stat) stat.hidden = true;
|
||||
root.insertBefore(panel, root.firstChild);
|
||||
|
||||
function liFor(p) {
|
||||
for (var i = 0; i < items.length; ++i) if (items[i].getAttribute("data-p") === p) return items[i];
|
||||
return null;
|
||||
}
|
||||
|
||||
function render() {
|
||||
var toks = tokens(state.ptr);
|
||||
var sel = toks.slice(0, state.level);
|
||||
var r = resolve(doc, sel);
|
||||
|
||||
// bar: root chip plus one button per reference token
|
||||
bar.innerHTML = "";
|
||||
var parts = [{ label: '""', text: "root", n: 0 }];
|
||||
toks.forEach(function (t, i) { parts.push({ label: joinTokens([t]), n: i + 1 }); });
|
||||
parts.forEach(function (part) {
|
||||
var b = el("button", "nj-pointer-seg" + (part.n === 0 ? " nj-pointer-seg--root" : ""),
|
||||
part.n === 0 ? "<code>\"\"</code>" : "<code>" + esc(part.label) + "</code>");
|
||||
b.type = "button";
|
||||
b.setAttribute("aria-pressed", part.n === state.level ? "true" : "false");
|
||||
if (part.n > state.level) b.classList.add("is-after");
|
||||
var prefix = joinTokens(toks.slice(0, part.n));
|
||||
b.setAttribute("aria-label", "Go to level " + part.n + ": " + ptrLabel(prefix) + (part.n === 0 ? " (the whole document)" : ""));
|
||||
b.addEventListener("click", function () { state.level = part.n; render(); focusSeg(part.n); });
|
||||
bar.appendChild(b);
|
||||
});
|
||||
|
||||
// tree highlight
|
||||
items.forEach(function (li) { li.classList.remove("is-on", "is-target", "is-pass", "is-miss"); });
|
||||
var depth = r.ok ? sel.length : r.depth;
|
||||
for (var d = 0; d <= depth; ++d) {
|
||||
var li = liFor(joinTokens(sel.slice(0, d)));
|
||||
if (!li) break;
|
||||
li.classList.add("is-on");
|
||||
if (d > 0) {
|
||||
for (var s = li.previousElementSibling; s; s = s.previousElementSibling) s.classList.add("is-pass");
|
||||
}
|
||||
if (r.ok && d === depth) li.classList.add("is-target");
|
||||
}
|
||||
if (!r.ok) {
|
||||
var miss = liFor(joinTokens(sel.slice(0, r.depth)));
|
||||
if (miss) miss.classList.add("is-miss");
|
||||
}
|
||||
|
||||
var shown = joinTokens(sel);
|
||||
out.innerHTML = r.ok
|
||||
? "<code>" + esc(ptrLabel(shown)) + "</code> resolves to <code class=\"nj-pointer-val\">" + esc(JSON.stringify(r.value)) + "</code>" +
|
||||
(shown === "" ? " <span class=\"nj-pointer-note\">(the whole document)</span>" : "")
|
||||
: "<code>" + esc(ptrLabel(shown)) + "</code> <span class=\"nj-pointer-err\">identifies no value</span>: " + esc(r.error) +
|
||||
". <span class=\"nj-pointer-note\">The token after <code>/</code> is the empty key, and the document has none.</span>";
|
||||
|
||||
Array.prototype.forEach.call(presets.children, function (b) {
|
||||
b.setAttribute("aria-pressed", b.getAttribute("data-p") === shown && state.level === tokens(state.ptr).length ? "true" : "false");
|
||||
});
|
||||
}
|
||||
function focusSeg(n) {
|
||||
var b = bar.children[n];
|
||||
if (b) b.focus();
|
||||
}
|
||||
function set(p, level) {
|
||||
state.ptr = p;
|
||||
state.level = level;
|
||||
render();
|
||||
}
|
||||
render();
|
||||
}
|
||||
|
||||
/* ---------- JSON Patch stepper ---------- */
|
||||
|
||||
function k(s) { return '<span class="nj-patch-k">"' + s + '"</span>'; }
|
||||
function s(v) { return '<span class="nj-patch-s">"' + v + '"</span>'; }
|
||||
function ins(x) { return '<span class="nj-patch-ins">' + x + "</span>"; }
|
||||
function src(x) { return '<span class="nj-patch-src">' + x + "</span>"; }
|
||||
var I = " ";
|
||||
|
||||
var OPS = [
|
||||
{ op: "replace", path: "/baz", extra: ', "value": "boo"' },
|
||||
{ op: "add", path: "/hello", extra: ', "value": ["world"]' },
|
||||
{ op: "remove", path: "/foo", extra: "" },
|
||||
{ op: "move", from: "/baz", path: "/hello/1", extra: "" },
|
||||
{ op: "copy", from: "/hello/0", path: "/greeting", extra: "" },
|
||||
{ op: "test", path: "/greeting", extra: ', "value": "world"' }
|
||||
];
|
||||
// each frame: document lines [html, line class, note], optional connector {from, to}, status text
|
||||
var FRAMES = [
|
||||
{ lines: [["{"], [I + k("baz") + ": " + s("qux") + ","], [I + k("foo") + ": " + s("bar")], ["}"]],
|
||||
status: "Start: the original document of the example below. Press Next to apply the first operation." },
|
||||
{ lines: [["{"], [I + k("baz") + ": " + s("qux") + ",", "del"], [I + k("baz") + ": " + s("boo") + ",", "add", "replaced"],
|
||||
[I + k("foo") + ": " + s("bar")], ["}"]],
|
||||
status: "replace /baz: the value \"qux\" is replaced by \"boo\"." },
|
||||
{ lines: [["{"], [I + k("baz") + ": " + s("boo") + ","], [I + k("foo") + ": " + s("bar") + ","],
|
||||
[I + k("hello") + ": [" + s("world") + "]", "add", "added"], ["}"]],
|
||||
status: "add /hello: the new member \"hello\" with the value [\"world\"] is added." },
|
||||
{ lines: [["{"], [I + k("baz") + ": " + s("boo") + ","], [I + k("foo") + ": " + s("bar") + ",", "del", "removed"],
|
||||
[I + k("hello") + ": [" + s("world") + "]"], ["}"]],
|
||||
status: "remove /foo: the member \"foo\" is removed. This is the result of the example below." },
|
||||
{ lines: [["{"], [I + k("baz") + ": " + s("boo") + ",", "del", "moved"],
|
||||
[I + k("hello") + ": [" + s("world") + ", " + ins(s("boo")) + "]", "mod", "from /baz"], ["}"]],
|
||||
arc: { from: 1, to: 2 },
|
||||
status: "move from /baz to /hello/1: \"boo\" is removed from /baz and inserted into the array at index 1." },
|
||||
{ lines: [["{"], [I + k("greeting") + ": " + s("world") + ",", "add", "copy of /hello/0"],
|
||||
[I + k("hello") + ": [" + src(s("world")) + ", " + s("boo") + "]"], ["}"]],
|
||||
arc: { from: 2, to: 1 },
|
||||
status: "copy from /hello/0 to /greeting: the value \"world\" is copied to the new member \"greeting\"." },
|
||||
{ lines: [["{"], [I + k("greeting") + ": " + s("world") + ",", "test", "test passed"],
|
||||
[I + k("hello") + ": [" + s("world") + ", " + s("boo") + "]"], ["}"]],
|
||||
status: "test /greeting: the value equals \"world\", so the document is unchanged. A failed test would make patch() throw other_error 501." }
|
||||
];
|
||||
|
||||
function opHtml(o) {
|
||||
var h = '{"op": "<span class="nj-patch-op">' + o.op + '</span>"';
|
||||
if (o.from) h += ', "from": "<span class="nj-patch-path">' + o.from + '</span>"';
|
||||
h += ', "path": "<span class="nj-patch-path">' + o.path + '</span>"' + esc(o.extra) + "}";
|
||||
return h;
|
||||
}
|
||||
|
||||
function initPatch(root) {
|
||||
if (root.dataset.njReady) return;
|
||||
root.dataset.njReady = "1";
|
||||
root.classList.add("nj-patch--js");
|
||||
var step = 0;
|
||||
|
||||
var stage = el("div", "nj-patch-stage");
|
||||
var cols = el("div", "nj-patch-cols");
|
||||
var left = el("div", "nj-patch-col");
|
||||
left.appendChild(el("div", "nj-patch-h", "Document"));
|
||||
var docBox = el("div", "nj-patch-doc");
|
||||
left.appendChild(docBox);
|
||||
var right = el("div", "nj-patch-col");
|
||||
right.appendChild(el("div", "nj-patch-h", "Patch"));
|
||||
var list = el("ol", "nj-patch-ops");
|
||||
OPS.forEach(function (o) { list.appendChild(el("li", "", "<code>" + opHtml(o) + "</code>")); });
|
||||
right.appendChild(list);
|
||||
cols.appendChild(left);
|
||||
cols.appendChild(right);
|
||||
stage.appendChild(cols);
|
||||
// controls and status sit under the document, so on a phone both stay in view together
|
||||
|
||||
var ctrl = el("div", "nj-patch-ctrl");
|
||||
function btn(label, aria, fn) {
|
||||
var b = el("button", "nj-patch-btn", label);
|
||||
b.type = "button";
|
||||
b.setAttribute("aria-label", aria);
|
||||
b.addEventListener("click", fn);
|
||||
ctrl.appendChild(b);
|
||||
return b;
|
||||
}
|
||||
var bReset = btn("Reset", "Back to the original document", function () { step = 0; render(true); });
|
||||
var bPrev = btn("Back", "Previous operation", function () { if (step > 0) { step--; render(true); } });
|
||||
var bNext = btn("Next", "Apply the next operation", function () { if (step < OPS.length) { step++; render(true); } });
|
||||
bNext.classList.add("nj-patch-btn--primary");
|
||||
var count = el("span", "nj-patch-count");
|
||||
ctrl.appendChild(count);
|
||||
left.appendChild(ctrl);
|
||||
var status = el("p", "nj-patch-status");
|
||||
status.setAttribute("aria-live", "polite");
|
||||
left.appendChild(status);
|
||||
root.insertBefore(stage, root.firstChild);
|
||||
|
||||
function render(animate) {
|
||||
var f = FRAMES[step];
|
||||
docBox.innerHTML = "";
|
||||
f.lines.forEach(function (ln) {
|
||||
var row = el("div", "nj-patch-line" + (ln[1] ? " nj-patch-line--" + ln[1] : ""));
|
||||
row.appendChild(el("span", "nj-patch-code", ln[0]));
|
||||
if (ln[2]) row.appendChild(el("span", "nj-patch-note", esc(ln[2])));
|
||||
docBox.appendChild(row);
|
||||
});
|
||||
if (f.arc) {
|
||||
var a = el("div", "nj-patch-arc " + (f.arc.to > f.arc.from ? "nj-patch-arc--down" : "nj-patch-arc--up"));
|
||||
var top = Math.min(f.arc.from, f.arc.to), n = Math.abs(f.arc.to - f.arc.from);
|
||||
a.style.top = "calc(var(--nj-patch-pad) + " + (top + 0.5) + " * var(--nj-patch-lh))";
|
||||
a.style.height = "calc(" + n + " * var(--nj-patch-lh))";
|
||||
a.setAttribute("aria-hidden", "true");
|
||||
docBox.appendChild(a);
|
||||
}
|
||||
docBox.classList.toggle("nj-patch-doc--anim", !!animate);
|
||||
Array.prototype.forEach.call(list.children, function (li, i) {
|
||||
li.className = i + 1 === step ? "is-cur" : (i + 1 < step ? "is-done" : "");
|
||||
if (i + 1 === step) li.setAttribute("aria-current", "step"); else li.removeAttribute("aria-current");
|
||||
});
|
||||
bPrev.disabled = step === 0;
|
||||
bReset.disabled = step === 0;
|
||||
bNext.disabled = step === OPS.length;
|
||||
count.textContent = "Step " + step + " of " + OPS.length;
|
||||
status.textContent = f.status;
|
||||
}
|
||||
render(false);
|
||||
}
|
||||
|
||||
function init() {
|
||||
Array.prototype.forEach.call(document.querySelectorAll("[data-nj-pointer-walk]"), initWalk);
|
||||
Array.prototype.forEach.call(document.querySelectorAll("[data-nj-patch]"), initPatch);
|
||||
}
|
||||
if (typeof window.document$ !== "undefined" && window.document$.subscribe) {
|
||||
window.document$.subscribe(init);
|
||||
} else if (document.readyState === "loading") {
|
||||
document.addEventListener("DOMContentLoaded", init);
|
||||
} else {
|
||||
init();
|
||||
}
|
||||
})();
|
||||