Creating a JS object with Object.create (null)?

I know many ways to create JS objects, but I did not know Object.create(null) .

Question:

it is exactly the same as:

 var p = {} 

against

 var p2 = Object.create(null); 

?

+135
javascript
Mar 20 '13 at 8:12
source share
4 answers

They are not equivalent. {}.constructor.prototype == Object.prototype whereas Object.create(null) is not inherited from anything and thus has no properties at all.

In other words: a javascript object inherits from Object by default, unless you explicitly create it with zero as a prototype, for example: Object.create(null) .

Instead, {} will be equivalent to Object.create(Object.prototype) .




In Chrome Devtool, you can see that Object.create(null) does not have the __proto__ property, but {} -.

enter image description here

+175
Mar 20 '13 at 8:37
source share

They are definitely not equivalent. I am writing this answer to explain in more detail why this matters.

  • var p = {};

    Creates an object that inherits properties and methods from Object .

  • var p2 = Object.create(null);

    Creates an object that does not inherit anything.

If you use the object as a map, and you create the object using method 1 above, then you should be especially careful when performing a search on the map. Since the properties and methods from Object are inherited, your code may work if there are keys on the map that you never inserted. For example, if you performed a search in toString , you will find a function, even if you never set this value. You can get around this as follows:

 if (Object.prototype.hasOwnProperty.call(p, 'toString')) { // we actually inserted a 'toString' key into p } 

Note that it is great to assign something to p.toString , it will simply override the inherited toString function to p .

Note that you cannot just do p.hasOwnProperty('toString') , because you can insert the "hasOwnProperty" key into p , so we force it to use the implementation in Object .

On the other hand, if you use method 2 above, you donโ€™t have to worry about things from Object appearing on the map.

You cannot check for a property with a simple if as follows:

 // Unreliable: if (p[someKey]) { // ... } 

The value can be an empty string, it can be false or null , or undefined , or 0 , or NaN , etc. To check if a property exists at all, you still need to use Object.prototype.hasOwnProperty.call(p, someKey) .

+94
Jan 12 '14 at 19:29
source share

Creating objects using {} will create an object whose prototype is Object.prototype which inherits the basic functions from the Object prototype and creating objects using Object.create(null) will create an empty object whose prototype is zero.

+1
Apr 12 '18 at 19:16
source share

If someone is looking for an implementation of Object.create (null), just to find out how it works. It is written using proto , which is non-standard and therefore, I do not recommend it .

 function objectCreateMimic() { /*optional parameters: prototype_object, own_properties*/ var P = arguments.length>0?arguments[0]:-1; var Q = arguments.length>1?arguments[1]:null; var o = {}; if(P!==null && typeof P === "object") { o.__proto__ = P; } else if(P===null) { o.__proto__ = null; } if(Q!==null && typeof Q === "object") { for(var key in Q) { o[key] = Q[key]; } } return o; } 

Note I wrote this out of curiosity and written only in simple words, for example, I do not transfer property descriptors from the second object to the returned object. p>

0
Nov 19 '14 at 6:51
source share



All Articles