2014-09-29 33 views
2

我正在通過CodeAcademy上的JavaScript軌道工作,並且遇到了對象II - >對象簡介II - >私有方法(25/30)的問題。我不瞭解指向事物背後的動機,指向其他事物。如果我們試圖獲得變量的價值,爲什麼不直接引用它呢?例如多層引用的動機? - Code Academy JavaScript

變種d是指無功ç 和 變種C指的變種b 和 變種b所VAR一個

爲什麼這樣做,而不是指一個變種開始?爲什麼要創建變量b,c和d?無論如何在私人方法 - 25/30問題的核心在下面。 *注 - 我把詳盡/確切的代碼在最底層


**var bankBalance = 7500;**     // Located within the Person class 

**var returnBalance = function()**   // Create returnBalance method which returns 
     **return bankBalance;**     // the bankBalance above      

t**his.askTeller = function() {**    // Create the askTeller method which calls 
     **return returnBalance;**    // returnBalance method above 

**var myBalanceMethod = john.askTeller();** // create a variable named myBalanceMethod 
               // which equals the value for askTeller method above 

**var myBalance = myBalanceMethod();**   // create a variable named myBalance which 
               // equals the value for myBalanceMethod method above 

**console.log(myBalance);**     // logs to the console the value of myBalance 

這一切都似乎是一個很大的麻煩。經歷所有這些麻煩的動機是什麼,而不是更直接地引用bankBalance?

下面我已經包含了我的確切的代碼(注意 - 它工作得很好我只是不明白的多層背後的推理)

**function Person(first,last,age) { 
    this.firstname = first; 
    this.lastname = last; 
    this.age = age; 
    var bankBalance = 7500; 

    var returnBalance = function() { 
     return bankBalance; 
    }; 

    // create the new function here 
    this.askTeller = function() { 
     return returnBalance; 
    }; 
} 

var john = new Person('John','Smith',30); 
console.log(john.returnBalance); 
var myBalanceMethod = john.askTeller(); 
var myBalance = myBalanceMethod(); 
console.log(myBalance);** 

回答

1

通過另一名引用自己是不是在正確的證明示例(這就是爲什麼真實世界示例如此必要,因此在使用時得到讚揚)。

當我們分配一個變量的東西,我們已經有一個參考,比如:

var cc = Components.Classes; 

,我們可以做到這一點爲簡便起見,如上述。只要上下文清楚,編寫cc而不是Components.classes可以使代碼更清晰易讀。一旦開始使用API​​,DOM或複雜對象,其用處變得相當清楚。在這種情況下,我可以代替我所有的Components.Classes引用,如:

Components.classes["@mozilla.org/messenger;1"]; 

cc["@mozilla.org/messenger;1"]; 

好多了 - 尤其是當你有來鏈接這些:

var os = Components.classes["@mozilla.org/observer-service;1"] 
        .getService(Components.interfaces.nsIObserverService); 

變爲:

var os = Cc["@mozilla.org/observer-service;1"].getService(Ci.nsIObserverService); 

現在它適合於單行,並且更容易vgrep/tokenize-your-eyes。

另一個優點是分配,例如,作爲函數的單一定義兩個或多個對象:

function _start() { /* start monitoring */ } 
function _stop() { /* stop monitoring */ } 

/* ... code ... */ 

process_observer.start = _start; 
process_observer.stop = _stop; 

memory_monitor.start = _start; 
memory_monitor.stop = _stop; 

在這個例子中,假設我們已經寫了_start_stop功能是不可知的東西我們的目標監視器和能夠適應任何監測對象,我們可以一次寫我們的功能和仍然將其分配給每個單獨的對象,所以我們可以稱之爲process_observer.start()代替start(process_observer)這將報答作用在物體上而不是的對象行爲(前者可能涉及暴露數據和方法,否則我們會想要保持隱藏,以防止錯誤並提高清晰度 - 這也可能會阻止我們使用某些設計模式)。這些當然是一個偏好問題,設計方法和觀點,但永遠不會低估代碼的可讀性和清晰度。另外,如果我們更改了_start_stop,則所有使用它們的對象都會發生更改,而不需要手動更改。 一個常見的用例是針對不同的平臺或瀏覽器使用不同的實現,並且在初始化時將正確的功能分配給所有使用它的對象,我們在這裏檢測運行的對象。

而且,你可能已經注意到,我沒有使用括號()當我指定我的函數對象擁有的變量 - 當你做到這一點喜歡你的例子:

myBalance = myBalanceMethod(); 

你並沒有使用myBalanceMethodmyBalance - 你打電話myBalanceMethod(因爲())和分配它的返回值myBalance - 非常大的陷阱。在HTML元素中分配點擊處理程序時,人們總是在這裏絆倒。

說實話,正如我在開始時所說的那樣,這個例子很糟糕 - 沒有理由以這種方式編寫代碼,而且,正如您已經發現自己的情況那樣,這會讓它更難理解而不是更輕鬆,這是混疊變量和函數的整個點,並且能夠自由地分配它們。