Select css 两个元素之间的兄弟姐妹
Select css siblings between two elements
我正在查看的 html 看起来像这样:
document.querySelectorAll('h4#unique_id ~ h5 ~p +p +h5').forEach(title => console.log(title))
<body>
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- selection should start here -->
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- and end here -->
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</body>
我想获取所有 h5
元素,如果可能,还想获取 p
元素。
到目前为止我有 document.querySelectorAll('h4#unique_id ~ h5 ~p +p +h5')
,但是它错过了我想要的第一个 h5
并且抓住了我不想要的最后一个。当我找到另一个 h4
.
时,我无法弄清楚兄弟选择器或如何使用 :not
或类似的方法来停止
这道题 relies on jquery which I don't have access to, and 需要知道元素的数量和位置,而我不知道。
仅使用 css 个选择器是否可行?
好的,您可以混合使用兄弟选择器而不是:
选择器是:
#unique_id~p:not(#unique_id~h4~p) /* any p following the unique id but not a p following another h4 after the unique id */
然后你为你的 h5s 重复这个选择器,结果是:
document.querySelectorAll('#unique_id~p:not(#unique_id~h4~p),#unique_id~h5:not(#unique_id~h4~h5)').forEach(title => title.style.color = 'red');
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
根据您的编辑 - 不要在第一个 h5 之前包含 p(选择器根据 Alohci 的评论略作修改):
document.querySelectorAll('#unique_id~:is(h5, h5~p):not(#unique_id ~ h4 ~ *)').forEach(title => title.style.color = 'red');
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
有趣的问题。如果我正确理解你的问题,你想记录所有不包含 some text I don't want
和 h5
元素的元素。
如果您有父元素,您可以使用 >
到 select 或与父元素结合使用 select 它的所有子元素 *
-select或.
您可以对一个语句应用多个 :not()
-selector。下面我只是 selected 所有 p
和 h4
元素前面有 h4#randome_id_234353
元素,像这样:
document.querySelectorAll('.container > *:not(h4#randome_id_234353 ~ p):not(h4#randome_id_234353 ~ h5):not(h4)').forEach(title => console.log(title))
<body>
<div class="container">
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</div>
</body>
如果您没有容器,您可以使用相同的逻辑来 log
所有 不 先于 h4#randome_id_234353
.
document.querySelectorAll('h4#unique_id ~ *:not(h4#randome_id_234353 ~ *):not(h4#randome_id_234353)').forEach(title => console.log(title))
<body>
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</body>
只有少数数组方法与 array-like 对象一起工作,因此我经常发现将 NodeList
(这是一个 可迭代对象,array-like object 但是,至关重要的是, 不是 一个 array
) 到一个 array
,这样我就可以做 更多用它做事
在这种情况下,通过将 NodeList
变成 array
我可以使用 javascript 方法 .filter()
这正是我需要从合集结束。
将 NodeList
变成 array
:
我怎样才能把这个static NodeList
:
let myClassElements = document.querySelectorAll('.myclass');
变成 array
?
通过将 spread syntax
(...
) 与 array literal
([]
) 组合:
let myClassElements = [... document.querySelectorAll('.myclass')];
在此基础上,我可以创建一个 array
我需要的所有元素(加上一些不必要的元素):
[...document.querySelectorAll('h4#unique_id ~ h5, h4#unique_id ~ p')]
还有另一个所有不必要元素的数组:
[...document.querySelectorAll('h4:not(#unique_id) ~ h5, h4:not(#unique_id) ~ p')]
然后我可以.filter()
从前者中分离出后者:
const rawListOfElements = [...document.querySelectorAll('h4#unique_id ~ h5, h4#unique_id ~ p')];
const elementsToRemove = [...document.querySelectorAll('h4:not(#unique_id) ~ h5, h4:not(#unique_id) ~ p')];
const mySelectedElements = rawListOfElements.filter((element) => elementsToRemove.includes(element) === false).forEach(title => console.log(title));
工作示例:
const rawListOfElements = [...document.querySelectorAll('h4#unique_id ~ h5, h4#unique_id ~ p')];
const elementsToRemove = [...document.querySelectorAll('h4:not(#unique_id) ~ h5, h4:not(#unique_id) ~ p')];
const mySelectedElements = rawListOfElements.filter((element) => elementsToRemove.includes(element) === false).forEach(title => console.log(title));
<body>
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- selection should start here -->
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- and end here -->
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</body>
我正在查看的 html 看起来像这样:
document.querySelectorAll('h4#unique_id ~ h5 ~p +p +h5').forEach(title => console.log(title))
<body>
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- selection should start here -->
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- and end here -->
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</body>
我想获取所有 h5
元素,如果可能,还想获取 p
元素。
到目前为止我有 document.querySelectorAll('h4#unique_id ~ h5 ~p +p +h5')
,但是它错过了我想要的第一个 h5
并且抓住了我不想要的最后一个。当我找到另一个 h4
.
:not
或类似的方法来停止
这道题
仅使用 css 个选择器是否可行?
好的,您可以混合使用兄弟选择器而不是:
选择器是:
#unique_id~p:not(#unique_id~h4~p) /* any p following the unique id but not a p following another h4 after the unique id */
然后你为你的 h5s 重复这个选择器,结果是:
document.querySelectorAll('#unique_id~p:not(#unique_id~h4~p),#unique_id~h5:not(#unique_id~h4~h5)').forEach(title => title.style.color = 'red');
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
根据您的编辑 - 不要在第一个 h5 之前包含 p(选择器根据 Alohci 的评论略作修改):
document.querySelectorAll('#unique_id~:is(h5, h5~p):not(#unique_id ~ h4 ~ *)').forEach(title => title.style.color = 'red');
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
有趣的问题。如果我正确理解你的问题,你想记录所有不包含 some text I don't want
和 h5
元素的元素。
如果您有父元素,您可以使用 >
到 select 或与父元素结合使用 select 它的所有子元素 *
-select或.
您可以对一个语句应用多个 :not()
-selector。下面我只是 selected 所有 p
和 h4
元素前面有 h4#randome_id_234353
元素,像这样:
document.querySelectorAll('.container > *:not(h4#randome_id_234353 ~ p):not(h4#randome_id_234353 ~ h5):not(h4)').forEach(title => console.log(title))
<body>
<div class="container">
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</div>
</body>
如果您没有容器,您可以使用相同的逻辑来 log
所有 不 先于 h4#randome_id_234353
.
document.querySelectorAll('h4#unique_id ~ *:not(h4#randome_id_234353 ~ *):not(h4#randome_id_234353)').forEach(title => console.log(title))
<body>
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</body>
只有少数数组方法与 array-like 对象一起工作,因此我经常发现将 NodeList
(这是一个 可迭代对象,array-like object 但是,至关重要的是, 不是 一个 array
) 到一个 array
,这样我就可以做 更多用它做事
在这种情况下,通过将 NodeList
变成 array
我可以使用 javascript 方法 .filter()
这正是我需要从合集结束。
将 NodeList
变成 array
:
我怎样才能把这个static NodeList
:
let myClassElements = document.querySelectorAll('.myclass');
变成 array
?
通过将 spread syntax
(...
) 与 array literal
([]
) 组合:
let myClassElements = [... document.querySelectorAll('.myclass')];
在此基础上,我可以创建一个 array
我需要的所有元素(加上一些不必要的元素):
[...document.querySelectorAll('h4#unique_id ~ h5, h4#unique_id ~ p')]
还有另一个所有不必要元素的数组:
[...document.querySelectorAll('h4:not(#unique_id) ~ h5, h4:not(#unique_id) ~ p')]
然后我可以.filter()
从前者中分离出后者:
const rawListOfElements = [...document.querySelectorAll('h4#unique_id ~ h5, h4#unique_id ~ p')];
const elementsToRemove = [...document.querySelectorAll('h4:not(#unique_id) ~ h5, h4:not(#unique_id) ~ p')];
const mySelectedElements = rawListOfElements.filter((element) => elementsToRemove.includes(element) === false).forEach(title => console.log(title));
工作示例:
const rawListOfElements = [...document.querySelectorAll('h4#unique_id ~ h5, h4#unique_id ~ p')];
const elementsToRemove = [...document.querySelectorAll('h4:not(#unique_id) ~ h5, h4:not(#unique_id) ~ p')];
const mySelectedElements = rawListOfElements.filter((element) => elementsToRemove.includes(element) === false).forEach(title => console.log(title));
<body>
<h4 id="unique_id"> foo bing bar </h4>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- selection should start here -->
<h5>title text 1</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 2</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<h5>title text 3</h5>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<p>some text</p>
<!-- and end here -->
<h4 id="randome_id_234353">title text</h4>
<p>some text I don't want</p>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
<h5>title text I don't want</h5>
<p>some text I don't want</p>
</body>