Antonio Padua
Antonio Padua

Reputation: 113

Arrayformula to find overlaps in date ranges

In a previous question that can be find here, the following formula to find overlaps in date ranges was kindly provided by Mr Shane:

=ARRAYFORMULA(TEXTJOIN(", ",TRUE,IF(($A1<=$B$1:$B$5)*($B1>=$A$1:$A$5)*($C1=$C$1:$C$5),IF(ROW($A$1:$A$5)=ROW(),"","Row"&ROW($A$1:$A$5)),"")))

When dragged down, it's result is (column D):

# A B C D
1 01/01/2022 02/01/2022 Task1 Row3
2 01/15/2022 02/15/2022 Task2
3 01/29/2022 02/03/2022 Task1 Row1, Row3
4 01/18/2022 02/22/2022 Task3
5 02/02/2022 02/15/2022 Task1 Row3

Link to the sheet

The question is: could it be replaced by an arrayformula?

Upvotes: 2

Views: 222

Answers (1)

SputnikDrunk2
SputnikDrunk2

Reputation: 4038

SUGGESTION

Perhaps you can use a Custom Google Sheet Function (=findOverlaps()) using a script to mimic the ARRAYFORMULA behaviour. You may check this sample script below that you can add as a bound script in your spreadsheet file:

Follow this quick guide on how to add a bound script in your spreadsheet.

Custom Function Script

function findOverlaps(arr) {
  var res = [];
  var filtered = arr.filter((data,index)=>{
                 return data[2] == arr.map((data)=>{return data[2]}).filter((a, i, aa) => aa.indexOf(a) === i && aa.lastIndexOf(a) !== i) ? data.push((parseInt(index)+1)) : null;
  });

  filtered.map((data,index)=>{
    for(var x=0; x < 2; x++){
      filtered.map((check)=>{
        res.push([arr.map((data)=>{return data[2]}).filter((a, i, aa) => aa.indexOf(a) === i && aa.lastIndexOf(a) !== i).join(''),data[3],dateRangeOverlaps((filtered[parseInt(index)][x]),check[0],check[1], check[3])]);
      });
    }
  });

  res = res.filter((z)=>{return z[0] == 'Task1' && z[2] != 'x' ? z[2] : ''});

  return arr.map((x,index)=>{
    return res.map((look)=>{
      if((parseInt(index)+1) == look[1]){
        return "Row"+look[2];
      }
    }).filter((fn)=>{return fn}).join(', ')
  });

}

function dateRangeOverlaps(currentDateToCheck, startDate, endDate, row) {
    return (currentDateToCheck > startDate && currentDateToCheck < endDate) ? row : 'x'
}

Demonstration

See this sample: enter image description here

Upvotes: 2

Related Questions