调用与事件关联的匿名函数

Invoking anonymous function associated with an event

以下代码不起作用:

<input id="inp" type="text"
onfocus="(function(){document.getElementById('inp').style.background="yellow";})">

但是这段代码可以正常工作:

<input id="inp" type="text"
onfocus="(function(e){document.getElementById('inp').style.background ='yellow';}(this)">

为什么第一个代码不起作用?

第一个不起作用,因为它被括在括号中,因此它是一个函数 "expression",而不是函数 "declaration"。表达式应该是 "evaluated",因此当您的元素获得焦点时,表达式会被计算,但不会被调用。此外,double-quotes 嵌套在 double-quotes 中,这会导致语法错误 ("yellow")。这些需要更改为单引号。

第二个有效,因为 "expression" 立即被第二组括号 (this) 调用。

但是,应避免使用这两种语法。不要使用内联 HTML 事件属性来连接事件处理回调函数,因为它们:

  • 创建难以阅读并导致重复的意大利面条式代码 代码
  • 创建改变 this 绑定的全局包装函数 函数
  • 不遵循 W3C DOM Event 标准

相反,在 JavaScript:

中编写事件处理程序

// Get a reference to the DOM element
var input = document.getElementById("inp");

// Wire up an event handler
input.addEventListener("focus", function(e){
  input.style.background ='yellow';
});
<input id="inp" type="text">

问题是您没有调用第一个函数。本质上,您是在声明一个函数但从未调用它。

示例:

(function() {
  console.log('I would do something but no one calls me');
}); // <-- Notice the lack of ()

(function() {
  console.log('I do something because I am called');
})(); // <-- Notice the () on the end

由于在函数中使用了双引号 ("),您在第一个示例中也遇到了麻烦。由于 onfocus 属性值必须用双引号引起来,因此您会过早地关闭该属性。

<input onfocus="console.log("I won't work since I'm closing the quotes");" />

第一个没有工作,因为: IIFE 语法类似于 (function(){}()) 并且黄色周围的 " 预关闭焦点。

更正后的语法是这样的。

<input id="inp" type="text" onfocus="(function(){document.getElementById('inp').style.background='yellow';})()">

斯科特已经很好地回答了你的问题。我只想添加到您的第二个示例中:

<input id="inp" type="text"
onfocus="(function(e){document.getElementById('inp').style.background ='yellow';}(this)">

应该是:

<input id="inp" type="text" onfocus="(function(that) {that.style.background='yellow'})(this);">

不需要使用document.getElemetnsById方法,因为您已经将"this"元素传递给自调用函数。

但是正如 Scott 已经提到的,您应该使用 DOM 事件标准,通过 HTLM 属性处理事件是老派。