我遇到Flowables的问题并将它们添加到compositeDisposables。 我想从Observable切换到Flowable,因为操作可能会发出1000或更多值。我对rxjava2缺乏经验,所以请原谅我,如果这个问题很愚蠢:)
到目前为止,我使用了这样的observable:
public Observable<String> uploadPictureRx(String path)
{
return Observable.create(new ObservableOnSubscribe<String>()
{
@Override
public void subscribe(ObservableEmitter<String> e) throws Exception
{
Uri file = Uri.fromFile(new File(path));
String segment = file.getLastPathSegment();
UploadTask uploadTask = reference.child("SomeChild").child(segment).putFile(file);
uploadTask.addOnFailureListener(new OnFailureListener()
{
@Override
public void onFailure(@NonNull Exception exception)
{
e.onError(exception);
}
}).addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>()
{
@Override
public void onSuccess(UploadTask.TaskSnapshot taskSnapshot)
{
//noinspection VisibleForTests
downloadUrl = taskSnapshot.getDownloadUrl();
String url = downloadUrl.getPath();
e.onNext(url);
e.onComplete();
}
}).addOnProgressListener(new OnProgressListener<UploadTask.TaskSnapshot>()
{
@Override
public void onProgress(UploadTask.TaskSnapshot taskSnapshot)
{
//noinspection VisibleForTests
long bytes = taskSnapshot.getBytesTransferred();
String bytesS = String.valueOf(bytes);
e.onNext(bytesS);
}
});
}
});
}
并调用这样的方法:
private void uploadPicToFireBaseStorage(String path)
{
compositeDisposable.add(storageService.uploadPictureRx(path)
.subscribeOn(Schedulers.io())
.observeOn(mainScheduler)
.subscribeWith(new DisposableObserver<String>()
{
@Override
public void onNext(String s)
{
String ss = s;
System.out.println(ss);
}
@Override
public void onError(Throwable e)
{
e.printStackTrace();
}
@Override
public void onComplete()
{
view.displayToast("Picture Upload completed");
}
})
);
}
这很好用!但是,当我尝试使用Flowable而不是observable时,它不会编译:
public Flowable<String> uploadPictureRx(String path)
{
return Flowable.create(new FlowableOnSubscribe<String>()
{
@Override
public void subscribe(FlowableEmitter<String> e) throws Exception
{
Uri file = Uri.fromFile(new File(path));
String segment = file.getLastPathSegment();
UploadTask uploadTask = reference.child("somechild").child(segment).putFile(file);
uploadTask.addOnFailureListener(new OnFailureListener()
{
@Override
public void onFailure(@NonNull Exception exception)
{
e.onError(exception);
}
}).addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>()
{
@Override
public void onSuccess(UploadTask.TaskSnapshot taskSnapshot)
{
//noinspection VisibleForTests
downloadUrl = taskSnapshot.getDownloadUrl();
String url = downloadUrl.getPath();
e.onNext(url);
e.onComplete();
}
}).addOnProgressListener(new OnProgressListener<UploadTask.TaskSnapshot>()
{
@Override
public void onProgress(UploadTask.TaskSnapshot taskSnapshot)
{
//noinspection VisibleForTests
long bytes = taskSnapshot.getBytesTransferred();
String bytesS = String.valueOf(bytes);
e.onNext(bytesS);
}
});
}
}, BackpressureStrategy.BUFFER);
}
错误是: 推断类型&#39; E&#39;对于类型参数&#39; E&#39;不在其范围内;应该实施&#39; org.reactivestreams.Subscriber
我的猜测是,Flowable没有实现Disposable,这就是为什么它不会编译。我不知道那是不是真的,只是我到目前为止最好的猜测。 或者我是否必须将subscribeWith()更改为subscribe()?我不知道这种改变会带来什么影响。
无论如何建议如何使这个工作并将这个Flowable变成我的compositedisposable非常感谢。
谢谢你们!
编辑:
尝试将DisposableObserver更改为订阅服务器。但是这会导致以下错误: Compiler Error
答案 0 :(得分:3)
Flowables出于Backpressure的原因使用Subscription而不是Disposable。基本上使用Subscription.request()方法告诉可观察到那个时刻我想要多少项。
更改您的代码:
private void uploadPicToFireBaseStorage(String path)
{
compositeDisposable.add(storageService.uploadPictureRx(path)
.subscribeOn(Schedulers.io())
.observeOn(mainScheduler)
.subscribeWith(new DisposableObserver<String>()
{
@Override
public void onNext(String s)
{
String ss = s;
System.out.println(ss);
}
@Override
public void onError(Throwable e)
{
e.printStackTrace();
}
@Override
public void onComplete()
{
view.displayToast("Picture Upload completed");
}
})
);
}
到
private void uploadPicToFireBaseStorage(String path)
{
compositeDisposable.add(storageService.uploadPictureRx(path)
.subscribeOn(Schedulers.io())
.observeOn(mainScheduler)
.subscribeWith(new ResourceSubscriber<String>()
{
@Override
public void onNext(String s)
{
String ss = s;
System.out.println(ss);
}
@Override
public void onError(Throwable e)
{
e.printStackTrace();
}
@Override
public void onComplete()
{
view.displayToast("Picture Upload completed");
}
})
);
}
答案 1 :(得分:3)
Flowable
根据 pub-sub模式工作,即 publisher - subscriber 模式
然而,
Observable
根据观察者模式
在 pub-sub模式中,有一个中间事件通道保存 publisher
发布的数据,然后是event channel
发出数据,subscriber
获取onNext(...)
中的数据。
然而,
在观察者模式中,observable
会直接发送数据或将数据直接投放到observer
。 这可能会造成背压。(因为它会一次性发出整个数据。)
所以使用(Flowable
)
.subscribeWith(new ResourceSubscriber<>) // in case of flowable
或者,
.subscribeWith(new DisposableSubscriber<>)
而在(observable
)的情况下使用
.subscribeWith(new ResourceObserver<>)