programing

rxjs의 flatMap, mergeMap, switchMap 및 concatMap?

linuxpc 2023. 6. 25. 18:30
반응형

rxjs의 flatMap, mergeMap, switchMap 및 concatMap?

누가 스위치맵과 플랫맵의 차이점을 자바스크립트 측면에서 설명해주세요 (각도 관점에서, rxjs 5)

제가 알기로는.

SwitchMap은 최신 관측 가능한 값만 내보내고 이전 관측 가능한 값을 취소합니다.

flatMap은 모든 개별 관측치를 수집하고 관측치의 순서에 상관없이 모든 관측치를 단일 배열로 반환합니다.비동기식으로 작동합니다.

concatMap은 순서를 보존하고 모든 관측 가능한 값을 방출하며, 동시에 작동합니다.

그래요?

mergeMap은 위와 어떻게 다릅니까?

누군가, 예를 들어 설명해 주세요.

이전 답변에서 이를 인용합니다.

  • flatMap/mergeMap - 모든 소스 항목에 대해 즉시 관찰 가능한 항목을 작성합니다. 이전의 모든 관찰 가능한 항목은 활성 상태로 유지됩니다.메모flatMap는 의 별칭입니다.mergeMap그리고.flatMapRxJS 8에서 제거됩니다.
  • concatMap - 이전 관찰이 완료될 때까지 기다렸다가 다음 관찰을 만듭니다.
  • switchMap - 모든 소스 항목에 대해 이전의 관찰 가능 항목을 완료하고 즉시 다음 항목을 만듭니다.
  • exhaustMap - 이전의 관찰 가능 항목이 완료되지 않은 동안 소스 항목이 무시됩니다.

다음은 소스가 즉시 항목(0,1,2,3,4)이고 지도 함수가 각 항목을 500ms 지연시키는 관찰 가능 항목을 생성할 때 각 연산자가 어떻게 동작하는지 보여주는 예입니다.

const { mergeMap, flatMap, concatMap, switchMap, exhaustMap } = Rx.operators;

const example = operator => () =>
  Rx.Observable.from([0,1,2,3,4])
  .pipe(
    operator(x => Rx.Observable.of(x).delay(500))
  )
  .subscribe(console.log, () => {}, () => console.log(`${operator.name} completed`));

const mm = example(mergeMap);
const fm = example(flatMap);
const cm = example(concatMap);    
const sm = example(switchMap);
const em = example(exhaustMap);
.examples > div {
  cursor: pointer;
  background-color: #4CAF50;
  color: white;
  padding: 7px 16px;
  display: inline-block;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/rxjs/5.5.8/Rx.js"></script>

<div class='examples'>
  <div onClick='mm()'>mergeMap </div>
  <div onClick='fm()'>flatMap</div>
  <div onClick='cm()'>concatMap</div>
  <div onClick='sm()'>switchMap</div>
  <div onClick='em()'>exhaustMap</div>
</div>

아래 대리석 다이어그램에서 5ms, 10ms, 20ms로 방출되는 소스 스트림은 *매핑됩니다.timer(0, 3): 3개 배출

mergeMap vs exhaustMap vs switchMap vs concatMap

여기서 이 대리석 다이어그램을 사용하십시오. "mergeMap vs exhaustMap vs switchMap vs concatMap"

이미 이 모든 멋진 답을 가지고 있기 때문에, 저는 좀 더 시각적인 설명을 덧붙이고 싶었습니다.

누군가에게 도움이 되길 바랍니다.

@자히 C, 멋진 답변 - 코드 샘플에 기능적 구성을 사용하는 것이 좋습니다.가능하다면, 시간이 지정된 관측치를 사용하여 추가적인 몇 가지 포인트를 설명하기 위해 그것을 빌리고 싶습니다.

외부, 내부 및 제어

이 연산자들은 모두 다음과 같은 변환 연산자입니다.map()공통적인 특징은 외부와 내부관찰할 수 있다는 것입니다.핵심적인 차이점은 외부 관측치가 내부 관측치를 제어하는 방식입니다.

비교하기 위해 코드 샘플은 쌍으로 실행되며 형식의 값을 출력합니다.[outerValue,innerValue]저는 테스트에 간격을 추가했고, 타이밍이 약간 겹치도록 내부 지연을 변경했습니다(사용된 공식은 다음과 같습니다).delay((5-x)*200)).


병합 맵 대 concatMap

이 두 값은 모두 모든 값을 출력하며, 차이는 순서입니다.

-로 정렬합니다.
[0,0],[1,0],[0,1],[2,0],[1,1],[3,0],[2,1],[4,0],[3,1],[4,1]

concatMap - 외부 관측 가능한 순서대로 정렬
[0,0],[0,1],[1,0],[1,1],[2,0],[2,1],[3,0],[3,1],[4,0],[4,1]

출력에서 mergeMap 외부 방출은 시퀀스에서 지연될 수 있지만 concatMap은 엄격한 외부 방출 시퀀스를 따릅니다.


스위치맵 대 배기맵

이 두 가지 모두 출력을 조절합니다.

스위치 맵 - 마지막 스로틀
[3,0],[4,0],[4,1]

맵 - by first - 1배로스틀
[0,0],[0,1],[4,0],[4,1]

출력에서 switchMap은 모든 불완전한 내부 방출을 조절하지만, 이후의 배기Map은 이전 방출이 완료될 때까지 방출합니다.


병합 맵 대 switchMap

switchmap은 정말 mergeMap이 사용되어야 하는 SO 답변에 자주 사용되기 때문에 이것을 넣었습니다.

-로 정렬합니다.
[0,0],[1,0],[0,1],[2,0],[1,1],[3,0],[2,1],[4,0],[3,1],[4,1]

스위치 맵 - 마지막 스로틀
[3,0],[4,0],[4,1]

주요 장점은 내부 관찰 가능한 타이밍에 따라 switchMap 출력을 예측할 수 없다는 것입니다. 예를 들어 내부가 http인 경우 결과는 연결 속도에 따라 달라질 수 있습니다.


console.clear()
const { mergeMap, flatMap, concatMap, switchMap, exhaustMap, delay, map, take, toArray } = Rx.operators;

const note = {
  mergeMap:  'Order by inner observable', 
  concatMap: 'Order by outer observable', 
  switchMap: 'Throttle by last', 
  exhaustMap: 'Throttle by first', 
}
const title = (operator) => {
  const opName = operator.name.replace('$1','')
  return `${opName} - ${note[opName]}`
}
const display = (x) => {
  return map(y => `[${x},${y}]`)
}
const inner = (x) => Rx.Observable.timer(0,500)
.pipe(
  delay((5-x)*200),
  display(x),
  take(2)
)

const example = operator => () => {
  Rx.Observable.interval(500).take(5)
  .pipe(
    operator(x => inner(x)),
    toArray(),
    map(vals => vals.join(','))
  )
  .subscribe(x => {
    console.log(title(operator))
    console.log(x)
  });
};

const run = (fn1, fn2) => {
  console.clear()
  fn1()
  fn2()
}
const mmVcm = () => run(example(mergeMap), example(concatMap));
const smVem = () => run(example(switchMap), example(exhaustMap));
const mmVsm = () => run(example(mergeMap), example(switchMap));
.examples > div {
  cursor: pointer;
  background-color: #4CAF50;
  color: white;
  padding: 7px 16px;
  display: inline-block;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/rxjs/5.5.8/Rx.js"></script>

<div class='examples'>
  <div onClick='mmVcm()'>mergeMap vs concatMap </div>
  <div onClick='smVem()'>switchMap vs exhaustMap</div>
  <div onClick='mmVsm()'>mergeMap vs switchMap </div>
</div>

여러분이 기상 채널을 구독하고 있다고 가정해 보겠습니다.기상 아나운서는 여러 작전을 수행한 후 그에게 전달된 보고서를 읽습니다.

  • 아나운서가 하나의 보고서를 읽고 있을 때 다른 보고서를 읽는 동안 다른 보고서가 들어옵니다.만약 그가 첫번째 보고서를 읽는 것을 멈추고 그것이 도착하자마자 새로운 보고서를 읽기 시작한다면 그는 하는 것입니다.switchMapswitchMap은 각 소스 값을 관측 가능한 출력에 병합되는 관측 가능한 값으로 투영하므로 가장 "최근" 관측 가능한 출력에서 값만 내보냅니다.

  • 만약 라디오 아나운서가 첫 번째가 끝날 때까지 새로운 보고서를 시작하지 않는다면, 우리는.concatMapconcatMap은 각 소스 값을 관측 가능한 출력으로 병합되는 관측 가능한 값에 투영합니다. 이는 각 소스 값이 다음 값을 병합하기 전에 완료될 때까지 직렬 방식으로 대기합니다.

  • 만약 아나운서가 여전히 읽고 있는 동안 새로운 보고서가 들어오고 그의 반응이 어떻게든 동시에 두 가지를 읽는 것이라면 우리는 그것을 가지고 있습니다.mergeMap/flatMapflatMap은 mergeMap의 별칭입니다.mergeMap은 각 소스 값을 관측 가능한 출력에서 병합되는 관측 가능한 값으로 투영하기 때문입니다."mergeMap"은 switchMap 및 concatMap의 보다 기본적인 버전입니다.

여기 다른 종류의 지도들 사이의 차이에 대한 한 가지 더 생각하는 방법이 있습니다.이것은 제가 그것을 이해하는 데 도움이 되었습니다.다른 사람들에게 도움이 되길 바랍니다.

다음 소스를 고려하십시오.

  • 알파벳에서 소문자를 생성하는 소스: a, b, c 및 d
  • 4개의 별도 "단어" 출처, 각각 알파벳의 특정 문자(a,b,c)로 시작하는 3개의 단어를 생성한 후 완료

서로 다른 종류의 지도 사이의 차이를 설명하기 위해, 우리는 알파벳 소스의 항목을 알파벳의 해당 문자에 해당하는 "단어" 소스에 연결하고, 각각의 다른 맵을 사용하여 서로 다른 결과를 확인합니다.

지도

이것은 관찰 가능한 다른 출처를 소개하지 않기 때문에 다른 지도와 다릅니다.들어오는 값을 다른 값으로 변환할 뿐입니다.

따라서 소문자 소스의 출력은 입력을 대문자로 변환하는 맵을 통해 다음과 같습니다.

Input: a,b,c,d

Output: A, B, C, D

스위치 맵

이렇게 하면 각 입력이 다른 소스로 변환되어 출력이 새 소스(즉, 새 소스에 가입)로 전환됩니다.다른 알파 입력이 도착하면 "워드" 소스가 변경됩니다(이전 "워드" 소스에서 등록 취소).

Input: a,b,c,d

Output: animal, aardvark, bull, baker, beach, cow, dog, day, dinner

콘캣 맵

다음 소스로 이동하기 전에 각 소스가 완료될 때까지 Concat이 대기한다는 점을 제외하고는 switchMap과 같습니다.

Input: a,b,c,d

Output: animal, aardvark, axe, bull, baker, beach, cow, car, cat, dog, day, dinner

배기 맵

Concat Map처럼 마지막 소스를 완료하는 동안 들어오는 모든 입력을 무시합니다.아래 예제에서는 이전 매핑된 소스가 완료되는 동안 알파 입력 "b"와 "d"가 모두 들어왔기 때문에 무시되었다고 가정합니다.

Input: a,b,c,d

Output: animal, aardvark, axe, cow, car, cat

지도 병합(일명 플랫 지도)

각 소스가 완료될 때까지 실행되지만 다른 소스가 계속 진행되는 동안 새 소스가 시작될 수 있다는 점에서 concatMap과 마찬가지로 시퀀스가 겹칩니다.

Input: a,b,c,d

Output: animal, aardvark, bull, axe, baker, cow, car, beach, dog, day, cat, dinner

이것은 시작 단계에서 이해하기에는 조금 깁니다. 적어도 저에게는요.

어쨌든 고려해 보십시오.

flatMap은 의다이다니입의 다른 이름입니다.mergeMap-mergeMap인 매개 변수 " " " 를 할 수 있습니다.concurrency에 몇 할 수 합니다.

concatMapmergeMap이 1/로 설정된

와 함께mergeMap하고 있는 .

switchMap당신이 설명한 대로 작동합니다. (자세한 내용은 이 좋은 기사를 참조하십시오. https://blog.angular-university.io/rxjs-switchmap-operator/) )

저는 얼마 전에 요청한 운영자를 사용하기 위한 데모/예시를 만들었습니다.

https://stackblitz.com/edit/rxjs-map-operators

관측 가능한 외부 값을 내보낼 구간 또는 클릭 중에서 선택할 수 있습니다.내부 관찰 가능한 경우 간격(3개 항목)을 내보낼지 http 요청을 보낼지 선택할 수 있습니다.

선택 항목 아래에 결과가 인쇄됩니다.

  1. switchMap - 주문 작업을 중지하고 새 주문 작업을 시작합니다.가장 최근의 주문만 완료될 것입니다.

  2. concatmap - 순서가 대기열에 추가됩니다.당신은 당신이 작업하는 어떤 순서든 끝내요.당신이 주문을 완료하면, 당신은 다음 주문에 대해 작업할 것입니다.

  3. mergeMap - 모든 주문이 지정되는 즉시 모든 주문에 대해 동시에 작업을 수행합니다.

  4. 배기 맵 - 새 주문을 무시하고 작업 중인 주문을 모두 마칩니다.완료되면 새 주문을 자유롭게 수락할 수 있습니다.

언급URL : https://stackoverflow.com/questions/49698640/flatmap-mergemap-switchmap-and-concatmap-in-rxjs

반응형