Define a prototype only for objects {...}

Is it possible to define a prototype only for {} -Objects?

In Javascript, almost everything is an object.

Object.prototype.test = function() { alert("test"); } 

All objects (including Number, String, and Array) will have this method. But I only want this for a struct object. > {...} <

You can first create all the prototypes for an object and remove it from others, such as Number, String and Array.

 // Overwrite Array.prototype.test = undefined; // or delete property 

It "works" ... The prototype is overwritten. But the key is still there.

 // Show all keys for (key in arr) { alert(key); // print index of array AND keynames } 

I am looking for the most elegant way to do this.

+5
source share
3 answers

You almost certainly don't want to modify the prototype of Object . This MDN JavaScript inheritance article sums up:

One commonly used feature is the extension of Object.prototype or one of the other built-in prototypes.

This method is called a monkey patch and breaks encapsulation. Although it is used in popular environments such as Prototype.js, there is still no good reason to clutter up built-in types with additional non-standard features.

In your example, removing the test property from Array will not have the desired effect. When Array.test is Array.test , it just searches the prototype chain and executes Object.test . This is illustrated by the following code:

 Object.prototype.test = function () { alert('In test'); } delete Array.prototype.test; //Calls Object.test and shows the alert [].test(); 

Instead, you can create a base class that you will control and inherit from it as needed. Below is a working demo.

 function MyBaseClass() { this.test = function () { log('In test'); }; } function Shape() { this.shapeAction = function () { log('Shape action'); }; } Shape.prototype = new MyBaseClass(); function Square() { this.squareAction = function () { log('Square action'); this.shapeAction(); }; } Square.prototype = new Shape(); //Test function can be called on Square, but not on Array var s = new Square(); s.squareAction(); s.shapeAction(); s.test(); try { [].test(); } catch (e) { log('Exception when trying to run Array.test: ' + e); } //Log function for demonstration purposes function log(s) { var e = document.createElement('p'); e.innerHTML = s; document.body.appendChild(e); } 
+2
source

with Array.prototype.test = undefined; your methods set the value to undefinied and this will not remove it.

If you really want to delete a method (property), use delete Array.prototype.test;

ps But in this case (with the object {} ) → you cannot get what you want with delete .

Array.prototype inherited from Object.prototype , and after removing Array.prototype.test your code will find Object.prototype.test and call it.

I think the best way to do what you want is to do something like this:

 Object.defineProperty(Object.prototype, 'test', { enumerable: false, configurable: false, writable: true, value: function(test) { alert('In test' + test); } }); Object.defineProperty(Array.prototype, 'test', { enumerable: false, configurable: false, writable: false, value: function() { throw new Error('You can\'t do it!'); } }); try { var a = []; var keys = ""; for (key in a) { keys += key + ', '; // get all keys } // call array test method -> will throw exception a.test('from array'); } catch (e) { // check keys -> test is not here console.log("Error: " + e.message + ' ' + "KEYS: " + keys); } var b = {}; // and this will work b.test('from object'); 
0
source

Well, although you can change the prototype of an object, this is highly discouraged. This is because all the libraries you ever use expect the object to not be affected. This can lead to very complex bug tracking and unexpected behavior of some libraries.

You need to learn the correct orientation of objects in JS. This is a very confusing topic for beginner js. I recommended that you read the excellence Nicholas Zakas Principles of Object Oriented JavaScript and the book You Don't Know JS by Kyle Simpson.

But you can start well with my explanation of how to make Object Orientation in javascript on my blog: http://www.ideasaboutcode.com/object-orientation-in-javascript/

hope this helps.

0
source

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


All Articles