38

我不是在问这是否可以:

Object.prototype.method = function(){};

考虑到它搞砸了,几乎每个人都认为这是邪恶for(var i in obj)的。

真正的问题

忽略

  • 无能的浏览器(不支持的浏览器Object.defineProperty
  • 财产冲突或压倒一切的可能性

假设您有一些非常有用的方法,这是否被认为是错误/不道德的?

Object.defineProperty(Object.prototype, 'methodOnSteriods',{
  value: function(){ /* Makes breakfast, solves world peace, takes out trash */ },
  writable: true,
  configurable: true,
  enumerable: false
});

如果您认为上述内容是不道德的,那么他们为什么会首先实施该功能?

4

5 回答 5

25

2021 年更新

尽管这是公认的答案,但 10 年的经验告诉我这不是最好的主意。您可以做的几乎任何事情都可以避免污染全局范围是一件非常非常好的事情。

下面的原始答案,为了后代,因为堆栈溢出不会让我删除一个接受的答案。


2011年的原始答案

我认为如果它在您的目标环境中工作就可以了。

此外,我认为原型扩展偏执狂被夸大了。只要您hasOwnProperty()像优秀的开发人员一样使用,一切都很好。最坏的情况是,您在其他地方重载该属性并丢失该方法。但如果你这样做,那是你自己的错。

于 2011-07-29T18:00:40.560 回答
10

我想说这几乎和以前一样邪恶。最大的问题,仍然和以前一样,是Object.prototype 是全局的。虽然您的方法目前可能正在解决世界和平,但它可能已经覆盖了其他人的方法(即保证银河和平),或者将来可能被您无法控制的某个图书馆覆盖(因此再次使世界陷入混乱)


新版本的 Javascript 具有许多与属性相关的特性,例如将属性定义为可枚举/不可枚举,具有 getter 和 setter... Object.defineProperty 存在以对此进行控制。

来自Mozilla 文档

此方法允许精确添加或修改对象的属性。通过赋值添加的普通属性会创建在属性枚举期间显示的属性(for...in 循环),其值可能会更改,也可能会被删除。此方法允许从默认值更改这些额外的详细信息。


这个新功能基本上是支持新功能所必需的,你应该在你自己的东西上使用它。能够修改 Object.prototype 只是它也是一个“正常”对象的副作用,并且和以前一样邪恶。

于 2011-07-29T18:00:15.173 回答
3

好吧,在“JavaScript:好的部分”中,有一个类似的功能,我认为这对于改进 javascript 基础对象(如字符串、日期等)非常有用,但仅此而已。

// Add a method conditionally. from "JavaScript: the good parts"

Function.prototype.method = function (name, func) {
    if (!this.prototype[name]) {
        this.prototype[name] = func;
    }
}
于 2011-07-29T18:29:44.347 回答
3

.hasOwnProperty()将通过继承属性排除迭代,我个人认为这通常更烦人而不是有用。它在很大程度上破坏了它的有用性Object.create()——具有讽刺意味的是,说服每个人都这样做的同一个人.hasOwnProperty()也提升了Object.create().

由于此处列出的原因,不应扩展 Object.prototype。如果你真的想扩展它,那么让扩展不可迭代。

我意识到这与所有已发布的最佳实践背道而驰,但我们真的应该停止“强制”.hasOwnProperty()对象键迭代并接受直接对象到对象继承的有用性。

于 2016-09-15T21:48:28.080 回答
0

简短的回答是肯定的,你应该这样做。

在做之前,有几个注意事项需要注意:
1.hasOwnProperty在迭代对象时使用,但这并不是真正的注意事项,在迭代对象的时候,hasOwnProperty反正我已经在使用了。
2.检查nameinObject.prototype.name是否已经存在,这样很安全,可以避免名字冲突。
3.利用Object.defineProperty(),只需添加额外的保护层。

如您所见,它不是很复杂。

一旦你处理了风险/缺点,现在的优势就来了:
1. 方法链,这只会使代码更易读、更简洁,并使编码更愉快。反过来让你更快乐,让你的生活更轻松。
2.解决了浏览器兼容性问题,反正你是在做polyfill。

PS:
肯定不要在与大型团队合作时这样做。

于 2016-08-31T04:56:05.617 回答