我需要检索第一个元素。
我用这段代码做到这一点......
$(element).find('.x').first();
据我了解,该代码...
element
从匹配的 中检索所有元素.x
,- 删除不需要的元素;
有没有更好的方法呢?喜欢$.findOne()
还是什么?
我需要检索第一个元素。
我用这段代码做到这一点......
$(element).find('.x').first();
据我了解,该代码...
element
从匹配的 中检索所有元素.x
,有没有更好的方法呢?喜欢$.findOne()
还是什么?
根据 jQuery 文档:
因为 :first 是一个 jQuery 扩展而不是 CSS 规范的一部分,所以使用 :first 的查询不能利用原生 DOM querySelectorAll() 方法提供的性能提升。为了在使用 :first 选择元素时获得最佳性能,首先使用纯 CSS 选择器选择元素,然后使用 .filter(":first")。
因此,将您的选择器重写为:
$(element).find('.x').filter(":first")
或(这个只会给你直接后代,并且会比 快.find
,除非你也在寻找嵌套元素)
$(element).children('.x').filter(":first")
应该会给你更好的结果。
更新在kingjiv和patrick dw的宝贵意见(见评论)之后,这两个似乎确实比.filter(':first')
文档声称的要快。
$(element).find('.x').first(); // faster
$($(element).find('.x')[0]); // fastest
如果你想让它真正快速,你应该使用本机浏览器方法。现代浏览器支持querySelector
[docs]:
var $result;
if(element.querySelector) {
$result = $(element.querySelector('.x'));
}
else {
$result = $(element).find('.x').first();
}
用法有点有限,因为它只有在element
是单个元素并且选择器是有效的 CSS 选择器时才有效。你可以用它做一个插件。但是,如果您考虑所有情况,例如多个元素等,则可能不再具有优势。
同样,如果您有一个非常具体的用例,这可能很有用,如果没有,请坚持使用 jQuery。
更新:事实证明,制作插件仍然更快:jsPerf benchmark
(function($) {
$.fn.findOne = function(selector) {
try {
var element, i = 0, l = this.length;
while(i < l && (element = this[i].querySelector(selector)) === null) {
i++;
}
return $(element);
}
catch(e) {
return this.find(selector).first();
}
};
}(jQuery));
这是如何工作的:
该插件迭代选定的 DOM 元素并调用querySelector
它们中的每一个。一旦找到一个元素,循环将终止并返回找到的元素。发生异常的原因有两个:
querySelector
在这两种情况下,插件都会回退到使用普通的 jQuery 方法。
尽管看起来很疯狂,但在我见过的每一个性能测试中,.first()
性能都比:first
.
正如大多数人所建议的那样,似乎 using$(element).find(".x:first")
应该具有更好的性能。但是,实际上.first
更快。我还没有研究 jquery 的内部来找出原因。
http://jsperf.com/jquery-select-first
显然使用[0]
然后重新包装在 jquery 对象中是最快的:
$($(element).find(".x")[0])
编辑:有关原因的解释,请参见 mrchief 的回答。显然,他们现在已将其添加到文档中。
这应该更好
$(element).find('.x:first');
使用:first
选择器:
$(element).find('.x:first')
最好写:
$('a:first');
你写的是“在'元素'中,找到'.x'并返回第一个”。可以这样表达
$('.x:first', element);
使用first-child伪类怎么样?像
$(element).find('.x:first-child')
但是,如果您的结构像
<div>
<p></p>
</div>
<div>
<p></p>
</div>
所以实际上这不是您要寻找的(如果您的意思是通用解决方案)。其他人:首先,这似乎是正确的方法
您的瓶颈实际上是.find()
,它搜索所有后代,而不仅仅是直系孩子。
最重要的是,您正在搜索一个类.x
(使用 jQuery 自定义搜索)而不是 ID 或标记名(使用本机 DOM 方法)。
我会使用 Mrchief 的答案,然后,如果可能的话,修复这两个瓶颈以加快您的选择器。
根据 jQuery 文档,这种方式很好,或者至少比使用:first
选择器更好。
您可以尝试作为替代方案.filter(":first")
,或者使用数组访问器获取第一个.find()
元素[0]
。
此外,.find()
您可以将其更改为:
$('.x', element)
将搜索范围缩小到.x
元素内的元素,而不是搜索整个文档。
您可以使用后代选择器组合$(element)
and调用;.find()
我不确定性能比较:
$("#element .x").first().hide();