1

I've a scenario where I've to iterate two list or arrays to get required values. So I am doing something like this:

var html = "";
$.each(list, function (i, set1) { //set1 is a list or array
     $.each(set1.Tabs, function (i, set2) { //set1.Tabs is another one
       html += "<li><a href='#" + set2.TabName + "'>" + set2.Details + "</a> <span class='ui-icon ui-icon-close' role='presentation'>Remove Tab</span></li>";                                   
    })
})

The above works fine, it returns me the required data. But the problem is, say the outer loop has 10 values and the inner loop has four values. So the inner loop gets iterated ten times with the four values. This is natural and it should do. I was trying to get distinct values using the following (For the outer loop specifically):

list = list.filter((x, i, a) => a.indexOf(x) === i);

Though the above should work, my expected output is as follows:

Input: [1, 2, 3, 3, 4, 5, 6, 6]
Output: [1, 2, 3, 4, 5, 6]

N.B: My concern is with the inner loop, not with the outer one. But to iterate the inner loop, I've to go through the outer loop. Is there any way I can get the inner loop work directly?

Update 1: Sample Code

$(document).ready(function() {
  var html = "";

  var data = [{
    "id": "0001",
    "type": "donut",
    "name": "Cake",
    "ppu": 0.55,
    "topping":
      [
        { "id": "5001", "type": "None" },
        { "id": "5002", "type": "Glazed" },
        { "id": "5005", "type": "Sugar" },
        { "id": "5007", "type": "Powdered Sugar" }
      ]
    },
    {
    "id": "0002",
    "type": "donut",
    "name": "Cake",
    "ppu": 0.55,
    "topping":
      [
        { "id": "5001", "type": "None" },
        { "id": "5002", "type": "Glazed" },
        { "id": "5005", "type": "Sugar" },
        { "id": "5007", "type": "Powdered Sugar" }
      ]
    }
  ]

  $.each(data, function(i, set1) { //set1 is a list or array
    $.each(set1.topping, function(i, set2) { //set1.Tabs is another one
      html += "<li><a href='#" + set2.id + "'>" + set2.type + "</a> <span class='ui-icon ui-icon-close' role='presentation'>Remove Tab</span></li>";
    })
  })

  $('#add').append(html);
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="add"></div>
Barmar
  • 741,623
  • 53
  • 500
  • 612
user8512043
  • 1,043
  • 12
  • 20
  • 2
    What's the question or issue you're having? Note that it may be more beneficial if you could add a sample of `list` to the question so we can recreate your environment, – Rory McCrossan Jan 18 '21 at 16:51
  • About the inner loop, use another variable for the index. `i` is used in the outer loop... so use `j` for the inner one. -- Beyond that, you did not post enought code to figure out your issue. – Louys Patrice Bessette Jan 18 '21 at 16:56
  • `list` is a 2-dimensional array. Are you trying to filter out duplicate rows, or just duplicate cells? – Barmar Jan 18 '21 at 16:56
  • If individual cells, is there a unique ID property in the `set2` objects? – Barmar Jan 18 '21 at 16:58
  • Filter out duplicate rows @Barmar. The inner loop works as expected but the outer loop gets me the unexpected repeated result set. – user8512043 Jan 18 '21 at 16:58
  • See https://stackoverflow.com/questions/27030/comparing-arrays-of-objects-in-javascript for how to compare arrays of objects. You can't just use `indexOf()`. – Barmar Jan 18 '21 at 17:01

1 Answers1

1

You can create unique toppings based on the id and then render the list using unique toppings. To create unique toppings, you can use flatMap() Object.values() and array#reduce.

$(document).ready(function() {
  var html = "";

  var data = [{
      "id": "0001",
      "type": "donut",
      "name": "Cake",
      "ppu": 0.55,
      "topping": [{
          "id": "5001",
          "type": "None"
        },
        {
          "id": "5002",
          "type": "Glazed"
        },
        {
          "id": "5005",
          "type": "Sugar"
        },
        {
          "id": "5007",
          "type": "Powdered Sugar"
        }
      ]
    },
    {
      "id": "0002",
      "type": "donut",
      "name": "Cake",
      "ppu": 0.55,
      "topping": [{
          "id": "5001",
          "type": "None"
        },
        {
          "id": "5002",
          "type": "Glazed"
        },
        {
          "id": "5005",
          "type": "Sugar"
        },
        {
          "id": "5007",
          "type": "Powdered Sugar"
        }
      ]
    }
  ]

  const uniqueToppings = Object.values(data
      .flatMap(o => o.topping)
      .reduce((r, {id, type}) => {
        r[id] = r[id] || {id, type};
        return r;
      },{}));;

  $.each(uniqueToppings, function(i, set) {
    html += "<li><a href='#" + set.id + "'>" + set.type + "</a> <span class='ui-icon ui-icon-close' role='presentation'>Remove Tab</span></li>";
  });

  $('#add').append(html);
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<div id="add"></div>
Hassan Imam
  • 21,956
  • 5
  • 41
  • 51