Suggestion: drop your ArrayList
and go with SortedMap
s. We are supposing two things here:
- your start and end times are
long
(note: code written for Java 7);
- your
GameWindow
class implements .equals()
and .hashCode()
correctly.
Given these prerequisites, write a dedicated class (say, GameWindowList
or something) in which you declare:
final SortedMap<Long, List<GameWindow>> startTimes = new TreeMap<>();
final SortedMap<Long, List<GameWindow>> endTimes = new TreeMap<>();
Adding a window is then:
public void addGameWindow(final GameWindow window)
{
final long startTime = window.startTime();
final long endTime = window.endTime();
List<GameWindow> list;
// Insert in start times
list = startTimes.get(startTime);
if (list == null) {
list = new ArrayList<>();
startTimes.put(startTime, list);
}
list.add(window);
// Insert in end times
list = endTimes.get(endTime);
if (list == null) {
list = new ArrayList<>();
endTimes.put(endTime, list);
}
list.add(window);
}
Looking the windows for a given time is then:
public List<GameWindow> getWindowsForTime(final long time)
{
// Submap of start times where the time is lower than or equal to
// the requested time
final SortedMap<Long, List<GameWindow>> validStartTimes
= startTimes.headMap(time);
// Submap of end times where the time is greater than or equal to
// the requested time
final SortedMap<Long, List<GameWindow>> validEndTimes
= endTimes.tailMap(time);
// Why GameWindow must implement equals and hashCode
final Set<GameWindow> startSet = new HashSet<>();
final Set<GameWindow> endSet = new HashSet<>();
// Insert into the start set all game windows whose start time
// is less than or equal to the requested time
for (final List<GameWindow> list: startTimes.headMap(time).values())
startSet.addAll(list);
// Insert into the end set all game windows whose end time
// is greater than or equal to the requested time
for (final List<GameWindow> list: endTimes.tailMap(time).values())
endSet.addAll(list);
// Only retain the intersection of both sets
startSet.retainAll(endSet);
// Return the result
return new ArrayList<>(startSet);
}
The two key elements are:
SortedMap
's .{tail,end}Map()
filter out immediately all windows whose either start or end time are not legal;
HashSet
is used to retain only the intersection of windows for which both the start time and end time are legal; hence the importance of GameWindow
implementing hashCode()
and equals()
.