List has custom object with overlap date ranges need to break all overlap ranges into new periods and keep non overlap AS IS in java

65 views Asked by At

Consider below example , inputList has overlap date ranges

        inputList.add(new DateRange(LocalDate.of(2023, 7, 1), LocalDate.of(2023, 7, 10)));
        inputList.add(new DateRange(LocalDate.of(2023, 7, 5), LocalDate.of(2023, 7, 30)));
        inputList.add(new DateRange(LocalDate.of(2023, 7, 10), LocalDate.of(2023, 7, 20)));
        inputList.add(new DateRange(LocalDate.of(2023, 7, 15), LocalDate.of(2023, 7, 20)));
        inputList.add(new DateRange(LocalDate.of(2023, 8, 1), LocalDate.of(2023, 8, 20)));

Need to merge all overlap period and keep remaining non overlap period in resultList

        resultList(new DateRange(LocalDate.of(2023, 7, 1), LocalDate.of(2023, 7, 04)));
         resultLis(new DateRange(LocalDate.of(2023, 7, 5), LocalDate.of(2023, 7, 09)));
         resultLis(new DateRange(LocalDate.of(2023, 7, 10), LocalDate.of(2023, 7, 10)));
         resultLis(new DateRange(LocalDate.of(2023, 7, 11), LocalDate.of(2023, 7, 14)));
         resultLis(new DateRange(LocalDate.of(2023, 7, 15), LocalDate.of(2023, 7, 20)));
         resultLis(new DateRange(LocalDate.of(2023, 7, 21), LocalDate.of(2023, 7, 30)));
         resultLis(new DateRange(LocalDate.of(2023, 8, 1), LocalDate.of(2023, 8, 20)));

With below code after overlap periods not splitting

class DateRange {
    LocalDate start;
    LocalDate end;

    public DateRange(LocalDate start, LocalDate end) {
        this.start = start;
        this.end = end;
    }

    @Override
    public String toString() {
        return "DateRange [start=" + start + ", end=" + end + "]";
    }
}

public class Main1 {
    public static void main(String[] args) {
        List<DateRange> inputList = new ArrayList<>();
        inputList.add(new DateRange(LocalDate.of(2023, 7, 1), LocalDate.of(2023, 7, 10)));
        inputList.add(new DateRange(LocalDate.of(2023, 7, 5), LocalDate.of(2023, 7, 30)));
        inputList.add(new DateRange(LocalDate.of(2023, 7, 10), LocalDate.of(2023, 7, 20)));
        inputList.add(new DateRange(LocalDate.of(2023, 7, 15), LocalDate.of(2023, 7, 20)));
        inputList.add(new DateRange(LocalDate.of(2023, 8, 1), LocalDate.of(2023, 8, 20)));

        List<DateRange> resultList = processDateRanges(inputList);
        resultList.forEach(System.out::println);
    }
    public static List<DateRange> processDateRanges(List<DateRange> inputList) {
        List<DateRange> result = new ArrayList<>();
        Collections.sort(inputList, Comparator.comparing(r -> r.start));

        for (int i = 0; i < inputList.size(); i++) {
            DateRange current = inputList.get(i);
            LocalDate start = current.start;
            LocalDate end = current.end;

            for (int j = i + 1; j < inputList.size(); j++) {
                DateRange next = inputList.get(j);
                if (next.start.isAfter(end.plusDays(1))) break;

                if (next.start.isAfter(start)) {
                    result.add(new DateRange(start, next.start.minusDays(1)));
                }
                if (next.end.isBefore(end)) {
                    result.add(new DateRange(next.start, next.end));
                    start = next.end.plusDays(1);
                } else {
                    start = next.start;
                    end = next.end;
                }
            }
            result.add(new DateRange(start, end));
            while (i + 1 < inputList.size() && inputList.get(i + 1).start.isBefore(end.plusDays(1))) {
                i++;
            }
        }

        return result;
    }

}

Getting output as

  1. 2023-07-01 - 2023-07-04
  2. 2023-07-05 - 2023-07-09
  3. 2023-07-10 - 2023-07-20
  4. 2023-07-15 - 2023-07-20
  5. 2023-07-21 - 2023-07-30
  6. 2023-08-01 - 2023-08-20

Expecting as below

  1. 2023-07-01 - 2023-07-04 - Before overlap period of 1st record
  2. 2023-07-05 - 2023-07-09 - overlap with 1st and 2nd record
  3. 2023-07-10 - 2023-07-10 - overlap with 1st, 2nd and 3rd record
  4. 2023-07-11 - 2023-07-14 - overlap with 2nd and 3rd record
  5. 2023-07-15 - 2023-07-20 - overlap with 2nd , 3rd and 4th record
  6. 2023-07-21 - 2023-07-30 - after overlap period of 2nd record
  7. 2023-08-01 - 2023-08-20 - Non overlap period
0

There are 0 answers