2009-11-10 130 views
7
var obj = {} 
obj.__setitem__ = function(key, value){ 
    this[key] = value * value 
} 
obj.x = 2 // 4 
obj.y = 3 // 9 

JavaScript沒有__setitem__,這個例子顯然不起作用。Python的等價物__setitem__

在蟒蛇__setitem__的工作原理是:

class CustomDict(dict): 
    def __setitem__(self, key, value): 
    super(CustomDict, self).__setitem__(key, value * value) 

d = CustomDict() 
d['x'] = 2 # 4 
d['y'] = 3 # 9 

是否有可能實現在JavaScript __setitem__行爲?所有棘手的解決方法將有所幫助。

回答

7

沒有,但有以下對象文字語法已建議對在JavaScript 2支持類似的功能計劃Mozilla bug 312116,似乎,這可能是它如何會爲對象文本來完成:

({ 
    get * (property) { 
    // handle property gets here 
    } 
}) 

我假設組也將支持(如set * (property, value) {...})。

+0

看起來不錯!你可以發佈一個鏈接到那裏建議的頁面嗎? – NVI 2009-11-11 00:35:37

+0

@NV:它在bugzilla.mozilla.org上有一些bug。我找不到一些簡單的搜索,所以它可能需要你一段時間才能找到它。 – 2009-11-11 01:28:05

+0

@NV:找到它:https://bugzilla.mozilla.org/show_bug.cgi?id=312116 – 2009-11-11 01:32:51

10

是否有可能在JavaScript中實現__setitem__行爲?

不。沒有getter/setter在JavaScript中的任意屬性。

在Firefox中,你可以使用JavaScript 1.5 +的getter和setter方法來定義xy性質廣場轉讓其值,例如:

var obj= { 
    _x: 0, 
    get x() { return this._x; }, 
    set x(v) { this._x=v*v; } 
}; 
obj.x= 4; 
alert(obj.x); 

但你必須聲明爲每一個setter預先命名的屬性。它不會跨瀏覽器工作。

1

我不認爲你可以在當前版本的Javascript中覆蓋[]運算符。在當前的Javascript中,對象主要只是關聯數組,所以[]運算符只是將一個鍵/值對添加到作爲對象的數組中。

您可以編寫方法來設置特定值或甚至將數字平方並將該值添加爲鍵/值對,但不會重載[]運算符。

Javascript2對操作符重載有一些規範,但該規範是MIA。

5

你可以做到這一點(如在JavaScript中也是關聯數組對象):

var obj = {}; 
obj._ = function(key, value){ 
    this[key] = value * value; 
} 
obj._('x', 2); // 4 
obj._('y', 3); // 9 

alert(obj.x + "," + obj.y); //--> 4,9 
+1

是的,我可以。但Python的__setitem__更漂亮。 – NVI 2009-11-11 00:09:59

+2

好吧,我把它改名爲'_',可能更像python一樣...... – manji 2009-11-11 00:17:42

+1

哦,我看到了諷刺。你怎麼能實現obj.x + = 2或類似的東西? – NVI 2009-11-11 00:29:59

5

在通常實現的Javascript版本中沒有真正的setter和getter,所以如果要模擬效果,必須使用一些不同的語法。對於屬性obj.x,使用obj.x()來訪問該屬性的值,並且使用obj.x(123)來設置該值看起來像是一個相當方便的語法。

可以實現這樣的:

// Basic property class 
function Property(value) { 
    this.setter(value); 
} 

Property.prototype.setter = function(value) { 
    this.value = value * value; 
} 

Property.prototype.getter = function() { 
    return this.value; 
} 

Property.prototype.access = function(value) { 
    if (value !== undefined) 
     this.setter(value); 
    return this.getter(); 
} 


// generator function to add convenient access syntax 
function make_property(value) { 
    var prop = new Property(value); 
    function propaccess(value) { 
     return prop.access(value); 
    } 
    return propaccess; 
} 

現在,通過make_property生成的屬性支持它們被分配期望的語法和平方值:

var obj = { 
    x: make_property(2) 
}; 

alert(obj.x()); // 4 
obj.x(3);  // set value 
alert(obj.x()); // 9