From 7a71ddfd0a103abeab1280aa33583d28f7e8e756 Mon Sep 17 00:00:00 2001 From: Pacien TRAN-GIRARD Date: Tue, 24 Nov 2015 18:32:47 +0100 Subject: Refactor Panda A.I. --- src/ch/epfl/maze/physical/zoo/Panda.java | 130 ++++++++++++++++++------------- src/ch/epfl/maze/util/Trail.java | 2 +- 2 files changed, 78 insertions(+), 54 deletions(-) (limited to 'src/ch') diff --git a/src/ch/epfl/maze/physical/zoo/Panda.java b/src/ch/epfl/maze/physical/zoo/Panda.java index f4c2035..2f46b6d 100644 --- a/src/ch/epfl/maze/physical/zoo/Panda.java +++ b/src/ch/epfl/maze/physical/zoo/Panda.java @@ -1,7 +1,8 @@ package ch.epfl.maze.physical.zoo; import ch.epfl.maze.physical.Animal; -import ch.epfl.maze.physical.ProbabilisticAnimal; +import ch.epfl.maze.physical.stragegies.picker.RandomPicker; +import ch.epfl.maze.physical.stragegies.reducer.BackwardReducer; import ch.epfl.maze.util.Direction; import ch.epfl.maze.util.Trail; import ch.epfl.maze.util.Vector2D; @@ -16,7 +17,7 @@ import java.util.stream.Collectors; * @author EPFL * @author Pacien TRAN-GIRARD */ -public class Panda extends ProbabilisticAnimal { +public class Panda extends Animal implements BackwardReducer, RandomPicker { private final Trail trail; @@ -27,19 +28,64 @@ public class Panda extends ProbabilisticAnimal { */ public Panda(Vector2D position) { super(position); + this.trail = new Trail(); } + /** + * Reduces the set of Direction choice using Trémeaux's Algorithm and, + * if possible, avoiding going backward. + * + * @param choices A set of possible choices + * @return A subset of choices + */ + @Override + public Set reduce(Set choices) { + Set bestChoices = this.selectBestDirections(choices); + return bestChoices.size() > 1 ? BackwardReducer.super.reduce(bestChoices) : bestChoices; + } + + /** + * Moves according to Trémeaux's Algorithm: when the panda + * moves, it will mark the ground at most two times (with two different + * colors). It will prefer taking the least marked paths. Special cases + * have to be handled, especially when the panda is at an intersection. + */ + @Override + public Direction move(Set choices) { + Direction choice = this.pick(this.reduce(choices)); + + if (this.shouldMarkCurrentPosition(choices, choice)) + this.markCurrentPosition(choices); + + return choice; + } + + @Override + public Animal copy() { + return new Panda(this.getPosition()); + } + /** * Checks if the current position is an intersection given the possible choices. * * @param choices A set of possible Directions - * @return T(the current position is an intersection) + * @return T(The set of choices corresponds to an intersection) */ - private boolean isIntersection(Set choices) { + private boolean onIntersection(Set choices) { return choices.size() > 2; } + /** + * Checks if the current position is a dead end. + * + * @param choices A set of possible Directions + * @return T(The set of choices and their Marking corresponds to a dead end) + */ + private boolean inDeadEnd(Set choices) { + return choices.size() == 1 && this.allChoicesLeadingTo(choices, Trail.Marking.AVOID_MARKING); + } + /** * Get the Marking at the adjacent position given the Direction. * @@ -51,6 +97,32 @@ public class Panda extends ProbabilisticAnimal { return this.trail.getMarking(pos); } + /** + * Determines if the current position should be marked according to the rules of the Trémeaux's Algorithm, + * avoiding intersections over-marking. + * + * @param choices A set of possible Directions + * @param choice The selected Direction + * @return T(the current position should be marked) + */ + private boolean shouldMarkCurrentPosition(Set choices, Direction choice) { + return !(this.onIntersection(choices) + && this.trail.getMarking(this.getPosition()) == Trail.Marking.AVOID_MARKING + && this.getMarkingAtDirection(choice) == Trail.Marking.NO_MARKING); + } + + /** + * Marks the current position according to the rules of the Trémeaux's Algorithm. + * + * @param choices A set of possible Direction to take + */ + private void markCurrentPosition(Set choices) { + if (this.inDeadEnd(choices)) + this.trail.markPosition(this.getPosition(), Trail.Marking.NO_GO_MARKING); + else + this.trail.markPosition(this.getPosition()); + } + /** * Checks if all Direction choices are leading to the given Marking. * @@ -86,7 +158,7 @@ public class Panda extends ProbabilisticAnimal { */ private Set selectBestDirections(Set choices) { // special case - if (this.isIntersection(choices) && this.allChoicesLeadingTo(choices, Trail.Marking.AVOID_MARKING)) + if (this.onIntersection(choices) && this.allChoicesLeadingTo(choices, Trail.Marking.AVOID_MARKING)) return EnumSet.of(this.getDirection().reverse()); // general case @@ -99,52 +171,4 @@ public class Panda extends ProbabilisticAnimal { return EnumSet.noneOf(Direction.class); } - /** - * Determines if the current position should be marked according to the rules of the Trémeaux's Algorithm, - * avoiding intersections over-marking. - * - * @param choices A set of possible Directions - * @param choice The selected Direction - * @return T(the current position should be marked) - */ - private boolean shouldMarkCurrentPosition(Set choices, Direction choice) { - return !(this.isIntersection(choices) - && this.trail.getMarking(this.getPosition()) == Trail.Marking.AVOID_MARKING - && this.getMarkingAtDirection(choice) == Trail.Marking.NO_MARKING); - } - - /** - * Marks the current position according to the rules of the Trémeaux's Algorithm. - * - * @param choices A set of possible Direction to take - */ - private void markCurrentPosition(Set choices) { - if (choices.size() == 1 && this.allChoicesLeadingTo(choices, Trail.Marking.AVOID_MARKING)) // dead end - this.trail.markPosition(this.getPosition(), Trail.Marking.NO_GO_MARKING); - else - this.trail.markPosition(this.getPosition()); - } - - /** - * Moves according to Trémeaux's Algorithm: when the panda - * moves, it will mark the ground at most two times (with two different - * colors). It will prefer taking the least marked paths. Special cases - * have to be handled, especially when the panda is at an intersection. - */ - @Override - public Direction move(Set choices) { - Set smartChoices = this.selectBestDirections(choices); - Direction choice = super.move(smartChoices); - - if (this.shouldMarkCurrentPosition(choices, choice)) - this.markCurrentPosition(choices); - - return choice; - } - - @Override - public Animal copy() { - return new Panda(this.getPosition()); - } - } diff --git a/src/ch/epfl/maze/util/Trail.java b/src/ch/epfl/maze/util/Trail.java index ed806c5..33e0975 100644 --- a/src/ch/epfl/maze/util/Trail.java +++ b/src/ch/epfl/maze/util/Trail.java @@ -54,7 +54,7 @@ public class Trail { */ public Marking getMarking(Vector2D position) { Marking marking = this.trail.get(position); - return marking != null ? marking : Marking.DEFAULT; + return marking != null ? marking : Marking.NO_MARKING; } /** -- cgit v1.2.3