使用 querySelectorAll 时,有没有办法在不使用 ID 的情况下引用上下文节点的直接子节点?
Posted
技术标签:
【中文标题】使用 querySelectorAll 时,有没有办法在不使用 ID 的情况下引用上下文节点的直接子节点?【英文标题】:When using querySelectorAll, is there a way to reference the immediate children of the context node, without using IDs? 【发布时间】:2012-07-11 13:08:25 【问题描述】:假设我有一个类似的 html 结构
<div id="a">
<div id="b">
<div id="c"></div>
</div>
</div>
要使用 querySelectorAll 对“a”的孩子进行查询,我可以这样做
//Get "b", but not "c"
document.querySelectorAll('#a > div')
我的问题是:是否可以在没有 ID 的情况下执行此操作,直接引用节点?我试过做
var a_div = document.getElementById('a')
a_div.querySelectorAll('> div') //<-- error here
但我收到一条错误消息,告诉我我使用的选择器无效。
如果有人想知道,我的实际用例会更复杂一些,比如 '> .foo .bar .baz' 所以我宁愿避免手动 DOM 遍历。目前我正在向根 div 添加一个临时 id,但这似乎是一个丑陋的黑客......
【问题讨论】:
另见:***.com/questions/3680876/… 【参考方案1】:document.querySelector('#a').querySelectorAll(':scope > div')
我不确定浏览器是否支持,但我在 chrome 和 chrome 移动打包应用程序上使用它并且效果很好。
【讨论】:
MDN on:scope
in querySelector
:Chrome,Firefox 32+,Safari 7,不是 Opera,不是 IE。【参考方案2】:
不,没有办法 (yet) 在不使用对该元素的引用的情况下引用某个元素的所有子元素。因为>
是child combinator,它表示父元素和子元素之间的关系,所以simple selector(父元素)是必需的(在您的示例中缺少)。
在评论中,BoltClock saidSelectors API Level 2 specification 定义了一个方法findAll
name 可能更改“它接受作为参数的可能被称为相对选择器(可以以组合子而不是复合选择器开头的选择器)”。
实现后,可以如下使用:
a_div.findAll('> div');
【讨论】:
这通常的解决方法是什么?向根元素添加(临时)id 是唯一的方法吗? @missingno 是的。另一种方法是循环遍历所有.childNodes
,使用childNodes[i].nodeName.toUpperCase()=='div'
测试child是否为div。
从技术上讲,“因为>
是一个组合器”,你不能用querySelectorAll()
做到这一点。在不久的将来,您将能够使用findAll()
执行此操作,它接受可能被称为相对选择器(可以以组合器而不是复合选择器开头的选择器)作为参数。请参阅Selectors API level 2 规范。
@BoltClock 感谢您提供的信息,我已经修改了答案。【参考方案3】:
我想我一定是误解了你的问题,但这就是我的解释......
var a = document.getElementById('a')
var results = a.querySelectorAll('div');
results 现在将包含您所有的子 div。
【讨论】:
results
不仅会保存子 div,还会保存 所有 个后代 div。
我想从结果中排除“c”div。 '#a > div' 选择器只返回“b” div。以上是关于使用 querySelectorAll 时,有没有办法在不使用 ID 的情况下引用上下文节点的直接子节点?的主要内容,如果未能解决你的问题,请参考以下文章
querySelectorAll()在与jsdom一起使用时返回空节点列表
Puppeteer 获取 querySelectorAll 的 innerText
js动态查询指定class名的所有元素,querySelectorAll()和querySelectorAll()的区别