__defineGetter__的整洁替代品?

Pac*_*ier 11 javascript getter-setter

吸气剂和二传手是VB.Net的美女:

Get
    Return width
End Get
Set(ByVal value As Integer)
    width = value
End Set
Run Code Online (Sandbox Code Playgroud)

在Javascript中,这可能是我们要做的:

function Test() {
    var width = 100;
    this.__defineGetter__("Width", function() {
        return width;
    });
    this.__defineSetter__("Width", function(value){
        width = value;
    });
}
Run Code Online (Sandbox Code Playgroud)

它看起来像一盘被kuri洗劫的意大利面.我们有什么更整洁的替代品?

注意:新代码应该使用new Test().Width而不是使用new Test().Width().

Poi*_*nty 11

使用ES5,您将能够:

function Test() {
  var a = 1;

  return {
    get A() { return a; },
    set A(v) { a = v; }
  };
}
Run Code Online (Sandbox Code Playgroud)

getter/setter函数当然可以执行您想要的任何操作.

  • 可以在此处找到不同的getter和setter(包括实时基准测试)的精彩概述:http://jsperf.com/object-defineproperty-vs-definegetter-vs-normal (3认同)

Koo*_*Inc 9

这是一个干净的(呃)替代方案(也适用于旧的脚本引擎):

function Test() {
  var a=1;
  return { A: { toString: function(){return a;} } };
}

alert(Test().A); //=> 1
Run Code Online (Sandbox Code Playgroud)

请注意,您不能使用它来定义私有/静态复杂结构.您只能使用此模式"获取"字符串或数字(因此是不可变变量).也许使用json可以增强模式.

[ edit ]使用json,您还可以通过这种方式为对象创建一个getter:

function Test() {
  var a=1,
  b = {foo:50, bar:100};

  return { 
          A: { toString: function(){return a;} } 
          foobar: { toString: function(){return JSON.stringify(b);}  } 
         };
}
var foobar = JSON.parse(Test().foobar);
alert(foobar.foo); //=> 50
Run Code Online (Sandbox Code Playgroud)


kyb*_*kos 6

在Ecmascript5中,"clean"(和符合标准)的方法是使用defineProperty.

function Test() {
    var a = 1;
    Object.defineProperty(this, "A", {get : function() { 
            return a;
        },  
        enumerable : true});
}
Run Code Online (Sandbox Code Playgroud)

这假设您只想查看如何定义getter.如果你想做的只是让Test不可变的实例(你可以做的好事),你应该使用冻结:

function Test() {
    this.a = 1;
    Object.freeze(this);
}
Run Code Online (Sandbox Code Playgroud)