3

在 getJSON 函数中未正确设置变量值。变量 $videoId 显示第一个警报中预期的 396 和 397。

但在第二个警报中,值 397 显示了两次。

我在这里错过了什么吗?我在这里找不到任何其他讨论此类问题的帖子。如果是这样,请指点我那里。

下面是 jQuery 代码。

 $( "div .ow_video_list_item").each(function(){         
     $videoId = $(this).children("a").attr("href").split("/")[5];
     alert($videoId);    ==> First Alert

     $.getJSON("video/get-embed/" + $videoId + "/", function (data)   
     {                        
         $.each(data, function (key, code) {                                  
             alert($videoId);   ==> Second Alert
         });       
     });  

  });

下面是 HTML 代码:

<div class="ow_video_list_item ow_small">
    <a href="http://site.com/video/396">Video 1</a>
</div>

<div class="ow_video_list_item ow_small">
    <a href="http://site.com/video/397">Video 2</a>
</div>
4

4 回答 4

1

假设$videoLink实际上$videoId正如评论所指出的那样:

这是因为该getJSON方法是异步的,并且您正在处理 javascript 闭包。当您执行getJSON回调时:

function (data)   
     {                        
         $.each(data, function (key, code) {                                  
             alert($videoId);   ==> Second Alert
         }); 

你已经循环了你的第一个每个循环,并且 $videoId 已经取了最后一个值,因此显示 397 两次。

看看 javascript 闭包是如何工作的:JavaScript 闭包是如何工作的?

于 2013-02-27T14:28:53.403 回答
1

当你做getJson方法时,你使用异步代码。在这种情况下,您给出的最后一个值$videoID397两个回调中都是警报值。有几种方法可以解决这个问题。例如,您可以返回videoID从操作中检索到的“数据”中的值getJson并使用它alert(data.videoID)。或者,您可以拥有一个带有适当键的值数组,而不是一个简单的整数变量。例如,它可以是索引(iin : $().each(function(i,e) {}))。你需要找到一种方法让它像那样工作。我确实认为这data.id将是最简单的方法!希望它有所帮助。

于 2013-02-27T14:32:36.323 回答
1

关于 getJson 的异步性质的其他评论是正确的。但大多数情况下,问题在于您使用了全局变量 $videoId。如果您更换:

$videoId = $(this).children("a").attr("href").split("/")[5];

经过

var $videoId = $(this).children("a").attr("href").split("/")[5];

即使使用异步方法,您也会没事的。

于 2013-02-27T14:45:29.947 回答
1

几件事。

  • 在您的代码中没有定义 $videoId,我假设 $videoLink 确实应该是 $videoId。以供将来参考,如果可能更容易执行类似的操作来访问该数据点

<a href="http://site.com/video/396" data-video-id="396">Video 1</a>

这样您就可以使用 轻松访问该视频 ID $(element).data('videoId')。为此还有其他策略,例如使用类。

  • 如果在您的代码示例中 $videoLink 不应该是 $videoId,那么 $videoId 是在该函数范围之外的某个地方定义的。有很多关于 JS 范围/闭包的资源。如果您正在做大量的 JS 开发工作,我建议您使用Javascript: The good parts

  • 回到假设您的代码示例中的 $videoLink 实际上是 $videoId 。您在该 .each 循环中分配它的值,但该变量本身并未在该函数内部“关闭”。它要么是全局的,要么是在每个循环范围之外的其他地方定义的。var在语句前面抛出 a$videoLink =以保持该 var 被包含。

  • 另一个潜在问题是您正在调用对服务器的异步调用,但取决于该异步调用范围之外的变量。大多数情况下,这些调用将在几毫秒内完成,但了解正在发生的事情的一个好方法是在脑海中单步执行代码,并假装每个服务器调用将花费 1 分钟。在您的示例中,外部循环运行一次,获取 396 的 id 然后触发 AJAX 请求,然后再次循环并为 id 397 执行相同的操作。服务器在第二个 ajax 请求所用的时间内没有响应开火。所以你现在有 2 个 ajax 请求。一分钟后他们回来了,哦,看,你的 $variableLink 变量的值为 397,因为它是在 ajax 回调函数之外定义的。解决方案?有几个。

还有其他方法可以做到这一点,但是在不知道除了跟踪该变量之外您正在尝试做什么的确切用例的情况下,很难说。但这应该给你一个很好的起点。

于 2013-02-27T15:25:40.690 回答