2011-07-07 52 views
7

到目前爲止,我一直在使用JavaScript中的new關鍵字。我一直在閱讀關於Object.create,我想知道我是否應該使用它。我不太明白的是,我經常需要運行構建代碼,所以我沒有看到Object.create會如何工作,因爲它不會觸發任何運行的功能。是否有任何理由在JavaScript中使用Object.create()或new?

有誰能告訴我,在這種情況下,我應該使用Object.create而不是new

+0

參見這個問題的答案:http://stackoverflow.com/questions/4166616/understanding-the-difference-between- object-create-and-new-somefunction-in-ja –

+0

看到這個以及所有新的答案,http://stackoverflow.com/questions/387707/whats-the-best-way-to-define-a-class -in-javascript –

回答

11

到目前爲止,如果你想創建一個對象,你只能用文字:

var obj = {}; 

Object構造。

var obj = Object(); 

但是這些方法都沒有讓你指定原型創建的對象的

這就是你現在可以用Object.create做什麼。它允許您創建一個新對象並將第一個參數設置爲新對象的原型。另外,它允許您設置作爲第二個參數提供的新對象的屬性。

它類似於做這樣的事情(沒有第二個參數):

function create(proto) { 
    var Constr = function(){}; 
    Constr.prototype = proto; 
    return new Constr(); 
} 

所以,如果你正在使用一個類似的結構,這個時候你想使用Object.create

它不是new的替代產品。這是更多的創建單個對象,應該從另一個對象更簡單的繼承。

實施例:

我有一個對象a

var a = { 
    someFunction: function() {} 
}; 

,我想b擴展這個對象。然後你可以使用Object.create

b = Object.create(a); 
b.someOtherFunction = function(){}; 

只要你有一個構造函數,但你只能從它實例一個對象,你也許能Object.create替換此。

有適用的一般規則。它很大程度上取決於構造函數在做什麼以及如何繼承其他對象等。

+0

也許我很密集,但我仍然不明白你什麼時候會使用Object.create vs new?你能給出一個使用Object.create的代碼示例,並解釋爲什麼新的不起作用? – jfriend00

+6

@ jfriend00:如果構造函數的唯一目的是創建一個從另一個對象繼承的空對象,則可以使用Object.create。 –

+0

這有幫助,謝謝。它看起來像它是YUI extend()的語言支持版本,用於創建繼承另一個對象原型的新對象。是對的嗎? – jfriend00

3

如前所述,當您想要簡單地設置新對象的原型時,通常會使用Object.create()。但是其他答案沒有提及的是,構造函數(需要新的)與其他函數並沒有什麼不同。實際上,任何函數都可以返回一個對象,並且在JavaScript中看到工廠函數(如構造函數,但它們不需要new,或使用this來引用新對象)很常見。工廠函數通常使用Object.create()來設置新對象的原型。

var barPrototype = { 
    open: function open() { /* ... */ }, 
    close: function close() { /* ... */ }, 
}; 
function createBar() { 
    return Object.create(barPrototype); 
} 

var bar = createBar(); 
2

超級末到本線程..但我認爲,需要作出一個重要的區別是,雖然構造函數只是函數,new操作符調用函數和捕捉生成的對象可以是在有用的時候一個動態的環境。它允許在構造函數的執行過程中引用屬性和方法,根據具體情況可能有用也可能無用。如果你更關心的是擁有一個集合原型,但是對象本身更加靜態,Object.create將是一個更好的選擇,因爲它更清晰,並且不會以意想不到的方式混淆原始鏈,因爲新操作符會。

一些簡單的例子..

var Foo = function(element) { 
    this.elem = element; 
    $(this.elem).css('color', 'blue'); 
    // using the new operator here gives access to this.elem 
    // immediately after that declaration is made, thus providing 
    // a comfortable dynamic system to work with 
} 

var bar = new Foo(someElem); 

爲並列於..

var foo = { 
    elem : element,    // assume elem exists 
    $(this.elem).css('color', 'blue')// in the lexical scope 
} 

var bar = Object.create(foo); 
// This.elem does not exist until the object is returned now 
// and the .css method call will not execute 

應該稍微更清楚你爲什麼會想使用一個比其他,作爲另一種簡單故障..

當您關心擁有一個動態物體而不是原型鏈時,請使用新功能

使用Object.create的時候,你不用關心動態性,而更多地關注有一個明確的原型鏈。我還會注意到,使用Object.create創建的對象也可以動態構建,方法是使用名爲init的方法,您可以根據需要構建屬性來指定屬性,並只在新鮮返回的對象上調用它。

每種方法都有起伏,但他們的用例在我看來是相當不同的。但是,您很可能會發現自己使用Object.create,因爲大多數情況下都會調用動態不太穩定的情況,並且需要繼承。

0

爲的Object.create()函數的精確的源代碼是:

function Object.Create(proto, propertiesObject) 
{ 
    var obj = {}; 

    Object.setPrototypeOf(obj, proto); 

    if(propertiesObject) 
    { 
     Object.defineProperties(obj, propertiesObject); 
    } 

    return obj; 
} 
相關問題