溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

JSON.parse和JSON.stringify怎么使用

發(fā)布時間:2022-01-04 16:54:24 來源:億速云 閱讀:115 作者:iii 欄目:開發(fā)技術(shù)

本篇內(nèi)容主要講解“JSON.parse和JSON.stringify怎么使用”,感興趣的朋友不妨來看看。本文介紹的方法操作簡單快捷,實用性強。下面就讓小編來帶大家學(xué)習(xí)“JSON.parse和JSON.stringify怎么使用”吧!

JSON格式,(簡寫JavaScript Object Notation),是一種用于數(shù)據(jù)交換的文本格式,書寫簡單。
基于JavaScript原生語法,能夠序列化對象、數(shù)組、數(shù)值、字符串、布爾值和 null。

在ES5中,增加了一個JSON對象,專門用來處理JSON格式的數(shù)據(jù)。
JSON是一個對象,但只有兩個方法:parse 和 stringify,不能作為構(gòu)造函數(shù),也無屬性。

typeof JSON === 'object'

JSON.parse

JSON.parse() 用來解析JSON字符串,得到對應(yīng)的JavaScript值或?qū)ο蟆?/p>

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

JSON.parse 語法

JSON.parse(text[, reviver])
  • text:要被解析成的字符串。
    如果傳入數(shù)字則會轉(zhuǎn)換成十進制數(shù)字輸出。
    如果傳入布爾值則直接輸出。
    如果傳入null則輸出null。
    不支持其他類型的值,否則報錯。

  • reviver: 可選,轉(zhuǎn)換器, 可以用來修改解析生成的原始值。

返回值: JavaScript對象/值, 對應(yīng)給定JSON文本的對象/值。

reviver 參數(shù)

reviver函數(shù),用于轉(zhuǎn)換處理解析到的JavaScript值,處理完后返回最終的結(jié)果。

轉(zhuǎn)換過程:

  • 解析的值本身和它可能包含的所有屬性,按照一定遍歷順序分別調(diào)用reviver函數(shù),屬性名和值作為參數(shù)兩個參數(shù) key 和 value 傳入。
    遍歷順序:按照層級,從內(nèi)往外遍歷,最終到達最頂層,則是解析值本身。

  • reviver返回undefined,則刪除該對象,如果返回了其他值,則該值會成為當(dāng)前屬性的新值。

  • 當(dāng)遍歷到最頂層時,因為沒有屬性了,參數(shù)key是空字符串'',參數(shù)value則是當(dāng)前解析值。

對于reviver函數(shù)的兩個參數(shù) key 和 value,不同的數(shù)據(jù)類型:

  • 基本值類型數(shù)據(jù)(string、number、boolean)和null,以及空對象{}和空數(shù)組[]
    則key是空字符串,value是對應(yīng)解析值。
    因為已經(jīng)是最頂層,并沒有別的屬性。

  • Object對象:
    則key和value都存在,與屬性名和值各自對應(yīng)。
    最頂層會返回一個參數(shù)key為空的值。

  • 數(shù)組:
    key對應(yīng)數(shù)組索引,value對應(yīng)元素值。
    最頂層會返回一個參數(shù)key為空的值。

基本類型的轉(zhuǎn)換:

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:{}

Object對象和數(shù)組:

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:: {}

數(shù)據(jù)處理:

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

JSON.parse 特性

在解析JSON字符串的時候,需要注意到JSON格式的一些規(guī)范,不然就容易報錯。
JSON數(shù)據(jù)對值的類型和格式,都有嚴格的規(guī)定,具體的規(guī)則如下:

  • 該方法使用字符串類型JSON格式數(shù)據(jù)。
    該方法也支持數(shù)字、布爾值和null三個類型的值,轉(zhuǎn)換出對應(yīng)的字面值。
    不支持其他類型。

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
  • 字符串必須使用雙引號,不能使用單引號。

JSON.parse('"String"')
// 'String'
JSON.parse('\'String\'')
// Uncaught SyntaxError: Unexpected token ' in JSON at position 0
  • 只支持十進制的字符串,但小數(shù)點后必須跟上數(shù)字。

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
  • 不能使用undefined、Symbol和BigInt,數(shù)字也不支持NaN、Infinity和-Infinity,都會報錯。

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
  • 復(fù)合類型,只能是:[] 和 {} 這樣的字面量。
    不能使用對象構(gòu)造函數(shù),因為會當(dāng)作執(zhí)行語句,不支持。
    不能使用Object和Array,也不能是函數(shù)、RegExp對象、Date對象、Error對象等。

JSON.parse('[]')
// []
JSON.parse('Object()')
// Uncaught SyntaxError: Unexpected token O in JSON at position 0
  • 對象的屬性名必須使用雙引號。

JSON.parse('{"key": 1 }')
// {key: 1}
JSON.parse('{key: 1 }')
// Uncaught SyntaxError: Unexpected token k in JSON at position 1
  • 數(shù)組或?qū)ο笞詈笠粋€成員的后面,不能加逗號。

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
  • 支持unicode轉(zhuǎn)義。

JSON.parse('{"\u0066":333}')
// {f: 333}
  • 部分控制字符、轉(zhuǎn)義字符不支持,如'\n'、'\t'等。

JSON.parse('"\n"')
// Uncaught SyntaxError: Unexpected token

解析的其他方法

將json字符串轉(zhuǎn)成json對象(js對象值),還可以使用其他方法,但是非安全代碼。

  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() 將一個JavaScript對象或值轉(zhuǎn)換為JSON格式字符串。

JSON.stringify 語法

JSON.stringify(value[, replacer [, space]])
  • value:將要序列化成 一個 JSON 字符串的JavaScript對象或值。

  • replacer 可選,用于處理將要序列化的值。

  • space 可選,指定縮進用的空白字符串,用于美化輸出。

返回值: 一個表示給定值的JSON格式字符串。

replacer參數(shù)

replacer 參數(shù)可以以下三種情況:

  • 如果是null、undefined或其他類型,則被忽略,不做處理;

JSON.stringify({key: 'json'}, null, null) // '{"key":"json"}'
JSON.stringify({key: 'json'}, true) // '{"key":"json"}'
  • 如果是一個數(shù)組,則只有包含在這個數(shù)組中的屬性名,才會最終被序列化到結(jié)果字符串中;
    只對對象的屬性有效,對數(shù)組無效。

const obj = {
  json: 'JSON',
  parse: 'PARSE',
  stringify: 'STRINGIFY'
}
JSON.stringify(obj, ['parse', 'stringify'])
// '{"parse":"PARSE","stringify":"STRINGIFY"}'
  • 如果是一個函數(shù),被序列化的值的每個屬性都會經(jīng)過該函數(shù)的轉(zhuǎn)換和處理;

處理過程:

  • 函數(shù)有兩個參數(shù),屬性名(key)和屬性值(value),都會被序列化;

  • 第一次調(diào)用時,key為空字符串,value則為需要序列化的整個對象;

  • 第二次處理時,會把第一次的的結(jié)果傳過來,后續(xù)的每一次的處理都將接收上一次處理的結(jié)果;

  • 后面,將依次處理每個屬性名和屬性值,完成后返回。

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"}}'

value的類型處理:

  • 如果返回基本類型字符串、數(shù)字、布爾值、null,則直接被添加到序列化后的JSON字符串中;

  • 如果返回其他對象,則會在后續(xù)依次序列化該對象的屬性,如果是函數(shù)則不作處理;

  • 如果返回或undefined,則不會輸出該屬性。

  • 序列化數(shù)組時,如果value返回undefined或者一個函數(shù),將會被null取代。

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"}'

下面示例,是返回對象值時的處理:

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

space 參數(shù)

space 參數(shù)用來控制結(jié)果字符串里面的間距,美化輸出??梢暂斎氲闹涤幸韵氯N情況:

  • 如果是一個數(shù)字, 序列化時,每一層級比上一層級多縮進對應(yīng)數(shù)字值的空格,范圍在 1 - 10,即最小1個最大10個空格;

  • 如果是一個字符串,序列化時,該字符串會添加在每行前面,每一層級比上一層級多縮進該字符串,最多是個字符,超過則截取字符串;

  • 如果是null、undefined或其他類型,則被忽略,不做處理。

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 特性

  • 基本類型值字符串、數(shù)字、布爾值,以及String、Boolean、Number對象值,都會轉(zhuǎn)成原始值字符串輸出。

JSON.stringify(333) // '333'
JSON.stringify(true) // 'true'
JSON.stringify(new String('333')) //'"333"'
JSON.stringify(Boolean(true)) // 'true'
  • 基本類型的字符串,轉(zhuǎn)換結(jié)果會帶雙引號。
    因為在還原時,雙引號會讓JavaScript知道是字符串,而不是變量。

JSON.stringify('json') === 'json' // false
JSON.stringify('json') === '"json"' // true
  • undefined、函數(shù)、symbol以及XML對象:

  • 出現(xiàn)在Object對象中時,會被忽略;

  • 出現(xiàn)在數(shù)組中時,會被序列化成null;

  • 單獨出現(xiàn)時,會返回undefined。

JSON.stringify(Symbol()) // undefined
JSON.stringify([Symbol(), Math.abs, undefined]) // '[null,null,null]'
JSON.stringify({ [Symbol()]: Math.abs, key: undefined }) // '{}'
  • NaN、Infinity和-Infinity等值,還有null,都會被序列化成null。

JSON.stringify(null) // 'null'
JSON.stringify(NaN) // 'null'
  • Object對象,以及Map/Set/WeakMap/WeakSet等復(fù)合類型對象,序列化時會忽略對象的不可遍歷屬性。

const obj = {}
Object.defineProperties(obj, {
  'json': { value: 'JSON', enumerable: true },
  'stringify': { value: 'STRINGIFY', enumerable: false }
})
JSON.stringify(obj)
// '{"json":"JSON"}'
  • 以symbol為屬性名的屬性將被忽略。

JSON.stringify({[Symbol()]: 333}) // '{}'
  • 除了數(shù)組,其他對象的屬性在序列化時,順序可能會亂。

const a = { '1': 911, 'r': 822, '11': 9922}
JSON.stringify(a)
// '{"1":911,"11":9922,"r":822}'
  • 轉(zhuǎn)換的對象如果定義了 toJSON() 方法,則該方法的返回值就是轉(zhuǎn)換對象的序列化結(jié)果。
    該過程會忽略其他屬性。

const a = { key: 'json' }
a.toJSON = () => 'JSON'
JSON.stringify(a)
// '"JSON"'
  • RegExp對象、Error對象都會序列化為空對象字符串。

JSON.stringify(/\d/) // "{}"
JSON.stringify(new Error())  // "{}"

想要序列化相應(yīng)對象,需要設(shè)置實現(xiàn)toJSON方法才行。

RegExp.prototype.toJSON = RegExp.prototype.toString
JSON.stringify(/\d/) // '"/\\\\d/"'
  • Date對象已經(jīng)定義了toJSON(),并將其轉(zhuǎn)換為string字符串,因此可被序列化。
    Date.toISOString()

JSON.stringify(new Date())
// '"2021-12-31T02:24:05.477Z"'
  • 循環(huán)引用的對象執(zhí)行此方法,會拋出錯誤。
    對象之間相互引用,形成無限循環(huán)。

const a = {}
a.key = a
JSON.stringify(a)
// Uncaught TypeError: Converting circular structure to JSON
  • 轉(zhuǎn)換BigInt類型的值會拋出TypeError錯誤。
    BigInt值不能JSON序列化

JSON.stringify(12n)
// Uncaught TypeError: Do not know how to serialize a BigInt
  • 更好的支持unicode轉(zhuǎn)義符

const a = {'\u0066': 333}
JSON.stringify(a)
// '{"f":333}'

到此,相信大家對“JSON.parse和JSON.stringify怎么使用”有了更深的了解,不妨來實際操作一番吧!這里是億速云網(wǎng)站,更多相關(guān)內(nèi)容可以進入相關(guān)頻道進行查詢,關(guān)注我們,繼續(xù)學(xué)習(xí)!

向AI問一下細節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI