diff --git a/README.md b/README.md index 4a1ef16..3db9dcc 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,25 @@ # HumanTaskDistributor Simple command-line tool that helps automate the process of distributing sets of tasks to many people, including weighted preference and historical variation. + +## Help +``` +usage: HumanTaskDistributor + -hl,--humans-list Path to a CSV file containing list + of humans to distribute tasks to. + First column should be the name of + the person, and second column can + be empty, or contain a + floating-point weight. + -o,--output Output file to write CSV + distribution data to. + -prev,--previous-distributions One or more CSV files containing + previous task distribution + results, to aid in balancing + distribution over multiple + iterations. Each should be of the + form: person name, task name + -tl,--tasks-list Path to a CSV file containing list + of tasks that can be distributed + to humans. First column should be + unique task name. +``` diff --git a/src/main/java/nl/andrewlalis/human_task_distributor/Distributor.java b/src/main/java/nl/andrewlalis/human_task_distributor/Distributor.java index f1efecc..ac21c96 100644 --- a/src/main/java/nl/andrewlalis/human_task_distributor/Distributor.java +++ b/src/main/java/nl/andrewlalis/human_task_distributor/Distributor.java @@ -22,6 +22,7 @@ public class Distributor { final float totalWeight = weightedHumans.values().stream().reduce(Float::sum).orElse(0.0f); final float averageTasksPerHuman = unweightedAverageTasksPerHuman / (totalWeight / taskDistributions.size()); + // Precompute the theoretical maximum number of tasks that each person should be assigned. Map maxTasksPerHuman = new HashMap<>(); weightedHumans.forEach((h, w) -> maxTasksPerHuman.put(h, w * averageTasksPerHuman)); @@ -30,6 +31,7 @@ public class Distributor { taskStack.addAll(tasks); Collections.shuffle(taskStack); + // Iteratively pop and assign each task to a person. while (!taskStack.empty()) { Task t = taskStack.pop(); Human h = this.chooseHumanForNextTask( diff --git a/src/main/java/nl/andrewlalis/human_task_distributor/HumanTaskDistributor.java b/src/main/java/nl/andrewlalis/human_task_distributor/HumanTaskDistributor.java index c793337..0e06ba0 100644 --- a/src/main/java/nl/andrewlalis/human_task_distributor/HumanTaskDistributor.java +++ b/src/main/java/nl/andrewlalis/human_task_distributor/HumanTaskDistributor.java @@ -25,11 +25,18 @@ public class HumanTaskDistributor { Map nameWeightMap = fileParser.parseHumanList(cmd.getOptionValue("hl")); Set tasks = fileParser.parseTaskList(cmd.getOptionValue("tl")); List>> previousDistributions = fileParser.parsePreviousTaskDistributions(cmd.getOptionValues("prev")); + + long start = System.currentTimeMillis(); Map> taskDistributions = new Distributor().generateDistribution(nameWeightMap, tasks, previousDistributions); - taskDistributions.forEach((key, value) -> { - System.out.println("Task distribution for " + key + ", " + value.size() + " tasks:"); - value.forEach(t -> System.out.println("\t" + t.getName())); - }); + long durationMillis = System.currentTimeMillis() - start; + System.out.printf( + "Completed distribution of %d tasks to %d people in %d ms.%n", + tasks.size(), + taskDistributions.keySet().size(), + durationMillis + ); + + // Write to a file. String filePath = cmd.hasOption("o") ? cmd.getOptionValue("o") : "distribution.csv"; CSVPrinter printer = new CSVPrinter(Files.newBufferedWriter(Paths.get(filePath), StandardCharsets.UTF_8), CSV_FORMAT); for (Map.Entry> entry : taskDistributions.entrySet()) { @@ -41,6 +48,9 @@ public class HumanTaskDistributor { } } printer.close(true); + + System.out.println("Wrote task distribution data to " + filePath); + } catch (Exception e) { System.err.println("Error: " + e.getMessage()); HelpFormatter hf = new HelpFormatter(); diff --git a/src/main/java/nl/andrewlalis/human_task_distributor/TaskDistribution.java b/src/main/java/nl/andrewlalis/human_task_distributor/TaskDistribution.java deleted file mode 100644 index 2ba2f40..0000000 --- a/src/main/java/nl/andrewlalis/human_task_distributor/TaskDistribution.java +++ /dev/null @@ -1,32 +0,0 @@ -package nl.andrewlalis.human_task_distributor; - -import lombok.Getter; - -import java.util.HashSet; -import java.util.Set; - -@Getter -public class TaskDistribution { - private final Human human; - private final float weight; - private final Set tasks; - - public TaskDistribution(Human human, float weight, Set tasks) { - this.human = human; - this.weight = weight; - this.tasks = tasks; - } - - public TaskDistribution(Human human, float weight) { - this(human, weight, new HashSet<>()); - } - - @Override - public String toString() { - return "TaskDistribution{" + - "human=" + human + - ", weight=" + weight + - ", tasks=" + tasks + - '}'; - } -}