Maison  >  Article  >  interface Web  >  Comment désactiver la réécriture d'objets JavaScript

Comment désactiver la réécriture d'objets JavaScript

不言
不言original
2018-07-09 10:41:371436parcourir

Cet article présente principalement comment interdire la réécriture d'objets JavaScript. Il a une certaine valeur de référence. Maintenant, je le partage avec tout le monde. Les amis dans le besoin peuvent s'y référer

Note du traducteur : . Utilisez Object.preventExtensions(), Object.seal() et Object.freeze() pour empêcher la réécriture des objets JavaScript.

  • Traducteur : Fundebug

  • Texte original : Empêcher la modification des objets JavaScript

En raison de JavaScript Flexibilité, on peut facilement remplacer certains objets définis par d'autres. En d’autres termes, n’importe qui peut remplacer les objets que nous définissons. Il s'agit d'une fonctionnalité très puissante que de nombreux développeurs souhaitent essayer d'étendre ou de modifier le comportement de certains objets. Par exemple, la méthode DOM document.getElementById() peut être remplacée. De manière générale, nous devrions éviter de faire cela car cela rendra le code difficile à maintenir et laissera des bugs difficiles à trouver. ECMAScript 5 introduit des méthodes qui permettent aux développeurs de restreindre la réécriture d'objets. Si vous développez des bibliothèques d'outils telles que jQuery, fundebug, etc., ou si votre équipe de développement est très nombreuse, les méthodes présentées dans cet article seront très utiles.

Ne remplacez pas les objets des autres.

Ne remplacez pas les objets des autres, c'est la règle d'or de JavaScript. Par exemple, lorsque vous remplacez une méthode, il est probable que cela affecte les bibliothèques qui dépendent de cette méthode, ce qui peut être très déroutant pour les autres développeurs.

// 示例代码1
window.originalAlert = window.alert;  
window.alert = function(msg) {  
    if (typeof msg === "string") {
        return console.log(msg);
    }
    return window.originalAlert(msg);
};

alert('ooh so awesome'); // 参数为字符串时,打印到控制台 
alert(3.14); // 参数为其他类型时,弹出对话框

Dans Exemple de code 1, j'ai modifié windows.alert : lorsque le paramètre est une chaîne, il est imprimé sur la console lorsque le paramètre est d'un autre type, une boîte de dialogue ; apparaît. De telles modifications affecteront évidemment les autres développeurs utilisant la méthode d'alerte. Si vous modifiez un objet DOM tel que getElementById(), cela entraînera des conséquences très graves.

Cela peut également causer des problèmes si vous ajoutez simplement de nouvelles méthodes à l'objet.

// 示例代码2
Math.cube = function(n) {  
    return Math.pow(n, 3);
};
console.log(Math.cube(2)); // 8

Le plus gros problème avec cette procédure est que cela peut provoquer des conflits de noms à l'avenir. Bien que l'objet Math n'ait actuellement pas de méthode cube, la prochaine version du standard JavaScript pourrait ajouter une méthode cube (bien sûr, c'est peu probable), ce qui signifie que nous remplacerons la méthode cube native. Dans un cas réel, la bibliothèque Prototype a défini la méthode document.getElementsByClassName(), qui a ensuite été ajoutée au standard JavaScript.

Malheureusement, nous ne pouvons pas empêcher d'autres développeurs de réécrire les objets que nous définissons. Nous avons alors besoin des méthodes présentées dans cet article :

Tout d'abord, autant le comparer via une table Object. .preventExtensions(), Object.seal() et Object.freeze() :

方法 禁止增加属性 禁止删除属性 禁止修改属性
Object.preventExtensions()
Object.seal()
Object.freeze()

Object.preventExtensions()

使用Object.preventExtensions(),可以禁止给对象添加新的方法或者属性。注意,修改或者删除对象已经存在的方法或者属性是没有问题的。使用Object.isExtensible()可以查看某个对象是否可以增加方法或者属性。

// 示例代码3
var song = {  
    title: 'Hope Leaves',
    artist: 'Opeth'
};


console.log(Object.isExtensible(song)); //true  
Object.preventExtensions(song);  
console.log(Object.isExtensible(song)); //false  


song.album = 'Damnation';
console.log(song.album);  // undefined


song.play = function() {  
    console.log('ahh soo awesome');
};
song.play(); // TypeError: song.play is not a function

示例代码3可知,执行Object.preventExtensions()之后,为song对象新增album以及play方法都失败了!

但是,当我们为song新增属性或者方法时,并没有报错。当我们使用了"use strict"采用严格模式时,情况就不一样了:

// 示例代码4
"use strict";

var song = {  
    title: 'Hope Leaves',
    artist: 'Opeth'
};

Object.preventExtensions(song);  

song.album = 'Damnation'; // Uncaught TypeError: Cannot add property album, object is not extensible

在严格模式下,给已经Object.preventExtensions的对象新增属性时,会立即报错。广告:如果你希望实时监控应用中类似的错误,欢迎免费试用Fundebug

Object.seal()

使用Object.seal(),可以禁止给对象添加属性或者方法(这一点与Object.preventExtension()的作用一致),同时禁止删除对象已经存在的属性或者方法。

// 示例代码5
"use strict"
var song = {
    title: 'Hope Leaves',
    artist: 'Opeth'
};

Object.seal(song);
console.log(Object.isExtensible(song)); //false  
console.log(Object.isSealed(song)); //true  

song.album = 'Damnation'; // Uncaught TypeError: Cannot add property album, object is not extensible
delete song.artist; // Uncaught TypeError: Cannot delete property 'artist' of #<Object>

Object.freeze()

使用Object.freeze(),可以禁止为对象增加属性或者方法(这一点与Object.preventExtension()的作用一致),同时禁止删除对象已经存在的属性或者方法(这一点与Object.seal()的作用一致),另外还禁止修改已经存在的属性或者方法。

// 示例代码6
"use strict"
var song = {
    title: 'Hope Leaves',
    artist: 'Opeth',
    getLongTitle: function()
    {
        return this.artist + " - " + this.title;
    }
};

Object.freeze(song);

console.log(Object.isExtensible(song)); // false  
console.log(Object.isSealed(song)); // true  
console.log(Object.isFrozen(song)); // true  

song.album = 'Damnation'; // Uncaught TypeError: Cannot add property album, object is not extensible  
delete song.artist; // Uncaught TypeError: Cannot delete property 'artist' of #<Object> 
song.getLongTitle = function() // Uncaught TypeError: Cannot assign to read only property 'getLongTitle' of object '#<Object>'
{
    return "foobar";
};

主流浏览器的最新版本都支持这些方法:

  • IE 9+

  • Firefox 4+

  • Safari 5.1+

  • Chrome 7+

  • Opera 12+

以上就是本文的全部内容,希望对大家的学习有所帮助,更多相关内容请关注PHP中文网!

相关推荐:

如何解决JS高程中的垃圾回收机制与常见内存泄露的问题

JavaScript创建对象的四种方式

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn