Здравствуйте, я новичок в RxJS и только знакомлюсь с операторами. Я хочу показать в консоли следующие 6 чисел с интервалом в одну секунду после нажатия кнопки. Я хочу сбросить этот счетчик после следующего щелчка с помощью switchMap.
Я пытался сделать это с помощью switchMap, но счетчик не сбрасывается.
obsSwitchMap: Observable<any>;
this.obsSwitchMap = of(null).pipe(
switchMap(x => from([1, 2, 3]).pipe(
concatMap(item => of(item).pipe(delay(300)))
)
)
)
onSwitchMapBtnClick() {
this.obsSwitchMap.subscribe(x => {
console.info(x)
})
}
Числа отображаются независимо друг от друга
Хотя вы хотите учиться, я думаю, вы должны учиться с самого начала, используя передовой опыт.
И это означает, что вы можете сделать это очень просто без switchMap :
const newInterval = () => rxjs.timer(0, 1000).pipe(
rxjs.operators.map(nb => new Array(6).fill(nb).map((v, i) => v + i + 1))
);
let subscription;
function resetTimer() {
subscription && subscription.unsubscribe();
subscription = newInterval().subscribe(v => console.info(v));
}
resetTimer();
<script src = "https://cdnjs.cloudflare.com/ajax/libs/rxjs/6.5.2/rxjs.umd.js"></script>
<button onclick = "resetTimer()">Reset timer</button>
Вот пример switchMap:
const horsemen = [
{ id: 1, name: 'Death' },
{ id: 2, name: 'Famine' },
{ id: 3, name: 'War' },
{ id: 4, name: 'Conquest' },
];
// Fake HTTP call of 1 second
function getHorseman(id) {
return rxjs
.of(horsemen.find(h => h.id === id))
.pipe(rxjs.operators.delay(1000));
}
const query = document.querySelector('input');
const result = document.querySelector('div.result');
// Listen to input
rxjs.fromEvent(query, 'input')
.pipe(
rxjs.operators.map(event => +event.target.value), // Get ID
rxjs.operators.switchMap(id => getHorseman(id)) // Get Horseman
).subscribe(horseman => {
let content;
if (horseman) content = `Horseman = ${horseman.name}`;
else content = `Horseman unknown`;
result.innerText = content;
});
<script src = "https://cdnjs.cloudflare.com/ajax/libs/rxjs/6.5.2/rxjs.umd.js"></script>
<input type = "text" placeholder = "Input an ID here (1-4)">
<div class = "result"></div>
Вместо этого попробуйте использовать этот пример: у вас есть наблюдаемый объект, содержащий идентификатор пользователя, и вам нужно получить имя этого пользователя (которое хранится в другом наблюдаемом объекте, содержащем массив { id: number, name: string }
.
Итак, когда мне следует использовать switchMap?
@szaranczazespizu switchMap используется для замены потока другим и отмены любой предыдущей подписки. Это очень полезно для таких вещей, как мгновенное исследование, автозаполнение и т. д.
@szaranczazespizu, конечно, я отредактировал свой пост. Если у вас есть вопросы по этому поводу, не стесняйтесь спрашивать меня.
Я нашел простое решение, используя switchMap. При каждом щелчке перезапускайте наблюдаемый счетчик и берите столько предметов, сколько хотите.
const btn = document.querySelector('button');
fromEvent(btn, 'click').pipe(
switchMap((item => interval(1000).pipe(take(6)))),
).subscribe(console.info)
Спасибо, но я искал пример, чтобы узнать кое-что о switchMap. Может быть, мой пример бесполезен, но может быть полезен для понимания