Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

array.indexOf in TypeScript/JavaScript [duplicate]

UPDATE: Although this question is marked as duplicated with this. But @ssube's way is neat and much smarter.

UPDATE2: Seems there is new way to do it in the comment by @Grungondola.

I am using Typescript.

This works well.

var array1 = [];
array1.push(5);
array1.push(6);
console.log("a", array2.indexOf(6));

But this does not work well. Because array2.indexOf returns -1 which means it does not find it.

var array2 = [];
array2.push({aa:5,bb:5});
array2.push({aa:6,bb:6});
console.log(array2.indexOf({aa:6,bb:6}));

Looks like indexOf does not support Object. Does TypeScript have its own ways to deal with this kind of problem? Thanks.

like image 995
Hongbo Miao Avatar asked Feb 04 '16 17:02

Hongbo Miao


1 Answers

No. The problem is not with Object, but that you are creating two different objects.

The object literal syntax ({foo: 'bar'}) declares an object inline. When the script is executed, the object is created. Using that syntax multiple times creates multiple objects.

You can easily test that with {foo: 3} === {foo: 3}. This will evaluate to false, but they are not the same object (reference).

The indexOf method checks if the object, string, number, etc, is present in the array. You're passing a new object, which is not in the array.

If you have a reference to the object, you can use that and indexOf will work:

var foo = {aa:5,bb:5}, bar = {aa:6,bb:6};
var array2 = [];
array2.push(foo);
array2.push(bar);
console.log(array2.indexOf(foo));

Because you're referring to the same instance, this will print the index.

You can also use filter or find with a predicate to perform a deep search:

function deepIndexOf(arr, obj) {
  return arr.findIndex(function (cur) {
    return Object.keys(obj).every(function (key) {
      return obj[key] === cur[key];
    });
  });
}

var array2 = [];
array2.push(foo);
array2.push(bar);
console.log(deepIndexOf(array2, foo));

This won't recurse into nested objects, but will accomplish the comparison you're looking for (equivalence on two objects and their immediate fields).

like image 149
ssube Avatar answered Nov 05 '22 07:11

ssube