JSON.stringify的使用和一些思维拓展

news/2024/7/11 1:15:32 标签: javascript, node.js, json, es6

平时在对一个数据进行凑合用的 json化,我们会直接 JSON.stringify(obj) 输出一个一行的字符串,并且会自动过滤掉 undefined、Function、Symbol等内容,对于递出现循环引用则会直接报错。

但它实际上能够接3个参数,而且,JSON.stringify 并非触摸不到对象里面的 undefined、Function、Symbol等。

JSON.stringify(obj, replacer?, space?)

https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/JSON/stringify

space 美化

space 大于0时是用来美化输出字符串,将内容输出成格式化后的效果,定义了缩进时的空格数。

const obj = {a: 1, b: [{ c: 2, d: 3 }]}
JSON.stringify(obj, null, 2);
/*
"{
  "a": 1,
  "b": [
    {
      "c": 2,
      "d": 3
    }
  ]
}"
*/

因此相比 js 代码需要用 ugilfyjs 等工具进行代码格式处理,json 格式的字符串可以直接用 JSON.stringify 完成排版美化。

replacer 遍历

replacer 是定义在 JSON.stringify 深度遍历时,处理到的键值对(如果是数组,键为下标;如果既不是对象也不是数组则没有键)进行一些特殊化处理,它支持数组函数两种有效类型,其他类型都将当做不发生任何处理(且正常运行)。

  1. 数组:只输出指定 key 的内容(但其父节点必须存在)
const obj = {a: 1, b: [{ c: 2, d: 3 }], e: undefined, f: () => {}};
obj.toString();                         // '[object object]'
JSON.stringify(obj);                    // '{"a":1,{"b":[{"c":2,"d":3}]}}'
JSON.stringify(obj, ['a', 'b']);        // '{"a":1, "b":[{}]}'
JSON.stringify(obj, ['a', 'd']);        // '{"a":1}',d 虽然指定了但它的节点b不在
JSON.stringify(obj, ['a', 'b', 'c']);   // '{"a":1, "b":[{"c":2}]}'

因此,JSON.stirngify可以用在数据筛选、保留纯数据的地方,例如后台返回部分数据。

  1. 函数 (key, value) => value:自定义处理

如果想要筛选掉一些字段,而不是像上面保留指定字段,则需要用函数来实现:

JSON.stringify(obj, (key, value) => {
  if (!['a', 'd'].includes(key)) {
    return value;
  }
})       // '{"b":{"c":2}}'

如果想保留输出字符串中含 undefined、Function 等内容,则可以不严谨地这样做:

JSON.stringify(obj, (key, value) => {
  if (value === undefined) {
    return '__undefined__';
  } else if (value instanceof Function) {
    return `__Function__${value.toString()}__Function__`;
  }
  return value;
})
.replace(/"__undefined__"/g, 'undefined')
.replace(/"?__Function__"?/g, '');
// {"a":1,"b":[{"c":2,"d":3}],"e":undefined,"fun":() => {}}

同时发现,JSON.stringify 以深度优先的递归算法遍历整个对象所有键值对:

在这里插入图片描述
因此我们可以利用它快速实现一个深度遍历对象的纯函数算法:

const DFTrace = (obj, handler) => {
  JSON.stringify(obj, (key, value) => {
    handler(key, value);
    return value;      // 这一句不可缺少
  })
}

http://www.niftyadmin.cn/n/1436934.html

相关文章

PHP中文网侵权事件

该网站于2017年09月09日14:25把我的文章“mysql七表查询实例(一) ” 和"[置顶] mysql七表查询实例(二) " 放到自…

TS类型断言简化对象类型声明

前言 在使用了 typescript 的项目开发中,有时候为了某个对象进行声明,经常需要写完 interface 之后,在赋值的时候又写了一遍相似的代码;当想对它增加一个键值,又得去增加 interface 的字段声明。因此很想和声明一个变…

vue 2 实现自定义组件一到多个v-model双向数据绑定的方法

前言 有时候我们需要对一个组件绑定自定义 v-model,以更方便地实现双向数据,例如自定义表单输入控件。 甚至有时候,我们想要实现绑定多个 “v-model”,也就是多个“双向绑定”,例如带表单输入的模块框,想…

博文防侵权小技巧

大家有什么防止博文被侵权的技巧也一起来讨论下吧!!!

用monkey脚本看自己的博文

这个脚本是适用于联想手机或者装有联想手机浏览器的手机。如果浏览量很多的话后续还会写一些百度浏览器版的脚本。