GroupBy

拿第一个例子开始,我们安装的应用程序列表按照字母表的顺序排序。然而,如果现在我们想按照最近更新日期来排序我们的App时该怎么办?RxJava提供了一个有用的函数从列表中按照指定的规则:groupBy()来分组元素。下图中的例子展示了groupBy()如何将发射的值根据他们的形状来进行分组。

GroupBy - 图1

这个函数将源Observable变换成一个发射Observables的新的Observable。它们中的每一个新的Observable都发射一组指定的数据。

为了创建一个分组了的已安装应用列表,我们在loadList()函数中引入了一个新的元素:

  1. Observable<GroupedObservable<String,AppInfo>> groupedItems = Observable.from(apps)
  2. .groupBy(new Func1<AppInfo,String>(){
  3. @Override
  4. public String call(AppInfo appInfo){
  5. SimpleDateFormat formatter = new SimpleDateFormat("MM/yyyy");
  6. return formatter.format(new Date(appInfo.getLastUpdateTime()));
  7. }
  8. });

现在我们创建了一个新的Observable,groupedItems,它将会发射一个带有GroupedObservable的序列。GroupedObservable是一个特殊的Observable,它源自一个分组的key。在这个例子中,key就是String,代表的意思是Month/Year格式化的最近更新日期。

这一点,我们已经创建了几个发射AppInfo数据的Observable,用来填充我们的列表。我们想保留字母排序和分组排序。我们将创建一个新的Observable将所有的联系起来,像往常一样然后订阅它:

  1. Observable.concat(groupedItems)
  2. .subscribe(new Observer<AppInfo>() {
  3. @Override
  4. public void onCompleted() {
  5. mSwipeRefreshLayout.setRefreshing(false);
  6. }
  7. @Override
  8. public void onError(Throwable e) {
  9. Toast.makeText(getActivity(), "Something went wrong!", Toast.LENGTH_SHORT).show();
  10. mSwipeRefreshLayout.setRefreshing(false);
  11. }
  12. @Override
  13. public void onNext(AppInfo appInfo) {
  14. mAddedApps.add(appInfo);
  15. mAdapter.addApplication(mAddedApps.size() - 1,appInfo);
  16. }
  17. });

我们的loadList()函数完成了,结果是:

GroupBy - 图2