有什么方法可以控制 Spring 批次的剩余项目?

Any Way to Control Remaining Item on Spring Batch?

如果我有这样的物品

-> [1,2,3,4,5,6,7,8,9,10]

如果 ChunkSize =3,spring 批处理 ItemReader 读取 item like

[1,2,3]
[4,5,6]
[7,8,9]
[10]

但是,我想

[1,2,3]
[4,5,6]
[7,8,9,10]

有什么办法吗?

您可以通过检查结果中最后一项的大小来进行调整,如果它小于 chunkSize,则将其附加到结果的 second-last 项:

fun main() {
    val l = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
    val chunkSize = 3
    val c = l.chunked(chunkSize)
        .let {
            println(it)  // basic chunked result
            if (it.size >= 2 && it.last().size < chunkSize)
                it.dropLast(2) + listOf(it.takeLast(2).flatten())
            else
                it
        }
    println(c)
}

listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) 的输出:

[[1, 2, 3], [4, 5, 6], [7, 8, 9], [10]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9, 10]]

输出完全正确的结束块,listOf(1, 2, 3, 4, 5, 6, 7, 8, 9):

[[1, 2, 3], [4, 5, 6], [7, 8, 9]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9]]

这是一个使用泛型实现的扩展函数,因此对任何类型的 Iterables 进行分块 + 合并:

fun <T> Iterable<T>.chunkedMergeSmall(chunkSize: Int) =
    chunked(chunkSize)
    .let {
        println(it)
        if (it.size >= 2 && it.last().size < chunkSize)
            it.dropLast(2) + listOf(it.takeLast(2).flatten())
        else
            it
    }

// println(list.chunkedMergeSmall(3))
for (i in 1..12) {   // added for testing

  val list = IntArray(i) { it + 1 }.toList()

  val result = list
    .chunked(3)
    .groupBy { it.count() }
    .run {
      values.flatten().run {
        when (keys.size) {
          1    -> this
          else -> dropLast(2).plusElement(takeLast(2).flatten())
        }
      }
    }

  println(result)

}

测试输出:

[[1]]
[[1, 2]]
[[1, 2, 3]]
[[1, 2, 3, 4]]
[[1, 2, 3, 4, 5]]
[[1, 2, 3], [4, 5, 6]]
[[1, 2, 3], [4, 5, 6, 7]]
[[1, 2, 3], [4, 5, 6, 7, 8]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9, 10]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9, 10, 11]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12]]