Java List拆分工具

将List拆分为多个子列表的工具,支持指定子列表长度或者子列表个数。

工具源码ListUtils:
package com.visy.utils;

import org.apache.commons.collections.CollectionUtils;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

public class ListUtils {
    /**
     * 将List拆分为多个指定长度的子列表
     * @param list 原始列表
     * @param size 子列表长度(元素个数)
     * 范围:1 <= size <= list.size()
     * 最后一个子列表长度可能 < size
     * @return 子列表集合
     * @param <T> 元素类型
     */
    public static <T> List<List<T>> splitBySize(List<T> list, int size){
        List<List<T>> resultList = new ArrayList<>();
        if(CollectionUtils.isEmpty(list)){
            return resultList;
        }

        //总的元素个数
        int total = list.size();

        if(size >= total){
            resultList.add(list);
            return resultList;
        }else if(size < 1){
            //元素个数最少1个
            size = 1;
        }

        //计算子列表个数
        int count = total/size + (total%size>0 ? 1 : 0);

        //把原始列表按指定大小拆分为多个List
        for(int i=0; i<count; i++) {
            int start = i*size, end = i==count-1 ? total : (i+1)*size;
            resultList.add(list.subList(start, end));
        }
        
        //返回拆分后的结果
        return resultList;
    }

    /**
     * 将List拆分为指定个数的子列表
     * @param list 原始列表
     * @param count 子列表个数
     * 范围:1 <= count <= list.size()
     * 子列表分配元素有余时,前N个子列表可能会多分1个元素,这样能保证尽量的均匀
     * @return 子列表集合
     * @param <T> 元素类型
     */
    public static <T> List<List<T>> splitByCount(List<T> list, int count){
        List<List<T>> resultList = new ArrayList<>();
        if(CollectionUtils.isEmpty(list)){
            return resultList;
        }
 
        //总的元素个数
        int total = list.size();

        //计算子列表分配的元素个数,以及平均分配后剩余的元素个数
        int size, sizeMod=0;
        if(count <= 1){ //至少拆分1个子列表
            resultList.add(list);
            return resultList;
        }else if(count >= total){ //每个子列表放1个元素可能不够分
            //则拆分为total个子列表, 分空的子列表没有意义
            count = total;
            //每个子列表分1个元素
            size = 1;
        }else{
            //计算每个子列表能够分到的元素个数(平均)
            size = total / count;
            //平均后多余的元素个数
            sizeMod = total % count;
        }

        int offset = 0;
        for(int i=0; i<count; i++) {
            int actualSize = size;
            if(sizeMod > 0){
                //前sizeMod个子列表多分1个元素,保证尽量均匀
                actualSize ++;
                sizeMod --;
            }
            int end = i==count-1 ? total : offset+actualSize;
            resultList.add(list.subList(offset, end));
            offset = end; //重置偏移位置
        }

        //返回拆分后的结果
        return resultList;
    }

    public static void main(String[] args) {

        List<Integer> emptyList = new ArrayList<>();
        List<Integer> list = Arrays.asList(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15);

        System.out.println(splitBySize(null, 3));
        System.out.println(splitBySize(emptyList, 3));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitBySize(list, -1));
        System.out.println(splitBySize(list, 0));
        System.out.println(splitBySize(list, 1));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitBySize(list, 15));
        System.out.println(splitBySize(list, 16));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitBySize(list, 5));
        System.out.println(splitBySize(list, 3));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitBySize(list, 4));
        System.out.println(splitBySize(list, 7));
        System.out.println("=====================================================================");
        System.out.println(splitByCount(null, 3));
        System.out.println(splitByCount(emptyList, 3));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitByCount(list, -1));
        System.out.println(splitByCount(list, 0));
        System.out.println(splitByCount(list, 1));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitByCount(list, 15));
        System.out.println(splitByCount(list, 16));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitByCount(list, 5));
        System.out.println(splitByCount(list, 3));
        System.out.println("---------------------------------------------------------------------");
        System.out.println(splitByCount(list, 4));
        System.out.println(splitByCount(list, 7));
    }
}
测试输出:
[]
[]
---------------------------------------------------------------------
[[1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11], [12], [13], [14], [15]]
[[1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11], [12], [13], [14], [15]]
[[1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11], [12], [13], [14], [15]]
---------------------------------------------------------------------
[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]]
[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]]
---------------------------------------------------------------------
[[1, 2, 3, 4, 5], [6, 7, 8, 9, 10], [11, 12, 13, 14, 15]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12], [13, 14, 15]]
---------------------------------------------------------------------
[[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15]]
[[1, 2, 3, 4, 5, 6, 7], [8, 9, 10, 11, 12, 13, 14], [15]]
=====================================================================
[]
[]
---------------------------------------------------------------------
[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]]
[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]]
[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]]
---------------------------------------------------------------------
[[1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11], [12], [13], [14], [15]]
[[1], [2], [3], [4], [5], [6], [7], [8], [9], [10], [11], [12], [13], [14], [15]]
---------------------------------------------------------------------
[[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12], [13, 14, 15]]
[[1, 2, 3, 4, 5], [6, 7, 8, 9, 10], [11, 12, 13, 14, 15]]
---------------------------------------------------------------------
[[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15]]
[[1, 2, 3], [4, 5], [6, 7], [8, 9], [10, 11], [12, 13], [14, 15]]

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值