这个问题在这里已经有了答案:
Why does querySelector('div span') match even though querySelector('div') does not?
(1 个回答)
去年关闭。
以下两种选择节点的方法不应该产生相同的结果吗?
let tmp = fruits.querySelector("ul:first-of-type li:first-of-type");
tmp = tmp.querySelector("span")
对比let tmp = fruits.querySelector("ul:first-of-type li:first-of-type span");
(查看实际操作here)我已经在 Firefox 和 chrome 中对此进行了测试。两种情况的结果不同。有人可以解释为什么吗?
堆栈片段中的示例:
let fruits = document.querySelector("[data-segment='fruits']");
console.log(fruits);
let tmp = fruits.querySelector("ul:first-of-type li:first-of-type")
tmp = tmp.querySelector("span")
console.log("Works:")
console.log(tmp)
console.log("Does not work:")
console.log(fruits.querySelector("ul:first-of-type li:first-of-type span"))
<main id="app" data-v-app="">
<section>
<h2>Tree</h2>
<ul role="tree">
<li role="treeitem" data-segment="fruits" aria-level="1" aria-setsize="3" aria-posinset="1" aria-expanded="true"><span tabindex="0">Fruits</span>
<ul role="group">
<li role="none" data-segment="oranges" aria-level="2" aria-setsize="5" aria-posinset="1"><span tabindex="-1">Oranges</span>
<!--v-if-->
</li>
<li role="none" data-segment="pineapple" aria-level="2" aria-setsize="5" aria-posinset="2"><span tabindex="-1">Pineapple</span>
<!--v-if-->
</li>
<li role="treeitem" data-segment="apples" aria-level="2" aria-setsize="5" aria-posinset="3" aria-expanded="false"><span tabindex="-1">Apples</span>
<ul role="group">
<li role="none" data-segment="macintosh" aria-level="3" aria-setsize="3" aria-posinset="1"><span tabindex="-1">Macintosh</span>
<!--v-if-->
</li>
<li role="none" data-segment="granny_smith" aria-level="3" aria-setsize="3" aria-posinset="2"><span tabindex="-1">Granny Smith</span>
<!--v-if-->
</li>
<li role="none" data-segment="fuji" aria-level="3" aria-setsize="3" aria-posinset="3"><span tabindex="-1">Fuji</span>
<!--v-if-->
</li>
</ul>
</li>
<li role="none" data-segment="bananas" aria-level="2" aria-setsize="5" aria-posinset="4"><span tabindex="-1">Bananas</span>
<!--v-if-->
</li>
<li role="none" data-segment="pears" aria-level="2" aria-setsize="5" aria-posinset="5"><span tabindex="-1">Pears</span>
<!--v-if-->
</li>
</ul>
</li>
<li role="none" data-segment="vegetables" aria-level="1" aria-setsize="3" aria-posinset="2"><span tabindex="-1">Vegetables</span>
<!--v-if-->
</li>
<li role="none" data-segment="grains" aria-level="1" aria-setsize="3" aria-posinset="3"><span tabindex="-1">Grains</span>
<!--v-if-->
</li>
</ul>
</section>
</main>
最佳答案
documentation解释它:
element = baseElement.querySelector(selectors);
Return value
The first descendant element of
baseElement
which matches the specified group ofselectors
. The entire hierarchy of elements is considered when matching, including those outside the set of elements includingbaseElement
and its descendants; in other words,selectors
is first applied to the whole document, not thebaseElement
, to generate an initial list of potential elements. The resulting elements are then examined to see if they are descendants ofbaseElement
. The first match of those remaining elements is returned by thequerySelector
method.
(强调我的。)
让我们考虑一个简化的例子:
console.log(document.getElementById("a").querySelector("ul li span"));
<ul>
<li id="a"><span>A</span>
<ul>
<li><span>B</span></li>
</ul>
</li>
</ul>
在这里,
baseElement
是 document.getElementById("a")
; selectors
是 "ul li span"
.document.querySelector("ul li span")
确实包括<span>
s,它们都在baseElement
里面. <span>A</span>
恰好是这个集合中的第一个。有一个相当新的伪类,叫做
:scope
这可能会有所帮助:console.log(document.getElementById("a").querySelector(":scope ul li span"));
<ul>
<li id="a"><span>A</span>
<ul>
<li><span>B</span></li>
</ul>
</li>
</ul>
关于javascript - 多个后代选择器,错误或误解?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67043990/