1

The function below looks like right but it works incorrectly

$.when(
    $.getJSON('compare/As_edit.json'), $.getJSON('compare/As_old.json'))
    .then(function (a,b) {
        //return $.extend(a, b);
        console.log($.extend(a, b));
    })

In console log I see:

Object {text: "As", icon: "icons/tree.png", children: Array[1]}

While it should be "children: Array2"

My files look like:

file1

{
  "text": "As",
  "icon": "icons/tree.png",
  "children": [
    {
      "text": "Class1",
      "children": [
        {
          "text": "Intern1",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        },
        {
          "text": "Intern2",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        }
      ]
    }
  ]
}

file2

{
  "text": "As",
  "icon": "icons/tree.png",
  "children": [
    {
      "text": "Class2",
      "children": [
        {
          "text": "Intern3",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        },
        {
          "text": "Intern4",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        }
      ]
    }
  ]
}

and in output I want to see

{
  "text": "As",
  "icon": "icons/tree.png",
  "children": [
    {
      "text": "Class1",
      "children": [
        {
          "text": "Intern1",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        },
        {
          "text": "Intern2",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        }
      ]
    },
    {
      "text": "Class2",
      "children": [
        {
          "text": "Intern3",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        },
        {
          "text": "Intern4",
          "-ORDER": "2",
          "children": [
            {
              "name": "--TRT",
              "text": "Name of Intern"
            }
          ]
        }
      ]
    }
  ]
}

But I am only getting output from the object in file2 What's wrong?

this is a fiddle example

after checked reference on Merge 2 arrays of objects, I have used next code

 $.when(
        $.getJSON('compare/Astella_edit.json'), $.getJSON('compare/Astella_old.json'))
        .then(function (a,b) {
            var arr3 = [];
            for (var i in a) {
                var shared = false;
                for (var j in b)
                    if (b[j].children == a[i].children) {
                        console.log('['+ (b[j].children == a[i].children) +']');
                        shared = true;
                        break;
                    }
                if (!shared) arr3.push(a[i])
            }
            arr3 = arr3.concat(b);
            console.log(arr3);
            //return arr3;
        })

and it is merged to me almost correct

[Object, Object, "success", Object]

so the first object is file1, second is file2

what is "success" mean in generated JSON and Where is the third object coming from?

Community
  • 1
  • 1
Anton
  • 788
  • 4
  • 14
  • 34

1 Answers1

2

You're expecting that $.extend will automagically merge your children Array:

/*file1*/ {"children" : ["a"]}

$.extended with:

/*file2*/ {"children": ["b"]}

will never become:

/*result*/ {"children": ["a", "b"]}

That's not the way $.extend works:
the result will always be: /*result*/ {"children": ["b"]} !

Take this for example:

var ob1 = {
  a : ["a"],
  b : ["b"]
};
var ob2 = {
  a : ["a"],
  b : ["XXX"],
  c : ["c"]
};
$.extend(ob1, ob2);
console.log( ob1 ); // {a: ["a"], b:["XXX"], c:["c"]}

as you can see $.extend actually "extended" and updated the object ob1 with the values from the ob2 object, but the property b didn't become ["b", "XXX"]

How to merge two arrays of objects? Merge 2 arrays of objects

Community
  • 1
  • 1
Roko C. Buljan
  • 196,159
  • 39
  • 305
  • 313
  • thank you a lot for explanation. Is there any way to merge it? – Anton Mar 02 '16 at 18:53
  • @Anton head to: http://stackoverflow.com/questions/7146217/merge-2-arrays-of-objects – Roko C. Buljan Mar 02 '16 at 18:56
  • thanks, I already has read those link and unfortunately underscore.js doesn't work with external files. Will try to learn more deep... – Anton Mar 02 '16 at 19:00
  • please check updated question – Anton Mar 02 '16 at 19:33
  • @Anton refer to: https://api.jquery.com/jquery.when/ . TLDR; when's `.than()` uses three callbacks, you're not interested in `a` and `b` (three response statuses each) but actually at the first `data` response: `a[0]` and `b[0]` – Roko C. Buljan Mar 02 '16 at 19:43
  • for (var i in a[0]) { var shared = false; for (var j in b[0]) if (b[j].children == a[i].children) { shared = true; break; } if (!shared) arr3.push(a[i]) } arr3 = arr3.concat(b); console.log(arr3); console log says children undefined – Anton Mar 02 '16 at 19:48
  • @Anton use `.then(function (oa, ob) { var a=oa[0], b = ob[0];` but anyways with that code you recently added I think you'll get the same result as using jQuery's `$.extend`... – Roko C. Buljan Mar 02 '16 at 19:51
  • exactly same, what's wrong now? – Anton Mar 02 '16 at 19:55
  • @Anton what you're trying to accomplish is not that easy. You need to **recursively loop all properties of an object**. When looping your primary logic should be: if a==b than o[i]=a. if a==Array && b==Array than o[i]=[a+b] etc etc etc – Roko C. Buljan Mar 02 '16 at 19:55
  • got it.. thank you so much for your help – Anton Mar 02 '16 at 19:57