Implement RecursiveFullyUsedArrayProcessor
This commit is contained in:
@ -1,5 +1,6 @@
|
||||
package aud.exam.prep.array;
|
||||
|
||||
import aud.exam.prep.Pair;
|
||||
import aud.exam.prep.SequenceProcessor;
|
||||
|
||||
abstract class FullyUsedArrayProcessor<T> implements SequenceProcessor<T, FullyUsedArray<T>> {
|
||||
@ -24,4 +25,34 @@ abstract class FullyUsedArrayProcessor<T> implements SequenceProcessor<T, FullyU
|
||||
return () ->
|
||||
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;
|
||||
}
|
||||
}
|
||||
|
@ -195,6 +195,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
|
||||
if (b.theArray.length < a.theArray.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (int i = 0; i < a.theArray.length; i++) {
|
||||
if (cmp.compare(a.theArray[i], b.theArray[i]) > 0) {
|
||||
return false;
|
||||
@ -416,12 +417,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
|
||||
|
||||
@Override
|
||||
public Pair<FullyUsedArray<T>, FullyUsedArray<T>> divideAlternating(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);
|
||||
var p = createPairForDivideAlternating(array);
|
||||
|
||||
for (int i = 0; i < array.theArray.length; i++) {
|
||||
if (i % 2 == 0) {
|
||||
@ -436,10 +432,6 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
|
||||
|
||||
@Override
|
||||
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 elementsInFst = 0;
|
||||
|
||||
@ -453,8 +445,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
|
||||
}
|
||||
}
|
||||
|
||||
p.fst.theArray = Arrays.newArray(elementsInFst);
|
||||
p.snd.theArray = Arrays.newArray(array.theArray.length - elementsInFst);
|
||||
var p = createPairForDivideAlternatingByRuns(array, elementsInFst);
|
||||
|
||||
runInFst = true;
|
||||
var indexA = 0;
|
||||
@ -477,10 +468,6 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
|
||||
|
||||
@Override
|
||||
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 greater = 0;
|
||||
|
||||
@ -494,8 +481,7 @@ public class IterativeFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor
|
||||
}
|
||||
}
|
||||
|
||||
p.fst.theArray = Arrays.newArray(less);
|
||||
p.snd.theArray = Arrays.newArray(greater);
|
||||
var p = createPairForDivideByPivot(less, greater);
|
||||
|
||||
var indexA = 0;
|
||||
var indexB = 0;
|
||||
|
@ -4,142 +4,698 @@ import aud.exam.prep.Pair;
|
||||
|
||||
import java.util.Comparator;
|
||||
import java.util.Iterator;
|
||||
import java.util.Objects;
|
||||
|
||||
public class RecursiveFullyUsedArrayProcessor<T> extends FullyUsedArrayProcessor<T> {
|
||||
|
||||
@Override
|
||||
public boolean find(FullyUsedArray<T> array, T t) {
|
||||
return false;
|
||||
return findRec(array, t, 0);
|
||||
}
|
||||
|
||||
private boolean findRec(FullyUsedArray<T> array, T t, int index) {
|
||||
if (index >= array.theArray.length) {
|
||||
return false;
|
||||
}
|
||||
if (Objects.equals(array.theArray[index], t)) {
|
||||
return true;
|
||||
}
|
||||
return findRec(array, t, index+1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean findBinary(FullyUsedArray<T> array, T t, Comparator<T> cmp) {
|
||||
return false;
|
||||
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;
|
||||
}
|
||||
|
||||
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
|
||||
public boolean override(FullyUsedArray<T> array, T from, T to) {
|
||||
return false;
|
||||
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;
|
||||
}
|
||||
if (Objects.equals(array.theArray[index], from)) {
|
||||
array.theArray[index] = to;
|
||||
return true;
|
||||
}
|
||||
return overrideRec(array, from, to, index+1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean overrideAll(FullyUsedArray<T> array, T from, T to) {
|
||||
return false;
|
||||
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;
|
||||
}
|
||||
|
||||
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
|
||||
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
|
||||
public boolean remove(FullyUsedArray<T> array, T t) {
|
||||
return false;
|
||||
if (!find(array, t)) {
|
||||
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
|
||||
public boolean removeAll(FullyUsedArray<T> array, T t) {
|
||||
return false;
|
||||
var size = countRemainingElementsForRemoveAll(array.theArray, t, 0);
|
||||
if (size == array.theArray.length) {
|
||||
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
|
||||
public boolean isAscending(FullyUsedArray<T> array, Comparator<T> cmp) {
|
||||
return false;
|
||||
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 isAscendingRec(array, cmp, index+1);
|
||||
}
|
||||
|
||||
@Override
|
||||
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
|
||||
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
|
||||
public boolean isItemWiseLessOrEqual(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
|
||||
return false;
|
||||
if (b.theArray.length < a.theArray.length) {
|
||||
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
|
||||
public boolean isItemWiseLess(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
|
||||
return false;
|
||||
if (b.theArray.length < a.theArray.length) {
|
||||
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
|
||||
public boolean isLexSmaller(FullyUsedArray<T> a, FullyUsedArray<T> b, Comparator<T> cmp) {
|
||||
return false;
|
||||
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;
|
||||
}
|
||||
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
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
|
||||
|
@ -313,10 +313,10 @@ public abstract class SequenceProcessorTest<S> {
|
||||
void testThat_isItemWiseLessWithAlmostSameIsTrue(List<Integer> list) {
|
||||
S a = processor.create(list);
|
||||
|
||||
var index = list.size()/2;
|
||||
if (list.isEmpty()) {
|
||||
list.add(1);
|
||||
} else {
|
||||
var index = list.size()/2;
|
||||
list.set(index, list.get(index)+1);
|
||||
}
|
||||
S b = processor.create(list);
|
||||
@ -330,14 +330,15 @@ public abstract class SequenceProcessorTest<S> {
|
||||
void testThat_isItemWiseLessWithPlus5Works(List<Integer> list) {
|
||||
S a = processor.create(list);
|
||||
|
||||
if (list.isEmpty()) {
|
||||
list.add(1);
|
||||
}
|
||||
|
||||
for (int i = 0; i < list.size(); i++) {
|
||||
if (i % 2 == 0) {
|
||||
list.set(i, list.get(i)+5);
|
||||
}
|
||||
}
|
||||
if (list.isEmpty()) {
|
||||
list.add(1);
|
||||
}
|
||||
S b = processor.create(list);
|
||||
|
||||
assertTrue(processor.isItemWiseLess(a, b, cmp));
|
||||
@ -353,7 +354,7 @@ public abstract class SequenceProcessorTest<S> {
|
||||
|
||||
@ParameterizedTest
|
||||
@ArgumentsSource(DoubleLatinProvider.class)
|
||||
void testThat_isLexSmallerWithWorksLikeStrings(String stringA, String stringB) {
|
||||
void testThat_isLexSmallerWorksLikeStringsDo(String stringA, String stringB) {
|
||||
S a = toSequenceByAscii(stringA);
|
||||
S b = toSequenceByAscii(stringB);
|
||||
|
||||
|
Reference in New Issue
Block a user