Niks Jain
Niks Jain

Reputation: 1647

Merge Object & Array: Javascript, JQuery

Illustrative example:

d1 = {
  "ean_code": ["OA13233394CN08", "8903327046534", "8903327014779"],
  "balance_qty": [5, 10, 15]
}

And

d2 = {
  "ean_code": ["OA13233394CN11", "OA13233394CN08", "8903327014779", "OA13233394CN09"],
  "scanned_qty": [30, 5, 20, 10, - 1],
}

Output:

d3 = {
  "ean_code": ["OA13233394CN08", "8903327046534", "8903327014779", "OA13233394CN11", "OA13233394CN09"],
  "scanned_qty": [5, 0, 20, 30, 10],
  "balance_qty": [5, 10, 15, 0, 0]
}

Explaination. d3['scanned_qty'][1] default value is 0, because value of d3['ean_code'][1] is belongs to d1['ean_code'] array and d1 object doesn't have scanned_qty key.

Best possible way to do this operation?

Upvotes: 3

Views: 1113

Answers (3)

Phil H
Phil H

Reputation: 20141

function merge(a,b) {
    var c = {};
    for(key in a.keys()) {
        c[key] = a[key].slice(0);
    }
    for(key in b.keys()) {
        if(typeof c[key] == 'undefined') {
            c[key] = b[key].slice(0);
        } else {
            var adds = b[key].filter(function(item){ 
                return (a[key].indexOf(item) == -1);
            });
            c[key].concat(adds);
        }
    }
    return c;
}

Upvotes: 0

Louis Ricci
Louis Ricci

Reputation: 21086

You just need a custom solution for your specific case.

  • Merge 2 objects with no sub-objects (no recursion required)
  • Final object's array fields must be the same length
  • Final object's array fields must preserve index coherency
  • Final object's array fields must use '0' as a default value

http://jsfiddle.net/8X5yB/4/

function customMerge(a, b, uniqueKey) {
    var result = {};
    var temp = {};
    var fields = {};
    // object 1
    for(var x=0; x<a[uniqueKey].length; x++) {
        id = a[uniqueKey][x];
        if(temp[id] == null) temp[id] = {};
        for(k in a) {
            if(k != uniqueKey) {
                fields[k] = '';
                temp[id][k] = (a[k].length > x ? a[k][x] : 0);
            }
        }
    }
    // object 2
    for(var x=0; x<b[uniqueKey].length; x++) {
        id = b[uniqueKey][x];
        if(temp[id] == null) temp[id] = {};
        for(k in b) {
            if(k != uniqueKey) {
                fields[k] = '';
                temp[id][k] = (b[k].length > x ? b[k][x] : 0);
            }
        }
    }
    // create result
    result[uniqueKey] = [];
    for(f in fields) result[f] = [];
    for(k in temp) {
        result[uniqueKey].push(k);
        for(f in fields) {
            result[f].push(temp[k][f] != null ? temp[k][f] : 0);
        }
    }
    return result;
}
...
var obj = customMerge(d1, d2, "ean_code");

Upvotes: 1

Vinay
Vinay

Reputation: 6322

Let's assume you have o1 and o2 as object 1 and 2, respectively.

var key,
    result = {}
    i,
    largestLength = 0,
    copyIntoResult = function (obj, key) {
        for (i = 0; i < obj[key].length; i += 1) {
            if (result[key].indexOf(obj[key][i]) === -1) {
                result[key].push(obj[key][i]);
            }
        }
    };

for (key in o1) {
    if (o1.hasOwnProperty(key) && o2.hasOwnProperty(key)) {
        result[key] = [];
        copyIntoResult(o1, key);
        copyIntoResult(o2, key);
        if (result[key].length > largestLength) {
            largestLength = result[key].length;
        }
    } else if (o1.hasOwnProperty(key)) {
        result[key] = [].concat(o1[key]);
        if (o1[key].length > largestLength) {
            largestLength = o1[key].length;
        }
    }
}
for (key in o2) {
    if (o2.hasOwnProperty(key) && !result[key]) {
        result[key] = [].concat(o2[key]);
        if (o2[key].length > largestLength) {
            largestLength = o2[key].length;
        }
    }
}

// result now has the merged result

for (key in result) {
    if (result[key].length < largestLength) {
        for (i = 0; i < (largestLength - result[key].length); i += 1) {
            result[key].push('');
        }
    }
}

EDIT: Upon the edit to your question, you can have all the arrays be the same length by equalizing the arrays to the maximum array length of the merged result. However, the default "blank" entry is up to you (in this case, I just used an empty string).

Upvotes: 1

Related Questions