为啥 $.each() 不遍历每个项目?

Posted

技术标签:

【中文标题】为啥 $.each() 不遍历每个项目?【英文标题】:Why doesn't $.each() iterate through every item?为什么 $.each() 不遍历每个项目? 【发布时间】:2012-11-18 20:50:34 【问题描述】:

我有以下标记,其中包含 10 个 pre 元素,类为 indent

​<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>
<pre class="indent"></pre>​

我正在使用以下 jQuery .each() 函数来遍历每个元素:

​$(function()    
    $.each(".indent", function(index)
       alert(index); 
    );    
);​

我希望看到 10 个警报,但我只看到 7 个

-- See Fiddle --


但是,这与$(".indent").each() 一样有效:

$(function()    
    $(".indent").each(function(index)
       alert(index); 
    );    
);​

-- See Fiddle --


查看$.each() 文档,我知道有区别:

$.each() 函数与 $(selector).each() 不同,它是 用于专门迭代 jQuery 对象。

但我不明白为什么在这种情况下,它不会遍历所有元素。

为什么会这样?

【问题讨论】:

使用console.log而不是alert,你会得到更好的调试数据。 $.each(".indent") 不会对 .indent 对象进行交互。它在“.indent”字符串上进行交互。 只是一个旁注:最好使用console.log而不是alert。更适合测试,关闭所有这些弹出窗口很痛苦。 @luschn 谢谢,早期版本确实使用了console.log(),但经过数小时的挠头和双重猜测,必须更改每一位代码以防万一:P 【参考方案1】:
$.each(".indent", function(index)

不会遍历 $('.indent') 的元素,而是遍历长度为 7 个字符的 ".indent" 字符串。

见reference


更详细的解释基于jQuery source code:

jQuery首先检查第一个参数obj(这里是你的字符串)是否有length

var ...
        length = obj.length,
        isObj = length === undefined || jQuery.isFunction( obj );

你的字符串有一个length(而不是一个函数),isObjfalse

在这种情况下,执行以下代码:

for ( ; i < length; ) 
    if ( callback.call( obj[ i ], i, obj[ i++ ] ) === false ) 
        break;
    

所以,给定函数f,下面的代码

$.each(".indent", f);

等价于

for (var i=0; i<".indent".length; i++) 
    var letter = ".indent"[i];
    f.call(letter, i, letter);

(您可以使用var f = function(i,v)console.log(v); 记录这些字母,或者使用var f = function()console.log(this); 提醒call 的微妙之处之一)

【讨论】:

我在一分钟内看到了 9 个支持 JS 添加功能的人,但有 17 个支持 .each()... 只是为了好玩:) 非常感谢。我最近也遇到这种问题。【参考方案2】:

$.each 遍历数据集合。由于您传递了一个包含 7 个字符的字符串,因此它将针对每个字符进行迭代。看使用示例:

$.each([52, 97], function(index, value)  
  alert(index + ': ' + value); 
);

【讨论】:

+1 用于指出 value 参数...我不知道为什么 JQuery 决定反转这两者,通常你希望 valueindex 更频繁 @Izkata 用于您通常使用的值 this(嗯,not always)。这就是为什么index 是最有用的参数,所以是第一个。【参考方案3】:

您正在遍历字符串,您应该将对象或数组传递给$.each 方法:

$(function()    
    $.each($(".indent"), function(index)
       alert(index);
    );    
);

【讨论】:

以上是关于为啥 $.each() 不遍历每个项目?的主要内容,如果未能解决你的问题,请参考以下文章

使用 For Each 循环遍历列表时删除列表中的项目

$(selector).each() 和$each() 的区别

为啥 Ruby on Rails 的 Enumerable 显示计数为 3 但“.each”仅打印出项目 1 次

$.each遍历实现延时

为啥嵌套在模板中的每个都不输出

jquery中append加进去的节点元素,为啥再使用each遍历里面相同的元素无效?