305

Is there any sort of "not in" operator in JavaScript to check if a property does not exist in an object? I couldn’t find anything about this around Google or Stack Overflow. Here’s a small snippet of code I’m working on where I need this kind of functionality:

var tutorTimes = {};

$(checked).each(function(idx){
  id = $(this).attr('class');

  if(id in tutorTimes){}
  else{
    //Rest of my logic will go here
  }
});

As you can see, I’d be putting everything into the else statement. It seems wrong to me to set up an ifelse statement just to use the else portion.

Sebastian Simon
  • 18,263
  • 7
  • 55
  • 75
Aaron
  • 10,386
  • 13
  • 37
  • 53

5 Answers5

528

It seems wrong to me to set up an if/else statement just to use the else portion...

Just negate your condition, and you'll get the else logic inside the if:

if (!(id in tutorTimes)) { ... }
Jordão
  • 55,340
  • 13
  • 112
  • 144
  • 11
    This style also fixes the JSHint "Confusing use of '!'" warning you'd get if you did if `( ! somekey in someobj )` – mikemaccana May 10 '12 at 11:32
  • 3
    Please note that **in** searches for the property name **anywhere** in the prototype chain. See my [answer](http://stackoverflow.com/a/12573605/36866) for more details. – some Sep 24 '12 at 22:19
  • 79
    I understand this is currently the best solution, but does anyone else agree that this is kinda ugly? – Jonah Jun 03 '16 at 01:58
  • 6
    If it's ugly then just wrap it in a function and give it a beautiful name ```let keyExists = (key, obj) => key in obj``` – Kamafeather Aug 27 '18 at 21:52
  • I totally agree. Indeed my naming skills could be improved too . ```let hasProperty``` "looks" better – Kamafeather Aug 27 '18 at 23:55
  • @mikemaccana, I'm pretty sure that's because (! somekey in someobj) becomes (false in someobj). – PRMan Jun 03 '22 at 16:20
80

Personally I find

if (id in tutorTimes === false) { ... }

easier to read than

if (!(id in tutorTimes)) { ... }

but both will work.

Forage
  • 2,726
  • 2
  • 18
  • 20
  • 1
    Thank you. I prefer the more direct version too. The other is fine but more chars to read and consider. "if something is false" is easy to understand – James Apr 04 '22 at 01:24
44

As already said by Jordão, just negate it:

if (!(id in tutorTimes)) { ... }

Note: The above test if tutorTimes has a property with the name specified in id, anywhere in the prototype chain. For example "valueOf" in tutorTimes returns true because it is defined in Object.prototype.

If you want to test if a property doesn't exist in the current object, use hasOwnProperty:

if (!tutorTimes.hasOwnProperty(id)) { ... }

Or if you might have a key that is hasOwnPropery you can use this:

if (!Object.prototype.hasOwnProperty.call(tutorTimes,id)) { ... }
some
  • 48,070
  • 14
  • 77
  • 93
  • Is it any *safer* to wrap the key in quotes and use `if(!tutorTimes.hasOwnProperty('id')) ...`? – Majid Fouladpour May 16 '18 at 21:17
  • 1
    @MajidFouladpour `id` is an variable that could have any value, `'id'` is a string with the two letters **i** and **d**, so `hasOwnProperty(id)` checks if the property specified in the variable *id* exists, and `hasOwnProperty('id')` checks if there is a property named id. – some May 17 '18 at 14:29
16

Two quick possibilities:

if(!('foo' in myObj)) { ... }

or

if(myObj['foo'] === undefined) { ... }
reedlauber
  • 371
  • 1
  • 5
  • 7
    Use `'undefined' === typeof xxx` instead. `undefined` is not a reserved word and is actually a global variable that can be overwritten (leading to hard to find bugs) – hugomg Nov 01 '11 at 20:32
  • 9
    @hippietrail doesn't work...the parens are required after the "!" and around the `'foo' in myObj)` – Phil Cooper May 07 '12 at 21:41
  • 5
    `myObj['foo']` could exist as a property and simply be set to `undefined` (i.e., with the statement `myObj.foo = undefined`). If you really want to see if the property itself doesn't exist, you need the `!('foo' in myObj)` notation. – Richard Connamacher Sep 04 '12 at 17:27
  • For the performance conscious among us, checking for `myObj.foo === undefined` is much faster (albeit potentially dangerous): [jsperf.com/not-in-vs-is-undefined](https://jsperf.com/not-in-vs-is-undefined). – etpinard May 07 '15 at 14:39
  • @hugomg I don't think that is a very good argument for not using `=== undefined`. Lots of things can break if people abuse a programming language by doing things like, for example, overwriting `undefined` in JavaScript. Also, see: https://stackoverflow.com/questions/8783510/javascript-how-dangerous-is-it-really-to-assume-undefined-is-not-overwritten – Zero3 Aug 28 '15 at 09:18
  • In 2011 @hugomg was right that undefined was a variable that could be overwritten with another value. That was changed in ECMA-262 5.1 Edition from June 2011. – some Nov 02 '18 at 00:36
  • You can overwrite a lot of stuff in Javascript. If someone redefines undefined, just fire them.... :) – PRMan Jun 03 '22 at 16:22
3

you can set the condition to be false

if ((id in tutorTimes === false)) { ... }
Alex Irabor
  • 401
  • 1
  • 6
  • 17