765

The function I am using now to check this is the following:

function inArray(needle,haystack)
{
    var count=haystack.length;
    for(var i=0;i<count;i++)
    {
        if(haystack[i]===needle){return true;}
    }
    return false;
}

It works. Is there a better way to do this?

vvvvv
  • 25,404
  • 19
  • 49
  • 81
Francisc
  • 77,430
  • 63
  • 180
  • 276
  • 1
    Looks fine to me. Of course, if your array is sorted you could do a binary-search instead. Or if each value in the array is always unique you could use a map-based approach instead. – aroth Sep 11 '11 at 12:42
  • 4
    The `==` operator? Do you really want to explicitly allow type coercion? Of course not. Therefore, use the `===` operator instead. – Šime Vidas Sep 11 '11 at 12:50
  • It's smart to declare `count` before the loop. You could also replace those two lines with just `for(var i=haystack.length; i--;)` – Greg Perham Feb 28 '13 at 00:53
  • For numbers one can also use the `in` operator (e.g. `(5 in array)`. It will probably be faster than other options, but won't work for string or objects or any other non-number. – Yuval A. Nov 17 '17 at 14:09

9 Answers9

1322

ECMAScript 2016 incorporates an includes() method for arrays that specifically solves the problem, and so is now the preferred method.

[1, 2, 3].includes(2);     // true
[1, 2, 3].includes(4);     // false
[1, 2, 3].includes(1, 2);  // false (second parameter is the index position in this array at which to begin searching)

As of JULY 2018, this has been implemented in almost all major browsers, if you need to support an older browser a polyfill is available.

Edit: Note that this returns false if the item in the array is an object. This is because similar objects are two different objects in JavaScript.

Alister
  • 27,049
  • 9
  • 40
  • 35
  • 31
    What's a polyfill? – nirvanaswap Aug 18 '16 at 22:27
  • 53
    @nirvanaswap A polyfill is a script you can use to ensure that any browser will have an implementation of something you're using. In this case, you'd add a script that checks `if ("includes" in Array.prototype)` and if not, implements it (using a solution like [Benny's answer](http://stackoverflow.com/a/18101063/2099674), for instance). The [MDN docs](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/includes) (also linked to in this answer) actually provide one for you. – FireSBurnsmuP Sep 20 '16 at 13:39
  • i used this like below, and working fine. And don't push duplicate value. Thanks a lot!! this.state.UpdatedfriendList.includes(s.valueKey)===false? this.state.UpdatedfriendList.push(s.valueKey):''; – Pankaj Jul 15 '17 at 06:35
  • How will be the performance if I have an array with 900 values? – Prithivi Raj Jan 23 '18 at 05:51
  • 1
    @PrithiviRaj It would be linear time, so performance impact would be directly proportional to the size of the array. – Alister Jan 23 '18 at 19:58
  • 2
    Using widely supported `myArray.indexOf(myVal) > -1` is same thing but safer – vinsa Aug 12 '18 at 23:09
  • @Alister : Please give clarification . [1, 2, 3].includes(1, 2) // true . for me it is giving the 'false' value. how come it is true. i checked in google chrome browser. The above condition will give results as --- true false false false false – Deepak Pookkote Mar 14 '19 at 14:10
  • Too bad this isn't supported in Google Apps Script – Kurt Leadley Aug 21 '19 at 21:05
  • Internet Explorer is not supported :( – César León Sep 06 '19 at 17:31
  • @CésarLeón Who wants to support that abomination? Only use this answer if you don't have to worry about supporting IE, otherwise there's other choices available on this page that are IE-friendly... – Jester Jan 07 '20 at 19:52
  • The polyfill link is broken. – Yousuf Khan Apr 20 '20 at 14:44
485

Code:

function isInArray(value, array) {
  return array.indexOf(value) > -1;
}

Execution:

isInArray(1, [1,2,3]); // true

Update (2017):

In modern browsers which follow the ECMAScript 2016 (ES7) standard, you can use the function Array.prototype.includes, which makes it way more easier to check if an item is present in an array:

const array = [1, 2, 3];
const value = 1;
const isInArray = array.includes(value);
console.log(isInArray); // true
gouessej
  • 3,640
  • 3
  • 33
  • 67
Benny Code
  • 51,456
  • 28
  • 233
  • 198
102

Just use indexOf:

haystack.indexOf(needle) >= 0

If you want to support old Internet Explorers (< IE9), you'll have to include your current code as a workaround though.

Unless your list is sorted, you need to compare every value to the needle. Therefore, both your solution and indexOf will have to execute n/2 comparisons on average. However, since indexOf is a built-in method, it may use additional optimizations and will be slightly faster in practice. Note that unless your application searches in lists extremely often (say a 1000 times per second) or the lists are huge (say 100k entries), the speed difference will not matter.

Community
  • 1
  • 1
phihag
  • 278,196
  • 72
  • 453
  • 469
  • `Array.prototype.indexOf` isn't implemented in IE8. – Šime Vidas Sep 11 '11 at 12:45
  • Not supported in IE (maybe only in 9) http://stackoverflow.com/questions/1744310/how-to-fix-array-indexof-in-javascript-for-ie-browsers – Shadow The GPT Wizard Sep 11 '11 at 12:45
  • 3
    This is noted on the page, but it's worth mentioning as part of the answer: `indexOf` is a relatively new addition to JavaScript, and is not supported in IE version prior to 9.0. Also worth noting that `indexOf` will still be O(n), so if the OP meant "better" in terms of speed/performance this won't really be any better, just shorter. – aroth Sep 11 '11 at 12:46
  • @Tomalak Geret'kal True, although the argument is very easy. Added a paragraph about performance, just in case that performance is what the OP meant with `better`. – phihag Sep 11 '11 at 13:03
  • Hi, I meant better speed-wise mostly. Length of code is important, but less so than speed. The array is not sorted, it's created while being checked. If a string value is not in the array it is added. – Francisc Sep 11 '11 at 13:59
  • 4
    @Francisc - Then you might try a map-based approach. Then your `inArray()` implementation could be as simple as `return haystack[needle] != undefined;`. – aroth Sep 11 '11 at 14:36
50

I benchmarked it multiple times on Google Chrome 52, but feel free to copypaste it into any other browser's console.


~ 1500 ms, includes (~ 2700 ms when I used the polyfill)

var array = [0,1,2,3,4,5,6,7,8,9]; 
var result = 0;

var start = new Date().getTime();
for(var i = 0; i < 10000000; i++)
{
  if(array.includes("test") === true){ result++; }
}
console.log(new Date().getTime() - start);

~ 1050 ms, indexOf

var array = [0,1,2,3,4,5,6,7,8,9]; 
var result = 0;

var start = new Date().getTime();
for(var i = 0; i < 10000000; i++)
{
  if(array.indexOf("test") > -1){ result++; }
}
console.log(new Date().getTime() - start);

~ 650 ms, custom function

function inArray(target, array)
{

/* Caching array.length doesn't increase the performance of the for loop on V8 (and probably on most of other major engines) */

  for(var i = 0; i < array.length; i++) 
  {
    if(array[i] === target)
    {
      return true;
    }
  }

  return false; 
}

var array = [0,1,2,3,4,5,6,7,8,9]; 
var result = 0;

var start = new Date().getTime();
for(var i = 0; i < 10000000; i++)
{
  if(inArray("test", array) === true){ result++; }
}
console.log(new Date().getTime() - start);
  • 7
    ~ 950 / 750 / 650 on my laptop. I just changed array to ['df','ff',2,3,4,5,6,333,8,9] and got ~ 950 / 900 / 3150 – Max Lipsky Apr 15 '19 at 15:10
27

Single line code.. will return true or false

!!(arr.indexOf("val")+1)
Akarsh Satija
  • 1,756
  • 2
  • 22
  • 28
21

You can use indexOf But not working well in the last version of internet explorer. Code:

function isInArray(value, array) {
  return array.indexOf(value) > -1;
}

Execution:

isInArray(1, [1,2,3]); // true

I suggest you use the following code:

function inArray(needle, haystack) {
 var length = haystack.length;
 for (var i = 0; i < length; i++) {
 if (haystack[i] == needle)
  return true;
 }
 return false;
}
Eem Jee
  • 1,239
  • 5
  • 30
  • 64
12

Since ECMAScript6, one can use Set :

var myArray = ['A', 'B', 'C'];
var mySet = new Set(myArray);
var hasB = mySet.has('B'); // true
var hasZ = mySet.has('Z'); // false
Nicolas
  • 739
  • 7
  • 7
10

You can use the _contains function from the underscore.js library to achieve this:

if (_.contains(haystack, needle)) {
  console.log("Needle found.");
};
Chris Alley
  • 3,015
  • 2
  • 21
  • 31
4

In lodash you can use _.includes (which also aliases to _.contains)

You can search the whole array:

_.includes([1, 2, 3], 1); // true

You can search the array from a starting index:

_.includes([1, 2, 3], 1, 1);  // false (begins search at index 1)

Search a string:

_.includes('pebbles', 'eb');  // true (string contains eb)

Also works for checking simple arrays of objects:

_.includes({ 'user': 'fred', 'age': 40 }, 'fred');    // true
_.includes({ 'user': 'fred', 'age': false }, false);  // true

One thing to note about the last case is it works for primitives like strings, numbers and booleans but cannot search through arrays or objects

_.includes({ 'user': 'fred', 'age': {} }, {});   // false
_.includes({ 'user': [1,2,3], 'age': {} }, 3);   // false
Connor Leech
  • 18,052
  • 30
  • 105
  • 150