Detaillierte Erklärung von JSON.parse und JSON.stringify

Das JSON-Format (abgekürzt als JavaScript Object Notation) ist ein Textformat für den Datenaustausch, das einfach zu schreiben ist.
Basierend auf der nativen JavaScript-Syntax kann es Objekte, Arrays, Zahlen, Zeichenfolgen, boolesche Werte und Nullen serialisieren.

In ES5 wird ein JSON-Objekt hinzugefügt, das speziell zur Verarbeitung von Daten im JSON-Format verwendet wird.
JSON ist ein Objekt, verfügt aber nur über zwei Methoden: parse und  stringify, kann nicht als Konstruktor verwendet werden und verfügt über keine Eigenschaften.

typeof JSON === 'object'

JSON.parse

JSON.parse() Wird zum Parsen von JSON-Strings verwendet, um entsprechende JavaScript-Werte oder -Objekte zu erhalten.

JSON.parse('{}') // {}
JSON.parse('true') // true
JSON.parse('null') // null

JSON.parse-Syntax

JSON.parse(text[, reviver])
  • text: Die Zeichenfolge, in die analysiert werden soll.
    Wenn eine Zahl übergeben wird, wird diese in eine Dezimalzahlausgabe umgewandelt.
    Wird ein boolescher Wert übergeben, wird dieser direkt ausgegeben.
    Wenn null übergeben wird, wird null ausgegeben.
    Werte anderer Typen werden nicht unterstützt, andernfalls wird ein Fehler gemeldet.
  • Reviver: Optionaler Konverter, mit dem der durch Parsen generierte Originalwert geändert werden kann.

Rückgabewert:  JavaScript-Objekt/Wert, Objekt/Wert entsprechend dem angegebenen JSON-Text.

Reviver-Parameter

Die Reviver-Funktion wird verwendet, um den analysierten JavaScript-Wert zu konvertieren und zu verarbeiten und nach der Verarbeitung das Endergebnis zurückzugeben.

Umwandlungsprozess:

  • key Der analysierte Wert selbst und alle darin enthaltenen Attribute werden gemäß einer bestimmten Durchlaufreihenfolge als Reviver-Funktion bezeichnet, und der Attributname und  der Wert werden als zwei Parameter übergeben  value .
    Durchlaufreihenfolge: Je nach Ebene wird von innen nach außen durchlaufen und schließlich die oberste Ebene erreicht, bei der es sich um den analysierten Wert selbst handelt.
  • Wenn reviver undefiniert zurückgibt, wird das Objekt gelöscht, und wenn ein anderer Wert zurückgegeben wird, wird der Wert zum neuen Wert der aktuellen Eigenschaft.
  • Beim Übergang zur obersten Ebene ist der Parameterschlüssel eine leere Zeichenfolge, da keine Attribute vorhanden sind '', und der Parameterwert ist der aktuell analysierte Wert.

key Für die Summe  der beiden Argumente der Reviver-Funktion stehen  valueunterschiedliche Datentypen zur Verfügung:

  • Grundlegende Daten vom Werttyp (Zeichenfolge, Zahl, boolescher Wert) und Null sowie leere Objekte {}und leere Arrays []:
    Der Schlüssel ist eine leere Zeichenfolge und der Wert ist der entsprechende analysierte Wert.
    Weil es bereits die oberste Ebene ist und keine anderen Attribute hat.
  • Objektobjekt:
    Sowohl Schlüssel als auch Wert sind vorhanden, entsprechend dem Attributnamen und -wert.
    Die oberste Ebene gibt einen Wert zurück, dessen Parameterschlüssel leer ist.
  • Array:
    Der Schlüssel entspricht dem Array-Index und der Wert entspricht dem Elementwert.
    Die oberste Ebene gibt einen Wert zurück, dessen Parameterschlüssel leer ist.

Konvertierung von Grundtypen:

JSON.parse('5', function (key, value) {
  console.log(`key:${key}, value:${value}`)
})
// key:, value:5
JSON.parse('null', function (key, value) {
  console.log(`key:${key}, value:${value}`)
})
// key:, value:null
JSON.parse('{}', function (key, value) {
  console.log(`key:${key}, value:`, value)
})
// key:, value:{}

Objektobjekte und Arrays:

JSON.parse('[1, 2]', function (key, value) {
  console.log(`key:${key}, value:`, value)
})
// key:0, value: 1
// key:1, value: 2
// key:, value: (2) [empty × 2]

JSON.parse('{ "user": "张三", "info": { "age": 25, "sex": 1 } }', function (key, value) {
  console.log(`key:${key}, value::`, value)
})
// key:user, value:: 张三
// key:age, value:: 25
// key:sex, value:: 1
// key:info, value:: {}
// key:, value:: {}

Datenverarbeitung:

JSON.parse('[1, 2]', function (key, value) {
  if(key === '') {
    return value
  }
  return value + 3
})
// [4, 5]

JSON.parse-Eigenschaften

Beim Parsen von JSON-Strings müssen Sie einige Spezifikationen des JSON-Formats beachten, da sonst leicht Fehler gemeldet werden.
Für JSON-Daten gelten strenge Vorschriften hinsichtlich der Art und des Formats von Werten. Die spezifischen Regeln lauten wie folgt:

  1. Diese Methode verwendet Daten im JSON-Format vom Typ Zeichenfolge.
    Diese Methode unterstützt außerdem drei Arten von Werten: Zahl, Boolescher Wert und Null und konvertiert den entsprechenden Literalwert.
    Andere Typen werden nicht unterstützt.
JSON.parse('"中国"')
// '中国'
JSON.parse(null) // null
JSON.parse(111.) // 111
JSON.parse(0x12) // 18
JSON.parse(true) // true
JSON.parse([])
// Uncaught SyntaxError: Unexpected end of JSON input
  1. Zeichenfolgen müssen doppelte Anführungszeichen und keine einfachen Anführungszeichen verwenden.
JSON.parse('"String"')
// 'String'
JSON.parse('\'String\'')
// Uncaught SyntaxError: Unexpected token ' in JSON at position 0
  1. Es werden nur Dezimalzeichenfolgen unterstützt, Zahlen müssen jedoch auf den Dezimalpunkt folgen.
JSON.parse('111') // 111
JSON.parse('0x12')
// Uncaught SyntaxError: Unexpected token x in JSON at position 1
JSON.parse('111.232') // 111.232
JSON.parse('111.')
// Uncaught SyntaxError: Unexpected end of JSON input
  1. Undefiniert, Symbol und BigInt können nicht verwendet werden, und Zahlen unterstützen NaN, Infinity und -Infinity nicht, und es wird ein Fehler gemeldet.
JSON.parse(undefined)
// Uncaught SyntaxError: Unexpected token u in JSON at position 0
JSON.parse(Symbol())
// Uncaught TypeError: Cannot convert a Symbol value to a string
JSON.parse('12n')
// Uncaught SyntaxError: Unexpected token n in JSON at position 2
  1. Zusammengesetzte Typen können nur sein: [] und  {} solche Literale.
    Der Objektkonstruktor kann nicht verwendet werden, da er als Ausführungsanweisung betrachtet wird, die nicht unterstützt wird.
    Objekt und Array können nicht verwendet werden, ebenso wenig wie Funktionen, RegExp-Objekte, Datumsobjekte, Fehlerobjekte usw.
JSON.parse('[]')
// []
JSON.parse('Object()')
// Uncaught SyntaxError: Unexpected token O in JSON at position 0
  1. Objekteigenschaftennamen müssen in doppelte Anführungszeichen gesetzt werden.
JSON.parse('{"key": 1 }')
// {key: 1}
JSON.parse('{key: 1 }')
// Uncaught SyntaxError: Unexpected token k in JSON at position 1
  1. Nach dem letzten Mitglied eines Arrays oder Objekts kann kein Komma eingefügt werden.
JSON.parse('[1, 2, 3, 4, ]')
// VM2771:1 Uncaught SyntaxError: Unexpected token ] in JSON at position 13
JSON.parse('{"key" : 1, }')
// VM2779:1 Uncaught SyntaxError: Unexpected token } in JSON at position 12
  1. Unterstützung für Unicode-Escapes.
JSON.parse('{"\u0066":333}')
// {f: 333}
  1. Einige Steuerzeichen und Escape-Zeichen werden nicht unterstützt, z. B. „\n“, „\t“ usw.
JSON.parse('"\n"')
// Uncaught SyntaxError: Unexpected token 

Andere Methoden zum Parsen

Um die JSON-Zeichenfolge in ein JSON-Objekt (JS-Objektwert) umzuwandeln, können Sie auch andere Methoden verwenden, es handelt sich jedoch nicht um einen sicheren Code.

  const str = '{"name":"json","age":18}'
  const json = JSON.parse(str)
  const json = eval("(" + str + ")")
  const json = (new Function("return " + str))()

JSON.stringify

JSON.stringify() Konvertieren Sie ein JavaScript-Objekt oder einen JavaScript-Wert in eine JSON-formatierte Zeichenfolge.

JSON.stringify-Syntax

JSON.stringify(value[, replacer [, space]])
  • Wert: Das JavaScript-Objekt oder der Wert, der in eine JSON-Zeichenfolge serialisiert wird.
  • Der Ersetzer ist optional und wird zur Verarbeitung des zu serialisierenden Werts verwendet.
  • Leerzeichen ist optional und gibt eine leere Zeichenfolge zum Einrücken an, die zur Verschönerung der Ausgabe verwendet wird.

Rückgabewert:  Eine JSON-formatierte Zeichenfolge, die den angegebenen Wert darstellt.

Ersatzparameter

Der Ersetzungsparameter kann in den folgenden drei Situationen vorliegen:

  1. Wenn es null, undefiniert oder von einem anderen Typ ist, wird es ignoriert und nicht verarbeitet.
JSON.stringify({key: 'json'}, null, null) // '{"key":"json"}'
JSON.stringify({key: 'json'}, true) // '{"key":"json"}'
  1. Wenn es sich um ein Array handelt, werden nur die im Array enthaltenen Eigenschaftsnamen in die Ergebniszeichenfolge serialisiert;
    nur gültig für Objekteigenschaften, nicht gültig für Arrays.
const obj = {
  json: 'JSON',
  parse: 'PARSE',
  stringify: 'STRINGIFY'
}
JSON.stringify(obj, ['parse', 'stringify'])
// '{"parse":"PARSE","stringify":"STRINGIFY"}'
  1. Wenn es sich um eine Funktion handelt, wird jedes Attribut des serialisierten Werts von der Funktion konvertiert und verarbeitet.

Verfahren:

  • Die Funktion verfügt über zwei Parameter, den Attributnamen (Schlüssel) und den Attributwert (Wert), die serialisiert werden.
  • Beim ersten Aufruf ist der Schlüssel eine leere Zeichenfolge und der Wert das gesamte Objekt, das serialisiert werden muss.
  • Bei der zweiten Verarbeitung wird das Ergebnis der ersten Verarbeitung übertragen und bei jeder weiteren Verarbeitung wird das Ergebnis der vorherigen Verarbeitung empfangen.
  • Später werden die einzelnen Attributnamen und Attributwerte nacheinander verarbeitet und nach Abschluss zurückgegeben.
JSON.stringify({ json: 1, stringify: { val: 'rr'} }, (key, value) => {
  console.log(`key:${key},value:`, value)
  return value
}) 
// key:,value: {json: 1, stringify: {…}}
// key:json,value: 1
// key:stringify,value: {val: 'rr'}
// key:val,value: rr
// '{"json":1,"stringify":{"val":"rr"}}'

Werttypverarbeitung:

  • Wenn der Basistyp Zeichenfolge, Zahl, boolescher Wert oder Null zurückgegeben wird, wird er direkt zur serialisierten JSON-Zeichenfolge hinzugefügt.
  • Wenn andere Objekte zurückgegeben werden, werden die Eigenschaften des Objekts der Reihe nach serialisiert. Wenn es sich um eine Funktion handelt, wird sie nicht verarbeitet.
  • Wenn zurückgegeben oder nicht definiert, wird die Eigenschaft nicht ausgegeben.
  • Wenn beim Serialisieren eines Arrays der Wert undefiniert oder eine Funktion zurückgibt, wird er durch null ersetzt.
JSON.stringify({ json: 1, stringify: 'rr' }, (key, value) => {
  if (typeof value === 'number') {
    return 'ss'
  }
  return value
}) 
// '{"json":"ss","stringify":"rr"}'

JSON.stringify({ json: 1, stringify: 'rr' }, (key, value) => {
  if (typeof value === 'number') {
    value = undefined
  }
  return value
}) 
// '{"stringify":"rr"}'

Das folgende Beispiel zeigt die Verarbeitung bei der Rückgabe eines Objektwerts:

JSON.stringify({ json: 1, stringify: 'rr' }, (key, value) => {
  if (typeof value === 'object') { // 第一次返回整个对象时,类型是object
    return { parse: 'dd' }
  }
  return value
}) 
'{"parse":"dd"}'

Raumparameter

Der Leerzeichenparameter wird verwendet, um den Abstand in der Ergebniszeichenfolge zu steuern und die Ausgabe zu verschönern. Es gibt drei Arten von Werten, die eingegeben werden können:

  • Wenn es sich um eine Zahl handelt, wird beim Serialisieren jede Ebene mit mehr Leerzeichen eingerückt, die dem Zahlenwert entsprechen als die vorherige Ebene, im Bereich von 1 bis 10, d. h. mindestens 1 und höchstens 10 Leerzeichen.
  • Wenn es sich um eine Zeichenfolge handelt, wird die Zeichenfolge während der Serialisierung vor jeder Zeile hinzugefügt und die Zeichenfolge wird auf jeder Ebene bis zu einem Zeichen weiter eingerückt als auf der vorherigen Ebene. Wenn die Zeichenfolge überschritten wird, wird sie abgefangen.
  • Wenn es null, undefiniert oder von einem anderen Typ ist, wird es ignoriert und nicht verarbeitet.
JSON.stringify({key: 'json'}, null, 2)
// '{\n  "key": "json"\n}'
JSON.stringify({key: 'json', list: { str: 'str' } }, null, '|-')
// '{\n|-"key": "json",\n|-"list": {\n|-|-"str": "str"\n|-}\n}'
JSON.stringify({key: 'json'}, null, null)
// '{"key":"json"}'

JSON.stringify-Eigenschaften

  1. Grundlegende Wertzeichenfolgen, Zahlen und boolesche Werte sowie Objektwerte vom Typ „Zeichenfolge“, „Boolescher Wert“ und „Zahl“ werden für die Ausgabe in primitive Wertezeichenfolgen konvertiert.
JSON.stringify(333) // '333'
JSON.stringify(true) // 'true'
JSON.stringify(new String('333')) //'"333"'
JSON.stringify(Boolean(true)) // 'true'
  1. Beim Grundtyp einer Zeichenfolge wird das Konvertierungsergebnis in doppelte Anführungszeichen gesetzt.
    Denn beim Zurücksetzen teilen die doppelten Anführungszeichen JavaScript mit, dass es sich um einen String und nicht um eine Variable handelt.
JSON.stringify('json') === 'json' // false
JSON.stringify('json') === '"json"' // true
  1. undefiniert, Funktionen, Symbole und XML-Objekte:
  • Wenn es in einem Object-Objekt erscheint, wird es ignoriert.
  • Wenn es in einem Array erscheint, wird es als null serialisiert;
  • Wenn es allein vorhanden ist, wird undefiniert zurückgegeben.
JSON.stringify(Symbol()) // undefined
JSON.stringify([Symbol(), Math.abs, undefined]) // '[null,null,null]'
JSON.stringify({ [Symbol()]: Math.abs, key: undefined }) // '{}'
  1. Werte wie NaN, Infinity und -Infinity sowie Null werden als Null serialisiert.
JSON.stringify(null) // 'null'
JSON.stringify(NaN) // 'null'
  1. Objektobjekte und Map/Set/WeakMap/WeakSetandere Objekte vom zusammengesetzten Typ ignorieren bei der Serialisierung die nicht durchlaufbaren Eigenschaften des Objekts.
const obj = {}
Object.defineProperties(obj, {
  'json': { value: 'JSON', enumerable: true },
  'stringify': { value: 'STRINGIFY', enumerable: false }
})
JSON.stringify(obj)
// '{"json":"JSON"}'
  1. Attribute mit Symbol als Attributname werden ignoriert.
JSON.stringify({[Symbol()]: 333}) // '{}'
  1. Mit Ausnahme von Arrays sind die Eigenschaften anderer Objekte bei der Serialisierung möglicherweise nicht in der richtigen Reihenfolge.
const a = { '1': 911, 'r': 822, '11': 9922}
JSON.stringify(a)
// '{"1":911,"11":9922,"r":822}'
  1. Wenn das konvertierte Objekt  toJSON() eine Methode definiert, ist der Rückgabewert der Methode das serialisierte Ergebnis des konvertierten Objekts.
    Der Prozess ignoriert andere Eigenschaften.
const a = { key: 'json' }
a.toJSON = () => 'JSON'
JSON.stringify(a)
// '"JSON"'
  1. Sowohl RegExp-Objekte als auch Error-Objekte werden als leere Objektzeichenfolgen serialisiert.
JSON.stringify(/\d/) // "{}"
JSON.stringify(new Error())  // "{}"

Um das entsprechende Objekt zu serialisieren, müssen Sie die toJSON-Methode implementieren.

RegExp.prototype.toJSON = RegExp.prototype.toString
JSON.stringify(/\d/) // '"/\\\\d/"'
  1. Das Date-Objekt hat toJSON() definiert und konvertiert es in eine Zeichenfolge, sodass es serialisiert werden kann.
    Das Gleiche Date.toISOString().
JSON.stringify(new Date())
// '"2021-12-31T02:24:05.477Z"'
  1. Objekte mit Zirkelverweisen führen diese Methode aus und es wird ein Fehler ausgegeben.
    Objekte beziehen sich aufeinander und bilden eine Endlosschleife.
const a = {}
a.key = a
JSON.stringify(a)
// Uncaught TypeError: Converting circular structure to JSON
  1. Das Konvertieren eines Werts vom Typ BigInt führt zu einem TypeError-Fehler.
    BigInt-Werte können nicht JSON-serialisiert werden
JSON.stringify(12n)
// Uncaught TypeError: Do not know how to serialize a BigInt
  1. Bessere Unterstützung für Unicode-Escape-Zeichen
const a = {'\u0066': 333}
JSON.stringify(a)
// '{"f":333}'

Supongo que te gusta

Origin blog.csdn.net/jh035/article/details/128128164
Recomendado
Clasificación