Passa al contenuto principale

2.3. Selectors (Selettori)

2.3. Selectors (Selettori)

I selettori compaiono solo all'interno di child segment (Sezione 2.5.1) e descendant segment (Sezione 2.5.2).

Un selettore produce una nodelist costituita da zero o più figli del valore di input.

Esistono vari tipi di selettori che producono figli di oggetti, figli di array, o figli di oggetti o array.

selector            = name-selector /
wildcard-selector /
slice-selector /
index-selector /
filter-selector

La sintassi e la semantica di ciascun tipo di selettore sono definite di seguito.

2.3.1. Name Selector (selettore per nome)

2.3.1.1. Syntax (sintassi)

Un name selector '' seleziona al massimo un valore di membro di oggetto.

A differenza di JSON, la sintassi JSONPath consente di racchiudere le stringhe tra virgolette singole o doppie.

name-selector = string-literal

string-literal      = %x22 *double-quoted %x22 /     ; "string"
%x27 *single-quoted %x27 ; 'string'
double-quoted       = unescaped /
%x27 / ; '
ESC %x22 / ; \"
ESC escapable
single-quoted       = unescaped /
%x22 / ; "
ESC %x27 / ; \'
ESC escapable
ESC                 = %x5C                           ; \ backslash
unescaped           = %x20-21 /                      ; see RFC 8259
; omit 0x22 "
%x23-26 /
; omit 0x27 '
%x28-5B /
; omit 0x5C \
%x5D-D7FF /
; skip surrogate code points
%xE000-10FFFF
escapable           = %x62 / ; b BS backspace U+0008
%x66 / ; f FF form feed U+000C
%x6E / ; n LF line feed U+000A
%x72 / ; r CR carriage return U+000D
%x74 / ; t HT horizontal tab U+0009
"/" / ; / slash (solidus) U+002F
"\" / ; \ backslash (reverse solidus) U+005C
(%x75 hexchar) ; uXXXX U+XXXX
hexchar             = non-surrogate /
(high-surrogate "\" %x75 low-surrogate)
non-surrogate = ((DIGIT / "A"/"B"/"C" / "E"/"F") 3HEXDIG) /
("D" %x30-37 2HEXDIG )
high-surrogate = "D" ("8"/"9"/"A"/"B") 2HEXDIG
low-surrogate = "D" ("C"/"D"/"E"/"F") 2HEXDIG
HEXDIG              = DIGIT / "A" / "B" / "C" / "D" / "E" / "F"

Note:

  • Le stringhe tra virgolette doppie seguono la sintassi delle stringhe JSON (Sezione 7 di [RFC8259]); le stringhe tra virgolette singole seguono uno schema analogo. Non è stato tentato di migliorare questa sintassi, quindi se si desidera fare l'escape di caratteri con valori scalari sopra 0xFFFF, come U+1F041 ("🁁", DOMINO TILE HORIZONTAL-02-02), essi devono essere rappresentati da una coppia di escape surrogate ("\uD83C\uDC41" in questo caso).

  • I caratteri alfabetici nelle stringhe tra virgolette sono case-insensitive in ABNF, quindi ciascuna delle cifre esadecimali negli escape \u (come specificato nelle regole referenziate da hexchar) può essere minuscola o maiuscola, mentre la u in \u deve essere minuscola (indicata come %x75).

2.3.1.2. Semantics (semantica)

Una stringa name-selector DEVE essere convertita in un nome di membro M rimuovendo le virgolette circostanti e sostituendo ciascuna sequenza di escape con il suo carattere Unicode equivalente, come mostrato nella Tabella 4:

Sequenza di escapeCarattere UnicodeDescrizione
\bU+0008BS backspace (backspace)
\tU+0009HT horizontal tab (tab orizzontale)
\nU+000ALF line feed (avanzamento riga)
\fU+000CFF form feed (avanzamento modulo)
\rU+000DCR carriage return (ritorno carrello)
"U+0022quotation mark (virgolette)
'U+0027apostrophe (apostrofo)
/U+002Fslash (solidus) (barra)
\U+005Cbackslash (reverse
solidus) (barra rovesciata)
\uXXXXvedereescape esadecimale
Sezione 2.3.1.1

Tabella 4: Sostituzioni delle sequenze di escape

Applicando il name-selector a un nodo oggetto si seleziona un valore di membro il cui nome è uguale al nome di membro M oppure non si seleziona nulla se non esiste tale valore di membro. Non viene selezionato nulla da un valore che non è un oggetto.

Nota: l'elaborazione del name selector richiede il confronto della stringa nome di membro M con le stringhe nome di membro nel JSON a cui il selettore viene applicato. Due stringhe DEVONO essere considerate uguali se e solo se sono sequenze identiche di valori scalari Unicode. In altre parole, le operazioni di normalizzazione NON DEVONO essere applicate né alla stringa nome di membro M dal JSONPath né alle stringhe nome di membro nel JSON prima del confronto.

2.3.1.3. Examples (esempi)

JSON:

{
"o": {"j j": {"k.k": 3}},
"'": {"@": 2}
}

Interrogazioni:

Gli esempi nella Tabella 5 mostrano il name selector in uso nei child segment.

QueryRisultatoPercorsi risultatoCommento
$.o['j j']{"k.k":$['o']['j j']Valore
3}denominato in
oggetto
annidato
$.o['j j']['k.k']3$['o']['j j']['k.k']Annidamento
più
profondo
$.o["j j"]["k.k"]3$['o']['j j']['k.k']Delimitatore
diverso
nell'
interrogazione,
Normalized
Path invariato
$["'"]["@"]2$[''']['@']Nomi di
membro
insoliti

Tabella 5: Esempi di name selector

2.3.2. Wildcard Selector (selettore jolly)

2.3.2.1. Syntax (sintassi)

Il wildcard selector consiste in un asterisco.

wildcard-selector = "*"

2.3.2.2. Semantics (semantica)

Un wildcard selector seleziona i nodi di tutti i figli di un oggetto o array. L'ordine in cui i figli di un oggetto compaiono nella nodelist risultante non è prescritto, poiché gli oggetti JSON sono non ordinati. I figli di un array compaiono in ordine di array nella nodelist risultante.

Nota: i figli di un oggetto sono i suoi valori di membro, non i nomi dei membri.

Il wildcard selector non seleziona nulla da un valore JSON primitivo (vale a dire un numero, una stringa, true, false, o null).

2.3.2.3. Examples (esempi)

JSON:

{
"o": {"j": 1, "k": 2},
"a": [5, 3]
}

Interrogazioni:

Gli esempi nella Tabella 6 mostrano il wildcard selector in uso in un child segment.

QueryRisultatoPercorsiCommento
risultato
$[*]{"j": 1,$['o']Valori di oggetto
"k": 2}$['a']
[5, 3]
$.o[*]1$['o']['j']Valori di oggetto
2$['o']['k']
$.o[*]2$['o']['k']Risultato
1$['o']['j']alternativo
$.o[*,1$['o']['j']Ordinamento
*]2$['o']['k']non deterministico
2$['o']['k']
1$['o']['j']
$.a[*]5$['a'][0]Elementi di array
3$['a'][1]

Tabella 6: Esempi di wildcard selector

L'esempio qui sopra con l'interrogazione $.o[*, *] mostra che il wildcard selector può produrre nodelist in ordini distinti ogni volta che compare nel child segment quando è applicato a un nodo oggetto con due o più membri (ma non quando è applicato a nodi oggetto con meno di due membri o a nodi array).

2.3.3. Index Selector (selettore per indice)

2.3.3.1. Syntax (sintassi)

Un index selector <index> abbina al massimo un valore di elemento di array.

index-selector = int ; decimal integer

int                 = "0" /
(["-"] DIGIT1 *DIGIT) ; - optional
DIGIT1 = %x31-39 ; 1-9 non-zero digit

Applicando il index-selector numerico si seleziona l'elemento corrispondente. JSONPath consente che sia negativo (vedere Sezione 2.3.3.2).

Per essere valido, il valore del index selector DEVE essere nell'intervallo I-JSON dei valori esatti (vedere Sezione 2.1).

Note:

  • Un index-selector è un intero (in base 10, come nei numeri JSON).

  • Come nei numeri JSON, la sintassi non consente interi simil-ottali con zeri iniziali, come 01 o -01.

2.3.3.2. Semantics (semantica)

Un index-selector non negativo applicato a un array seleziona un elemento di array usando un indice a base zero. Ad esempio, il selettore 0 seleziona il primo, e il selettore 4 seleziona il quinto elemento di un array sufficientemente lungo. Non viene selezionato nulla, e non è un errore, se l'indice è fuori dall'intervallo dell'array. Non viene selezionato nulla da un valore che non è un array.

Un index-selector negativo conta dalla fine dell'array all'indietro, ottenendo un index-selector non negativo equivalente sommando la lunghezza dell'array all'indice negativo. Ad esempio, il selettore -1 seleziona l'ultimo, e il selettore -2 seleziona il penultimo elemento di un array con almeno due elementi. Come con gli indici non negativi, non è un errore se tale elemento non esiste; ciò significa semplicemente che nessun elemento è selezionato.

2.3.3.3. Examples (esempi)

JSON:

["a","b"]

Interrogazioni:

Gli esempi nella Tabella 7 mostrano il index selector in uso in un child segment.

QueryRisultatoPercorsi risultatoCommento
$[1]"b"$[1]Elemento di array
$[-2]"a"$[0]Elemento di array, dalla fine

Tabella 7: Esempi di index selector

2.3.4. Array Slice Selector (selettore di fetta di array)

2.3.4.1. Syntax (sintassi)

L'array slice selector ha la forma <start>::. Abbina elementi da array a partire dall'indice <start> e finendo a (ma non includendo) <end>, incrementando di step con un default di 1.

slice-selector = [start S] ":" S [end S] [":" [S step ]]

start = int ; included in selection end = int ; not included in selection step = int ; default: 1

Il slice selector consiste in tre interi decimali opzionali separati da due punti. Il secondo due punti può essere omesso quando il terzo intero è omesso.

Per essere validi, gli interi forniti DEVONO essere nell'intervallo I-JSON dei valori esatti (vedere Sezione 2.1).

2.3.4.2. Semantics (semantica)

Il slice selector è stato ispirato dall'operatore di fetta proposto per ECMAScript 4 (ES4), che non fu mai rilasciato, e da quello di Python.

2.3.4.2.1. Informal Introduction (introduzione informale)

Questa sezione è informativa.

Il taglio di array (array slicing) è ispirato al comportamento del metodo Array.prototype.slice del linguaggio JavaScript, come definito dallo standard ECMA-262 [ECMA-262], con l'aggiunta del parametro step, ispirato dall'espressione di fetta di Python.

L'espressione di fetta di array start:end:step seleziona elementi agli indici a partire da start, incrementando di step, e terminando con end (che è esso stesso escluso). Così, ad esempio, l'espressione 1:3 (dove step ha default 1) seleziona elementi con indici 1 e 2 (in quell'ordine), mentre 1:5:2 seleziona elementi con indici 1 e 3.

Quando step è negativo, gli elementi sono selezionati in ordine inverso. Così, ad esempio, 5:1:-2 seleziona elementi con indici 5 e 3 (in quell'ordine), e ::-1 seleziona tutti gli elementi di un array in ordine inverso.

Quando step è 0, nessun elemento è selezionato. (Questo è l'unico caso che differisce dal comportamento di Python, che in questo caso solleva un errore.)

La sezione seguente specifica il comportamento completamente, senza dipendere dal comportamento di JavaScript o Python.

2.3.4.2.2. Normative Semantics (semantica normativa)

Un'espressione di fetta seleziona un sottoinsieme degli elementi dell'array di input nello stesso ordine dell'array o in ordine inverso, a seconda del segno del parametro step. Non seleziona nodi da un nodo che non è un array.

Una fetta è definita dai due parametri di fetta start ed end, e da un delta di iterazione step. Ciascuno di questi parametri è opzionale. Nel resto di questa sezione, len denota la lunghezza dell'array di input.

Il valore predefinito per step è 1. I valori predefiniti per start ed end dipendono dal segno di step, come mostrato nella Tabella 8.

Condizionestartend
step >= 00len
step < 0len - 1-len - 1

Tabella 8: Valori predefiniti di start ed end per la fetta di array

I parametri start ed end dell'espressione di fetta non sono direttamente utilizzabili come limiti di fetta e devono prima essere normalizzati. La normalizzazione a questo scopo è definita come:

FUNCTION Normalize(i, len): IF i >= 0 THEN RETURN i ELSE RETURN len + i END IF

Il risultato dell'espressione di indice di array i applicata a un array di lunghezza len è il risultato dell'espressione di fetta di array Normalize(i, len):Normalize(i, len)+1:1.

I parametri start ed end dell'espressione di fetta sono usati per derivare i limiti inferiore e superiore della fetta. La direzione dell'iterazione, definita dal segno di step, determina quale dei parametri è il limite inferiore e quale è il limite superiore:

FUNCTION Bounds(start, end, step, len): n_start = Normalize(start, len) n_end = Normalize(end, len)

IF step >= 0 THEN lower = MIN(MAX(n_start, 0), len) upper = MIN(MAX(n_end, 0), len) ELSE upper = MIN(MAX(n_start, -1), len-1) lower = MIN(MAX(n_end, -1), len-1) END IF

RETURN (lower, upper)

L'espressione di fetta seleziona elementi con indici tra i limiti inferiore e superiore. Nel seguente pseudocodice, a(i) è l'elemento i+1-esimo dell'array a (vale a dire a(0) è il primo elemento, a(1) il secondo, e così via).

IF step > 0 THEN

i = lower WHILE i < upper: SELECT a(i) i = i + step END WHILE

ELSE if step < 0 THEN

i = upper WHILE lower < i: SELECT a(i) i = i + step END WHILE

END IF

Quando step = 0, nessun elemento è selezionato, e l'array risultante è vuoto.

2.3.4.3. Examples (esempi)

JSON:

["a", "b", "c", "d", "e", "f", "g"]

Interrogazioni:

Gli esempi nella Tabella 9 mostrano l'array slice selector in uso in un child segment.

QueryRisultatoPercorsiCommento
risultato
$[1:3]"b"$[1]Fetta con
"c"$[2]step
predefinito
$[5:]"f"$[5]Fetta senza
"g"$[6]indice
finale
$[1:5:2]"b"$[1]Fetta con
"d"$[3]step 2
$[5:1:-2]"f"$[5]Fetta con
"d"$[3]step
negativo
$[::-1]"g"$[6]Fetta in
"f"$[5]ordine
"e"$[4]inverso
"d"$[3]
"c"$[2]
"b"$[1]
"a"$[0]

Tabella 9: Esempi di array slice selector

2.3.5. Filter Selector (selettore di filtro)

I filter selector sono usati per iterare sugli elementi o membri di valori strutturati, vale a dire array e oggetti JSON. I valori strutturati sono identificati nella nodelist fornita dal child o descendant segment usando il filter selector.

Per ciascuna iterazione (elemento/membro), viene valutata un'espressione logica (la filter expression), che decide se il nodo dell'elemento/membro è selezionato. (Sebbene un'espressione logica valuti a ciò che matematicamente è un valore Booleano, questa specifica usa il termine logical per mantenere una distinzione dai valori Booleani che JSON può rappresentare.)

Durante il processo di iterazione, l'espressione di filtro riceve il nodo di ciascun elemento di array o valore di membro di oggetto del valore strutturato filtrato; tale elemento o valore di membro è allora noto come current node (nodo corrente).

Il nodo corrente può essere usato come inizio di una o più interrogazioni JSONPath in sottoespressioni dell'espressione di filtro, notate tramite il current-node-identifier @. Ciascuna interrogazione JSONPath può essere usata sia per verificare l'esistenza di un risultato dell'interrogazione, sia per ottenere un valore JSON specifico risultante da quell'interrogazione che può poi essere usato in un confronto, o come function argument (argomento di funzione).

I filter selector possono usare function extensions, trattate nella Sezione 2.4. All'interno dell'espressione logica per un filter selector, le function expression possono essere usate per operare su nodelist e valori. L'insieme delle funzioni disponibili è estensibile, con un certo numero di funzioni predefinite (vedere Sezione 2.4) e la possibilità di registrare ulteriori funzioni fornita dal subregistry "Function Extensions" (Sezione 3.2). Quando una funzione è definita, le viene dato un nome univoco, e il suo valore di ritorno e ciascuno dei suoi parametri ricevono un declared type (tipo dichiarato). Il sistema di tipi ha ambito limitato; il suo scopo è esprimere restrizioni che, senza funzioni, sono implicite nella grammatica delle espressioni di filtro. Il sistema di tipi guida anche le conversioni (Sezione 2.4.2) che imitano il modo in cui diversi tipi di espressioni sono gestiti nella grammatica quando le function expression non sono in uso.

2.3.5.1. Syntax (sintassi)

Il filter selector ha la forma ?<logical-expr>.

filter-selector = "?" S logical-expr

Poiché l'espressione di filtro è composta da costituenti privi di effetti collaterali, l'ordine di valutazione non deve essere (e non è) definito. Analogamente, per congiunzione (&&) e disgiunzione (||) (definite in seguito), sia un'implementazione in cortocircuito sia una completamente valutativa conducono allo stesso risultato; entrambe le strategie di implementazione sono quindi valide.

Il nodo corrente è accessibile tramite il current node identifier @. Questo identificatore indirizza il nodo corrente del filter-selector che racchiude direttamente l'identificatore. Nota: all'interno di filter-selector annidati, non esiste sintassi per indirizzare il nodo corrente di altro se non il filter-selector che racchiude direttamente (vale a dire dei filter-selector che racchiudono il filter-selector che racchiude direttamente l'identificatore).

Le espressioni logiche offrono gli usuali operatori Booleani (|| per OR, && per AND, e ! per NOT). Hanno la semantica normale dell'algebra di Boolean e ne obbediscono alle leggi (ad esempio, vedere [BOOLEAN-LAWS]). Le parentesi possono essere usate all'interno di logical-expr per il raggruppamento.

Non è richiesto che logical-expr consista in un'espressione tra parentesi (come richiesto in [JSONPath-orig]), sebbene possa esserlo, e la semantica è la stessa che senza parentesi.

logical-expr = logical-or-expr logical-or-expr = logical-and-expr *(S "||" S logical-and-expr) ; disjunction ; binds less tightly than conjunction logical-and-expr = basic-expr *(S "&&" S basic-expr) ; conjunction ; binds more tightly than disjunction

basic-expr          = paren-expr /
comparison-expr /
test-expr

paren-expr = [logical-not-op S] "(" S logical-expr S ")" ; parenthesized expression logical-not-op = "!" ; logical NOT operator

Un'espressione di test verifica l'esistenza di un nodo designato da un'interrogazione incorporata (vedere Sezione 2.3.5.2.1) oppure verifica il risultato di una function expression (vedere Sezione 2.4). In quest'ultimo caso, se il tipo di risultato dichiarato della funzione è LogicalType (vedere Sezione 2.4.1), verifica se il risultato è LogicalTrue; se il tipo di risultato dichiarato è NodesType, verifica se il risultato è non vuoto. Se il tipo di risultato dichiarato è ValueType, il suo uso in un'espressione di test non è well-typed (vedere Sezione 2.4.3).

test-expr           = [logical-not-op S]
(filter-query / ; existence/non-existence
function-expr) ; LogicalType or NodesType
filter-query = rel-query / jsonpath-query
rel-query = current-node-identifier segments
current-node-identifier = "@"

Le comparison expression sono disponibili per confronti tra valori primitivi (vale a dire numeri, stringhe, true, false, e null). Questi possono essere ottenuti tramite valori letterali; singular query, ciascuna delle quali seleziona al massimo un nodo, il cui valore è poi usato; o function expression (vedere Sezione 2.4) di tipo ValueType.

comparison-expr     = comparable S comparison-op S comparable
literal = number / string-literal /
true / false / null
comparable = literal /
singular-query / ; singular query value
function-expr ; ValueType
comparison-op = "==" / "!=" /
"<=" / ">=" /
"<" / ">"
singular-query      = rel-singular-query / abs-singular-query
rel-singular-query = current-node-identifier singular-query-segments
abs-singular-query = root-identifier singular-query-segments
singular-query-segments = *(S (name-segment / index-segment))
name-segment = ("[" name-selector "]") /
("." member-name-shorthand)
index-segment = "[" index-selector "]"

I letterali possono essere notati nel modo usuale per JSON (con l'estensione che le stringhe possono usare delimitatori a virgoletta singola).

Nota: i caratteri alfabetici nelle stringhe tra virgolette sono case-insensitive in ABNF, quindi all'interno di un numero in virgola mobile, l'espressione ABNF "e" può essere il carattere 'e' o 'E'.

true, false, e null sono solo minuscoli (case-sensitive).

number              = (int / "-0") [ frac ] [ exp ] ; decimal number
frac = "." 1*DIGIT ; decimal fraction
exp = "e" [ "-" / "+" ] 1*DIGIT ; decimal exponent
true = %x74.72.75.65 ; true
false = %x66.61.6c.73.65 ; false
null = %x6e.75.6c.6c ; null

La Tabella 10 elenca gli operatori delle espressioni di filtro in ordine di precedenza dal più alto (lega più strettamente) al più basso (lega meno strettamente).

PrecedenzaTipo operatoreSintassi
5Raggruppamento(...)
Function Expressionsname(...)
4NOT logico!
3Relazioni== !=
< <= > >=
2AND logico&&
1OR logico

Tabella 10: Precedenza degli operatori delle espressioni di filtro

2.3.5.2. Semantics (semantica)

Il filter selector opera esclusivamente con array e oggetti. Il suo risultato è una lista di (zero, uno, multipli, o tutti) i loro elementi di array o valori di membro, rispettivamente. Applicato a un valore primitivo, non seleziona nulla (e quindi non contribuisce al risultato del filter selector).

Nella nodelist risultante, i figli di un array sono ordinati per la loro posizione nell'array. L'ordine in cui i figli di un oggetto (a differenza di un array) compaiono nella nodelist risultante non è prescritto, poiché gli oggetti JSON sono non ordinati.

2.3.5.2.1. Existence Tests (test di esistenza)

Un'interrogazione da sola in un contesto logico è un test di esistenza che produce true se l'interrogazione seleziona almeno un nodo e produce false se l'interrogazione non seleziona alcun nodo.

I test di esistenza differiscono dai confronti in quanto:

  • Operano con interrogazioni relative o assolute arbitrarie (non solo

singular query).

  • Operano con interrogazioni che selezionano valori strutturati.

Per esaminare il valore di un nodo selezionato da un'interrogazione, è necessario un confronto esplicito. Ad esempio, per verificare se il nodo selezionato dall'interrogazione @.foo ha il valore null, usare @.foo == null (vedere Sezione 2.6) piuttosto che il test di esistenza negato [email protected] (che produce false se @.foo seleziona un nodo, indipendentemente dal valore del nodo). Analogamente, @.foo == false produce true solo se @.foo seleziona un nodo e il valore di quel nodo è false.

2.3.5.2.2. Comparisons (confronti)

Gli operatori di confronto == e < sono definiti per primi, e poi questi sono usati per definire !=, <=, >, e >=.

Quando uno dei lati di un confronto produce una nodelist vuota o il risultato speciale Nothing (vedere Sezione 2.4.1):

  • Un confronto usando l'operatore == produce true se e solo se

l'altro lato produce anch'esso una nodelist vuota o il risultato speciale Nothing.

  • Un confronto usando l'operatore < produce false.

Quando un'interrogazione o function expression su uno dei lati di un confronto produce una nodelist costituita da un singolo nodo, quel lato è sostituito dal valore del suo nodo e poi:

  • Un confronto usando l'operatore == produce true se e solo se il

confronto è tra:

  • numeri attesi per interoperare, come da Sezione 2.2 di I-JSON

[RFC7493], che risultano uguali usando l'uguaglianza matematica normale,

  • numeri, almeno uno dei quali non è atteso per interoperare

come da I-JSON, dove i numeri risultano uguali usando un'uguaglianza specifica dell'implementazione,

  • valori primitivi uguali che non sono numeri,

  • array uguali, vale a dire array della stessa lunghezza dove ciascun

elemento del primo array è uguale all'elemento corrispondente del secondo array, oppure

  • oggetti uguali senza nomi duplicati, vale a dire dove:

o entrambi gli oggetti hanno la stessa raccolta di nomi (senza duplicati) e

o per ciascuno di tali nomi, i valori associati al nome dagli oggetti sono uguali.

  • Un confronto usando l'operatore < produce true se e solo se il

confronto è tra valori che sono entrambi numeri o entrambi stringe e che soddisfano il confronto:

  • i numeri attesi per interoperare, come da Sezione 2.2 di I-JSON

[RFC7493], DEVONO essere confrontati usando l'ordinamento matematico normale; i numeri non attesi per interoperare, come da I-JSON, POSSONO essere confrontati usando un ordinamento specifico dell'implementazione,

  • la stringa vuota risulta minore di qualsiasi stringa non vuota, e

  • una stringa non vuota risulta minore di un'altra stringa non vuota

se e solo se la prima stringa inizia con un valore scalare Unicode inferiore alla seconda stringa o se entrambe le stringhe iniziano con lo stesso valore scalare Unicode e il resto della prima stringa risulta minore del resto della seconda stringa.

!=, <=, >, e >= sono definiti in termini degli altri operatori di confronto. Per qualsiasi a e b:

  • Il confronto a != b produce true se e solo se a == b produce

false.

  • Il confronto a <= b produce true se e solo se a < b produce true

oppure a == b produce true.

  • Il confronto a > b produce true se e solo se b < a produce true.

  • Il confronto a >= b produce true se e solo se b < a produce true

oppure a == b produce true.

2.3.5.3. Examples (esempi)

Il primo insieme di esempi mostra alcune espressioni di confronto e il loro risultato con un dato valore JSON come input.

JSON:

{
"obj": {"x": "y"},
"arr": [2, 3]
}

Confronti:

ConfrontoRisultatoCommento
$.absent1 == $.absent2trueNodelist vuote
$.absent1 <= $.absent2true== implica <=
$.absent == 'g'falseNodelist vuota
$.absent1 != $.absent2falseNodelist vuote
$.absent != 'g'trueNodelist vuota
1 <= 2trueConfronto numerico
1 > 2falseConfronto numerico
13 == '13'falseTipo non corrispondente
'a' <= 'b'trueConfronto tra stringhe
'a' > 'b'falseConfronto tra stringhe
$.obj == $.arrfalseTipo non corrispondente
$.obj != $.arrtrueTipo non corrispondente
$.obj == $.objtrueConfronto tra oggetti
$.obj != $.objfalseConfronto tra oggetti
$.arr == $.arrtrueConfronto tra array
$.arr != $.arrfalseConfronto tra array
$.obj == 17falseTipo non corrispondente
$.obj != 17trueTipo non corrispondente
$.obj <= $.arrfalseOggetti e array non
offrono confronto <
$.obj < $.arrfalseOggetti e array non
offrono confronto <
$.obj <= $.objtrue== implica <=
$.arr <= $.arrtrue== implica <=
1 <= $.arrfalseGli array non offrono
confronto <
1 >= $.arrfalseGli array non offrono
confronto <
1 > $.arrfalseGli array non offrono
confronto <
1 < $.arrfalseGli array non offrono
confronto <
true <= truetrue== implica <=
true > truefalseI Boolean non offrono
confronto <

Tabella 11: Esempi di confronto

Il secondo insieme di esempi mostra alcune interrogazioni JSONPath complete che usano filter selector e i risultati della valutazione di tali interrogazioni su un dato valore JSON come input. (Nota: due delle interrogazioni impiegano function extensions; vedere le Sezioni 2.4.6 e 2.4.7 per i dettagli.)

JSON:

{
"a": [3, 5, 1, 2, 4, 6,
{"b": "j"},
{"b": "k"},
{"b": {}},
{"b": "kilo"}
],
"o": {"p": 1, "q": 2, "r": 3, "s": 5, "t": {"u": 6}},
"e": "f"
}

Interrogazioni:

Gli esempi nella Tabella 12 mostrano il filter selector in uso in un child segment.

QueryRisultatoPercorsi risultatoCommento
$.a[[email protected] == 'kilo']{"b": "kilo"}$['a'][9]Confronto del valore di membro
$.a[?(@.b == 'kilo')]{"b": "kilo"}$['a'][9]Interrogazione equivalente con parentesi racchiudenti
$.a[?@>3.5]5, 4, 6$['a'][1], $['a'][4], $['a'][5]Confronto del valore di array
$.a[[email protected]]{"b": "j"}, {"b": "k"}, {"b": {}}, {"b": "kilo"}$['a'][6], $['a'][7], $['a'][8], $['a'][9]Esistenza del valore di array
$[?@.*]array e oggetto come nell'RFC$['a'], $['o']Esistenza di interrogazioni non singolari
$[?@[[email protected]]]array come nell'RFC$['a']Filtri annidati
$.o[?@<3, ?@<3]1, 2 (ordine variabile)$['o']['p'], $['o']['q']Ordinamento non deterministico
$.a[?@<2 || @.b == "k"]1, {"b": "k"}$['a'][2], $['a'][7]OR logico sul valore di array
$.a[?match(@.b, "[jk]")]{"b": "j"}, {"b": "k"}$['a'][6], $['a'][7]Corrispondenza con espressione regolare sul valore di array
$.a[?search(@.b, "[jk]")]{"b": "j"}, {"b": "k"}, {"b": "kilo"}$['a'][6], $['a'][7], $['a'][9]Ricerca con espressione regolare sul valore di array
$.o[?@>1 && @<4]2, 3$['o']['q'], $['o']['r']AND logico sul valore di oggetto
$.o[?@>1 && @<4] (alternativa)3, 2$['o']['r'], $['o']['q']Risultato alternativo
$.o[[email protected] || @.x]{"u": 6}$['o']['t']OR logico sul valore di oggetto
$.a[[email protected] == $.x]3, 5, 1, 2, 4, 6$['a'][0] fino a $['a'][5]Confronto di interrogazioni senza valori
$.a[?@ == @]primitivi e valori strutturati come nell'RFC$['a'][0] fino a $['a'][9]Confronti di valori primitivi e strutturati

Tabella 12: Esempi di filter selector

L'esempio qui sopra con l'interrogazione $.o[?@&lt;3, ?@&lt;3] mostra che un filter selector può produrre nodelist in ordini distinti ogni volta che compare nel child segment.