BatchUtil.java 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. package com.energy.online.data.service.util;
  2. import java.util.*;
  3. import java.util.function.BiConsumer;
  4. import java.util.function.BiFunction;
  5. import java.util.function.Consumer;
  6. import java.util.function.Function;
  7. import java.util.stream.Collectors;
  8. /**
  9. * 批量处理工具
  10. *
  11. * @author wangwenbing
  12. * @date 2022-03-29
  13. */
  14. public class BatchUtil {
  15. /**
  16. * 分批处理
  17. *
  18. * @param data 要处理的数据
  19. * @param batchNum 每次处理数量
  20. * @param consumer 处理方法
  21. * @param <T>
  22. * @return
  23. */
  24. public static <T> void batchHandle(List<T> data, int batchNum, Consumer<List<T>> consumer){
  25. if (data == null || data.isEmpty()) {
  26. return;
  27. }
  28. int len = data.size();
  29. int fromIdx = 0;
  30. int toIdx = batchNum;
  31. List<T> partialData = null;
  32. while (true) {
  33. toIdx = toIdx > len ? len : toIdx;
  34. partialData = data.subList(fromIdx, toIdx);
  35. if (partialData.isEmpty()) {
  36. break;
  37. }
  38. fromIdx = toIdx;
  39. toIdx = fromIdx + batchNum;
  40. consumer.accept(partialData);
  41. }
  42. }
  43. /**
  44. * 提取新增数据
  45. *
  46. * @param newData
  47. * @param oldData
  48. * @return
  49. */
  50. public static <T> List<T> filterInsertData(
  51. List<T> newData, List<T> oldData, Function<T, Object> keyFunction) {
  52. Set<Object> newKeys = newData.stream().map(e -> keyFunction.apply(e)).collect(Collectors.toSet());
  53. Set<Object> oldKeys = oldData.stream().map(e -> keyFunction.apply(e)).collect(Collectors.toSet());
  54. Set<Object> needInsertKeys = new HashSet<>(newKeys);
  55. needInsertKeys.removeAll(oldKeys);
  56. List<T> result = new ArrayList<>();
  57. newData.stream().forEach(e -> {
  58. Object key = keyFunction.apply(e);
  59. if (needInsertKeys.contains(key)) {
  60. result.add(e);
  61. }
  62. });
  63. return result;
  64. }
  65. /**
  66. * 提取更新数据
  67. *
  68. * @param newData
  69. * @param oldData
  70. * @param keyFunction
  71. * @param isChange old,new
  72. * @param idSetter
  73. * @param idGetter
  74. * @return
  75. */
  76. public static <T, ID> List<T> filterUpdateData(
  77. List<T> newData, List<T> oldData,
  78. Function<T, Object> keyFunction,
  79. BiFunction<T, T, Boolean> isChange,
  80. BiConsumer<T, ID> idSetter,
  81. Function<T, ID> idGetter) {
  82. Set<Object> newKeys = newData.stream().map(e -> keyFunction.apply(e)).collect(Collectors.toSet());
  83. Set<Object> oldKeys = oldData.stream().map(e -> keyFunction.apply(e)).collect(Collectors.toSet());
  84. Map<Object, T> oldDataMap = oldData
  85. .stream().collect(Collectors.toMap(e -> keyFunction.apply(e), e -> e, (o, n) -> n));
  86. Set<Object> needUpdateKeys = new HashSet<>(newKeys);
  87. needUpdateKeys.retainAll(oldKeys);
  88. List<T> result = new ArrayList<>();
  89. newData.stream().forEach(e -> {
  90. Object key = keyFunction.apply(e);
  91. if (needUpdateKeys.contains(key)) {
  92. T oldRecord = oldDataMap.get(key);
  93. if (oldRecord != null && isChange.apply(oldRecord, e)) {
  94. idSetter.accept(e, idGetter.apply(oldRecord));
  95. result.add(e);
  96. }
  97. }
  98. });
  99. return result;
  100. }
  101. /**
  102. * 提取删除数据
  103. *
  104. * @param newData
  105. * @param oldData
  106. * @return
  107. */
  108. public static <T> List<T> filterDeleteData(
  109. List<T> newData, List<T> oldData, Function<T, Object> keyFunction) {
  110. Set<Object> newKeys = newData.stream().map(e -> keyFunction.apply(e)).collect(Collectors.toSet());
  111. Set<Object> oldKeys = oldData.stream().map(e -> keyFunction.apply(e)).collect(Collectors.toSet());
  112. Set<Object> needDeleteKeys = new HashSet<>(oldKeys);
  113. needDeleteKeys.removeAll(newKeys);
  114. List<T> result = new ArrayList<>();
  115. oldData.stream().forEach(e -> {
  116. Object key = keyFunction.apply(e);
  117. if (needDeleteKeys.contains(key)) {
  118. result.add(e);
  119. }
  120. });
  121. return result;
  122. }
  123. }