【问题标题】:Accessing variables in objects in javascript without "this"在没有“this”的情况下访问javascript中对象中的变量
【发布时间】:2010-11-23 17:20:06
【问题描述】:
  <HTML>
    <HEAD>
      <SCRIPT LANGUAGE="JavaScript">
        function Peon(number) {
            this.number = number;

            this.inc = function() {
                number=number+1;
            };

            return true;
        }
        var p=new Peon(10);

        function returnNumber() {
            p.inc();
            alert(p.number);
        }
      </SCRIPT>
    </HEAD>
    <BODY>

      <INPUT id="b00" TYPE="button" Value="Click" onClick="returnNumber()">

    </BODY>
  </HTML>

此代码无法按预期工作。有没有办法让它工作而无需编写

this.number=this.number+1;

这是一个微不足道的选择,但在更大的代码中没有这个。* 会使其更具可读性。有可能吗?

【问题讨论】:

    标签: javascript variables object this


    【解决方案1】:

    你可以将number设为“私有”,但是你需要一个getter

        function Peon(number) {
            var number = number;
    
            // increment
            this.inc = function() {
                number++;
            };
    
            // a simple getter
            this.getNumber = function() {
                return number;
            }
        }
        var p = new Peon(10);
        p.inc();
        alert(p.getNumber());
    

    您应该阅读 Douglas Crockfords 的“The Good Parts”以了解有关如何使用此模式的更多信息,Google Books 提供了(有限的)预览。

    你也不需要从构造函数返回一些东西,你的return true 是多余的。

    【讨论】:

    • 您可以在他的网站上了解 Crockford 的私人会员模式:javascript.crockford.com/private.html非常重要要注意,如果您要拥有很多 Peons,这个私人成员模式比仅使用属性消耗的内存明显更多,因为每个单独的对象都将在构造函数中定义两个函数的自己的副本。它们不是,也不能在对象之间共享。所以权衡是隐私与内存使用。内存消耗是 IE 和 Firefox 的主要问题。如果你只需要几个 Peons,那没关系。
    • 谢谢,这就是我要找的东西
    • return true 确实是多余的,并且在构造函数的末尾基本上被忽略了,但是返回一个对象而不是一个基元将不会被忽略,并且会返回该对象而不是新的 Peon 对象。
    【解决方案2】:

    不,您必须使用 this 来引用 this 对象上的属性。请注意,JavaScript 中的 this 与其他一些语言(如 C 或 Java)中的 this 非常不同。更多herehere

    您的代码所做的是访问传递给Peon 构造函数的number 参数,而不是您在构造函数中创建的this.number 属性。这就是为什么它不能按预期工作,但也不会失败。

    没有理由在Peon 构造函数中定义您的inc 操作,顺便说一句,还有一些很好的理由不这样做(通过Peon 创建的每个单独的对象都将拥有自己的copy 该函数)。因此,您可以这样定义它:

    function Peon(number) {
        this.number = number;
    
        // Don't return values out of constructor functions, it's
        // an advanced thing to do. In your case, you were returning
        // `true` which was being completely ignored by the JavaScript
        // interpreter. If you had returned an object, the `this` object
        // created for the `new Peon()` call would have been thrown away
        // and the object you returned used instead.
    }
    
    Peon.prototype.inc = function() {
        ++this.number;
    };
    
    var p=new Peon(10);
    
    function returnNumber() {
        p.inc();
        alert(p.number); // alerts 11
    }
    

    【讨论】:

    • +1 给你和@Ivo。两者相结合,总体上是一个很好的答案。
    • 作为旁注 - 为什么使用 ++this.number 而不是 this.number++?我知道他们的评估略有不同,但在这个用例中是可以互换的。只是好奇,因为我倾向于更频繁地看到 this.number++ 形式。
    • @Matt:我的母语是英语,其中“动词-名词”是一种比“名词-动词”更常见的语音模式,所以我写了“increment x”(++x ) 而不是“x 增量”(x++)。如果我的母语是德语,我怀疑我会写x++。 :-) 在绝大多数情况下,现实世界没有区别。 (我强调“现实世界”,因为否则潜伏者会突袭并尝试进行微优化。:-))
    【解决方案3】:

    不是真的,但是这个更简洁一点

    this.number++
    

    实际上,作为旁注,您最好在 Peon 的构造函数之外声明 .inc。你可以用原型来做到这一点。这样,每次创建 Peon 类型的对象时都不会重新构建 inc 函数。

    Peon.prototype.inc = function(){
        this.number++;
    }
    

    或者,您可以使用p.number++,而不是使用p.inc()。这是我能想到的避免使用 this 关键字的唯一方法。

    【讨论】:

      【解决方案4】:

      我能看到的唯一可读方式是:

      this.inc = function() {
         this.number++;
      };
      

      否则,在您的“更大代码”假设中,您可以执行以下操作:

      this.inc = function() {
         var number = this.number; // obviously simple here.  Imagine more complexity
         number++;
      };
      

      【讨论】:

        【解决方案5】:

        是的,您不需要在 javascript 中使用“this”。您可以通过闭包而不是“this”访问变量

        function createPeon(number) {
        
          function inc() {
              number=number+1;
          };
          function getNumber() {
              return number;
          }
        
          return { inc, getNumber };
        }
        var p=createPeon(10);
        p.inc();
        alert(p.getNumber());

        【讨论】:

          猜你喜欢
          • 2011-03-17
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多