第二十三节:JSON简介、表示方法、序列化、反序列化、深拷贝解决方案

一. Json简介

1. 说明

 在目前的开发中,JSON是一种非常重要的数据格式,它并不是编程语言,而是一种可以在服务器和客户端之间传输的数据格式。

 (1). JSON的全称是JavaScript Object Notation(JavaScript对象符号)

 (2). JSON是由Douglas Crockford构想和设计的一种轻量级资料交换格式,算是JavaScript的一个子集;

 (3). 但是虽然JSON被提出来的时候是主要应用JavaScript中,但是目前已经独立于编程语言,可以在各个编程语言中使用;

 (4). 很多编程语言都实现了将JSON转成对应模型的方式;

2. 其它传输格式

 (1). XML:在早期的网络传输中主要是使用XML来进行数据交换的,但是这种格式在解析、传输等各方面都弱于JSON,所以目前已经很少在被使用了;

 (2). Protobuf:另外一个在网络传输中目前已经越来越多使用的传输格式是protobuf,但是直到2021年的3.x版本才支持JavaScript,所以目前在前端使用的较少;

3. Json的使用场景

 (1).网络数据的传输JSON数据;

 (2).项目的某些配置文件;

 (3).非关系型数据库(NoSQL)将json作为存储格式;

 

二. Json表示方法

1 简单值

     数字(Number)、字符串(String,不支持单引号)、布尔类型(Boolean)、null类型;

"ypf"

2 对象值

    由key、value组成,key是字符串类型,并且必须添加双引号,值可以是简单值、对象值、数组值;

{
    "name": "ypf",
    "age": 18,
    "friend": {
      "name": "lmr"
    },
    "hobbies": ["篮球", "足球"]
  }
  

3 数组值

   数组的值可以是简单值、对象值、数组值;

[
    "abc",
    123,
    {
      "name": "ypf"
    }
  ]

注意:Json中不能用单引号,不能写注释。

 

三. Json序列化

1. 含义

    JavaScript中的复杂类型转化成JSON格式的字符串。

2. 方法

    JSON.stringify() 方法

    A. 直接转换,不传其它参数

    B. 第二个参数replacer,可以传递一个数组表示哪些key需要序列化,也可以传入回调函数,对value进行处理

    C. 第三个参数space,增加可读性, 比如传入数字代表空格,传入--代表分隔

    D. 如果对象中含有toJSON方法,直接调用toJSON方法

代码分享:

{
	const obj1 = {
		name: "ypf1",
		age: 18,
		friends: {
			name: "lmr",
		},
		hobbies: ["篮球", "足球"],
	};
	const obj2 = {
		name: "ypf1",
		age: 18,
		friends: {
			name: "lmr",
		},
		hobbies: ["篮球", "足球"],
		toJSON() {
			return "hhhh";
		},
	};

	// 1.1 直接转换
	console.log("--------1.1 直接转换--------");
	const jsonString1 = JSON.stringify(obj1);
	console.log(jsonString1);
	// 1.2 第二个参数replacer
	console.log("-------1.2 第二个参数replacer--------");
	// 1.2.1 传入数组,表示哪些key需要序列化
	const jsonString2 = JSON.stringify(obj1, ["name", "age"]);
	console.log(jsonString2); //"{"name":"ypf1","age":18}"
	// 1.2.2 传入回调函数,可以对value值进行处理
	const jsonString3 = JSON.stringify(obj1, (key, value) => {
		if (key == "age") {
			return value + 10;
		}
		return value;
	});
	console.log(jsonString3);
	// 1.3 第三个参数space,增加可读性
	console.log("-- 1.3 第三个参数space,增加可读性--");
	console.log(JSON.stringify(obj1, null, 2)); //代表2个空格
	console.log(JSON.stringify(obj1, null, "---")); //代表---分隔
	// 1.4 对象中含有toJSON方法
	console.log("-- 1.4 对象中含有toJSON方法--");
	console.log(JSON.stringify(obj2)); //hhhh
}

运行结果:

 

四. Json反序列化

1. 含义

    用来解析JSON字符串,构造由字符串描述的JavaScript值或对象

2. 方法

    JSON.parse()方法

    A. 直接转换,不传其它参数

    B. 第二个参数receiver,可以对value进行处理

代码分享:

{
	console.log("--------2. json反序列化----------");
	const JSONString =
		'{"name":"ypf","age":18,"friends":{"name":"lmr"},"hobbies":["篮球","足球"]}';

	// 2.1 直接转换
	console.log(JSON.parse(JSONString));
	// 2.2 第二个参数receiver,可以对value进行处理
	const obj = JSON.parse(JSONString, (key, value) => {
		if (key === "age") {
			return value + 10;
		}
		return value;
	});
	console.log(obj);
}

运行结果:

 

五. 深拷贝解决方案

 (关于引用赋值、深拷贝、浅拷贝详见:https://www.cnblogs.com/yaopengfei/p/15261698.html)

 方案:

    我们可以先JSON.stringify,然后JSON.parse(),实现对象的深拷贝。

 缺陷:

   这种方案对方法是无能为力的,是因为stringify并不会对函数进行处理,最终的对象里的方法就不见了。

代码分享:
{
	console.log("--------3. 深拷贝---------");
	const obj = {
		name: "ypf1",
		age: 18,
		friends: {
			name: "lmr",
		},
		hobbies: ["篮球", "足球"],
		test() {
			console.log("test is starting");
		},
	};
	// 缺陷:创建出来的info中是没有test函数的,这是因为stringify并不会对函数进行处理;
	const jsonString = JSON.stringify(obj);
	console.log(jsonString); //字符串中没有test方法
	const info3 = JSON.parse(jsonString);
	obj.friends.name = "curry";
	console.log(info3.friends.name); //ypf1
	console.log(info3); //没有test方法
}
运行结果:

 

 

 

!

  • 作       者 : Yaopengfei(姚鹏飞)
  • 博客地址 : http://www.cnblogs.com/yaopengfei/
  • 声     明1 : 如有错误,欢迎讨论,请勿谩骂^_^。
  • 声     明2 : 原创博客请在转载时保留原文链接或在文章开头加上本人博客地址,否则保留追究法律责任的权利。
 
posted @ 2022-04-16 16:49  Yaopengfei  阅读(203)  评论(1编辑  收藏  举报