【问题标题】:Implications when an input has the same name as another input's ID输入与另一个输入的 ID 同名时的含义
【发布时间】:2015-05-25 18:33:13
【问题描述】:

下面的脚本让我吃惊。它产生以下结果:

互联网探索

aaa: 未定义 bbb: 未定义 ccc: value3 ddd: value4 eee: value5

FireFox 和 Chrome

aaa: bbb: ccc: value3 ddd: value4 eee: value5

为什么当一个输入与另一个输入的名称具有相同的 ID(或相反)时,输入没有值?

function testResults(form) {
  alert([
    "aaa: " + form.aaa.value,
    "bbb: " + form.bbb.value,
    "ccc: " + form.ccc.value,
    "ddd: " + form.ddd.value,
    "eee: " + form.eee.value
  ].join(',    '));
}
<form>
  <input type="text" name="aaa" id="bbb" value="value1" />
  <input type="text" name="bbb" id="aaa" value="value2" />
  <input type="text" name="ccc" id="ccc" value="value3" />
  <input type="text" name="ddd" value="value4" />
  <input type="text" id="eee" value="value5" />
  <input type="submit" onclick="testResults(this.form)"/>
</form>

【问题讨论】:

  • 错误的闭包,就像在 JavaScript 中经常发生的那样......
  • @kuroineko 是的,我知道,但问题与一个元素与另一个元素 ID 同名时的冲突有关。

标签: javascript html forms dom


【解决方案1】:

DOM 很奇怪……

querySelector 会让你通过姓名或身份证获得。这就像 jQuery 选择器。

form.querySelector('[name=aaa]').value
form.querySelector('#aaa').value

顺便说一句,它没有值的原因是form.aaa 尝试通过idname 匹配并返回多个元素。试图获取返回 "" 的值,或者显然是 IE 中的 undefined

【讨论】:

  • 谢谢。我对正在发生的事情更感兴趣,但感谢querySelector 上的提示,并将对其进行调查。给定我的原始代码,console.log(form.aaa) 显示 RadioNodeList 元素?
  • 最初没有注意到您对所发生情况的解释。谢谢
【解决方案2】:

当您通过名称或 ID 访问表单元素时使用的算法在 spec 中定义:

form 元素为命名属性检索编制索引时,用户 代理必须运行以下步骤:

  1. candidates 成为一个活动的 RadioNodeList 对象,其中包含表单所有者为 form 元素的所有列出的元素 id 属性或 name 属性等于 name,但有例外 的input 元素的type 属性处于图像按钮状态, 按树顺序排列。

  2. 如果 candidates 为空,则让 candidates 为一个活动的 RadioNodeList 对象,其中包含所有 img 元素的后代元素 form 元素并且具有 id 属性或 name 属性 等于 name,按树顺序排列。

  3. 如果 candidates 为空,nameform 元素的过去名称映射中的条目之一的名称:返回与 名字在那张地图上。

  4. 如果 candidates 包含多个节点,则返回 candidates 并中止这些步骤。

  5. 否则,candidates 只包含一个节点。在 form 元素的过去名称映射中添加从 namecandidates 中的节点的映射, 用相同的名称替换上一个条目(如果有)。

  6. 返回候选中的节点

具体来说,问题是form.aaa有两个候选,所以它返回一个RadioNodeList集合(步骤4):

form.aaa; // RadioNodeList [ <input#bbb>, <input#aaa> ]
form.aaa[0]; // <input#bbb>
form.aaa[1]; // <input#aaa>

对于form.eee,只有一个候选者,因此将其返回(第 6 步):

$0.eee; // <input#eee>

【讨论】:

  • 另外,form.aaa.value 应该返回空字符串,而不是像 IE 那样未定义。这是定义here
  • 你的意思是 IE 做的不对?不可思议!所以,我从规范和 DOM 的角度来看,ID 或名称没有优先级,它们都只是添加到一个集合中。是否有任何最佳做法可以使用其中一种方法?
  • @user1032531 如果要发送表单,最好使用名称。如果您想在 JS 中更快地获取元素(使用 getElementById),请使用 ID(不过,您可以使用带有名称的 getElementsByName)。一种常见的方法是同时使用 ID 和名称,但每个元素使用相同的字符串。
  • 谢谢 Oriol。这很有帮助。通常,我对名称和 ID 使用相同的字符串,但很高兴知道其中的含义!另外,感谢您使用酷炫的运行代码片段编辑我的原始帖子。我会在未来学习如何做到这一点。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2022-12-22
  • 2023-04-03
  • 1970-01-01
  • 2011-11-20
  • 2018-04-05
  • 1970-01-01
相关资源
最近更新 更多