引言:为什么这个主题如此重要?
\n如果你曾经写过 jQuery 代码,需要获取或设置 HTML 元素的特性值,你很可能遇到过两个方法:.prop() 和 .attr()。乍一看,它们做的是同一件事。但实际上,它们之间的区别是数百个 bug 和 Stack Overflow 上数千个问题的根源。
在这篇逐步教程中,我们将一劳永逸地弄清楚 jQuery 中 .prop() 和 .attr() 的区别,何时使用哪一个,以及如何避免陷阱。我们将编写实际代码,观察浏览器的真实行为,并记住一个简单的规则。
这篇文章不是枯燥的文档。它是你在 jQuery 中最令人困惑的主题之一的个人指南。
\n\n简要说明:特性 vs 属性
\n在深入代码之前,我们先了解一些理论。在 DOM(文档对象模型)中有两个概念:
\n- \n
- 特性(attribute) — 写在 HTML 代码中的内容。例如,
<input type="checkbox" checked="checked">。特性始终是字符串。 \n - 属性(property) — 浏览器读取 HTML 后,存储在 DOM 元素对象中的内容。属性可以是任何数据类型:字符串、布尔值、数字、对象。 \n
.attr() 方法处理特性。.prop() 方法处理属性。听起来很简单?是的,但有一些细微差别。
主要陷阱:布尔特性
\n最让新手头疼的常见例子是复选框、单选按钮和其他具有布尔特性(checked、disabled、selected、readonly)的元素。
假设你有这样的 HTML:
\n<input type="checkbox" id="myCheckbox" checked>\n你想检查复选框是否被选中。很自然地会这样写:
\nconsole.log( $('#myCheckbox').attr('checked') ); // "checked" (字符串!)\nconsole.log( $('#myCheckbox').prop('checked') ); // true (布尔值!)\n这就是区别!如果 HTML 中存在该特性,.attr() 返回字符串 "checked",如果不存在则返回 undefined。而 .prop() 根据 DOM 中元素的当前状态返回 true 或 false。
现在最有趣的是:如果用户取消选中复选框会发生什么?
\n// 用户取消选中后:\nconsole.log( $('#myCheckbox').attr('checked') ); // "checked"!(HTML 未改变)\nconsole.log( $('#myCheckbox').prop('checked') ); // false (状态已改变)\n这就是为什么使用 .attr() 检查复选框状态是错误的。 HTML 中的 checked 特性保持不变,而 DOM 中的 checked 属性会动态变化。.prop() 始终给出最新的答案。
经验法则
\n有一个简单的规则可以帮助你避免错误:
\n- \n
- 当你需要获取或修改元素的动态状态时(例如,
checked、disabled、selected、input 的value),使用.prop()。 \n - 当你需要读取或修改 HTML 中的静态特性时(例如,
href、src、data-*、id、class),使用.attr()。 \n
记住:.prop() 用于在运行过程中会变化的属性。.attr() 用于在标记中定义的特性。
逐步示例:处理 disabled
\n让我们再分析一个经典案例——带有 disabled 特性的按钮。
<button id="myButton" disabled>点击我</butto