Implement RecursiveFullyUsedArrayProcessor

This commit is contained in:
2021-08-30 21:26:49 +02:00
parent ab87b2e964
commit 7f5707b9c0
4 changed files with 618 additions and 44 deletions

View File

@ -1,5 +1,6 @@
package aud.exam.prep.array; package aud.exam.prep.array;
import aud.exam.prep.Pair;
import aud.exam.prep.SequenceProcessor; import aud.exam.prep.SequenceProcessor;
abstract class FullyUsedArrayProcessor<T> implements SequenceProcessor<T, FullyUsedArray<T>> { abstract class FullyUsedArrayProcessor<T> implements SequenceProcessor<T, FullyUsedArray<T>> {
@ -24,4 +25,34 @@ abstract class FullyUsedArrayProcessor<T> implements SequenceProcessor<T, FullyU
return () -> return () ->
new ArrayIterator<>(array.theArray, 0, array.theArray.length); new ArrayIterator<>(array.theArray, 0, array.theArray.length);
} }
protected Pair<FullyUsedArray<T>, FullyUsedArray<T>> createPairForDivideAlternating(FullyUsedArray<T> array) {
var p = new Pair<FullyUsedArray<T>, FullyUsedArray<T>>();
p.fst = new FullyUsedArray<>();
p.snd = new FullyUsedArray<>();
p.snd.theArray = Arrays.newArray(array.theArray.length / 2);
p.fst.theArray = Arrays.newArray(array.theArray.length - p.snd.theArray.length);
return p;
}
protected Pair<FullyUsedArray<T>, FullyUsedArray<T>> createPairForDivideByPivot(int less, int greater) {
var p = new Pair<FullyUsedArray<T>, FullyUsedArray<T>>();
p.fst = new FullyUsedArray<>();
p.snd = new FullyUsedArray<>();
p.fst.theArray = Arrays.newArray(less);
p.snd.theArray = Arrays.newArray(greater);
return p;
}
protected Pair<FullyUsedArray<T>, FullyUsedArray<T>> createPairForDivideAlternatingByRuns(FullyUsedArray<T> array, int elementsInFst) {
var p = new Pair<FullyUsedArray<T>, FullyUsedArray<T>>();
p.fst = new FullyUsedArray<>();
p.snd = new FullyUsedArray<>();
p.fst.theArray = Arrays.newArray(elementsInFst);
p.snd.theArray = Arrays.newArray(array.theArray.length - elementsInFst);
return p;
}
} }

View File

@ -195,6 +195,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
if (b.theArray.length < a.theArray.length) { if (b.theArray.length < a.theArray.length) {
return false; return false;
} }
for (int i = 0; i < a.theArray.length; i++) { for (int i = 0; i < a.theArray.length; i++) {
if (cmp.compare(a.theArray[i], b.theArray[i]) > 0) { if (cmp.compare(a.theArray[i], b.theArray[i]) > 0) {
return false; return false;
@ -416,12 +417,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
@Override @Override
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternating(FullyUsedArray<T> array) { public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternating(FullyUsedArray<T> array) {
var p = new Pair<FullyUsedArray<T>, FullyUsedArray<T>>(); var p = createPairForDivideAlternating(array);
p.fst = new FullyUsedArray<>();
p.snd = new FullyUsedArray<>();
p.snd.theArray = Arrays.newArray(array.theArray.length / 2);
p.fst.theArray = Arrays.newArray(array.theArray.length - p.snd.theArray.length);
for (int i = 0; i < array.theArray.length; i++) { for (int i = 0; i < array.theArray.length; i++) {
if (i % 2 == 0) { if (i % 2 == 0) {
@ -436,10 +432,6 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
@Override @Override
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternatingByRuns(FullyUsedArray<T> array, Comparator<T> cmp) { public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternatingByRuns(FullyUsedArray<T> array, Comparator<T> cmp) {
var p = new Pair<FullyUsedArray<T>, FullyUsedArray<T>>();
p.fst = new FullyUsedArray<>();
p.snd = new FullyUsedArray<>();
var runInFst = true; var runInFst = true;
var elementsInFst = 0; var elementsInFst = 0;
@ -453,8 +445,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
} }
} }
p.fst.theArray = Arrays.newArray(elementsInFst); var p = createPairForDivideAlternatingByRuns(array, elementsInFst);
p.snd.theArray = Arrays.newArray(array.theArray.length - elementsInFst);
runInFst = true; runInFst = true;
var indexA = 0; var indexA = 0;
@ -477,10 +468,6 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
@Override @Override
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideByPivot(FullyUsedArray<T> array, T pivot, Comparator<T> cmp) { public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideByPivot(FullyUsedArray<T> array, T pivot, Comparator<T> cmp) {
var p = new Pair<FullyUsedArray<T>, FullyUsedArray<T>>();
p.fst = new FullyUsedArray<>();
p.snd = new FullyUsedArray<>();
var less = 0; var less = 0;
var greater = 0; var greater = 0;
@ -494,8 +481,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
} }
} }
p.fst.theArray = Arrays.newArray(less); var p = createPairForDivideByPivot(less, greater);
p.snd.theArray = Arrays.newArray(greater);
var indexA = 0; var indexA = 0;
var indexB = 0; var indexB = 0;

View File

@ -4,142 +4,698 @@ import aud.exam.prep.Pair;
import java.util.Comparator; import java.util.Comparator;
import java.util.Iterator; import java.util.Iterator;
import java.util.Objects;
public class RecursiveFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor<T> { public class RecursiveFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor<T> {
@Override @Override
public boolean find(FullyUsedArray<T> array, T t) { public boolean find(FullyUsedArray<T> array, T t) {
return findRec(array, t, 0);
}
private boolean findRec(FullyUsedArray<T> array, T t, int index) {
if (index >= array.theArray.length) {
return false; return false;
} }
if (Objects.equals(array.theArray[index], t)) {
return true;
}
return findRec(array, t, index+1);
}
@Override @Override
public boolean findBinary(FullyUsedArray<T> array, T t, Comparator<T> cmp) { public boolean findBinary(FullyUsedArray<T> array, T t, Comparator<T> cmp) {
return findBinaryRec(array, t, cmp, 0, array.theArray.length-1);
}
private boolean findBinaryRec(FullyUsedArray<T> array, T t, Comparator<T> cmp, int start, int end) {
if (start > end) {
return false; return false;
} }
var index = (start+end) / 2;
var c = cmp.compare(t, array.theArray[index]);
if (c == 0) {
return true;
}
if (c > 0) {
return findBinaryRec(array, t, cmp, index+1, end);
}
return findBinaryRec(array, t, cmp, start, index-1);
}
@Override @Override
public boolean override(FullyUsedArray<T> array, T from, T to) { public boolean override(FullyUsedArray<T> array, T from, T to) {
return overrideRec(array, from, to, 0);
}
private boolean overrideRec(FullyUsedArray<T> array, T from, T to, int index) {
if (index >= array.theArray.length) {
return false; return false;
} }
if (Objects.equals(array.theArray[index], from)) {
array.theArray[index] = to;
return true;
}
return overrideRec(array, from, to, index+1);
}
@Override @Override
public boolean overrideAll(FullyUsedArray<T> array, T from, T to) { public boolean overrideAll(FullyUsedArray<T> array, T from, T to) {
return overrideAllRec(array, from, to, 0);
}
private boolean overrideAllRec(FullyUsedArray<T> array, T from, T to, int index) {
if (index >= array.theArray.length) {
return false; return false;
} }
var modified = false;
if (Objects.equals(array.theArray[index], from)) {
array.theArray[index] = to;
modified = true;
}
return overrideAllRec(array, from, to, index+1) || modified;
}
@Override @Override
public void insertInOrder(FullyUsedArray<T> array, T t, Comparator<T> cmp) { public void insertInOrder(FullyUsedArray<T> array, T t, Comparator<T> cmp) {
T[] newArray = Arrays.newArray(array.theArray.length+1);
insertElementsInOrder(array.theArray, newArray, t, cmp, 0);
array.theArray = newArray;
}
private void insertElementsInOrder(T[] oldArray, T[] newArray, T t, Comparator<T> cmp, int index) {
if (index == oldArray.length) {
newArray[index] = t;
} else if (cmp.compare(t, oldArray[index]) < 0) {
newArray[index] = t;
insertRestOfElements(oldArray, newArray, index);
} else {
newArray[index] = oldArray[index];
insertElementsInOrder(oldArray, newArray, t, cmp, index+1);
}
}
private void insertRestOfElements(T[] oldArray, T[] newArray, int index) {
if (index >= oldArray.length) {
return;
}
newArray[index+1] = oldArray[index];
insertRestOfElements(oldArray, newArray, index+1);
} }
@Override @Override
public boolean remove(FullyUsedArray<T> array, T t) { public boolean remove(FullyUsedArray<T> array, T t) {
if (!find(array, t)) {
return false; return false;
} }
T[] newArray = Arrays.newArray(array.theArray.length-1);
removeRec(array.theArray, newArray, t, 0);
array.theArray = newArray;
return true;
}
private void removeRec(T[] oldArray, T[] newArray, T t, int index) {
if (Objects.equals(oldArray[index], t)) {
copyRestOfElementsForRemove(oldArray, newArray, index+1);
return;
}
newArray[index] = oldArray[index];
removeRec(oldArray, newArray, t, index+1);
}
private void copyRestOfElementsForRemove(T[] oldArray, T[] newArray, int index) {
if (index >= oldArray.length) {
return;
}
newArray[index-1] = oldArray[index];
copyRestOfElementsForRemove(oldArray, newArray, index+1);
}
@Override @Override
public boolean removeAll(FullyUsedArray<T> array, T t) { public boolean removeAll(FullyUsedArray<T> array, T t) {
var size = countRemainingElementsForRemoveAll(array.theArray, t, 0);
if (size == array.theArray.length) {
return false; return false;
} }
T[] newArray = Arrays.newArray(size);
removeAllRec(array.theArray, 0, newArray, 0, t);
array.theArray = newArray;
return true;
}
private void removeAllRec(T[] src, int indexSrc, T[] dst, int indexDst, T t) {
if (indexSrc >= src.length) {
return;
}
if (!Objects.equals(t, src[indexSrc])) {
dst[indexDst] = src[indexSrc];
indexDst++;
}
removeAllRec(src, indexSrc+1, dst, indexDst, t);
}
private int countRemainingElementsForRemoveAll(T[] array, T t, int index) {
if (index >= array.length) {
return 0;
}
var current = 0;
if (!Objects.equals(t, array[index])) {
current++;
}
return current + countRemainingElementsForRemoveAll(array, t, index+1);
}
@Override @Override
public boolean isAscending(FullyUsedArray<T> array, Comparator<T> cmp) { public boolean isAscending(FullyUsedArray<T> array, Comparator<T> cmp) {
if (array.theArray.length < 2) {
return true;
}
return isAscendingRec(array.theArray, cmp, 0);
}
private boolean isAscendingRec(T[] array, Comparator<T> cmp, int index) {
if (index >= array.length-1) {
return true;
}
if (cmp.compare(array[index], array[index+1]) > 0) {
return false; return false;
} }
return isAscendingRec(array, cmp, index+1);
}
@Override @Override
public T max(FullyUsedArray<T> array, Comparator<T> cmp) { public T max(FullyUsedArray<T> array, Comparator<T> cmp) {
return null; if (array.theArray.length == 0) {
throw new IllegalArgumentException("The sequence may not be empty");
}
return maxRec(array.theArray, cmp, 1, array.theArray[0]);
}
private T maxRec(T[] array, Comparator<T> cmp, int index, T max) {
if (index >= array.length) {
return max;
}
if (cmp.compare(max, array[index]) < 0) {
max = array[index];
}
return maxRec(array, cmp, index+1, max);
} }
@Override @Override
public T secondMax(FullyUsedArray<T> array, Comparator<T> cmp) { public T secondMax(FullyUsedArray<T> array, Comparator<T> cmp) {
return null; if (array.theArray.length < 2) {
throw new IllegalArgumentException("The sequence must contains at least 2 elements");
}
T secondMax, max;
if (cmp.compare(array.theArray[0], array.theArray[1]) < 0) {
secondMax = array.theArray[0];
max = array.theArray[1];
} else {
secondMax = array.theArray[1];
max = array.theArray[0];
}
return secondMaxRec(array.theArray, cmp, 2, max, secondMax);
}
private T secondMaxRec(T[] array, Comparator<T> cmp, int index, T max, T secondMax) {
if (index >= array.length) {
return secondMax;
}
if (cmp.compare(max, array[index]) < 0) {
secondMax = max;
max = array[index];
} else if (cmp.compare(secondMax, array[index]) < 0) {
secondMax = array[index];
}
return secondMaxRec(array, cmp, index+1, max, secondMax);
} }
@Override @Override
public boolean isItemWiseLessOrEqual(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) { public boolean isItemWiseLessOrEqual(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
if (b.theArray.length < a.theArray.length) {
return false; return false;
} }
return isItemWiseLessOrEqualRec(a.theArray, b.theArray, 0, cmp);
}
private boolean isItemWiseLessOrEqualRec(T[] a, T[] b, int index, Comparator<T> cmp) {
if (index >= a.length) {
return true;
}
if (cmp.compare(a[index], b[index]) > 0) {
return false;
}
return isItemWiseLessOrEqualRec(a, b, index+1, cmp);
}
@Override @Override
public boolean isItemWiseLess(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) { public boolean isItemWiseLess(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
if (b.theArray.length < a.theArray.length) {
return false; return false;
} }
return isItemWiseLessRec(a.theArray, b.theArray, 0, cmp);
}
private boolean isItemWiseLessRec(T[] a, T[] b, int index, Comparator<T> cmp) {
if (index >= a.length) {
return index < b.length;
}
var c = cmp.compare(a[index], b[index]);
if (c > 0) {
return false;
}
if (c < 0) {
return isItemWiseLessOrEqualRec(a, b, index+1, cmp);
}
return isItemWiseLessRec(a, b, index+1, cmp);
}
@Override @Override
public boolean isLexSmaller(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) { public boolean isLexSmaller(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
return isLexSmallerRec(a.theArray, 0, b.theArray, 0, cmp);
}
private boolean isLexSmallerRec(T[] a, int indexA, T[] b, int indexB, Comparator<T> cmp) {
if (indexA >= a.length) {
return indexB < b.length;
}
if (indexB >= b.length) {
return false; return false;
} }
var c = cmp.compare(a[indexA], b[indexB]);
if (c > 0) {
return false;
}
if (c < 0) {
return true;
}
return isLexSmallerRec(a, indexA+1, b, indexB+1, cmp);
}
@Override @Override
public void exchangePairs(FullyUsedArray<T> array) { public void exchangePairs(FullyUsedArray<T> array) {
exchangePairsRec(array.theArray, 1);
}
private void exchangePairsRec(T[] array, int index) {
if (index >= array.length-1) {
return;
}
T t = array[index];
array[index] = array[index +1];
array[index +1] = t;
exchangePairsRec(array, index+2);
} }
@Override @Override
public void rotateTriples(FullyUsedArray<T> array) { public void rotateTriples(FullyUsedArray<T> array) {
rotateTriplesRec(array.theArray, 1);
}
private void rotateTriplesRec(T[] array, int index) {
if (index >= array.length - 2) {
return;
}
T t = array[index+2];
array[index+2] = array[index+1];
array[index+1] = array[index];
array[index] = t;
rotateTriplesRec(array, index+3);
} }
@Override @Override
public void removeEverySecond(FullyUsedArray<T> array) { public void removeEverySecond(FullyUsedArray<T> array) {
T[] newArray = Arrays.newArray(array.theArray.length - array.theArray.length / 2);
removeEverySecondRec(array.theArray, newArray, 0);
array.theArray = newArray;
}
private void removeEverySecondRec(T[] oldArray, T[] newArray, int index) {
if (index >= newArray.length) {
return;
}
newArray[index] = oldArray[index*2];
removeEverySecondRec(oldArray, newArray, index+1);
} }
@Override @Override
public void doubleAllKeys(FullyUsedArray<T> array) { public void doubleAllKeys(FullyUsedArray<T> array) {
T[] newArray = Arrays.newArray(array.theArray.length * 2);
doubleAllKeysRec(array.theArray, newArray, 0);
array.theArray = newArray;
}
private void doubleAllKeysRec(T[] array, T[] newArray, int index) {
if (index >= array.length) {
return;
}
newArray[index * 2] = array[index];
newArray[index * 2 + 1] = array[index];
doubleAllKeysRec(array, newArray, index+1);
} }
@Override @Override
public FullyUsedArray<T> rotateRight(FullyUsedArray<T> array) { public FullyUsedArray<T> rotateRight(FullyUsedArray<T> array) {
return null; if (array.theArray.length == 0) {
return array;
}
T t = array.theArray[array.theArray.length-1];
rotateRightRec(array.theArray, array.theArray.length-1);
array.theArray[0] = t;
return array;
}
private void rotateRightRec(T[] array, int index) {
if (index < 1) {
return;
}
array[index] = array[index-1];
rotateRightRec(array, index-1);
} }
@Override @Override
public FullyUsedArray<T> rotateLeft(FullyUsedArray<T> array) { public FullyUsedArray<T> rotateLeft(FullyUsedArray<T> array) {
return null; if (array.theArray.length == 0) {
return array;
}
T t = array.theArray[0];
rotateLeftRec(array.theArray, 0);
array.theArray[array.theArray.length-1] = t;
return array;
}
private void rotateLeftRec(T[] array, int index) {
if (index >= array.length-1) {
return;
}
array[index] = array[index+1];
rotateLeftRec(array, index+1);
} }
@Override @Override
public void removeDuplicates(FullyUsedArray<T> array) { public void removeDuplicates(FullyUsedArray<T> array) {
if (array.theArray.length < 2) {
return;
}
var count = 1 + countRemainingElementsForRemoveDuplicates(array.theArray, 1);
T[] newArray = Arrays.newArray(count);
newArray[0] = array.theArray[0];
removeDuplicatesRec(array.theArray, newArray, 1, 1);
array.theArray = newArray;
}
private void removeDuplicatesRec(T[] array, T[] newArray, int src, int dst) {
if (src >= array.length) {
return;
}
if (!Objects.equals(array[src], array[src-1])) {
newArray[dst] = array[src];
dst++;
}
removeDuplicatesRec(array, newArray, src+1, dst);
}
private int countRemainingElementsForRemoveDuplicates(T[] array, int index) {
if (index >= array.length) {
return 0;
}
var current = 0;
if (!Objects.equals(array[index], array[index-1])) {
current++;
}
return current + countRemainingElementsForRemoveDuplicates(array, index+1);
} }
@Override @Override
public FullyUsedArray<T> invert(FullyUsedArray<T> array) { public FullyUsedArray<T> invert(FullyUsedArray<T> array) {
return null; invertRec(array.theArray, 0);
return array;
}
private void invertRec(T[] array, int index) {
if (index >= array.length / 2) {
return;
}
T t = array[index];
array[index] = array[array.length - 1 - index];
array[array.length - 1 - index] = t;
invertRec(array, index+1);
} }
@Override @Override
public FullyUsedArray<T> clone(FullyUsedArray<T> array) { public FullyUsedArray<T> clone(FullyUsedArray<T> array) {
return null; var newArray = new FullyUsedArray<T>();
newArray.theArray = Arrays.newArray(array.theArray.length);
copyRestOfElements(array.theArray, 0, newArray.theArray, 0);
return newArray;
} }
@Override @Override
public FullyUsedArray<T> alternate(FullyUsedArray<T> a, FullyUsedArray<T> b) { public FullyUsedArray<T> alternate(FullyUsedArray<T> a, FullyUsedArray<T> b) {
return null; var newArray = new FullyUsedArray<T>();
newArray.theArray = Arrays.newArray(a.theArray.length + b.theArray.length);
alternateRec(a.theArray, 0, b.theArray, 0, newArray.theArray, 0);
return newArray;
}
private void alternateRec(T[] a, int indexA, T[] b, int indexB, T[] array, int index) {
if (indexA >= a.length) {
copyRestOfElements(b, indexB, array, index);
} else if (indexB >= b.length) {
copyRestOfElements(a, indexA, array, index);
} else {
array[index] = a[indexA];
array[index+1] = b[indexB];
alternateRec(a, indexA+1, b, indexB+1, array, index+2);
}
} }
@Override @Override
public FullyUsedArray<T> merge(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) { public FullyUsedArray<T> merge(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
return null; var newArray = new FullyUsedArray<T>();
newArray.theArray = Arrays.newArray(a.theArray.length + b.theArray.length);
mergeRec(a.theArray, 0, b.theArray, 0, newArray.theArray, 0, cmp);
return newArray;
}
private void mergeRec(T[] a, int indexA, T[] b, int indexB, T[] newArray, int index, Comparator<T> cmp) {
if (indexA >= a.length) {
copyRestOfElements(b, indexB, newArray, index);
return;
}
if (indexB >= b.length) {
copyRestOfElements(a, indexA, newArray, index);
return;
}
if (cmp.compare(a[indexA], b[indexB]) < 0) {
newArray[index] = a[indexA];
mergeRec(a, indexA+1, b, indexB, newArray, index+1, cmp);
} else {
newArray[index] = b[indexB];
mergeRec(a, indexA, b, indexB+1, newArray, index+1, cmp);
}
}
private void copyRestOfElements(T[] src, int srcIndex, T[] dst, int dstIndex) {
if (srcIndex >= src.length) {
return;
}
dst[dstIndex] = src[srcIndex];
copyRestOfElements(src, srcIndex+1, dst, dstIndex+1);
} }
@Override @Override
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternating(FullyUsedArray<T> array) { public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternating(FullyUsedArray<T> array) {
return null; var p = createPairForDivideAlternating(array);
divideAlternatingRec(p, array.theArray, 0, 0, 0);
return p;
}
private void divideAlternatingRec(Pair<FullyUsedArray<T>, FullyUsedArray<T>> p, T[] array,
int index, int indexA, int indexB) {
if (index >= array.length) {
return;
}
if (index % 2 == 0) {
p.fst.theArray[indexA] = array[index];
divideAlternatingRec(p, array, index+1, indexA+1, indexB);
} else {
p.snd.theArray[indexB] = array[index];
divideAlternatingRec(p, array, index+1, indexA, indexB+1);
}
} }
@Override @Override
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternatingByRuns(FullyUsedArray<T> array, Comparator<T> cmp) { public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternatingByRuns(FullyUsedArray<T> array, Comparator<T> cmp) {
return null; var elementsInFst = countElementsInFirst(array.theArray, cmp, true, 0);
var p = createPairForDivideAlternatingByRuns(array, elementsInFst);
divideAlternatingByRunsRec(array.theArray, p, cmp, true, 0, 0, 0);
return p;
}
private void divideAlternatingByRunsRec(T[] array, Pair<FullyUsedArray<T>, FullyUsedArray<T>> p, Comparator<T> cmp,
boolean runInFst, int index, int indexA, int indexB) {
if (index >= array.length) {
return;
}
if (runInFst) {
p.fst.theArray[indexA] = array[index];
indexA++;
} else {
p.snd.theArray[indexB] = array[index];
indexB++;
}
if (index < array.length-1 && cmp.compare(array[index], array[index + 1]) > 0) {
runInFst = !runInFst;
}
divideAlternatingByRunsRec(array, p, cmp, runInFst, index+1, indexA, indexB);
}
private int countElementsInFirst(T[] array, Comparator<T> cmp, boolean runInFst, int index) {
if (index >= array.length) {
return 0;
}
var countCurrentElement = 0;
if (runInFst) {
countCurrentElement++;
}
if (index < array.length-1 && cmp.compare(array[index], array[index + 1]) > 0) {
runInFst = !runInFst;
}
return countCurrentElement + countElementsInFirst(array, cmp, runInFst, index+1);
} }
@Override @Override
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideByPivot(FullyUsedArray<T> array, T pivot, Comparator<T> cmp) { public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideByPivot(FullyUsedArray<T> array, T pivot, Comparator<T> cmp) {
return null; var counts = new Pair<Integer, Integer>();
counts.fst = 0;
counts.snd = 0;
countLessAndGreater(array.theArray, pivot, cmp, 0, counts);
var p = createPairForDivideByPivot(counts.fst, counts.snd);
divideByPivotRec(array.theArray, pivot, cmp, p, 0, 0, 0);
return p;
}
private void divideByPivotRec(T[] array, T pivot, Comparator<T> cmp, Pair<FullyUsedArray<T>, FullyUsedArray<T>> p,
int index, int indexA, int indexB) {
if (index >= array.length) {
return;
}
var c = cmp.compare(array[index], pivot);
if (c < 0) {
p.fst.theArray[indexA] = array[index];
divideByPivotRec(array, pivot, cmp, p, index+1, indexA+1, indexB);
} else if (c > 0) {
p.snd.theArray[indexB] = array[index];
divideByPivotRec(array, pivot, cmp, p, index+1, indexA, indexB+1);
} else {
divideByPivotRec(array, pivot, cmp, p, index+1, indexA, indexB);
}
}
private void countLessAndGreater(T[] array, T pivot, Comparator<T> cmp, int index, Pair<Integer, Integer> counts) {
if (index >= array.length) {
return;
}
var c = cmp.compare(array[index], pivot);
if (c < 0) {
counts.fst++;
}
if (c > 0) {
counts.snd++;
}
countLessAndGreater(array, pivot, cmp, index+1, counts);
} }
@Override @Override

View File

@ -313,10 +313,10 @@ public abstract class SequenceProcessorTest<S> {
void testThat_isItemWiseLessWithAlmostSameIsTrue(List<Integer> list) { void testThat_isItemWiseLessWithAlmostSameIsTrue(List<Integer> list) {
S a = processor.create(list); S a = processor.create(list);
var index = list.size()/2;
if (list.isEmpty()) { if (list.isEmpty()) {
list.add(1); list.add(1);
} else { } else {
var index = list.size()/2;
list.set(index, list.get(index)+1); list.set(index, list.get(index)+1);
} }
S b = processor.create(list); S b = processor.create(list);
@ -330,14 +330,15 @@ public abstract class SequenceProcessorTest<S> {
void testThat_isItemWiseLessWithPlus5Works(List<Integer> list) { void testThat_isItemWiseLessWithPlus5Works(List<Integer> list) {
S a = processor.create(list); S a = processor.create(list);
if (list.isEmpty()) {
list.add(1);
}
for (int i = 0; i < list.size(); i++) { for (int i = 0; i < list.size(); i++) {
if (i % 2 == 0) { if (i % 2 == 0) {
list.set(i, list.get(i)+5); list.set(i, list.get(i)+5);
} }
} }
if (list.isEmpty()) {
list.add(1);
}
S b = processor.create(list); S b = processor.create(list);
assertTrue(processor.isItemWiseLess(a, b, cmp)); assertTrue(processor.isItemWiseLess(a, b, cmp));
@ -353,7 +354,7 @@ public abstract class SequenceProcessorTest<S> {
@ParameterizedTest @ParameterizedTest
@ArgumentsSource(DoubleLatinProvider.class) @ArgumentsSource(DoubleLatinProvider.class)
void testThat_isLexSmallerWithWorksLikeStrings(String stringA, String stringB) { void testThat_isLexSmallerWorksLikeStringsDo(String stringA, String stringB) {
S a = toSequenceByAscii(stringA); S a = toSequenceByAscii(stringA);
S b = toSequenceByAscii(stringB); S b = toSequenceByAscii(stringB);