initial commit
This commit is contained in:
87
java/reverse/FastReverseTest.java
Normal file
87
java/reverse/FastReverseTest.java
Normal file
@@ -0,0 +1,87 @@
|
||||
package reverse;
|
||||
|
||||
import base.ExtendedRandom;
|
||||
import base.Named;
|
||||
import base.Selector;
|
||||
import base.TestCounter;
|
||||
import wordStat.WordStatTest;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.function.BiFunction;
|
||||
import java.util.function.LongBinaryOperator;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.IntStream;
|
||||
|
||||
/**
|
||||
* @author Georgiy Korneev (kgeorgiy@kgeorgiy.info)
|
||||
*/
|
||||
public final class FastReverseTest {
|
||||
// === 3637
|
||||
|
||||
private static final Named<BiFunction<ExtendedRandom, Integer, String>> OCT = Named.of("",
|
||||
(r, i) -> r.nextBoolean() ? Integer.toString(i) : Integer.toOctalString(i) + (r.nextBoolean() ? "o" : "O")
|
||||
);
|
||||
private static final Named<BiFunction<ExtendedRandom, Integer, String>> DEC = Named.of("", (r, i) -> Integer.toString(i));
|
||||
|
||||
private static final Named<String> PUNCT = Named.of(
|
||||
"",
|
||||
IntStream.range(0, Character.MAX_VALUE)
|
||||
.filter(ch -> ch == ' ' || Character.getType(ch) == Character.START_PUNCTUATION || Character.getType(ch) == Character.END_PUNCTUATION)
|
||||
.filter(ch -> ch != 13 && ch != 10)
|
||||
.mapToObj(Character::toString)
|
||||
.collect(Collectors.joining())
|
||||
);
|
||||
|
||||
public static final Named<ReverseTester.Op> MIN_C = Named.of("MinC", scan2((a, b) -> b));
|
||||
public static final Named<ReverseTester.Op> MIN = Named.of("Min", scan2(Math::min));
|
||||
|
||||
private static ReverseTester.Op scan2(final LongBinaryOperator reduce) {
|
||||
return ints -> {
|
||||
// This code is intentionally obscure
|
||||
final int length = Arrays.stream(ints).mapToInt(r -> r.length).max().orElse(0);
|
||||
final long[] cs = new long[length];
|
||||
final long[] cc = new long[length + 1];
|
||||
Arrays.fill(cs, Integer.MAX_VALUE);
|
||||
Arrays.fill(cc, Integer.MAX_VALUE);
|
||||
//noinspection NestedAssignment
|
||||
final long[][] rows = range(ints.length).mapToObj(i -> {
|
||||
range(ints[i].length).forEachOrdered(j -> cc[j] = reduce.applyAsLong(
|
||||
cc[j + 1],
|
||||
cs[j] = Math.min(cs[j], ints[i][j])
|
||||
));
|
||||
return Arrays.copyOf(cc, ints[i].length);
|
||||
})
|
||||
.toArray(long[][]::new);
|
||||
return range(ints.length).mapToObj(i -> rows[i]).toArray(long[][]::new);
|
||||
};
|
||||
}
|
||||
|
||||
private static IntStream range(final int length) {
|
||||
return IntStream.iterate(length - 1, i -> i >= 0, i -> i - 1);
|
||||
}
|
||||
|
||||
|
||||
// === Common
|
||||
|
||||
public static final int MAX_SIZE = 1_000_000 / TestCounter.DENOMINATOR / TestCounter.DENOMINATOR;
|
||||
|
||||
public static final Selector SELECTOR = new Selector(FastReverseTest.class)
|
||||
.variant("Base", ReverseTester.variant(MAX_SIZE, ReverseTest.REVERSE))
|
||||
.variant("3637", ReverseTester.variant(MAX_SIZE, "", MIN_C, OCT, DEC, PUNCT))
|
||||
.variant("3839", ReverseTester.variant(MAX_SIZE, "", MIN, OCT, DEC, PUNCT))
|
||||
.variant("3435", ReverseTester.variant(MAX_SIZE, ReverseTest.ROTATE, PUNCT))
|
||||
.variant("3233", ReverseTester.variant(MAX_SIZE, ReverseTest.EVEN, PUNCT))
|
||||
.variant("4142", ReverseTester.variant(MAX_SIZE, ReverseTest.AVG, PUNCT))
|
||||
.variant("4749", ReverseTester.variant(MAX_SIZE, ReverseTest.SUM, PUNCT))
|
||||
|
||||
;
|
||||
|
||||
|
||||
private FastReverseTest() {
|
||||
}
|
||||
|
||||
public static void main(final String... args) {
|
||||
SELECTOR.main(args);
|
||||
WordStatTest.main(args);
|
||||
}
|
||||
}
|
||||
165
java/reverse/ReverseTest.java
Normal file
165
java/reverse/ReverseTest.java
Normal file
@@ -0,0 +1,165 @@
|
||||
package reverse;
|
||||
|
||||
import base.Named;
|
||||
import base.Selector;
|
||||
import base.TestCounter;
|
||||
import reverse.ReverseTester.Op;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.function.IntToLongFunction;
|
||||
import java.util.function.LongBinaryOperator;
|
||||
import java.util.stream.IntStream;
|
||||
|
||||
/**
|
||||
* Tests for {@code Reverse} homework.
|
||||
*
|
||||
* @author Georgiy Korneev (kgeorgiy@kgeorgiy.info)
|
||||
*/
|
||||
public final class ReverseTest {
|
||||
// === Base
|
||||
public static final Named<Op> REVERSE = Named.of("", ReverseTester::transform);
|
||||
|
||||
|
||||
// === Max
|
||||
|
||||
public static final Named<Op> MAX_C = Named.of("MaxC", scan2((a, b) -> b));
|
||||
public static final Named<Op> MAX = Named.of("Max", scan2(Math::max));
|
||||
|
||||
private static Op scan2(final LongBinaryOperator reduce) {
|
||||
return ints -> {
|
||||
// This code is intentionally obscure
|
||||
final int length = Arrays.stream(ints).mapToInt(r -> r.length).max().orElse(0);
|
||||
final long[] cs = new long[length];
|
||||
final long[] cc = new long[length + 1];
|
||||
Arrays.fill(cs, Integer.MIN_VALUE);
|
||||
Arrays.fill(cc, Integer.MIN_VALUE);
|
||||
//noinspection NestedAssignment
|
||||
final long[][] rows = range(ints.length).mapToObj(i -> {
|
||||
range(ints[i].length).forEachOrdered(j -> cc[j] = reduce.applyAsLong(
|
||||
cc[j + 1],
|
||||
cs[j] = Math.max(cs[j], ints[i][j])
|
||||
));
|
||||
return Arrays.copyOf(cc, ints[i].length);
|
||||
})
|
||||
.toArray(long[][]::new);
|
||||
return range(ints.length).mapToObj(i -> rows[i]).toArray(long[][]::new);
|
||||
};
|
||||
}
|
||||
|
||||
private static IntStream range(final int length) {
|
||||
return IntStream.iterate(length - 1, i -> i >= 0, i -> i - 1);
|
||||
}
|
||||
|
||||
|
||||
// === Rotate
|
||||
public static final Named<Op> ROTATE = Named.of("Rotate", ints -> {
|
||||
final List<int[]> rows = new ArrayList<>(List.of(ints));
|
||||
return IntStream.range(0, Arrays.stream(ints).mapToInt(r -> r.length).max().orElse(0))
|
||||
.mapToObj(c -> {
|
||||
rows.removeIf(r -> r.length <= c);
|
||||
return range(rows.size()).mapToObj(rows::get).mapToLong(r -> r[c]).toArray();
|
||||
})
|
||||
.toArray(long[][]::new);
|
||||
});
|
||||
|
||||
|
||||
// === Even
|
||||
public static final Named<Op> EVEN = Named.of(
|
||||
"Even",
|
||||
ints -> ReverseTester.transform(IntStream.range(0, ints.length)
|
||||
.mapToObj(i -> IntStream.range(0, ints[i].length)
|
||||
.filter(j -> (i + j) % 2 == 0)
|
||||
.map(j -> ints[i][j]))
|
||||
.map(IntStream::toArray).toArray(int[][]::new))
|
||||
);
|
||||
|
||||
// Sum
|
||||
@FunctionalInterface
|
||||
interface LongTernaryOperator {
|
||||
long applyAsLong(long a, long b, long c);
|
||||
}
|
||||
|
||||
public static final Named<Op> SUM = cross("Sum", 0, Long::sum, (r, c, v) -> r + c - v);
|
||||
|
||||
private static long[][] cross(
|
||||
final int[][] ints,
|
||||
final IntToLongFunction map,
|
||||
final LongBinaryOperator reduce,
|
||||
final int zero,
|
||||
final LongTernaryOperator get
|
||||
) {
|
||||
// This code is intentionally obscure
|
||||
final long[] rt = Arrays.stream(ints)
|
||||
.map(Arrays::stream)
|
||||
.mapToLong(row -> row.mapToLong(map).reduce(zero, reduce))
|
||||
.toArray();
|
||||
final long[] ct = new long[Arrays.stream(ints).mapToInt(r -> r.length).max().orElse(0)];
|
||||
Arrays.fill(ct, zero);
|
||||
Arrays.stream(ints).forEach(r -> IntStream.range(0, r.length)
|
||||
.forEach(i -> ct[i] = reduce.applyAsLong(ct[i], map.applyAsLong(r[i]))));
|
||||
return IntStream.range(0, ints.length)
|
||||
.mapToObj(r -> IntStream.range(0, ints[r].length)
|
||||
.mapToLong(c -> get.applyAsLong(rt[r], ct[c], ints[r][c]))
|
||||
.toArray())
|
||||
.toArray(long[][]::new);
|
||||
}
|
||||
|
||||
private static Named<Op> cross(
|
||||
final String name,
|
||||
final int zero,
|
||||
final LongBinaryOperator reduce,
|
||||
final LongTernaryOperator get
|
||||
) {
|
||||
return Named.of(name, ints -> cross(ints, n -> n, reduce, zero, get));
|
||||
}
|
||||
|
||||
public static final Named<Op> AVG = avg(
|
||||
"Avg",
|
||||
ints -> cross(ints, n -> n, Long::sum, 0, (r, c, v) -> r + c - v),
|
||||
ints -> cross(ints, n -> 1, Long::sum, 0, (r1, c1, v1) -> r1 + c1 - 1)
|
||||
);
|
||||
|
||||
private static Named<Op> avg(
|
||||
final String name,
|
||||
final Op fs,
|
||||
final Op fc
|
||||
) {
|
||||
return Named.of(name, ints -> avg(ints, fs.apply(ints), fc.apply(ints)));
|
||||
}
|
||||
|
||||
private static long[][] avg(final int[][] ints, final long[][] as, final long[][] ac) {
|
||||
return IntStream.range(0, ints.length).mapToObj(i -> IntStream.range(0, ints[i].length)
|
||||
.mapToLong(j -> as[i][j] / ac[i][j])
|
||||
.toArray())
|
||||
.toArray(long[][]::new);
|
||||
}
|
||||
|
||||
|
||||
// === Common
|
||||
|
||||
public static final int MAX_SIZE = 10_000 / TestCounter.DENOMINATOR;
|
||||
|
||||
public static final Selector SELECTOR = selector(ReverseTest.class, MAX_SIZE);
|
||||
|
||||
private ReverseTest() {
|
||||
// Utility class
|
||||
}
|
||||
|
||||
public static Selector selector(final Class<?> owner, final int maxSize) {
|
||||
return new Selector(owner)
|
||||
.variant("Base", ReverseTester.variant(maxSize, REVERSE))
|
||||
.variant("3637", ReverseTester.variant(maxSize, MAX_C))
|
||||
.variant("3839", ReverseTester.variant(maxSize, MAX))
|
||||
.variant("3435", ReverseTester.variant(maxSize, ROTATE))
|
||||
.variant("3233", ReverseTester.variant(maxSize, EVEN))
|
||||
.variant("4142", ReverseTester.variant(maxSize, AVG))
|
||||
.variant("4749", ReverseTester.variant(maxSize, SUM))
|
||||
;
|
||||
}
|
||||
|
||||
public static void main(final String... args) {
|
||||
SELECTOR.main(args);
|
||||
}
|
||||
}
|
||||
299
java/reverse/ReverseTester.java
Normal file
299
java/reverse/ReverseTester.java
Normal file
@@ -0,0 +1,299 @@
|
||||
package reverse;
|
||||
|
||||
import base.*;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.function.*;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.IntStream;
|
||||
|
||||
/**
|
||||
* @author Georgiy Korneev (kgeorgiy@kgeorgiy.info)
|
||||
*/
|
||||
public final class ReverseTester {
|
||||
|
||||
public static final Named<Op> TRANSFORM = Named.of("", ReverseTester::transform);
|
||||
public static final Named<String> SPACE = Named.of("", " ");
|
||||
|
||||
@FunctionalInterface
|
||||
public interface Op extends Function<int[][], long[][]> {}
|
||||
|
||||
private static final int[] DIVISORS = {100, 10, 1};
|
||||
|
||||
private final Op transform;
|
||||
private final BiFunction<ExtendedRandom, Integer, String> inputToString;
|
||||
private final BiFunction<ExtendedRandom, Integer, String> outputToString;
|
||||
private final String name;
|
||||
private final String spaces;
|
||||
|
||||
private ReverseTester(final String className, final Op transform, final String spaces) {
|
||||
this(className, transform, spaces, (r, i) -> Integer.toString(i), (r, i) -> Long.toString(i));
|
||||
}
|
||||
|
||||
private ReverseTester(
|
||||
final String className,
|
||||
final Op transform,
|
||||
final String spaces,
|
||||
final BiFunction<ExtendedRandom, Integer, String> inputToString,
|
||||
final BiFunction<ExtendedRandom, Integer, String> outputToString
|
||||
) {
|
||||
name = className;
|
||||
this.transform = transform;
|
||||
this.spaces = spaces;
|
||||
this.inputToString = inputToString;
|
||||
this.outputToString = outputToString;
|
||||
}
|
||||
|
||||
private static Consumer<TestCounter> variant(final int maxSize, final Supplier<ReverseTester> tester) {
|
||||
return counter -> tester.get().run(counter, maxSize);
|
||||
}
|
||||
|
||||
public static Consumer<TestCounter> variant(final int maxSize, final Named<Op> transform) {
|
||||
return variant(maxSize, transform, SPACE);
|
||||
}
|
||||
|
||||
|
||||
public static Consumer<TestCounter> variant(final int maxSize, final Named<Op> transform, final Named<String> spaces) {
|
||||
Objects.requireNonNull(transform);
|
||||
Objects.requireNonNull(spaces);
|
||||
return variant(
|
||||
maxSize,
|
||||
() -> new ReverseTester("Reverse" + transform.name() + spaces.name(), transform.value(), spaces.value())
|
||||
);
|
||||
}
|
||||
|
||||
public static Consumer<TestCounter> variant(
|
||||
final int maxSize,
|
||||
final String suffix,
|
||||
final Named<BiFunction<ExtendedRandom, Integer, String>> input,
|
||||
final Named<BiFunction<ExtendedRandom, Integer, String>> output
|
||||
) {
|
||||
return variant(maxSize, suffix, TRANSFORM, input, output);
|
||||
}
|
||||
|
||||
public static Consumer<TestCounter> variant(
|
||||
final int maxSize,
|
||||
final String suffix,
|
||||
final Named<Op> op,
|
||||
final Named<BiFunction<ExtendedRandom, Integer, String>> input,
|
||||
final Named<BiFunction<ExtendedRandom, Integer, String>> output
|
||||
) {
|
||||
return variant(maxSize, suffix, op, input, output, SPACE);
|
||||
}
|
||||
|
||||
public static Consumer<TestCounter> variant(
|
||||
final int maxSize,
|
||||
final String suffix,
|
||||
final Named<Op> op,
|
||||
final Named<BiFunction<ExtendedRandom, Integer, String>> input,
|
||||
final Named<BiFunction<ExtendedRandom, Integer, String>> output,
|
||||
final Named<String> spaces
|
||||
) {
|
||||
final String out = input.name().contains(output.name()) ? "" : output.name();
|
||||
return variant(maxSize, () -> new ReverseTester(
|
||||
"Reverse" + op.name() + input.name() + out + suffix + spaces.name(),
|
||||
op.value(),
|
||||
spaces.value(),
|
||||
input.value(),
|
||||
output.value()
|
||||
));
|
||||
}
|
||||
|
||||
private void run(final TestCounter counter, final int maxSize) {
|
||||
new Checker(counter, maxSize, Runner.packages("", "reverse").std(name), spaces).test();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public static long[][] transform(final int[][] ints) {
|
||||
return IntStream.range(1, ints.length + 1)
|
||||
.mapToObj(i -> ints[ints.length - i])
|
||||
.map(is -> IntStream.range(1, is.length + 1).mapToLong(i -> is[is.length - i]).toArray())
|
||||
.toArray(long[][]::new);
|
||||
}
|
||||
|
||||
/**
|
||||
* @author Georgiy Korneev (kgeorgiy@kgeorgiy.info)
|
||||
*/
|
||||
private class Checker extends BaseChecker {
|
||||
private final int maxSize;
|
||||
private final Runner runner;
|
||||
private final String spaces;
|
||||
private final Set<String> manualTests = new HashSet<>();
|
||||
|
||||
Checker(final TestCounter counter, final int maxSize, final Runner runner, final String spaces) {
|
||||
super(counter);
|
||||
this.maxSize = maxSize;
|
||||
this.runner = runner;
|
||||
this.spaces = spaces;
|
||||
}
|
||||
|
||||
public void manualTest(final int[][] ints) {
|
||||
for (final List<int[]> permutation : permutations(new ArrayList<>(Arrays.asList(ints)))) {
|
||||
final int[][] input = permutation.toArray(int[][]::new);
|
||||
final String[][] lines = toString(input, inputToString);
|
||||
if (manualTests.add(Arrays.deepToString(lines))) {
|
||||
test(lines, toString(transform.apply(input), outputToString));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void test(final int[][] ints) {
|
||||
test(toString(ints, inputToString), toString(transform.apply(ints), outputToString));
|
||||
}
|
||||
|
||||
public void test(final String[][] input, final String[][] output) {
|
||||
final List<String> inputLines = toLines(input, random().randomString(spaces, 1, 10));
|
||||
final List<String> outputLines = toLines(output, " ");
|
||||
runner.testEquals(counter, inputLines, outputLines);
|
||||
}
|
||||
|
||||
private String[][] toString(final int[][] ints, final BiFunction<ExtendedRandom, Integer, String> toString) {
|
||||
return Arrays.stream(ints)
|
||||
.map(row -> Arrays.stream(row).mapToObj(i -> toString.apply(random(), i)).toArray(String[]::new))
|
||||
.toArray(String[][]::new);
|
||||
}
|
||||
|
||||
private String[][] toString(final long[][] ints, final BiFunction<ExtendedRandom, Integer, String> toString) {
|
||||
return Arrays.stream(ints)
|
||||
.map(row -> Arrays.stream(row).mapToObj(i -> toString.apply(random(), (int) i)).toArray(String[]::new))
|
||||
.toArray(String[][]::new);
|
||||
}
|
||||
|
||||
private List<String> toLines(final String[][] data, final String delimiter) {
|
||||
if (data.length == 0) {
|
||||
return Collections.singletonList("");
|
||||
}
|
||||
return Arrays.stream(data)
|
||||
.map(row -> String.join(delimiter, row))
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
|
||||
public int[][] random(final int[] profile) {
|
||||
final int col = random().nextInt(Arrays.stream(profile).max().orElse(0));
|
||||
final int row = random().nextInt(profile.length);
|
||||
final int m = random().nextInt(5) - 2;
|
||||
final int[][] ints = Arrays.stream(profile).mapToObj(random().getRandom()::ints).map(IntStream::toArray).toArray(int[][]::new);
|
||||
Arrays.stream(ints).filter(r -> col < r.length).forEach(r -> r[col] = Math.abs(r[col]) / 2 * m);
|
||||
ints[row] = Arrays.stream(ints[row]).map(Math::abs).map(v -> v / 2 * m).toArray();
|
||||
return ints;
|
||||
}
|
||||
|
||||
public void test() {
|
||||
manualTest(new int[][]{
|
||||
{1}
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1, 2},
|
||||
{3}
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1, 2, 3},
|
||||
{4, 5},
|
||||
{6}
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1, 2, 3},
|
||||
{},
|
||||
{4, 5},
|
||||
{6}
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1, 2, 3},
|
||||
{-4, -5},
|
||||
{6}
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1, -2, 3},
|
||||
{},
|
||||
{4, -5},
|
||||
{6}
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1, 2, 0},
|
||||
{1, 0},
|
||||
{0},
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{1},
|
||||
{1, 3},
|
||||
{1, 2, 3},
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{-1},
|
||||
{-1, -2},
|
||||
{-1, -2, -3},
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{},
|
||||
});
|
||||
manualTest(new int[][]{
|
||||
{},
|
||||
{},
|
||||
{},
|
||||
});
|
||||
testRandom(tweakProfile(constProfile(10, 10), new int[][]{}));
|
||||
testRandom(tweakProfile(constProfile(100, 100), new int[][]{}));
|
||||
testRandom(randomProfile(100, maxSize));
|
||||
testRandom(randomProfile(maxSize / 10, maxSize));
|
||||
testRandom(randomProfile(maxSize, maxSize));
|
||||
for (final int d : DIVISORS) {
|
||||
final int size = maxSize / d;
|
||||
testRandom(tweakProfile(constProfile(size / 2, 0), new int[][]{{size / 2, 0}}));
|
||||
testRandom(tweakProfile(randomProfile(size, size / 2), new int[][]{{size / 2, 0}}));
|
||||
testRandom(tweakProfile(constProfile(size / 2, 0), new int[][]{{size / 2, size / 2 - 1}}));
|
||||
testRandom(tweakProfile(constProfile(size / 3, 1), new int[][]{{size / 3, size / 6, size / 3 - 1}}));
|
||||
}
|
||||
}
|
||||
|
||||
private int[] randomProfile(final int length, final int values) {
|
||||
final int[] profile = new int[length];
|
||||
for (int i = 0; i < values; i++) {
|
||||
profile[random().nextInt(0, length - 1)]++;
|
||||
}
|
||||
return profile;
|
||||
}
|
||||
|
||||
private void testRandom(final int[] profile) {
|
||||
test(random(profile));
|
||||
}
|
||||
|
||||
private int[] constProfile(final int length, final int value) {
|
||||
final int[] profile = new int[length];
|
||||
Arrays.fill(profile, value);
|
||||
return profile;
|
||||
}
|
||||
|
||||
private int[] tweakProfile(final int[] profile, final int[][] mods) {
|
||||
for (final int[] mod : mods) {
|
||||
Arrays.stream(mod).skip(1).forEach(i -> profile[i] = mod[0]);
|
||||
}
|
||||
return profile;
|
||||
}
|
||||
}
|
||||
|
||||
private static <T> List<List<T>> permutations(final List<T> elements) {
|
||||
final List<List<T>> result = new ArrayList<>();
|
||||
permutations(new ArrayList<>(elements), result, elements.size() - 1);
|
||||
return result;
|
||||
}
|
||||
|
||||
private static <T> void permutations(final List<T> elements, final List<List<T>> result, final int n) {
|
||||
if (n == 0) {
|
||||
result.add(List.copyOf(elements));
|
||||
} else {
|
||||
for (int i = 0; i < n; i++) {
|
||||
permutations(elements, result, n - 1);
|
||||
if (n % 2 == 1) {
|
||||
Collections.swap(elements, i, n);
|
||||
} else {
|
||||
Collections.swap(elements, 0, n);
|
||||
}
|
||||
}
|
||||
permutations(elements, result, n - 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
7
java/reverse/package-info.java
Normal file
7
java/reverse/package-info.java
Normal file
@@ -0,0 +1,7 @@
|
||||
/**
|
||||
* Tests for <a href="https://www.kgeorgiy.info/courses/prog-intro/homeworks.html#reverse">Reverse</a> homework
|
||||
* of <a href="https://www.kgeorgiy.info/courses/prog-intro/">Introduction to Programming</a> course.
|
||||
*
|
||||
* @author Georgiy Korneev (kgeorgiy@kgeorgiy.info)
|
||||
*/
|
||||
package reverse;
|
||||
Reference in New Issue
Block a user