diff options
Diffstat (limited to 'BJC-Utils2/src/main/java/bjc/utils/funcutils')
4 files changed, 214 insertions, 28 deletions
diff --git a/BJC-Utils2/src/main/java/bjc/utils/funcutils/EnumUtils.java b/BJC-Utils2/src/main/java/bjc/utils/funcutils/EnumUtils.java new file mode 100644 index 0000000..f490727 --- /dev/null +++ b/BJC-Utils2/src/main/java/bjc/utils/funcutils/EnumUtils.java @@ -0,0 +1,64 @@ +package bjc.utils.funcutils; + +import java.util.Random; +import java.util.function.Consumer; + +import bjc.utils.funcdata.FunctionalList; +import bjc.utils.funcdata.IFunctionalList; + +/** + * Utility methods on enums + * + * @author ben + * + */ +public class EnumUtils { + /** + * Get a random value from an enum + * + * @param <E> + * The type of the enum + * @param enumClass + * The class of the enum + * @param rnd + * The random source to use + * @return A random value from the specified enum + */ + public static <E extends Enum<E>> E getRandomValue(Class<E> enumClass, + Random rnd) { + E[] enumValues = enumClass.getEnumConstants(); + + return new FunctionalList<>(enumValues).randItem(rnd); + } + + /** + * Do an action for a random number of enum values + * + * @param <E> + * The type of the enum + * @param enumClass + * The enum class + * @param nValues + * The number of values to execute the action on + * @param action + * The action to perform on random values + * @param rnd + * The source of randomness to use + */ + public static <E extends Enum<E>> void doForValues(Class<E> enumClass, + int nValues, Consumer<E> action, Random rnd) { + E[] enumValues = enumClass.getEnumConstants(); + + IFunctionalList<E> valueList = new FunctionalList<>(enumValues); + + int randomValueCount = enumValues.length - nValues; + + for (int i = 0; i <= randomValueCount; i++) { + E rDir = valueList.randItem(rnd); + + valueList.removeMatching(rDir); + } + + valueList.forEach(action); + } +} diff --git a/BJC-Utils2/src/main/java/bjc/utils/funcutils/FileUtils.java b/BJC-Utils2/src/main/java/bjc/utils/funcutils/FileUtils.java new file mode 100644 index 0000000..fd09fbb --- /dev/null +++ b/BJC-Utils2/src/main/java/bjc/utils/funcutils/FileUtils.java @@ -0,0 +1,77 @@ +package bjc.utils.funcutils; + +import java.io.IOException; +import java.nio.file.FileVisitResult; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.SimpleFileVisitor; +import java.nio.file.attribute.BasicFileAttributes; +import java.util.function.BiPredicate; + +/** + * Utilities for doing things with files + * + * @author ben + * + */ +public class FileUtils { + private static final class FunctionalFileVisitor + extends SimpleFileVisitor<Path> { + private BiPredicate<Path, BasicFileAttributes> traversalPredicate; + private BiPredicate<Path, BasicFileAttributes> traversalAction; + + public FunctionalFileVisitor( + BiPredicate<Path, BasicFileAttributes> traversalPredicate, + BiPredicate<Path, BasicFileAttributes> traversalAction) { + this.traversalPredicate = traversalPredicate; + this.traversalAction = traversalAction; + } + + @Override + public FileVisitResult preVisitDirectory(Path dir, + BasicFileAttributes attrs) throws IOException { + if (traversalPredicate.test(dir, attrs)) { + return FileVisitResult.CONTINUE; + } + + return FileVisitResult.SKIP_SUBTREE; + } + + @Override + public FileVisitResult visitFile(Path file, + BasicFileAttributes attrs) throws IOException { + if (traversalAction.test(file, attrs)) { + return FileVisitResult.CONTINUE; + } + + return FileVisitResult.TERMINATE; + } + } + + /** + * Traverse a directory recursively. This is a depth-first traversal + * + * + * @param root + * The directory to start the traversal at + * @param traversalPredicate + * The predicate to determine whether or not to traverse a + * directory + * @param traversalAction + * The action to invoke upon each file in the directory. + * Returning true means to continue the traversal, returning + * false stops it + * @throws IOException + * if the walk throws an exception + * + * TODO If it becomes necessary, write another overload for + * this with all the buttons and knobs from walkFileTree + */ + public static void traverseDirectory(Path root, + BiPredicate<Path, BasicFileAttributes> traversalPredicate, + BiPredicate<Path, BasicFileAttributes> traversalAction) + throws IOException { + Files.walkFileTree(root, new FunctionalFileVisitor( + traversalPredicate, traversalAction)); + } +} diff --git a/BJC-Utils2/src/main/java/bjc/utils/funcutils/FuncUtils.java b/BJC-Utils2/src/main/java/bjc/utils/funcutils/FuncUtils.java new file mode 100644 index 0000000..d89b7da --- /dev/null +++ b/BJC-Utils2/src/main/java/bjc/utils/funcutils/FuncUtils.java @@ -0,0 +1,44 @@ +package bjc.utils.funcutils; + +import java.util.function.BiFunction; +import java.util.function.Function; +import java.util.function.IntConsumer; + +/** + * Utility things for functions + * + * @author ben + * + */ +public class FuncUtils { + /** + * Do the specified action the specified number of times + * + * @param nTimes + * The number of times to do the action + * @param cons + * The action to perform + */ + public static void doTimes(int nTimes, IntConsumer cons) { + for (int i = 0; i < nTimes; i++) { + cons.accept(i); + } + } + + /** + * Convert a binary function into a unary function that returns a + * function + * + * @param <A> The initial type of the function + * @param <B> The intermediate type of the function + * @param <C> The terminal type of the function + * @param func The function to transform + * @return The function transformed into a unary function returning a function + */ + public static <A, B, C> Function<A, Function<B, C>> curry2( + BiFunction<A, B, C> func) { + return (arg1) -> (arg2) -> { + return func.apply(arg1, arg2); + }; + } +} diff --git a/BJC-Utils2/src/main/java/bjc/utils/funcutils/ListUtils.java b/BJC-Utils2/src/main/java/bjc/utils/funcutils/ListUtils.java index 1d2750b..871e1cf 100644 --- a/BJC-Utils2/src/main/java/bjc/utils/funcutils/ListUtils.java +++ b/BJC-Utils2/src/main/java/bjc/utils/funcutils/ListUtils.java @@ -6,8 +6,9 @@ import java.util.function.Consumer; import java.util.function.Function; import bjc.utils.data.GenHolder; -import bjc.utils.data.Pair; +import bjc.utils.data.IPair; import bjc.utils.funcdata.FunctionalList; +import bjc.utils.funcdata.IFunctionalList; /** * Utilities for manipulating FunctionalLists that don't belong in the @@ -20,7 +21,7 @@ public class ListUtils { private static final int MAX_NTRIESPART = 50; private static final class TokenDeaffixer - implements BiFunction<String, String, FunctionalList<String>> { + implements BiFunction<String, String, IFunctionalList<String>> { private String token; public TokenDeaffixer(String tok) { @@ -28,7 +29,7 @@ public class ListUtils { } @Override - public FunctionalList<String> apply(String operatorName, + public IFunctionalList<String> apply(String operatorName, String operatorRegex) { if (operatorName == null) { throw new NullPointerException( @@ -53,7 +54,7 @@ public class ListUtils { } private static final class TokenSplitter - implements BiFunction<String, String, FunctionalList<String>> { + implements BiFunction<String, String, IFunctionalList<String>> { private String tokenToSplit; public TokenSplitter(String tok) { @@ -61,7 +62,7 @@ public class ListUtils { } @Override - public FunctionalList<String> apply(String operatorName, + public IFunctionalList<String> apply(String operatorName, String operatorRegex) { if (operatorName == null) { throw new NullPointerException( @@ -77,10 +78,10 @@ public class ListUtils { return new FunctionalList<>(tokenToSplit); } - FunctionalList<String> splitTokens = new FunctionalList<>( + IFunctionalList<String> splitTokens = new FunctionalList<>( tokenToSplit.split(operatorRegex)); - FunctionalList<String> result = new FunctionalList<>(); + IFunctionalList<String> result = new FunctionalList<>(); int tokenExpansionSize = splitTokens.getSize(); @@ -112,17 +113,17 @@ public class ListUtils { */ private static final class GroupPartIteration<E> implements Consumer<E> { - private FunctionalList<FunctionalList<E>> returnedList; - private GenHolder<FunctionalList<E>> currentPartition; - private FunctionalList<E> rejectedItems; + private IFunctionalList<IFunctionalList<E>> returnedList; + private GenHolder<IFunctionalList<E>> currentPartition; + private IFunctionalList<E> rejectedItems; private GenHolder<Integer> numberInCurrentPartition; private int numberPerPartition; private Function<E, Integer> elementCounter; public GroupPartIteration( - FunctionalList<FunctionalList<E>> returned, - GenHolder<FunctionalList<E>> currPart, - FunctionalList<E> rejects, + IFunctionalList<IFunctionalList<E>> returned, + GenHolder<IFunctionalList<E>> currPart, + IFunctionalList<E> rejects, GenHolder<Integer> numInCurrPart, int nPerPart, Function<E, Integer> eleCount) { this.returnedList = returned; @@ -174,8 +175,8 @@ public class ListUtils { * The number of elements to put in each partition * @return A list partitioned according to the above rules */ - public static <E> FunctionalList<FunctionalList<E>> groupPartition( - FunctionalList<E> input, Function<E, Integer> elementCounter, + public static <E> IFunctionalList<IFunctionalList<E>> groupPartition( + IFunctionalList<E> input, Function<E, Integer> elementCounter, int numberPerPartition) { if (input == null) { throw new NullPointerException("Input list must not be null"); @@ -192,17 +193,17 @@ public class ListUtils { /* * List that holds our results */ - FunctionalList<FunctionalList<E>> returnedList = new FunctionalList<>(); + IFunctionalList<IFunctionalList<E>> returnedList = new FunctionalList<>(); /* * List that holds current partition */ - GenHolder<FunctionalList<E>> currentPartition = new GenHolder<>( + GenHolder<IFunctionalList<E>> currentPartition = new GenHolder<>( new FunctionalList<>()); /* * List that holds elements rejected during current pass */ - FunctionalList<E> rejectedElements = new FunctionalList<>(); + IFunctionalList<E> rejectedElements = new FunctionalList<>(); /* * The effective number of elements in the current partitition @@ -251,9 +252,9 @@ public class ListUtils { * @return A list of tokens split on all the operators * */ - public static FunctionalList<String> splitTokens( - FunctionalList<String> input, - Deque<Pair<String, String>> operators) { + public static IFunctionalList<String> splitTokens( + IFunctionalList<String> input, + Deque<IPair<String, String>> operators) { if (input == null) { throw new NullPointerException("Input must not be null"); } else if (operators == null) { @@ -261,7 +262,7 @@ public class ListUtils { "Set of operators must not be null"); } - GenHolder<FunctionalList<String>> returnedList = new GenHolder<>( + GenHolder<IFunctionalList<String>> returnedList = new GenHolder<>( input); operators.forEach((operator) -> returnedList @@ -282,9 +283,9 @@ public class ListUtils { * @return The tokens that have been deaffixed * */ - public static FunctionalList<String> deAffixTokens( - FunctionalList<String> input, - Deque<Pair<String, String>> operators) { + public static IFunctionalList<String> deAffixTokens( + IFunctionalList<String> input, + Deque<IPair<String, String>> operators) { if (input == null) { throw new NullPointerException("Input must not be null"); } else if (operators == null) { @@ -292,7 +293,7 @@ public class ListUtils { "Set of operators must not be null"); } - GenHolder<FunctionalList<String>> returnedList = new GenHolder<>( + GenHolder<IFunctionalList<String>> returnedList = new GenHolder<>( input); operators.forEach((operator) -> returnedList @@ -311,7 +312,7 @@ public class ListUtils { * The list of tokens to collapse * @return The collapsed string of tokens */ - public static String collapseTokens(FunctionalList<String> input) { + public static String collapseTokens(IFunctionalList<String> input) { if (input == null) { throw new NullPointerException("Input must not be null"); } @@ -329,7 +330,7 @@ public class ListUtils { * The seperator to use for seperating tokens * @return The collapsed string of tokens */ - public static String collapseTokens(FunctionalList<String> input, + public static String collapseTokens(IFunctionalList<String> input, String seperator) { if (input == null) { throw new NullPointerException("Input must not be null"); |
