jQuery元素无法选择parent()

时间:2010-09-28 11:35:25

标签: jquery jquery-selectors

似乎使用包含:contains(sub)sub的{​​{1}}的{​​{1}}选择的元素无法访问其父母。

以下示例应说明我在Safari和Camino(Mac上的Gecko)中遇到的问题:

<

输出是:

>

任何想法为什么第四个是<html> <head> <script type="text/javascript" src="http://code.jquery.com/jquery-1.4.2.min.js"></script> </head> <body> <p><strong>bar</strong></p> <p><strong>&lt;foo&gt;</strong></p> <script type="text/javascript"> alert($('body strong:contains("bar")').length); alert($('body strong:contains("bar")').parent().length); alert($('body strong:contains("<foo>")').length); alert($('body strong:contains("<foo>")').parent().length); // this fails alert($('body strong').length); alert($('body strong').parent().length); // two p elements alert($('body strong').parent().parent().length); // one body </script> </body> </html> 而不是1 1 1 0 2 2 1 ,或者我如何绕过这个?

This page提到在选择器中转义名称,但这也不起作用(另外,我不确定它是否适用)。

4 个答案:

答案 0 :(得分:3)

免责声明:这不是使用Tatu's answer的解决方案/解决方法,这只是对问题的描述以及导致奇怪行为的奇怪行为。

问题的根源在于the regex that jQuery uses to identify an HTML Fragment

/^[^<]*(<[\w\W]+>)[^>]*$|^#([\w-]+)$/

哪个 匹配您的选择器:

body strong:contains("<foo>")

You can try it out

alert(/^[^<]*(<[\w\W]+>)[^>]*$|^#([\w-]+)$/.test('body strong:contains("<foo>")​​​'));​

所以它认为它是一个HTML片段......总的来说这些是等价的:

$('body strong:contains("<foo>")');
$('<foo>');

看到第二个更清楚的说明它是一个文件片段......没有父母。它位于匹配数组中的第二个位置,您只能看到<foo>again try it out

alert(/^[^<]*(<[\w\W]+>)[^>]*$|^#([\w-]+)$/.exec('body strong:contains("<foo>")')[1]);​

这导致您最终以this code path in jQuery's $()结束,构建片段。

所以简而言之,我认为这是一个jQuery错误。

答案 1 :(得分:2)

不知道导致contains()失败的原因,但您可以使用.filter()替代:

alert($('body strong').filter(function() {
    return /<foo>/.test( $(this).text() );
}).parent().length);

按预期返回1。这很难看,但很有效。

答案 2 :(得分:1)

<foo>被评估为标记,因此它的父项除了空标记外都不包含任何内容,因此为0。

编辑:要完全理解这一点:$('body strong:contains("foo")').text().length其中的$('body strong:contains("<foo>")').length来自&gt;的1表示强者中有一个文本节点,因此长度为1,文本长度为1是5。

有趣的是跟踪>无法正确选择&gt;,而>似乎有效,因为<foo用作<foo>一个css选择器。因此,{{1}}有效,但不是{{1}}

这是一个小提琴页面:http://jsfiddle.net/2XEUg/1/

答案 3 :(得分:1)

这显然是jQuery的选择器解析的问题。如果选择器中存在<>,则jQuery将该参数标识为文档片段而不是选择器。结果是一个 tagName 为“FOO”的元素,相同的选择器会出现同样的问题:

$('body <foo>')
$('body strong:not(<foo>')

你的情况唯一的区别是你使用了一个有效的选择器,jQuery正确地识别它。

我在基于选择器的解决方法上做了几次尝试,但Tatu Ulmanen's是唯一有效的方法。

编辑:似乎你也可以使用 .find()

$(document.body).find('strong:contains("<foo>")')