将 Observables 收集到列表中似乎不会立即发出集合

2024-01-08

我使用 RxJava 来收集单独发出的 Observables 列表,并将它们组合成一个 Observables 列表(本质上与 flatMap 相反)。这是我的代码:

        // myEvent.findMemberships() returns an Observable<List<Membership>>

        myEvent.findMemberships()
             .flatMap(new Func1<List<Membership>, Observable<User>>() {
               @Override
               public Observable<User> call(List<Membership> memberships) {
                 List<User> users = new ArrayList<User>();
                 for (Membership membership : memberships) {
                   users.add(membership.getUser());
                 }
                 return Observable.from(users);
               }
             })
             .toList()
             .subscribeOn(Schedulers.newThread())
             .observeOn(AndroidSchedulers.mainThread())
             .subscribe(new Observer<List<User>>() {
               @Override
               public void onCompleted() { }

               @Override
               public void onError(Throwable e) {
                 Timber.e(e, "Error when trying to get memberships");
               }

               @Override
               public void onNext(List<User> users) {
                 Timber.d("%d users emitted", users.size());
               }
             })

我注意到我的 onNext 从未被调用。我似乎无法理解这一点。如果我删除 .toList 调用并基本上输出各个用户(如下所示),它会通过发出每个项目来工作。

subscriptions //
    .add(currentEvent.findMemberships()
             .flatMap(new Func1<List<Membership>, Observable<User>>() {
               @Override
               public Observable<User> call(List<Membership> memberships) {
                 List<User> users = new ArrayList<User>();
                 for (Membership membership : memberships) {
                   users.add(membership.getUser());
                 }
                 return Observable.from(users);
               }
             })
             .subscribeOn(Schedulers.newThread())
             .observeOn(AndroidSchedulers.mainThread())
             .subscribe(new Observer<User>() {
               @Override
               public void onCompleted() { }

               @Override
               public void onError(Throwable e) {
                 Timber.e(e, "Error when trying to get memberships");
               }

               @Override
               public void onNext(User user) {
                 Timber.d("%d users emitted", user.getName());
               }
             }));

Q1.我对 .toList 的理解不正确吗?

Q2。如何组合一串单独发射的流Observable<Object>变成一个单一的Observable<List<Object>> ?

** EDIT

@kjones 完全解决了这个问题。我没有通过 findMemberships 调用来调用 onComplete 。我在下面添加了代码片段。我的真实用例有点复杂,有更多的转换,这就是为什么我需要使用 .toList 调用。正如 @zsxwing 也正确指出的那样,对于这个用例,一个简单的地图就足够了。

public Observable<List<Membership>> findMemberships() {
return Observable.create(new Observable.OnSubscribe<List<Membership>>() {
  @Override
  public void call(Subscriber<? super List<Membership>> subscriber) {
    try {
      // .....
      List<Membership> memberships = queryMyDb();

      subscriber.onNext(memberships);

      // BELOW STATEMENT FIXES THE PROBLEM ><
      // subscriber.onCompleted();

    } catch (SQLException e) {
      // ...
    }
  }
});

}


看起来像由myEvent.findMemberships()call 永远不会调用 onComplete。你能显示这段代码吗?

如果是这种情况,就可以解释您所看到的行为。这.toList()在所有项目都已发出(由 onComplete 发出信号)之前,不会发出列表。

你的第二个版本没有.toList(),将按如下方式进行:

.findMemberships()
    emits a single List<Membership>
.flatMap()
    transforms List<Membership> into a single List<User>
    Observable.from(users) creates an observable that emits each user
.subscribe()
    onNext() is called for each user
    onCompleted() is never called.

您的原始版本:

.findMemberships()
    emits a single List<Membership>
.flatMap()
    transforms List<Membership> into a single List<User>
    Observable.from(users) creates an observable that emits each user
.toList()
    buffers each User waiting for onCompleted() to be called
    onCompleted is never called because the .findMemberships Observable never completes

有几种解决方案:

1) 使findMemberShips()Observable 调用 onComplete。如果 Observable 返回的是findMemberShips()是一个 Rx 主题(PublishSubject、BehaviourSubject 等)

2) Use Observable.just()代替Observable.from()。你已经有一个List<User>在 .flatMap() 中,只需返回它即可。使用Observable.from(users)创建一个发出每个用户的 Observable。Observable.just(users)会创建一个发出单个信号的 ObservableList<User>。不需要.toList().

3) Use .map()代替.flatMap()。再次强调,不需要.toList()。由于每个List<Membership>转变为List<User>你只需要使用.map().

myEvent
    .findMemberships()
    .map(new Func1<List<Membership>, List<User>>() {
        @Override
        public List<User> call(List<Membership> memberships) {
            List<User> users = new ArrayList<User>();
            for (Membership membership : memberships) {
                users.add(membership.getUser());
            }
            return users;
         }
    })
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

将 Observables 收集到列表中似乎不会立即发出集合 的相关文章

  • 如何在android上的python kivy中关闭应用程序后使服务继续工作

    我希望我的服务在关闭应用程序后继续工作 但我做不到 我听说我应该使用startForeground 但如何在Python中做到这一点呢 应用程序代码 from kivy app import App from kivy uix floatl
  • 插入最大日期(独立于数据库)

    在我的本地设置中 我使用一个简单的 H2 数据库 托管 解决方案将有另一个 类似但不相同 数据库 我需要将最大可能日期插入到日期时间列中 我尝试使用 Instant MAX 但是 这会导致列中出现 169104626 12 11 20 08
  • OpenCV 中的 Gabor 内核参数

    我必须在我的应用程序中使用 Gabor 过滤器 但我不知道这个 OpenCV 方法参数值 我想对虹膜进行编码 启动 Gabor 过滤器并获取特征 我想对 12 组 Gabor 参数值执行此操作 然后我想计算 Hamming Dystans
  • 正则表达式拆分数字和字母组,不带空格

    如果我有一个像 11E12C108N 这样的字符串 它是字母组和数字组的串联 如何在中间没有分隔符空格字符的情况下分割它们 例如 我希望分割结果为 tokens 0 11 tokens 1 E tokens 2 12 tokens 3 C
  • Android在排序列表时忽略大小写

    我有一个名为路径的列表 我目前正在使用以下代码对字符串进行排序 java util Collections sort path 这工作正常 它对我的 列表进行排序 但是它以不同的方式处理第一个字母的情况 即它用大写字母对列表进行排序 然后用
  • 比较两个文本文件的最快方法是什么,不将移动的行视为不同

    我有两个文件非常大 每个文件有 50000 行 我需要比较这两个文件并识别更改 然而 问题是如果一条线出现在不同的位置 它不应该显示为不同的 例如 考虑这个文件A txt xxxxx yyyyy zzzzz 文件B txt zzzzz xx
  • JavaFX 中具有自定义内容的 ListView

    How i can make custom ListView with JavaFx for my app I need HBox with image and 2 Labels for each line listView 您可以通过查看
  • 我需要什么库才能在 Java 中访问这个 com.sun.image.codec.jpeg?

    我正在用java创建一个图像水印程序 并导入了以下内容 import com sun image codec jpeg JPEGCodec import com sun image codec jpeg JPEGEncodeParam im
  • Java 文件上传速度非常慢

    我构建了一个小型服务 它从 Android 设备接收图像并将其保存到 Amazon S3 存储桶中 代码非常简单 但是速度非常慢 事情是这样的 public synchronized static Response postCommentP
  • 画透明圆,外面填充

    我有一个地图视图 我想在其上画一个圆圈以聚焦于给定区域 但我希望圆圈倒转 也就是说 圆的内部不是被填充 而是透明的 其他所有部分都被填充 请参阅这张图片了解我的意思 http i imgur com zxIMZ png 上半部分显示了我可以
  • Hazelcast 分布式锁与 iMap

    我们目前使用 Hazelcast 3 1 5 我有一个简单的分布式锁定机制 应该可以跨多个 JVM 节点提供线程安全性 代码非常简单 private static HazelcastInstance hInst getHazelcastIn
  • hibernate锁等待超时超时;

    我正在使用 Hibernate 尝试模拟对数据库中同一行的 2 个并发更新 编辑 我将 em1 getTransaction commit 移至 em1 flush 之后我没有收到任何 StaleObjectException 两个事务已成
  • react-native run-android 失败并出现错误:任务 ':app:dexDebug' 执行失败

    我使用的是 Windows 8 1 和react native cli 1 0 0 and react native 0 31 0 添加后react native maps对于该项目 我运行了命令react native upgrade并给
  • Java整数双除法混淆[重复]

    这个问题在这里已经有答案了 方案1 int sum 30 double avg sum 4 result is 7 0 not 7 5 VS 方案2 int sum 30 double avg sum 4 0 Prints lns 7 5
  • 欧洲中部时间 14 日 3 月 30 日星期五 00:00:00 至 日/月/年

    我尝试解析格式日期Fri Mar 30 00 00 00 CET 14至 日 月 年 这是我的代码 SimpleDateFormat formatter new SimpleDateFormat dd MM yyyy System out
  • 如何知道抛出了哪个异常

    我正在对我们的代码库进行审查 有很多这样的陈述 try doSomething catch Exception e 但我想要一种方法来知道 doSomething 抛出了哪个异常 在 doSomething 的实现中没有 throw 语句
  • Cucumber Java 与 Spring Boot 集成 - Spring @Autowired 抛出 NullPointer 异常

    我正在为 Spring boot 应用程序编写 cucumber java 单元测试来测试每个功能 当我与 Spring Boot 集成时 Autowired 类抛出 NullPointer 异常 Spring Boot应用程序类 Spri
  • Trie 数据结构 - Java [关闭]

    Closed 这个问题不符合堆栈溢出指南 help closed questions 目前不接受答案 是否有任何库或文档 链接提供了在 java 中实现 Trie 数据结构的更多信息 任何帮助都会很棒 Thanks 你可以阅读Java特里树
  • ServletContainer 类未找到异常

    我无法再编译我的球衣项目 并且出现以下异常 GRAVE Servlet Project API threw load exception java lang ClassNotFoundException com sun jersey spi
  • 如何在 JFreeChart 中设置多个系列的线条粗细?

    我创建了很多图表 在他们每个人中我都需要打电话 renderer setSeriesStroke i new BasicStroke 2 0f 对于每个系列 renderer is chart getXYPlot getRenderer 我

随机推荐