Einige Browserereignisse können in kurzer Zeit mehrmals schnell ausgelöst werden, z. B. das Ändern der Fenstergröße oder das Herunterscrollen der Seite. Wenn Sie beispielsweise auf Seitenfenster-Scroll-Ereignisse hören und der Benutzer weiterhin schnell auf der Seite nach unten scrollt, kann das Scroll-Ereignis innerhalb von 3 Sekunden tausende Male ausgelöst werden, was zu schwerwiegenden Leistungsproblemen führen kann.
Wenn Sie während eines Interviews über die Erstellung einer Anwendung sprechen und Ereignisse wie Scrollen, Fenstergrößenänderung oder Tastendrücke auftreten, erwähnen Sie unbedingt Entprellen und Funktionsdrosselung, um die Seitengeschwindigkeit und -leistung zu verbessern. Die Essenz dieser beiden Brüder liegt in der Form des Abschlusses. Durch Umschließen der dem Ereignis entsprechenden Rückruffunktion, Zwischenspeichern der Zeitinformationen in Form einer freien Variablen und schließlich Verwenden von setTimeout zum Steuern der Auslösehäufigkeit des Ereignisses.
Throttle: Die erste Person hat das letzte Wort
Die zentrale Idee von Throttle ist: Innerhalb eines bestimmten Zeitraums, egal wie viele Rückrufe Sie auslösen, werde ich nur den ersten erkennen und nach Ablauf des Timers geben eine Antwort.
Lassen Sie mich zunächst eine kleine Geschichte erzählen: Ein Passagier stieg gerade aus dem Flugzeug und brauchte ein Auto, also rief er den einzigen Flughafenbus am Flughafen an, um ihn abzuholen. Der Fahrer fuhr zum Flughafen und dachte, er sei schon gekommen, also solle er noch ein paar Leute mitnehmen, damit sich die Fahrt lohnt – ich warte zehn Minuten und schaue mal. Also schaltete der Fahrer den Timer ein und begrüßte die Gäste hinter ihm, einer nach dem anderen in den Bus einzusteigen. Während dieser zehn Minuten können die Passagiere, die hinten aus dem Flugzeug ausgestiegen sind, nur diesen Bus nehmen. Nach zehn Minuten muss dieser Bus weggeschickt werden, egal wie viele Passagiere hinter dem Flugzeug nicht überfüllt sind.
In dieser Geschichte ist der „Fahrer“ unser Gashebel, der den Zeitpunkt der Abfahrt steuert; der „Passagier“ sind die Rückrufaufgaben, die aufgrund unserer häufigen Betriebsereignisse weiterhin anfallen, und er muss die Vereinbarungen des übernehmen „Fahrer“ und „Timer“ sind die Zeitinformationen, die in Form einer freien Variablen vorliegen. Sie sind die Grundlage für die Entscheidung des „Fahrers“, das Auto endgültig zu starten. entspricht der Ausführung der Callback-Funktion.
Zusammenfassend lässt sich sagen, dass die sogenannte „Drosselung“ dadurch erreicht wird, dass nachfolgende Rückrufanfragen für einen bestimmten Zeitraum ignoriert werden. Solange ein Gast eine Fahrt wünscht, startet der Fahrer einen Timer für ihn. Innerhalb einer bestimmten Zeitspanne müssen sich alle nachfolgenden Gäste, die eine Fahrt benötigen, anstellen, um an dieser Fahrt teilzunehmen, und niemand kann anrufen mehr Fahrten.
Es entspricht der tatsächlichen Interaktion: Immer wenn der Benutzer ein Scroll-Ereignis auslöst, starten wir den Timer für diesen Auslösevorgang. Für einen bestimmten Zeitraum werden alle nachfolgenden Scroll-Ereignisse als „Passagiere in einem Auto“ behandelt – sie können keine neuen Scroll-Rückrufe auslösen. Bis „ein Zeitraum“ erreicht ist, wird der Rückruf ausgeführt, der dem zum ersten Mal ausgelösten Scroll-Ereignis entspricht, und nachfolgende Scroll-Rückrufe, die „innerhalb eines Zeitraums“ ausgelöst werden, werden von der Drosselklappe ignoriert.
Jetzt gemeinsam einen Gashebel umsetzen:
// fn是我们需要包装的事件回调, interval是时间间隔的阈值 function throttle(fn, interval) { // last为上一次触发回调的时间 let last = 0 // 将throttle处理结果当作函数返回 return function () { // 保留调用时的this上下文 let context = this // 保留调用时传入的参数 let args = arguments // 记录本次触发回调的时间 let now = +new Date() // 判断上次触发的时间和本次触发的时间差是否小于时间间隔的阈值 if (now - last >= interval) { // 如果时间间隔大于我们设定的时间间隔阈值,则执行回调 last = now; fn.apply(context, args); } } } // 用throttle来包装scroll的回调 const better_scroll = throttle(() => console.log('触发了滚动事件'), 1000)
Debounce: Der Letzte hat das letzte Wort
Der zentrale Gedanke von Anti-Shake ist: Ich werde bis zum Ende auf dich warten. Innerhalb einer bestimmten Zeitspanne werde ich, egal wie viele Rückrufe Sie auslösen, nur den letzten wiedererkennen.
Erzählen Sie weiter die Geschichte des fahrenden Fahrers. Diesmal war der Fahrer geduldiger. Nachdem der erste Fahrgast in den Bus eingestiegen ist, beginnt der Fahrer mit der Zeitmessung (z. B. zehn Minuten). Wenn innerhalb von zehn Minuten ein anderer Passagier auftaucht, löscht der Fahrer den Timer und wartet weitere zehn Minuten (verzögertes Warten). Solange es keinen solchen Fahrgast gibt und in den nächsten zehn Minuten seit dem Einsteigen keine neuen Fahrgäste in den Bus einsteigen, wird der Fahrer denken, dass niemand diesen Bus wirklich nehmen muss, und wird wegfahren.
Vergleichen wir Throttle, um die Entprellung zu verstehen: In der Throttle-Logik hat „die erste Person das letzte Wort“, es misst nur den ersten Passagier und führt den Rückruf aus, wenn die Zeit abgelaufen ist. Debounce glaubt, dass „die letzte Person das letzte Wort hat“ und Debounce stellt für jeden neuen Passagier einen neuen Timer ein.
Jetzt gemeinsam eine Entprellung implementieren:
// fn是我们需要包装的事件回调, delay是每次推迟执行的等待时间 function debounce(fn, delay) { // 定时器 let timer = null // 将debounce处理结果当作函数返回 return function () { // 保留调用时的this上下文 let context = this // 保留调用时传入的参数 let args = arguments // 每次事件被触发时,都去清除之前的旧定时器 if(timer) { clearTimeout(timer) } // 设立新定时器 timer = setTimeout(function () { fn.apply(context, args) }, delay) } } // 用debounce来包装scroll的回调 const better_scroll = debounce(() => console.log('触发了滚动事件'), 1000)
Verwenden Sie Throttle, um die Entprellung zu optimieren
Das Problem mit der Entprellung ist, dass sie „zu geduldig“ ist. Stellen Sie sich vor, wenn der Benutzer sehr häufig arbeitet, wartet er nicht auf das Ende der durch Entprellen eingestellten Verzögerungszeit, bevor er den nächsten Vorgang ausführt, sodass bei jeder Entprellung der Timer für den Benutzer neu generiert wird und die Rückruffunktion unzählige Male verzögert wird. Häufige Verzögerungen führen dazu, dass Benutzer keine Antwort erhalten und außerdem den Eindruck haben, dass „diese Seite hängen bleibt“.
Um eine Selbstzerstörung zu vermeiden, müssen wir uns die Idee der Drosselung ausleihen, um eine „End-Line“-Entprellung zu erzeugen – Sie können warten, aber ich habe meine Prinzipien: Innerhalb der Verzögerungszeit kann ich den Timer regenerieren für Sie; aber solange die Verzögerungszeit abgelaufen ist, muss ich dem Benutzer eine Antwort geben. Diese „Kombination“-Idee aus Drosselung und Entprellung wurde von vielen ausgereiften Front-End-Bibliotheken auf die Implementierung ihrer erweiterten Drosselungsfunktion angewendet:
// fn是我们需要包装的事件回调, delay是时间间隔的阈值 function throttle(fn, delay) { // last为上一次触发回调的时间, timer是定时器 let last = 0, timer = null // 将throttle处理结果当作函数返回 return function () { // 保留调用时的this上下文 let context = this // 保留调用时传入的参数 let args = arguments // 记录本次触发回调的时间 let now = +new Date() // 判断上次触发的时间和本次触发的时间差是否小于时间间隔的阈值 if (now - last < delay) { // 如果时间间隔小于我们设定的时间间隔阈值,则为本次触发操作设立一个新的定时器 clearTimeout(timer) timer = setTimeout(function () { last = now fn.apply(context, args) }, delay) } else { // 如果时间间隔超出了我们设定的时间间隔阈值,那就不等了,无论如何要反馈给用户一次响应 last = now fn.apply(context, args) } } } // 用新的throttle包装scroll的回调 const better_scroll = throttle(() => console.log('触发了滚动事件'), 1000) document.addEventListener('scroll', better_scroll)
Verwendung von Entprellung und Drosselung in Lodash in Vue
事件节流和防抖是提高性能或降低网络开销的好方法。虽然 Vue 1曾经支持对事件的节流和防抖,但是在Vue 2中为了保持核心的简单性,删除对事件的节流和防抖的支持。因此,在Vue 2对对事件进行防抖和节流我们可以使用 lodash
来做。
安装
可以通过 yarn 或 npm 安装 lodash。
# Yarn $ yarn add lodash # NPM $ npm install lodash --save
注意:如果我们不想导入lodash
的所有内容,而只导入所需的部分,则可以通过一些Webpack构建自定义来解决问题。 还可以使用lodash.throttle
和lodash.debounce
等软件包分别安装和导入lodash
的各个部分。
throttling 方法
要对事件进行节流处理方法非常简单,只需将要调用的函数包装在lodash的_.throttle
函数中即可。
<template> <button @click="throttledMethod()">Click me as fast as you can!</button> </template> <script> import _ from 'lodash' export default { methods: { throttledMethod: _.throttle(() => { console.log('I get fired every two seconds!') }, 2000) } } </script>
debouncing 方法
尽管节流在某些情况下很有用,但一般情况我们经常使用的是防抖。 防抖实质上将我们的事件分组在一起,并防止它们被频繁触发。 要在Vue组件中使用节流,只需将要调用的函数包装在lodash的_.debounce
函数中。
<template> <button @click="throttledMethod()">Click me as fast as you can!</button> </template> <script> import _ from 'lodash' export default { methods: { throttledMethod: _.debounce(() => { console.log('I only get fired once every two seconds, max!') }, 2000) } } </script>
参考:
相关推荐:
更多编程相关知识,请访问:编程入门!!
Das obige ist der detaillierte Inhalt vonWie kann man Shake-and-Drossel-Ereignisse in Vue verhindern?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!