Compare commits
11 Commits
542c093222
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
886de3df55 | ||
|
|
145682e44f | ||
|
|
e28e179e2b | ||
|
|
6b7eda244c | ||
|
|
c9523a9a23 | ||
|
|
457804d251 | ||
|
|
ff10df17c3 | ||
|
|
2df2500b77 | ||
|
|
427e963cac | ||
|
|
335854583e | ||
|
|
26e9858ca3 |
@@ -28,8 +28,7 @@ public class APFactory implements AbstractAPFactory {
|
||||
|
||||
@Override
|
||||
public LocalDayPlan createLocalDayPlan(LocalDay day, Instant start, Instant end) {
|
||||
// TODO Return an instance of your class that implements LocalDayPlan
|
||||
return null;
|
||||
return new LocalDayPlanImpl(day, start, end);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -12,6 +12,13 @@ public class AppointmentImpl implements Appointment {
|
||||
|
||||
private AppointmentRequest request;
|
||||
|
||||
public AppointmentImpl(Instant start, AppointmentRequest request) {
|
||||
this.start = start;
|
||||
this.request = request;
|
||||
|
||||
this.stop = start.plus(request.duration());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Instant start() {
|
||||
return start;
|
||||
|
||||
@@ -3,6 +3,7 @@ package appointmentplanner;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.time.LocalTime;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.function.Predicate;
|
||||
@@ -19,7 +20,7 @@ import appointmentplanner.customlist.api.CustomLinkedList;
|
||||
|
||||
public class LocalDayPlanImpl implements LocalDayPlan {
|
||||
|
||||
private CustomLinkedList<AppointmentImpl> timeline = new CustomLinkedListImpl<>();
|
||||
private CustomLinkedList<Appointment> timeline = new CustomLinkedListImpl<>();
|
||||
|
||||
public LocalDayPlanImpl(LocalDay day, Instant start, Instant end) {
|
||||
this.day = day;
|
||||
@@ -55,8 +56,7 @@ public class LocalDayPlanImpl implements LocalDayPlan {
|
||||
|
||||
@Override
|
||||
public Optional<Appointment> addAppointment(AppointmentData appointmentData, LocalTime startTime) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'addAppointment'");
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -67,20 +67,25 @@ public class LocalDayPlanImpl implements LocalDayPlan {
|
||||
|
||||
@Override
|
||||
public AppointmentRequest removeAppointment(Appointment appointment) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'removeAppointment'");
|
||||
Appointment removedItem = timeline.remove(appointment);
|
||||
return removedItem == null ? null : removedItem.request();
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<AppointmentRequest> removeAppointments(Predicate<Appointment> filter) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'removeAppointments'");
|
||||
|
||||
CustomLinkedList<AppointmentRequest> removedRequests = new CustomLinkedListImpl<>();
|
||||
|
||||
for (Appointment appointment : timeline.removeFound(filter)) {
|
||||
removedRequests.add(appointment.request());
|
||||
}
|
||||
|
||||
return removedRequests.toArrayList();
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Appointment> appointments() {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'appointments'");
|
||||
return timeline.toArrayList();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -89,28 +94,46 @@ public class LocalDayPlanImpl implements LocalDayPlan {
|
||||
throw new UnsupportedOperationException("Unimplemented method 'findMatchingFreeSlotsOfDuration'");
|
||||
}
|
||||
|
||||
private CustomLinkedList<TimeSlot> traverseGapsFitting(Duration toFind, CustomLinkedList<TimeSlot> goodSlots,
|
||||
Instant startOfBefore, Iterator<Appointment> iterator) {
|
||||
|
||||
boolean hasNext = iterator.hasNext();
|
||||
|
||||
Appointment nextAppointment = hasNext ? iterator.next() : null;
|
||||
|
||||
TimeSlot possibleFittingSlot = new TimeSlotImpl(hasNext ? nextAppointment.end() : startOfDay(),
|
||||
startOfBefore == null ? endOfDay() : startOfBefore);
|
||||
|
||||
if (possibleFittingSlot.fits(toFind)) {
|
||||
goodSlots.add(possibleFittingSlot);
|
||||
}
|
||||
|
||||
if (!hasNext) {
|
||||
return goodSlots;
|
||||
}
|
||||
|
||||
return traverseGapsFitting(toFind, goodSlots, nextAppointment.start(), iterator);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TimeSlot> findGapsFitting(Duration duration) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'findGapsFitting'");
|
||||
return traverseGapsFitting(duration, new CustomLinkedListImpl<>(), null, timeline.iterator()).toArrayList();
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Appointment> findAppointments(Predicate<Appointment> filter) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'findAppointments'");
|
||||
return timeline.find(filter).toArrayList();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean contains(Appointment appointment) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'contains'");
|
||||
return timeline.contains(appointment);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int nrOfAppointments() {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'nrOfAppointments'");
|
||||
return timeline.size();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
package appointmentplanner;
|
||||
|
||||
import java.time.Instant;
|
||||
|
||||
import appointmentplanner.api.TimeSlot;
|
||||
|
||||
public class TimeSlotImpl implements TimeSlot {
|
||||
|
||||
private Instant start;
|
||||
private Instant end;
|
||||
|
||||
public TimeSlotImpl(Instant start, Instant end) {
|
||||
this.start = start;
|
||||
this.end = end;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Instant start() {
|
||||
return start;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Instant end() {
|
||||
return end;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,6 +1,8 @@
|
||||
package appointmentplanner.customlist;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.function.Predicate;
|
||||
|
||||
import appointmentplanner.customlist.api.CustomLinkedList;
|
||||
|
||||
@@ -84,31 +86,32 @@ public class CustomLinkedListImpl<T> implements CustomLinkedList<T> {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void remove(T item) {
|
||||
public T remove(T item) {
|
||||
|
||||
if (head == null) {
|
||||
return;
|
||||
return null;
|
||||
}
|
||||
|
||||
if (head.getItem().equals(item)) {
|
||||
head = head.getNext();
|
||||
return;
|
||||
return item;
|
||||
}
|
||||
|
||||
CustomLinkedListNode<T> beforeNode = traverseFind(head, item, ItemPosition.BEFORE);
|
||||
|
||||
if (beforeNode == null) {
|
||||
return;
|
||||
return item;
|
||||
}
|
||||
|
||||
CustomLinkedListNode<T> nodeToRemove = beforeNode.getNext();
|
||||
|
||||
if (beforeNode.getNext() == null) {
|
||||
beforeNode.setNext(null);
|
||||
return;
|
||||
return item;
|
||||
}
|
||||
|
||||
beforeNode.setNext(nodeToRemove.getNext());
|
||||
return item;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -120,6 +123,7 @@ public class CustomLinkedListImpl<T> implements CustomLinkedList<T> {
|
||||
}
|
||||
|
||||
CustomLinkedListNode<T> nodeBefore = traverseFind(head, reference, ItemPosition.BEFORE);
|
||||
|
||||
CustomLinkedListNode<T> nodeToInsert = new CustomLinkedListNode<>(nodeBefore.getNext(), item);
|
||||
nodeBefore.setNext(nodeToInsert);
|
||||
}
|
||||
@@ -172,4 +176,48 @@ public class CustomLinkedListImpl<T> implements CustomLinkedList<T> {
|
||||
return recursiveSizeCalc(this.head, 1);
|
||||
}
|
||||
|
||||
private CustomLinkedList<T> traverseFilter(Predicate<T> filter, CustomLinkedListNode<T> node,
|
||||
CustomLinkedList<T> found) {
|
||||
|
||||
if (node == null) {
|
||||
return found;
|
||||
}
|
||||
|
||||
T item = node.getItem();
|
||||
|
||||
if (filter.test(item)) {
|
||||
found.add(item);
|
||||
}
|
||||
|
||||
return traverseFilter(filter, node.getNext(), found);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CustomLinkedList<T> find(Predicate<T> filter) {
|
||||
return traverseFilter(filter, head, new CustomLinkedListImpl<>());
|
||||
}
|
||||
|
||||
@Override
|
||||
public CustomLinkedList<T> removeFound(Predicate<T> filter) {
|
||||
CustomLinkedList<T> items = find(filter);
|
||||
for (T item : items) {
|
||||
remove(item);
|
||||
}
|
||||
return items;
|
||||
}
|
||||
|
||||
private ArrayList<T> mapToArrayList(CustomLinkedListNode<T> node, ArrayList<T> list) {
|
||||
if (node == null) {
|
||||
return list;
|
||||
}
|
||||
mapToArrayList(node.getNext(), list);
|
||||
list.add(node.getItem());
|
||||
return list;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ArrayList<T> toArrayList() {
|
||||
return mapToArrayList(head, new ArrayList<>());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -17,6 +17,9 @@ public class CustomLinkedListIterator<T> implements Iterator<T> {
|
||||
|
||||
@Override
|
||||
public boolean hasNext() {
|
||||
if (lastNode == null) {
|
||||
return false;
|
||||
}
|
||||
return lastNode.getNext() != null;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,157 +0,0 @@
|
||||
package appointmentplanner.customlist;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.ListIterator;
|
||||
|
||||
import appointmentplanner.customlist.api.*;
|
||||
|
||||
public class CustomListToJavaBinding<T> implements List<T> {
|
||||
|
||||
private CustomLinkedList<T> list;
|
||||
|
||||
public CustomListToJavaBinding(CustomLinkedList<T> list) {
|
||||
this.list = list;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean add(T arg0) {
|
||||
list.add(arg0);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void add(int arg0, T arg1) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Cannot add to exact index in linked list");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean addAll(Collection<? extends T> c) {
|
||||
c.stream().forEach(list::add);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean addAll(int index, Collection<? extends T> c) {
|
||||
throw new UnsupportedOperationException("Cannot add to exact index in linked list");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void clear() {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'clear'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsAll(Collection<?> c) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'containsAll'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public T get(int index) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'get'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public int indexOf(Object o) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'indexOf'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() {
|
||||
return list.size() == 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterator<T> iterator() {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'iterator'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public int lastIndexOf(Object o) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'lastIndexOf'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ListIterator<T> listIterator() {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'listIterator'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ListIterator<T> listIterator(int index) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'listIterator'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean remove(Object o) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'remove'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public T remove(int index) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'remove'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean removeAll(Collection<?> c) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'removeAll'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean retainAll(Collection<?> c) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'retainAll'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public T set(int arg0, T arg1) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'set'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public int size() {
|
||||
return list.size();
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<T> subList(int fromIndex, int toIndex) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'subList'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object[] toArray() {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'toArray'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T[] toArray(T[] arg0) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'toArray'");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean contains(Object o) {
|
||||
try {
|
||||
T bal = (T) o;
|
||||
return list.contains(bal);
|
||||
} catch (Exception e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
|
||||
package appointmentplanner.customlist.api;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.function.Predicate;
|
||||
|
||||
public interface CustomLinkedList<T> extends Iterable<T> {
|
||||
@@ -24,4 +25,6 @@ public interface CustomLinkedList<T> extends Iterable<T> {
|
||||
int size();
|
||||
|
||||
CustomLinkedList<T> find(Predicate<T> filter);
|
||||
|
||||
ArrayList<T> toArrayList();
|
||||
}
|
||||
|
||||
@@ -2,15 +2,19 @@ package appointmentplanner;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.util.List;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
import org.junit.jupiter.params.provider.MethodSource;
|
||||
|
||||
import appointmentplanner.api.LocalDay;
|
||||
import appointmentplanner.api.LocalDayPlan;
|
||||
import appointmentplanner.api.TimeSlot;
|
||||
|
||||
public class LocalDayPlanTest {
|
||||
|
||||
@@ -23,14 +27,14 @@ public class LocalDayPlanTest {
|
||||
|
||||
@ParameterizedTest
|
||||
@MethodSource("provideLocalDPDataset")
|
||||
void ldPlanInit_shouldBeSuccessful(LocalDay day, Instant start, Instant end) {
|
||||
void ldpInit_shouldBeSuccessful(LocalDay day, Instant start, Instant end) {
|
||||
LocalDayPlan plan = new LocalDayPlanImpl(day, start, end);
|
||||
assertThat(plan).isNotNull();
|
||||
}
|
||||
|
||||
@ParameterizedTest
|
||||
@MethodSource("provideLocalDPDataset")
|
||||
void ldPlanGetters_shouldReturnSetValues(LocalDay day, Instant start, Instant end) {
|
||||
void ldpGetters_shouldReturnSetValues(LocalDay day, Instant start, Instant end) {
|
||||
LocalDayPlan plan = new LocalDayPlanImpl(day, start, end);
|
||||
|
||||
assertThat(plan.day()).isEqualTo(day);
|
||||
@@ -40,9 +44,18 @@ public class LocalDayPlanTest {
|
||||
|
||||
@ParameterizedTest
|
||||
@MethodSource("provideLocalDPDataset")
|
||||
void ldToString_shouldReturnStringContainingLocalDateAndTimeZone(LocalDay day, Instant start, Instant end) {
|
||||
void ldpToString_shouldReturnStringContainingLocalDateAndTimeZone(LocalDay day, Instant start, Instant end) {
|
||||
LocalDayPlan plan = new LocalDayPlanImpl(day, start, end);
|
||||
|
||||
assertThat(plan.toString()).contains(day.zone().toString(), day.date().toString());
|
||||
}
|
||||
|
||||
@Test
|
||||
void ldpFindMatchingFreeSlotsOnEmptyDay() {
|
||||
LocalDayPlan plan = TestData.emptyWorkingDay();
|
||||
|
||||
List<TimeSlot> freeSlots = plan.findGapsFitting(Duration.ofHours(2));
|
||||
|
||||
assertThat(freeSlots.size()).isEqualTo(1);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,6 +2,7 @@ package appointmentplanner.customlist.api;
|
||||
|
||||
import static org.assertj.core.api.Assertions.*;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
@@ -174,6 +175,20 @@ public class CustomLinkedListTest {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
void cllToArrayList() {
|
||||
|
||||
String[] items = new String[] { "Uz", "toho", "mam", "dost" };
|
||||
|
||||
CustomLinkedList<String> ll = initPopulatedList(items);
|
||||
|
||||
ArrayList<String> convertedAl = ll.toArrayList();
|
||||
|
||||
for (int i = 0; i < items.length; i++) {
|
||||
assertThat(items[i]).isEqualTo(convertedAl.get(i));
|
||||
}
|
||||
}
|
||||
|
||||
private CustomLinkedList<String> initPopulatedList(String... initData) {
|
||||
CustomLinkedList<String> list = new CustomLinkedListImpl<>();
|
||||
Stream.of(initData).forEach(list::add);
|
||||
|
||||
Reference in New Issue
Block a user