如何修改主题输出类型?
How to modify subject output type?
我有以下单例:
public abstract class Store<Input, Output> {
private BehaviorSubject<Input> subject = BehaviorSubject.create();
private Observable<Output> observable; //also a singleton
public final Subscription register(Subscriber<Output> subscriber) {
if (observable == null) {
observable = subject.compose(getTransformer()); //is this hot?
}
return observable.subscribe(subscriber);
}
public final void unregister(Subscription subscription) { //unregister }
//applies operators to the original stream to transform Input -> Output
protected abstract Observable.Transformer<Input, Output> getTransformer();
public final void onNext(Input event) { subject.onNext(event);}
}
问题: 当我旋转设备或最小化应用程序时,observable 死机(中止网络执行)。 subject.compose()
是否返回一个冷的可观察对象,如果是,为什么?
我尝试使用 publish.autoConnect()
/ share()
使其变热,现在它不会在旋转时死掉...但是 BehaviourSubject
会损坏。当我旋转设备时,我没有在订阅时获得第一个值。
我怎样才能转换 subject
的输出值并使其仍然像 subject
那样工作? SAMPLE PROJECT
日志:
USER: hits button to fetch from network
D: Retrieving from
network... D: Network request executed successfully
D: Caching to memory
USER: hits button to fetch from network again
D: Retrieving from network...
USER: pressed home button, app backgrounded
D:.unsubscribe()
事实证明,我一直在使用错误的主题。这是我上面想要实现的正确版本:
public abstract class RxStore<Input, Output> {
private BehaviorRelay<Output> relay;
public final Subscription register(Subscriber<Output> subscriber) {
if (relay == null) {
relay = BehaviorRelay.create(defaultValue());
}
return relay.subscribe(subscriber);
}
public final void unregister(Subscription subscription) {
if (subscription != null && !subscription.isUnsubscribed()) {
subscription.unsubscribe();
}
}
public void execute(Input event) {
buildObservable(event).subscribe(relay);
}
/**
* @return the first or default value emitted to subscribers
*/
protected Output defaultValue() {
return null;
}
/**
* @return an buildObservable responsible of handling its own errors.
*/
protected abstract Observable<Output> buildObservable(Input event);
}
编辑:
我发现这种方法非常有用。我在产品中使用这种方法,我写了一篇关于这个的文章:
https://medium.com/@FerRaviola/rxandroid-an-event-bus-on-steroids-9699e93eca98#.tqbxleo4h
我有以下单例:
public abstract class Store<Input, Output> {
private BehaviorSubject<Input> subject = BehaviorSubject.create();
private Observable<Output> observable; //also a singleton
public final Subscription register(Subscriber<Output> subscriber) {
if (observable == null) {
observable = subject.compose(getTransformer()); //is this hot?
}
return observable.subscribe(subscriber);
}
public final void unregister(Subscription subscription) { //unregister }
//applies operators to the original stream to transform Input -> Output
protected abstract Observable.Transformer<Input, Output> getTransformer();
public final void onNext(Input event) { subject.onNext(event);}
}
问题: 当我旋转设备或最小化应用程序时,observable 死机(中止网络执行)。 subject.compose()
是否返回一个冷的可观察对象,如果是,为什么?
我尝试使用 publish.autoConnect()
/ share()
使其变热,现在它不会在旋转时死掉...但是 BehaviourSubject
会损坏。当我旋转设备时,我没有在订阅时获得第一个值。
我怎样才能转换 subject
的输出值并使其仍然像 subject
那样工作? SAMPLE PROJECT
日志:
USER: hits button to fetch from network
D: Retrieving from
network... D: Network request executed successfully
D: Caching to memory
USER: hits button to fetch from network again
D: Retrieving from network...
USER: pressed home button, app backgrounded
D:.unsubscribe()
事实证明,我一直在使用错误的主题。这是我上面想要实现的正确版本:
public abstract class RxStore<Input, Output> {
private BehaviorRelay<Output> relay;
public final Subscription register(Subscriber<Output> subscriber) {
if (relay == null) {
relay = BehaviorRelay.create(defaultValue());
}
return relay.subscribe(subscriber);
}
public final void unregister(Subscription subscription) {
if (subscription != null && !subscription.isUnsubscribed()) {
subscription.unsubscribe();
}
}
public void execute(Input event) {
buildObservable(event).subscribe(relay);
}
/**
* @return the first or default value emitted to subscribers
*/
protected Output defaultValue() {
return null;
}
/**
* @return an buildObservable responsible of handling its own errors.
*/
protected abstract Observable<Output> buildObservable(Input event);
}
编辑:
我发现这种方法非常有用。我在产品中使用这种方法,我写了一篇关于这个的文章:
https://medium.com/@FerRaviola/rxandroid-an-event-bus-on-steroids-9699e93eca98#.tqbxleo4h