美文网首页
[Guava]-使用Iterators进行分组时遇见的坑

[Guava]-使用Iterators进行分组时遇见的坑

作者: 程序员驿站 | 来源:发表于2018-04-03 15:12 被阅读167次

平常我们需要对一个大的list进行分批操作,一般使用Iterators#partition和paddedPartition方法(也可以使用Lists#partition)具体使用方式:

List<Order> result = Lists.newArrayListWithCapacity(orders.size());
for (List<String> orderList : Iterables.paddedPartition(orders, DEFAULT_MAX_SIZE)) {
    //doSomething.....
}

使用paddedPartition会出现一个问题,当最后一批的数据小于DEFAULT_MAX_SIZE时候,会把剩下的数据填充为null,比如

list = [1,2,3,4,5] -------paddedPartition(list,3)-------->[[1,2],[3,4],[5,null]]

我们看下源码

public static <T> UnmodifiableIterator<List<T>> paddedPartition(Iterator<T> iterator, int size) {
    return partitionImpl(iterator, size, true);
  }

  private static <T> UnmodifiableIterator<List<T>> partitionImpl(
      final Iterator<T> iterator, final int size, final boolean pad) {
    checkNotNull(iterator);
    checkArgument(size > 0);
    return new UnmodifiableIterator<List<T>>() {
      @Override
      public boolean hasNext() {
        return iterator.hasNext();
      }

      @Override
      public List<T> next() {
        if (!hasNext()) {
          throw new NoSuchElementException();
        }
        Object[] array = new Object[size];
        int count = 0;
        for (; count < size && iterator.hasNext(); count++) {
          array[count] = iterator.next();
        }
        for (int i = count; i < size; i++) {
          array[i] = null; // 这里重点,在这一步会判断下最后一页的剩余数据设置为null
        }

        @SuppressWarnings("unchecked") // we only put Ts in it
        List<T> list = Collections.unmodifiableList((List<T>) Arrays.asList(array));
      // 这里会根据pad 判断是否返回list 还会 重新生成一个list 
        return (pad || count == size) ? list : list.subList(0, count);
      }
    };
  }

我们再看下他的孪生的方法

 public static <T> UnmodifiableIterator<List<T>> partition(Iterator<T> iterator, int size) {
    return partitionImpl(iterator, size, false);
  }

都是使用的同一个方法 一个pad(填充)设置为true,一个设置的false

另外,上面我们提到过Lists#partition的方法,他的做法是构建两个新的类实现的

public static <T> List<List<T>> partition(List<T> list, int size) {
    checkNotNull(list);
    checkArgument(size > 0);
    return (list instanceof RandomAccess)
        ? new RandomAccessPartition<T>(list, size)
        : new Partition<T>(list, size);
  }

相关文章

  • [Guava]-使用Iterators进行分组时遇见的坑

    平常我们需要对一个大的list进行分批操作,一般使用Iterators#partition和paddedParti...

  • Laravel groupBy用法

    Laravel使用查询构建器(Laravel Eloquent)进行分组的演示,有一个小坑吧。 其中groupBy...

  • SQL分组查询

    一.分组查询 1.使用group by进行分组查询 在使用group by关键字时,在select列表中可以指定的...

  • (8)依赖管理

    依赖分组 Gradle将对依赖进行分组,比如编译Java时使用的是这组依赖,运行Java时又可以使用另一组依赖。每...

  • iOS11 cell 间距拉伸问题

    在 iOS11时,当我们在使用 tableView 进行分组时( style:UITableViewStyleG...

  • [21] 《R数据科学》分组

    按多个变量分组 当使用多个变量进行分组时,每次统计摘要会用掉一个分组变量,这样就可以对数据集进行循序渐进的分析: ...

  • 分组密码DES

    分组密码的原理 DES是分组密码,分组密码将消息进行等长分组,使用同一密钥对每个分组进行加密。 DES算法 DES...

  • 8. 分组数据

    分组数据 使用分组可将数据分为多个逻辑组,对每个组进行聚集计算。 创建分组 分组使用SELECT 语句的GROUP...

  • 如何取消已经提交的Spark任务

    使用一个SparkContext时,可以针对不同的Job进行分组提交和取消: 分组提交任务 为了防止其他任务被取消...

  • (Boolan)STL与泛型编程学习笔记(第二周)

    STL整体结构 STL主要由六部分组成,分别为容器(containers)、迭代器(iterators)、空间配置...

网友评论

      本文标题:[Guava]-使用Iterators进行分组时遇见的坑

      本文链接:https://www.haomeiwen.com/subject/sxtchftx.html