2013-02-11 63 views
0

我在其中一個應用程序中使用了Revealing模塊模式,並且無法在調用init方法之後讓它返回字符串變量的值目的。目標是設置stringVar的值並從我的UI中檢索它。 arrayVar的作品。如何在JavaScript中返回字符串值Revealing模塊模式

謝謝, 克里斯

<script type="text/javascript" src="http://code.jquery.com/jquery-latest.min.js"></script> 

<script type="text/javascript"> 
    var viewModel = null; 
    $(document).ready(function() { 
     viewModel = new ViewModel(); 
     viewModel.init(); 
     // writes "object1" to ul 
     $("#log").append("<li>" + viewModel.arrayVar[0] + "</li>"); 
     // writes "" to ul 
     $("#log").append("<li>" + viewModel.stringVar + "</li>"); 
    }); 

    ViewModel = (function() { 
     var 
      arrayVar = new Array(), 
      stringVar = '', 
      init = function() { 
       // load data from external source 
       arrayVar.push("object1"); 
       arrayVar.push("object2"); 
       stringVar = "string value 1"; 
      }; 
     return { 
      arrayVar: arrayVar, 
      stringVar: stringVar, 
      init: init 
     }; 
    }); 

</script> 
+0

這是因爲'stringVar'在return語句不是一個參考,但副本(一個新的字符串)。 – numbers1311407 2013-02-11 01:53:16

+0

它爲什麼與arrayVar一起工作? – user135498 2013-02-11 02:53:53

+0

arrayVar是一個數組,因此它是一個參考,而不是一個值 – Marc 2013-02-11 16:21:33

回答

0

這裏的問題是,字符串是不可變的,所以當你在init重新分配stringVar,它實際上是一個新的字符串替換變量,使對象從指向原來的構造函數返回。

解決此問題的最簡單方法是使用getter函數代替直接訪問。如果你想要類似財產的訪問,有幾個選項。有__defineGetter__,它被廢棄,那麼ECMA5干將,這將是有限的兼容性:

// your constructor 
function() { 
    // ... 

    var getStr = function() { 
    return stringVar; 
    }; 

    // saving the returned object to a variable, as a few of the options 
    // involve operating on an object. 
    var m = { 
    // typical getter function 
    getStr: getStr, 

    // ecma5 pretty syntax getter property 
    get str1() { return getStr() } 
    }; 

    // __defineGetter__ variant 
    m.__defineGetter__("str2", getStr); 

    // ecma5 Object.defineProperty variant 
    Object.defineProperty(m, "str3", {get: getStr, enumerable: true}); 

    return m; 
} 

// access them like: 
viewModel.getStr(); 
viewModel.str1; 
viewModel.str2; 
viewModle.str3; 
+0

這正是我的想法,但我的大腦被拋出循環,因爲我認爲所有的變量都是變體,它們之間沒有任何區別。使用getter的問題是我不想多次調用外部數據源,我試圖弄清楚如何在對象中保存響應,以便通過屬性訪問它。有任何想法嗎? – user135498 2013-02-12 01:00:26

+0

使用getter並不意味着您將不得不再次加載外部資源。你可以保持原樣,除了不是返回變量'stringVar',而是返回一個函數,它返回構造函數的'stringVar'本地。這樣你可以在'init'中替換它並返回新的值。 – numbers1311407 2013-02-12 07:21:16

+0

謝謝。這解決了這個問題。 – user135498 2013-02-14 05:11:51

0

「本」 的作品。雙關語意:)

init = function() { 
    // load data from external source 
    this.arrayVar.push("object1"); 
    this.arrayVar.push("object2"); 
    this.stringVar = "string value 1"; 
}; 
+0

這是我的理解,揭示模塊模式的主要好處之一是,你不必使用'this'來確定變量的範圍。該示例的工作原理是不向arrayVar添加「this」,但不適用於stringVar。我認爲我錯過了一些巧妙的東西。謝謝。 – user135498 2013-02-11 02:53:00

+0

'This' is missing the point,pun continue :-) – numbers1311407 2013-02-11 17:59:47

相關問題