简体   繁体   中英

Merge array of arrays using javascript

I'm a javascript beginner and I'm trying to merge two arrays.

I have two arrays like this:

 arr1[
{
        description : "this is a object",
        array       : ["a","b"]
 }
    ]

 arr2[
{
       array : ["c","d"]
} 
   ]

And I want to get a resulting javascript object like this

result = { description : "this is a object", array : ["a","b","c","d"]}

The order of elements isn't important to me. So I tried the following.

result = $.extend(true, {},arr1,arr2)[0];

But this returns the following output

result = { description : "this is a object", array : ["c","d"] }

Which isn't what I want the result to be since it's missing values. How can I merge them the way I want?

You're confusing arrays and hashes. The presence of the colon separator in your "arrays" suggests you're trying to define hashes. Hashes must be delimited by braces {} rather than square brackets [] .

Assuming you're trying to define and combine two hashes, here's how it could be done without any genericity, IOW by explicitly specifying how to incorporate each key/value pair from each input hash into the combined hash:

 var obj1 = { description : "this is an object", array : ["a","b"] }; var obj2 = { array : ["c","d"] }; var res = { description : obj1.description, array : obj1.array.concat(obj2.array) }; alert(res.description); // "this is an object" alert(res.array); // a,b,c,d 


Now, for a more general solution, you can code "standard" logic for how to handle various data types and their collisions in the input pair of hashes:

 var obj1 = { description : "this is an object", array : ["a","b"] }; var obj2 = { array : ["c","d"] }; function combine(obj1,obj2) { var res = {}; for (var k1 in obj1) { if (!obj1.hasOwnProperty(k1)) continue; if (obj2.hasOwnProperty(k1)) { // collision if (typeof(obj1[k1]) !== typeof(obj2[k1])) throw "type mismatch under key \\""+k1+"\\"."; if (Array.isArray(obj1[k1])) { res[k1] = obj1[k1].concat(obj2[k1]); } else if (typeof(obj1[k1]) === 'string' || obj1[k1] instanceof String) { res[k1] = obj1[k1]+obj2[k1]; } else if (typeof(obj1[k1]) === 'object') { res[k1] = combine(obj1[k1],obj2[k1]); } else { throw "unsupported collision type "+typeof(obj1[k1])+" under key \\""+k1+"\\"."; } } else { res[k1] = obj1[k1]; } } for (var k2 in obj2) { if (!obj2.hasOwnProperty(k2)) continue; if (obj1.hasOwnProperty(k1)) continue; // already handled it above res[k2] = obj2[k2]; } return res; } var res = combine(obj1,obj2); alert(res.description); // "this is an object" alert(res.array); // a,b,c,d 


Following your edit, my solutions are still applicable; you just have to index the arrays first to extract the contained objects. So here would be the revised implementation:

Solution 1:

var res = {
    description : arr1[0].description,
    array       : arr1[0].array.concat(arr2[0].array)
};

Solution 2:

var res = combine(arr1[0],arr2[0]);

Perhaps you should take a look at this implementation of a recursive merge function .

It should have the same behavior as the PHP array_merge_recursive.

code:

function array_merge_recursive(arr1, arr2) {
  //  discuss at: http://phpjs.org/functions/array_merge_recursive/
  // original by: Subhasis Deb
  //    input by: Brett Zamir (http://brett-zamir.me)
  // bugfixed by: Kevin van Zonneveld (http://kevin.vanzonneveld.net)
  //  depends on: array_merge
  //   example 1: arr1 = {'color': {'favourite': 'read'}, 0: 5}
  //   example 1: arr2 = {0: 10, 'color': {'favorite': 'green', 0: 'blue'}}
  //   example 1: array_merge_recursive(arr1, arr2)
  //   returns 1: {'color': {'favorite': {0: 'red', 1: 'green'}, 0: 'blue'}, 1: 5, 1: 10}

  var idx = '';

  if (arr1 && Object.prototype.toString.call(arr1) === '[object Array]' &&
    arr2 && Object.prototype.toString.call(arr2) === '[object Array]') {
    for (idx in arr2) {
      arr1.push(arr2[idx]);
    }
  } else if ((arr1 && (arr1 instanceof Object)) && (arr2 && (arr2 instanceof Object))) {
    for (idx in arr2) {
      if (idx in arr1) {
        if (typeof arr1[idx] === 'object' && typeof arr2 === 'object') {
          arr1[idx] = this.array_merge(arr1[idx], arr2[idx]);
        } else {
          arr1[idx] = arr2[idx];
        }
      } else {
        arr1[idx] = arr2[idx];
      }
    }
  }

  return arr1;
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM