2011-05-28 110 views
2

這很清楚我不明白函數如何在Javascript中作用域。下面是最新的例子:界定Javascript功能範圍問題

function riseData() { 
    var jsonResult; 
    $.ajax({ 
     success: function(data, textStatus, jqXHR){ 
      jsonResult = jqXHR.responseText; 
      alert("Inside: " + jsonResult); 
     },   
     error: function (jqXHR, textStatus, errorThrown) { 
      $('#errLog').append('<br>Status: ' + qXHR.statusText);     
     } 
    }); 
    return jsonResult; 
} 

$(document).ready(function(){ 
    var intervalID = setInterval('UTCclock()',100); 
    alert("Outside: " + riseData());        
}); 

當我執行此,「內」提醒功能正常,但「外面」警報顯示「不確定」,儘管riseData()顯然定義只有幾行早。代碼中有一個$ .ajaxSetup,它定義了ajax調用的參數。 ajax調用成功返回「Inside」警報中的請求數據。

我只是沒有絲毫的線索如何使必要的數據(jqXHR.responseText)可用於腳本的其他部分。

任何人都可以指出我在一個「Javascript範圍傻瓜」如何解決這個問題?

+0

riseData()實際上返回了var'jsonResult'這是在返回時爲空值。問題是您的AJAX呼叫 – JohnP 2011-05-28 06:24:44

回答

5

你的例子的作用域很好。你的問題是你不明白JavaScript如何主要是異步的。

讓我通過你的例子來展示你。

  1. 您的文檔就緒處理程序運行。
  2. 它叫riseData
  3. riseData聲明變量jsonResult
  4. riseData調用$.ajax,它調度一個AJAX請求完成,但響應將在稍後發生。
  5. 由於$.ajax通常是非阻塞/異步的,因此riseData會繼續並返回jsonResult。由於尚未分配jsonResult,因爲AJAX請求尚未完成,因此將返回缺省值undefined
  6. 在文檔準備好處理程序中,最終以alert("Outside: "+undefined);結束。

事件循環到幾毫秒後,這種情況發生:

  1. 的AJAX請求完成。 jQuery將其轉發給您的回調。
  2. jsonResult已設置,但riseData已返回。
  3. riseData裏面的文件就緒處理程序已提醒undefined與新數據警報。

這個問題有兩種解決方案。第一種解決方案很簡單,但通常會導致用戶體驗變差。此解決方案將async: false選件添加到$.ajax。這使得$.ajax阻止並凍結瀏覽器。

第二種解決方案是對幾乎所有東西都採用異步樣式。這意味着讓riseData接受回調並在AJAX響應處理程序中調用它。以下是用此方法轉換的代碼:

function riseData(callback) { 
    $.ajax({ 
     success: function(data, textStatus, jqXHR){ 
      var jsonResult = jqXHR.responseText; 
      alert("Inside: " + jsonResult); 
      callback(jsonResult); 
     },   
     error: function (jqXHR, textStatus, errorThrown) { 
      $('#errLog').append('<br>Status: ' + qXHR.statusText);     
     } 
    }); 
} 

$(document).ready(function(){ 
    //var intervalID = setInterval('UTCclock()',100); 
    // Unrelated, but it's better to pass a 
    // function into setInterval than a string. 
    var intervalID = setInterval(UTCclock, 100); 
    riseData(function(jsonResult) { 
     alert("Outside: " + jsonResult); 
    }); 
}); 
+0

AHA !!謝謝。所以設置... 。 asynch:false, 在$ .axaxSetup()中修正了它。 – RAMilewski 2011-05-28 07:16:57

+0

現在我所要做的就是掌握「迷你降價」,這似乎改變了發佈帖子發佈評論的規則。 添加空格的Inr似乎是不可能的。 ......無論如何,感謝您的幫助! – RAMilewski 2011-05-28 07:23:49

0

這只是部分範圍問題。您的ajax調用是異步的,所以riseData()函數在執行ajax調用之前返回一個值。嘗試在方法外設置變量。

var jsonResult; 

function riseData() { 

    $.ajax({ 
... 

jsonResult不僅可以在riseData()中使用,也可以在out中使用。但是,您仍然會在完成填充時出現問題。

的鏈接多一點的解釋:

What is the scope of variables in JavaScript?

+0

根本沒有範圍問題。如果'$ .ajax'是同步的,它會工作得很好。因此,沒有範圍問題。 – icktoofay 2011-05-28 06:29:12

+0

如果.ajax不同步,那麼如果該值將在別處使用,則存在範圍問題。是不同步的ajax和矛盾的考慮異步是在縮略語。 – 2011-05-28 06:32:41

+0

確實,如果你認爲AJAX嚴格來說就是這個縮寫詞,那麼它就是一個矛盾,但許多人也使用AJAX代替XML來使用JSON ......無論如何,OP會返回'jsonResult'並使用返回值功能。沒有試圖通過'riseData'之外'jsonResult'的名稱來訪問'jsonResult'。 – icktoofay 2011-05-28 06:34:42