【发布时间】:2021-02-28 08:08:03
【问题描述】:
在方法中使用事件时传递事件是更好的做法还是隐含它:
选项1:
<input @keyup.enter="chooseMe($event)"/>
选项2:
<input @keyup.enter="chooseMe"/>
chooseMe(evt) {
console.log(evt)
}
【问题讨论】:
在方法中使用事件时传递事件是更好的做法还是隐含它:
选项1:
<input @keyup.enter="chooseMe($event)"/>
选项2:
<input @keyup.enter="chooseMe"/>
chooseMe(evt) {
console.log(evt)
}
【问题讨论】:
我假设您询问的是性能而不是开发人员的意见。 (例如,可以说显式传递$event 参数会使组件的意图更清晰,但这是一种观点。它也更冗长。)
编译器会围绕任何使用函数调用的处理程序(即属性值中的())生成一个包装函数,以允许将$event 作为参数传递。在您的示例中使用 .enter 之类的修饰符时,即使没有调用它也会这样做。
要测试任何性能影响,您可以使用JSBench.me 之类的测试套件。下面是这样一个test 在 Windows/Chrome 上运行的结果。
<div @click="test"></div>
结果::每秒 ~502,653 次操作。
<div @click="test($event)"></div>
结果::每秒 ~536,685 次操作。
在这种情况下,包含$event 会更快(以难以察觉的幅度)。但是差异微不足道,以至于无关紧要。如果您必须编译 500,000 个事件处理程序,则两种语法的编译操作将花费大约 1 秒。
【讨论】:
在 Option1 中,每次渲染组件时都会创建一个表达式。但是,在每个循环的选项 2 中,只处理一种方法。所以,最好在模板中定义方法和地址。
考虑这个示例:
<list>
<li
v-for="item in items" :key="item.id"
@click="theClickHandler(item)"
></li>
</list>
每个渲染中有一个theClickHandler方法和item.length不同的表达式(最多)!!
要处理这种情况,您可以使用HTML data attributes:
<list>
<li
v-for="item in items" :key="item.id"
:data-id="item.id"
@click="theClickHandler"
></li>
</list>
并在handler方法中获取点击的item:
theClickHandler(e) {
const id = e.target.dataset.id
const [item] = this.items.filter(x => x.id === id)
console.log('clicked item:', item)
},
【讨论】: