我想在函数运行后延迟它,这样它就不能在这段时间内再次运行。
实现它的示例:
ngOnInit() {
setInterval(() => this.functionWithTimeLimit(), 500);
}
functionWithTimeLimit() {
if(allowedToRun){
console.log('Run me every 2 seconds at most');
allowedToRun = false;
setTimeout(() => allowedToRun = true, 2000); // Allow to execute this function again after two seconds
}
}
但我确信有更好的方法可以使用 rxjs 来做到这一点。我怎样才能做到这一点?
最佳答案
有多种方法可以做到这一点。
一种方法是创建一个 RxJS Subject
并路由函数调用以从中发出通知。在订阅这个可观察的内容中,您可以使用 RxJS throttleTime
运算符(operator)在指定的时间内忽略后续排放。
尝试以下操作
Controller
import { Subject } from 'rxjs';
import { throttleTime, takeUntil } from 'rxjs/operators';
export class AppComponent implements OnInit, OnDestroy {
completed$ = new Subject<any>();
trigger$ = new Subject<any>();
constructor() { }
functionWithTimeLimit() {
console.log('called functionWithTimeLimit');
}
ngOnInit() {
this.trigger$.pipe(
throttleTime(2000), // <-- ignore notifications for 2s after an emission
takeUntil(this.completed$) // <-- use to close the subscription
).subscribe(this.functionWithTimeLimit.bind(this));
}
ngOnDestroy() {
this.completed$.next(); // <-- close impending subscriptions
}
}
模板
<button (mouseup)="trigger$.next()">Trigger function</button>
工作示例:Stackblitz
在上面的示例中,假设最初按下按钮应该直接触发该功能。但现在我们在按下按钮时发出可观察的结果并触发其订阅中的函数。
更新:throttleTime
和 debounceTime
之间的差异
throttleTime
将在单个通知后将后续通知暂停固定的时间。
var { fromEvent } = rxjs;
var { throttleTime, map } = rxjs.operators;
var inputBox = document.getElementById('search');
var displayBox = document.getElementById('display');
fromEvent(inputBox, 'keyup').pipe(
map(event => event.currentTarget.value),
throttleTime(2000),
).subscribe(value => displayBox.innerHTML = value);
<script src="https://unpkg.com/<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="dfada7b5ac9fe9f1ebf1ef" rel="noreferrer noopener nofollow">[email protected]</a>/bundles/rxjs.umd.min.js"></script>
Keep on typing. It will render the value continuously every 2 sec.<br><br>
<input type="text" id="search" />
<p id="display"></p>
debounceTime
将在每个通知后将后续通知暂停固定的时间。
var { fromEvent } = rxjs;
var { debounceTime, map } = rxjs.operators;
var inputBox = document.getElementById('search');
var displayBox = document.getElementById('display');
fromEvent(inputBox, 'keyup').pipe(
map(event => event.currentTarget.value),
debounceTime(2000),
).subscribe(value => displayBox.innerHTML = value);
<script src="https://unpkg.com/<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="0d7f75677e4d3b2339233d" rel="noreferrer noopener nofollow">[email protected]</a>/bundles/rxjs.umd.min.js"></script>
Keep on typing. It'll render only after 2 seconds after the typing stops.<br><br>
<input type="text" id="search" />
<p id="display"></p>
关于javascript - 不允许函数在执行后一段时间内继续执行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63189239/