(뭔가... 비슷하다는 느낌이 들어서 차이점이 궁금했습니다)
.store(in:) = 구독 생명주기 관리 (메모리/취소 관리)
.eraseToAnyPublisher() = 타입 숨기기 (인터페이스 정리/설계용)
역할: Combine 구독을 메모리에 유지하고, 나중에 자동으로 취소되게 관리하는 용도
Combine에서 pusliber.sink {...} 를 호출하면 구독 객체 (AnyCancellable)가 생성됨. 이것을 어디에도 저장하지 않으면 -> 바로 메모리에서 해제되고 -> 네트워크 요청 / 스트림 즉시 취소됩니다. 그래서 반드시 저장해야 합니다.
.store(in: &cancellables)는 이 구독을 cancellabes에 저장해 두고, ViewModel이 살아 있는 동안 유지하고, ViewModel이 해제되면 자동으로 cancel 해 줘라는 뜻입니다.
만약 안 쓴다면?
hospitalNetwork.getHospitalList()
.sink { ... } // ❌ store 안 함
sink 실행되자마자 cancellable 바로 해제 -> 네트워크 요청 거의 즉시 취소 -> 값 안 옴 / completion 안 옴 / 이상한 버그 발생
이건 메모리랑 전혀 상관없고, 설계 / 타입 추상화용입니다.
URLSession.DataTaskPublisher
.tryMap { ... }
.decode(...)
.map(...)
이 함수의 실제 반환 타입은:
Publishers.Map<
Publishers.Decode<
Publishers.TryMap<
URLSession.DataTaskPublisher, Data
>,
HospitalAPIResponse
>,
[Hospital]
>
이걸 함수 시그니처에 쓰면: 읽기/수정불가능 + 외부 코드 전부 깨짐
그래서 타입 지우기를 하는 것입니다. .eraseToAnyPublisher()
이 Publisher의 내부 타입은 숨시고, 그냥 AnyPublisher<[Hospital], URLError>로만 보이게 하자" 하는 것입니다.
정리하자면, 둘은 목적과 역할이 완전히 다릅니다.
.eraseToAnyPublisher()는 반환 타입을 숨기기 위한 설계용 도구 (인터페이스 안정성).store(in:)은 구독을 유지하고 메모리 누수를 막기 위한 생명 주기 관리 도구 (메모리 안정성)