-2

I have a json file like as below

[{
    "id": 2,
    "name": "Ali",
    "records":[{
        "type": "L",
        "total": 123
    }, {
        "type": "P",
        "total": 102
    }]
},{
    "id": 3,
    "name": "Mete",
    "records":[{
        "type": "O",
        "total": 100
    }, {
        "type": "T",
        "total": 88
    }]
}]

I want to convert to like this

[{
    "id": 2,
    "name": "Ali",
    record: {
        "type": "L",
        "total": 123
    }
},{
    "id": 2,
    "name": "Ali",
    record: {
        "type": "P",
        "total": 102
    }
},{
    "id": 3,
    "name": "Mete",
    record: {
        "type": "O",
        "total": 100
    }
},{
    "id": 3,
    "name": "Mete",
    record: {
        "type": "T",
        "total": 88
    }
}]

how can i do it using javascript?

Mr.Ayanlar
  • 450
  • 1
  • 6
  • 12

4 Answers4

1

Here is what you could do. However, this doesn't work in IE as is as Object.assign that is being used, isn't yet supported in IE. However, it could be replaced with any javascript object clone methods.

You could check : What is the most efficient way to deep clone an object in JavaScript?

var input = [{
  "id": 2,
  "name": "Ali",
  "records": [{
    "type": "L",
    "total": 123
  }, {
    "type": "P",
    "total": 102
  }]
}, {
  "id": 3,
  "name": "Mete",
  "records": [{
    "type": "O",
    "total": 100
  }, {
    "type": "T",
    "total": 88
  }]
}];


var output = [];
input.forEach((obj) => {
  var records = obj.records;
  delete obj.records;

  records.forEach((record) => {
    // Doesnt have any support in IE.
    var newRecord = Object.assign({}, obj);
    newRecord.record = record;
    output.push(newRecord);
  });
});

console.log(output);

If you are fine to use jQuery, here is what you could do.

var input = [{
  "id": 2,
  "name": "Ali",
  "records": [{
    "type": "L",
    "total": 123
  }, {
    "type": "P",
    "total": 102
  }]
}, {
  "id": 3,
  "name": "Mete",
  "records": [{
    "type": "O",
    "total": 100
  }, {
    "type": "T",
    "total": 88
  }]
}];


var output = [];
input.forEach((obj) => {
  var records = obj.records;
  delete obj.records;

  records.forEach((record) => {
    var newRecord = jQuery.extend({}, obj);
    newRecord.record = record;
    output.push(newRecord);
  });
});

console.log(output);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
Community
  • 1
  • 1
Sreekanth
  • 3,110
  • 10
  • 22
  • thank you @Sreekanth. It is worked chrome. Please tell me how can i do it in addition at IE. – Mr.Ayanlar Nov 25 '16 at 06:02
  • As I mentioned in the answer, you have to implement a clone method yourself (have a look at the link I posted). Or you could use jQuery.extend (https://api.jquery.com/jquery.extend/) – Sreekanth Nov 25 '16 at 06:10
  • I research then write comment and i found it from angular copy method. thank you so much. Also i could not do it for classical methods. Because i think array push methods async – Mr.Ayanlar Nov 25 '16 at 06:42
0

There's a few ways but Array.prototype.map seems to fit the bill. This blurb should get you started:

// We'll assume your original array is called myArray
var newArray = myArray.map ( function ( d ) {
  return { 
    id : (d.id || 'theIDYouWant'), 
    name : (d.name || 'theNameYouWant' ),
    record : { type : d.type, total : d.total }
  }
} );

var jsonStr = JSON.stringify ( newArray );
console.log ( jsonStr ); // should write out your JSON as expected.
Tim Consolazio
  • 4,802
  • 2
  • 19
  • 28
  • This doesn't really answer the question, using map on the initial data means you will only ever get the first "record" item included. – Evan Trimboli Nov 24 '16 at 21:47
  • It's a bit to get the OP started. I'm sure he'd figure out that he could just iterate the record objects as well in a nested loop. Sure you could write out all the code if you wanted but I think "use Array.prototype.map" is a useful answer. – Tim Consolazio Nov 24 '16 at 21:49
0

Here's a functional (but probably not very efficient) way of doing it:

function transform(data) {
    // Merge the sub arrays together
    return [].concat.apply([], (data.map(person => {
        // Return an array of copied objects for each person
        return person.records.map(record => {
            // For each record, copy the person information
            return {
                id: person.id,
                name: person.name,
                record: record
            };
        });
    })));
}

console.log(transform([{
    "id": 2,
    "name": "Ali",
    "records":[{
        "type": "L",
        "total": 123
    }, {
        "type": "P",
        "total": 102
    }]
},{
    "id": 3,
    "name": "Mete",
    "records":[{
        "type": "O",
        "total": 100
    }, {
        "type": "T",
        "total": 88
    }]
}]));
Evan Trimboli
  • 29,900
  • 6
  • 45
  • 66
0

This will do it and save what you want in new_json

  • try running the code snippet below

json = [{
  "id": 2,
  "name": "Ali",
  "records": [{
    "type": "L",
    "total": 123
  }, {
    "type": "P",
    "total": 102
  }]
}, {
  "id": 3,
  "name": "Mete",
  "records": [{
    "type": "O",
    "total": 100
  }, {
    "type": "T",
    "total": 88
  }]
}]

new_json = [];

for (var i = 0; i < json.length; i++) {
  for (j = 0; j < json[i]['records'].length; j++) {
    new_json.push({
      id: json[i]['id'],
      name: json[i]['name'],
      record: json[i]['records'][j]
    })
  }
}

console.log(new_json);
Dan Kreiger
  • 5,358
  • 2
  • 23
  • 27