在没有jQuery的情况下,在node.js上合并或合并JSON
我有这样的多个JSON
var object1 = {name: "John"}; var object2 = {location: "San Jose"};
他们不是嵌套或类似的东西。 基本上不同的领域。 我需要在node.js中将它们合并为一个JSON
,如下所示:
{name: "John", location: "San Jose"}
我可以使用jQuery就好了。 这是浏览器中的一个工作示例:
http://jsfiddle.net/qhoc/agp54/
但是,如果我在node.js中这样做,我不想加载jQuery(这是有点过度使用,再加上node.js'jQuery不能在我的Windows机器上工作)。
那么有没有一种简单的方法来做类似于没有jQuery的 $.extend()
?
一个正常的循环?
function extend(target) { var sources = [].slice.call(arguments, 1); sources.forEach(function (source) { for (var prop in source) { target[prop] = source[prop]; } }); return target; } var object3 = extend({}, object1, object2);
这是一个基本的出发点。 你可能想要添加一个像hasOwnProperty
检查的东西,或添加一些逻辑来处理多个源对象具有相同标识符的属性的情况。
这是一个工作的例子 。
附注 :你所说的“JSON”实际上是正常的JavaScript对象。 JSON只是一种与JavaScript共享一些语法的文本格式。
还有内置的util._extend:
var extend = require('util')._extend var o = extend({}, {name: "John"}); extend(o, {location: "San Jose"});
它不做一个深层复制,一次只允许两个参数,但是内置的。我看到这个提到克隆节点中的对象的问题: https : //stackoverflow.com/a/15040626 。
如果您担心使用“私人”方法,您可以随时代理:
// myutil.js exports.extend = require('util')._extend;
如果它消失了,用你自己的实现replace它。 这是(大约)他们的实施:
exports.extend = function(origin, add) { if (!add || (typeof add !== 'object' && add !== null)){ return origin; } var keys = Object.keys(add); var i = keys.length; while(i--){ origin[keys[i]] = add[keys[i]]; } return origin; };
像詹姆斯评论的那样, 下划线的extend
是实现这个最简单和最快捷的方法。
这是一个使用下划线的例子:
var _ = require('underscore'), // npm install underscore to install object1 = {name: "John"}, object2 = {location: "San Jose"}; var target = _.extend(object1, object2);
对象1将获得object2的属性并被返回并分配给目标。 你也可以这样做,取决于你是否介意object1被修改:
var target = {}; _.extend(target, object1, object2);
你应该使用“ Object.assign() ” ; 不需要为浅层合并这样一个简单的用例重新发明轮子。
Object.assign()方法用于将所有可枚举属性的值从一个或多个源对象复制到目标对象。 它会返回目标对象。
var o1 = { a: 1 }; var o2 = { b: 2 }; var o3 = { c: 3 }; var obj = Object.assign(o1, o2, o3); console.log(obj); // { a: 1, b: 2, c: 3 } console.log(o1); // { a: 1, b: 2, c: 3 }, target object itself is changed
即使是来自Node.js的人也这样说 :
_extend
从来不打算在内部NodeJS模块之外使用。 社区无论如何find并使用它。 它已被弃用,不应在新代码中使用。 JavaScript通过Object.assign
具有非常类似的内置function。
这就是说,请记住, Object.assign不适用于Node.js的0.X版本 。 如果您正在使用这些版本之一,则可以使用require("util")._extend
,如上面的链接所示 – 不应该有任何问题 ,因为这些旧版本不会再更新。
PS:如果你真的对深度合并感兴趣(其中任何深度的内部对象数据都是recursion合并的),你可以使用像deepmerge , assign-deep或lodash.merge这样的软件包 ,它们非常小,使用。
使用合并 。
$ npm install merge
示例代码:
var merge = require('merge'), // npm install -g merge original, cloned; console.log( merge({ one: 'hello' }, { two: 'world' }) ); // {"one": "hello", "two": "world"} original = { x: { y: 1 } }; cloned = merge(true, original); cloned.x.y++; console.log(original.xy, cloned.xy); // 1, 2
我看到这个线程太旧了,但是我只是把这个答案放在了日志里。
在上面的一个注释中,你提到你想在你的项目中使用'express',在依赖列表中有'connect'库。 实际上,“connect.utils”库包含一个“合并”方法。 所以你可以使用第三方的实现,而无需添加任何新的第三方库。
这是简单的解决scheme,合并JSON。 我做了以下。
- 使用
JSON.stringify(object)
将每个JSON转换为string。 - 使用
+
运算符连接所有的JSONstring。 - 将模式
/}{/g
replace为","
-
将结果stringparsing回JSON对象
var object1 = {name: "John"}; var object2 = {location: "San Jose"}; var merged_object = JSON.parse((JSON.stringify(object1) + JSON.stringify(object2)).replace(/}{/g,","))
由此产生的合并JSON将是
{name: "John", location: "San Jose"}
你也可以使用这个称为吸收的轻量级npm包
它是27行代码,1kb,并使用recursion来执行深度对象合并。
var absorb = require('absorb'); var obj1, obj2; obj1 = { foo: 123, bar: 456 }; obj2 = { bar: 123, key: 'value' } absorb(obj1, obj2); console.log(obj1); // Output: { foo: 123, bar: 123, key: 'value' }
你也可以用它来做一个克隆,或者只有在源对象中不存在的情况下才传输值,如何在提供的链接中详细说明。
如果你需要特殊的行为,如嵌套的对象扩展或数组replace,你可以使用Node.js的extendify 。
var extendify = require('extendify'); _.extend = extendify({ inPlace: false, arrays : 'replace', isDeep: true }); obj1 = { a:{ arr: [1,2] }, b: 4 }; obj2 = { a:{ arr: [3] } }; res = _.extend(obj1,obj2); console.log(JSON.stringify(res)); //{'a':{'arr':[3]},'b':4}
Lodash是这类公用事业的另一个强大的工具带选项。 请参阅: _.merge()
(这是recursion的)
var object = { 'a': [{ 'b': 2 }, { 'd': 4 }] }; var other = { 'a': [{ 'c': 3 }, { 'e': 5 }] }; _.merge(object, other); // => { 'a': [{ 'b': 2, 'c': 3 }, { 'd': 4, 'e': 5 }] }
使用Object.assign()方法可以轻松完成 –
var object1 = {name: "John"}; var object2 = {location: "San Jose"}; var object3 = Object.assign(object1,object2); console.log(object3);
现在object3是{名称:'约翰',位置:'圣何塞'}
下面的代码将帮助你合并两个具有嵌套对象的JSON对象。
function mergeJSON(source1,source2){ /* * Properties from the Souce1 object will be copied to Source2 Object. * Note: This method will return a new merged object, Source1 and Source2 original values will not be replaced. * */ var mergedJSON = Object.create(source2);// Copying Source2 to a new Object for (var attrname in source1) { if(mergedJSON.hasOwnProperty(attrname)) { if ( source1[attrname]!=null && source1[attrname].constructor==Object ) { /* * Recursive call if the property is an object, * Iterate the object and set all properties of the inner object. */ mergedJSON[attrname] = zrd3.utils.mergeJSON(source1[attrname], mergedJSON[attrname]); } } else {//else copy the property from source1 mergedJSON[attrname] = source1[attrname]; } } return mergedJSON; }
你可以使用Lodash
const _ = require('lodash'); let firstObject = {'email' : 'email@email.com}; let secondObject = { 'name' : { 'first':message.firstName } }; _.merge(firstObject, secondObject)
从这里正确的解决scheme更好的方法,以不改变目标:
function extend(){ let sources = [].slice.call(arguments, 0), result = {}; sources.forEach(function (source) { for (let prop in source) { result[prop] = source[prop]; } }); return result; }
让object1
和object2
是两个JSON对象。
var object1 = [{"name": "John"}]; var object2 = [{"location": "San Jose"}]; object1.push(object2);
这将简单地追加object2
中的object1
:
[{"name":"John"},{"location":"San Jose"}]