【发布时间】:2019-01-22 23:39:05
【问题描述】:
为什么这个选择器起作用:
document.querySelectorAll('table tr:not(:nth-child(even))');
虽然此选择器不会(抛出 TypeError):
document.querySelectorAll('table tr:not(tr:nth-child(even))');
var query = (selector) => {
return document.querySelectorAll(selector);
};
try {
var select_a = 'table tr:not(:nth-child(even))';
var select_b = 'table tr:not(tr:nth-child(even))';
query(select_a).forEach((node) => {
node.style.color = 'red';
});
query(select_b).forEach((node) => {
node.style.color = 'blue';
});
} catch (e) {
query('div:nth-child(3)')[0].textContent = e.toString();
}
var query = (selector) => {
return document.querySelectorAll(selector);
};
try {
var select_a = 'table tr:not(:nth-child(even))';
var select_b = 'table tr:not(tr:nth-child(even))';
query(select_a).forEach((node) => {
node.style.color = 'red';
});
query(select_b).forEach((node) => {
node.style.color = 'blue';
});
} catch (e) {
query('div:nth-child(3)')[0].textContent = e.toString();
}
<table>
<tr>
<td>row 1 first-name</td>
<td>row 1 last-name</td>
<td>row-1 email</td>
</tr>
<tr>
<td>row 2 first-name</td>
<td>row 2 last-name</td>
<td>row-2 email</td>
</tr>
<tr>
<td>row 3 first-name</td>
<td>row 3 last-name</td>
<td>row-3 email</td>
</tr>
<tr>
<td>row 4 first-name</td>
<td>row 4 last-name</td>
<td>row-4 email</td>
</tr>
<tr>
<td>row 5 first-name</td>
<td>row 5 last-name</td>
<td>row-5 email</td>
</tr>
</table>
<div>Why does select_a work but not select_b?</div>
<div></div>
【问题讨论】:
-
为什么它应该起作用? :-)
-
因为
:not()只接受一个“简单选择器”,而tr:nth-child(even)不是。 drafts.csswg.org/selectors-3/#simple-selectors-dfn “简单的选择器可以是类型选择器、通用选择器、属性选择器、类选择器、ID 选择器或伪类。” -
我认为这是因为 CSS Selector Level 3 语法将
:not()子句中的选择器限制为simple-selector,可以是 either “类型”选择器(如tr)或一个“子类”选择器。根据该规则(这让我有点困惑),同时拥有tr和:next-child()是错误的,因为两者都是。 -
我认为这是一个有趣的问题,因为从错误消息中看不出问题是什么。此外,我认为 Selector Level 4 语法放宽了规则并允许“复合”选择器。
-
@Pointy 是的,没错,选择器级别 4 取消了限制,支持 选择器列表。 (“简单/复合/复杂选择器列表是简单、复合或复杂选择器的逗号分隔列表。当类型不重要或在周围散文中指定时,这也称为选择器列表” )