element.matches()是原生dom方法,通过css选择器精准返回布尔值判断元素类型,无需冗长if判断;createfilter函数封装该能力,支持多类型、伪类、属性等灵活过滤,兼容ie9+且零基础易上手。

用 matches 编写通用元素类型过滤器,核心不是写一堆 if 判断,而是利用 CSS 选择器的表达力 + Element.matches() 的布尔返回值做精准筛选。零基础也能上手,关键在理解“匹配即有效”这个逻辑。
什么是 matches?它为什么适合做类型过滤?
Element.matches(selector) 是原生 DOM 方法,接收一个 CSS 选择器字符串,返回 true 或 false——表示该元素是否符合这个选择器规则。它不依赖框架,兼容性好(IE9+),且能复用你已有的 CSS 选择器知识。
比如:document.querySelector('button').matches('button') → truedocument.querySelector('input').matches('button, select, textarea') → false
这比手动判断 el.tagName === 'BUTTON' 或写一长串 instanceof 更简洁、更可扩展。
最简可用版:单个类型过滤器
从最基础开始,封装一个只判断是否为按钮的函数:
function isButton(el) {
return el instanceof Element && el.matches('button');
}
说明:
• 先用 el instanceof Element 做安全校验,避免传入 null、文本节点等非元素对象报错;
• 再用 matches('button') 判断是否为原生 <button></button>;
• 同理,el.matches('input[type="text"]') 可精确到输入框类型。
通用版:支持多类型、伪类、属性的灵活过滤器
真正实用的过滤器得能“一句话定义一类元素”。下面这个函数接受任意合法 CSS 选择器,返回判断函数:
function createFilter(selector) {
if (typeof selector !== 'string' || !selector.trim()) {
throw new Error('selector must be a non-empty string');
}
return function(el) {
return el instanceof Element && el.matches(selector);
};
}
用法示例:const isInteractive = createFilter('button, [onclick], input:not([type="hidden"])');const isHeader = createFilter('h1, h2, h3, h4, h5, h6');const hasDataAttr = createFilter('[data-role="menu-item"]');
优势:
• 一行 selector 定义规则,无需修改函数体;
• 支持组合选择器、伪类(如 :disabled)、属性选择器、否定伪类(:not());
• 返回的函数可直接用于 Array.prototype.filter() 或事件委托判断。
实战小技巧:结合 NodeList 和事件委托
过滤器常配合批量操作使用。例如,只对页面中所有可点击元素绑定事件:
const isClickable = createFilter('a[href], button, [onclick], input[type="submit"]');
document.querySelectorAll('*').forEach(el => {
if (isClickable(el)) {
el.addEventListener('click', handleClick);
}
});
或在事件委托中快速识别目标:
document.body.addEventListener('click', e => {
if (isClickable(e.target)) {
console.log('用户点了一个可交互元素:', e.target);
}
});
注意:
• 不要用 e.currentTarget 替代 e.target,因为过滤的是实际被点击的元素;
• 若需排除子元素(如按钮内的图标),可在 selector 中加 :not(*) 或用 e.target.closest(selector) 替代。
不复杂但容易忽略:selector 字符串必须语法正确,否则 matches() 会静默返回 false。调试时可先在控制台用 $0.matches('your-selector') 手动验证。










