/** * @description 传入一个对象或者数组,返回一个新的对象,内部的引用值也会修改 * @param {Object | Array} obj - 一个引用类型 Object 或者 Array * @returns {Object | Array} - 返回新的值 */ function copy(obj) { // 使用map作为缓存,缓存把对象作为key,克隆后的新内容作为值 var oCatch = new Map() return deepClone(obj) function deepClone(obj) { // 判断这个值是否是引用值,如果不是的话就返回 if (typeof obj !== "object" || obj === null) return obj; // 传入的值是一个引用类型,直接在缓存中查找,找到直接返回 if(oCatch.has(obj)) return oCatch.get(obj) // 判断数组是否是数组,如果是数组就采用数组的方式便利,否则使用对象的方式便利 var newObj = null; if (Array.isArray(obj)) { newObj = []; // 将新的引用类型存入缓存 oCatch.set(obj, newObj) var n = obj.length; for (var i = 0; i < n; i++) { newObj[i] = deepClone(obj[i]); } } else { newObj = {}; // 将新的引用类型存入缓存 oCatch.set(obj, newObj) var keys = Object.keys(obj); var n = keys.length; for (var i = 0; i < n; i++) { newObj[keys[i]] = deepClone(obj[keys[i]]); } } return newObj; }; } var a = { name: "小红" }; // {name: '小红', b: {a: a, nema: '小王'}} var b = { a: a, name: "小王" }; a.b = b; var c = copy(a) console.log(c.name); console.log(c.b.a); console.log(c.b.name);