覆盖自定义对象的原生javascript函数名称是否安全?

时间:2014-05-13 22:39:21

标签: javascript native-methods

在创建自定义对象时,给它方法是否安全(在我目前的情况下,"阅读","写"&"保存" )覆盖原生js函数?

有问题的对象永远不必写入DOM(或以其他方式使用它正在丢失的功能);这些方法名称是理想的,所以我很好奇,然后很惊讶很难找到一个明确的答案。以下示例。谢谢。

/**
 * Ticket class
 * @param category
 * @param issuedBy
 * @param reissuable If true, lock cannot be overridden by the same method that locked it
 * @returns {Ticket}
 * @constructor
 */
Ticket = function (category, issuedBy, reissuable) {
    //properties
    this.id = Date.now().toString();
    this.category = category;
    this.resolved = false;
    this.issuingMethod = issuedBy;
    this.reissuable = reissuable === true;
    this.data = {};

    //methods
    this.resolve = function () { return this.resolved = true;};
    this.read = function (dataPath) { // find dataPath in this.data }
    this.write = function (dataPath, value) { // add value to dataPath of this.data}

    return this;
};

2 个答案:

答案 0 :(得分:2)

在提供的代码示例中,您不会覆盖任何本机Object.prototype方法。但是,如果您不小心,可能会覆盖从Object.prototype继承的本机方法。

function MyObject() {}

MyObject.prototype.hasOwnProperty = function () { return true; };

new MyObject().hasOwnProperty('test'); //true

显然这会产生误导,在这种情况下,我会选择在您的域中具有类似含义的其他函数名称,而不是覆盖本机Object.prototype.hasOwnProperty函数。

在另一个答案中已经说过,调用没有new关键字的构造函数也可能会覆盖全局本机变量。虽然这是非常正确的,但它会产生更多的负面影响,而不仅仅是可能覆盖原生全局变量。 使用JSHint等强大的工具来挽救您的代码(就像您应该这样)将避免这些错误。

答案 1 :(得分:2)

它并不完全安全。在没有new的情况下调用构造函数时,this指向全局对象。

var ticket = Ticket(); //this.document will point to the global document object

他们理解您的代码的关键是它使用this这是一个特殊的关键字,可能意味着不同的东西;

  • 如果不在函数内,则表示window<script>alert(this.name)</script>
  • 当没有附加对象的独立函数调用时,(alert()),this指向window对象
  • 使用点语法(ticket.resolve())调用时,this指向点左侧的对象(ticket)。
  • 当作为构造函数(new Ticket)调用时,this是一个新的空对象,其原型链中有Ticket.prototype
  • 从内联HTML处理程序(onclick="alert(this.id)")调用时,this指向附加事件的HTML元素
  • setTimeoutsetInterval和AJAX回调等功能调用时,this通常指向window
  • 使用applycall调用函数时,您可以指定this将会是什么
  • 您通常可以使用Function.bind确保使用正确的
  • 调用您的函数

在调用var ticket = Ticket()的情况下,所有代码(如this.name = 'something')都将创建或覆盖现有的全局变量,在本例中为窗口的name

如果您关心此问题,可以通过执行以下操作来缓解此问题。

    Ticket = function (category, issuedBy, reissuable) {
    if (!this instanceof Ticket) { // called as a function
         return new Ticket(category, issusedBy, reissuable);
    }
    //properties
    this.id = Date.now().toString();

要以通用方式执行此操作,您可以看到此链接http://js-bits.blogspot.com/2010/08/constructors-without-using-new.html

请注意,这可能是不必要的锅炉铭牌代码,可以通过following code conventions and enforcing them

来避免