Getting an array index for an element based on one of its properties

Given an array of objects, I am trying to write a method that can get the index of an element where a specific property has a value that happened ntimes in the array.

What I'm trying to achieve is perhaps easier to describe with this code:

var foods = [
    {
        name: "orange",
        owner: "bob"
    },
    {
        name: "carrot",
        owner: "fred"
    },
    {
        name: "apple",
        owner: "bob"
    },
    {
        name: "onion",
        owner: "fred"
    },
    {
        name: "banana",
        owner: "bob"
    },
    {
        name: "pear",
        owner: "bob"
    }
];

function getIndex(owner, nthItem){
    // solution code
}

getIndex("bob", 3); // should return 4 as it is the index of bob 3rd item in foods

I would prefer a well-formed underscore / lodash solution over a 20-bit pure JS single-line. If you can do it less than with pure JS then this is a great toc.

I tried some things with _.groupBy and _.pluck to get separate lists, but cannot find a way to translate this information back to the index from the original array.

+4
4

, 20+ js, for:

var foods = [
    {
        name: "orange",
        owner: "bob"
    },
    {
        name: "carrot",
        owner: "fred"
    },
    {
        name: "apple",
        owner: "bob"
    },
    {
        name: "onion",
        owner: "fred"
    },
    {
        name: "banana",
        owner: "bob"
    },
    {
        name: "pear",
        owner: "bob"
    }
];

function getIndex(owner, nthItem) {
  var cur = 0;
  for (var i = 0; i < foods.length; i++) {
    if (foods[i].owner == owner) {
      if (cur + 1 == nthItem) return i;
      cur += 1;
    }
  }
  return -1;
}

document.body.innerHTML = getIndex("bob", 3);
Hide result

map filter

var foods = [{
  name: "orange",
  owner: "bob"
}, {
  name: "carrot",
  owner: "fred"
}, {
  name: "apple",
  owner: "bob"
}, {
  name: "onion",
  owner: "fred"
}, {
  name: "banana",
  owner: "bob"
}, {
  name: "pear",
  owner: "bob"
}];

function getIndex(owner, nthItem) {
  var item = foods.map(function(el, index) {
      return {
        el: el,
        index: index
      };
    })
    .filter(function(el) {
      return el.el.owner == owner;
    })[nthItem-1];
  
  return item? item.index : -1;
}

document.body.innerHTML = getIndex("bob", 3);
Hide result
+4

getIndex , -1, getIndex.

function getIndex(owner, nthItem){
  var noOfTimes = 1;
  for(var i = 0; i < foods.length && noOfTimes <= nthItem; i++) {
    if(foods[i].owner == owner) noOfTimes++;
  }
  //returns -1 if it did not find the expected output.
  return i >= foods.length || noOfTimes < nthItem  ?  -1 : i - 1;
}
+2

foods , - -.

var foods = [
    {
        name: "orange",
        owner: "bob"
    },
    {
        name: "carrot",
        owner: "fred"
    },
    {
        name: "apple",
        owner: "bob"
    },
    {
        name: "onion",
        owner: "fred"
    },
    {
        name: "banana",
        owner: "bob"
    },
    {
        name: "pear",
        owner: "bob"
    }
];

var hashmap = foods.reduce(
    function (prev, curr, i, arr) {
        if (curr.owner in prev)
            prev[curr.owner].push(i);
        else
            prev[curr.owner] = [i];
        return prev;
    }, {}); // hashmap contains { bob: [ 0, 2, 4, 5 ], fred: [ 1, 3 ] }

function getIndex(owner, nthItem){
    return hashmap[owner][nthItem - 1];
}

getIndex("bob", 3); // returns 4
+2

lodash:

function getIndex(owner, nthItem) {
    return _.indexOf(foods,
        _.filter(foods, { owner: owner })[nthItem - 1]);
}

filter(), owner. nthItem . , indexOf(), n- foods. -1, .

+1
source

Source: https://habr.com/ru/post/1615962/


All Articles