bdi4jade
Changes
bdi-jade/src/log4j.properties 3(+1 -2)
Details
diff --git a/bdi-jade/src/br/ufrgs/inf/bdi4jade/core/BDIAgent.java b/bdi-jade/src/br/ufrgs/inf/bdi4jade/core/BDIAgent.java
index fe58077..e367a4a 100644
--- a/bdi-jade/src/br/ufrgs/inf/bdi4jade/core/BDIAgent.java
+++ b/bdi-jade/src/br/ufrgs/inf/bdi4jade/core/BDIAgent.java
@@ -115,6 +115,7 @@ public class BDIAgent extends Agent {
synchronized (intentions) {
Map<Goal, GoalStatus> goalStatus = new HashMap<Goal, GoalStatus>();
Iterator<Intention> it = intentions.iterator();
+ List<Intention> doneIntentions = new LinkedList<>();
while (it.hasNext()) {
Intention intention = it.next();
GoalStatus status = intention.getStatus();
@@ -122,7 +123,7 @@ public class BDIAgent extends Agent {
case ACHIEVED:
case NO_LONGER_DESIRED:
case UNACHIEVABLE:
- intention.fireGoalFinishedEvent();
+ doneIntentions.add(intention);
it.remove();
break;
default:
@@ -130,6 +131,9 @@ public class BDIAgent extends Agent {
break;
}
}
+ for (Intention intention : doneIntentions) {
+ intention.fireGoalFinishedEvent();
+ }
Set<Goal> generatedGoals = optionGenerationFunction
.generateGoals(goalStatus);
diff --git a/bdi-jade/src/br/ufrgs/inf/bdi4jade/softgoal/NamedSoftgoal.java b/bdi-jade/src/br/ufrgs/inf/bdi4jade/softgoal/NamedSoftgoal.java
new file mode 100644
index 0000000..40bd762
--- /dev/null
+++ b/bdi-jade/src/br/ufrgs/inf/bdi4jade/softgoal/NamedSoftgoal.java
@@ -0,0 +1,72 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.softgoal;
+
+/**
+ * @author ingrid
+ *
+ */
+public class NamedSoftgoal implements Softgoal {
+
+ private static final long serialVersionUID = 3958189054716876043L;
+
+ private final String name;
+
+ public NamedSoftgoal(String name) {
+ this.name = name;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#equals(java.lang.Object)
+ */
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj)
+ return true;
+ if (obj == null)
+ return false;
+ if (getClass() != obj.getClass())
+ return false;
+ NamedSoftgoal other = (NamedSoftgoal) obj;
+ if (name == null) {
+ if (other.name != null)
+ return false;
+ } else if (!name.equals(other.name))
+ return false;
+ return true;
+ }
+
+ /**
+ * @return the name
+ */
+ public String getName() {
+ return name;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#hashCode()
+ */
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = 1;
+ result = prime * result + ((name == null) ? 0 : name.hashCode());
+ return result;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#toString()
+ */
+ @Override
+ public String toString() {
+ return name;
+ }
+
+}
diff --git a/bdi-jade/src/br/ufrgs/inf/bdi4jade/util/reasoning/UtilityBasedPlanSelectionStrategy.java b/bdi-jade/src/br/ufrgs/inf/bdi4jade/util/reasoning/UtilityBasedPlanSelectionStrategy.java
index c7fe22a..53db146 100644
--- a/bdi-jade/src/br/ufrgs/inf/bdi4jade/util/reasoning/UtilityBasedPlanSelectionStrategy.java
+++ b/bdi-jade/src/br/ufrgs/inf/bdi4jade/util/reasoning/UtilityBasedPlanSelectionStrategy.java
@@ -23,8 +23,12 @@
package br.ufrgs.inf.bdi4jade.util.reasoning;
import java.util.List;
+import java.util.Map;
import java.util.Set;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
import br.ufrgs.inf.bdi4jade.core.BDIAgent;
import br.ufrgs.inf.bdi4jade.goal.Goal;
import br.ufrgs.inf.bdi4jade.plan.Plan;
@@ -42,16 +46,18 @@ import br.ufrgs.inf.bdi4jade.softgoal.Softgoal;
*/
public class UtilityBasedPlanSelectionStrategy implements PlanSelectionStrategy {
+ private final Log log;
private final BDIAgent myAgent;
public UtilityBasedPlanSelectionStrategy(BDIAgent myAgent) {
+ this.log = LogFactory.getLog(getClass());
this.myAgent = myAgent;
}
@SuppressWarnings("unchecked")
private double calculateExpectedUtility(Plan plan, Softgoal softgoal) {
- List<PlanContribution> contributions = (List<PlanContribution>) plan
- .getMetadata(Plan.DefaultMetadata.CONTRIBUTIONS);
+ List<PlanContribution> contributions = ((Map<Softgoal, List<PlanContribution>>) plan
+ .getMetadata(Plan.DefaultMetadata.CONTRIBUTIONS)).get(softgoal);
double expectedUtility = 0;
if (contributions != null) {
@@ -90,13 +96,14 @@ public class UtilityBasedPlanSelectionStrategy implements PlanSelectionStrategy
Double preference = preferences
.getPreferenceForSoftgoal(softgoal);
if (preference != null) {
-
double expectedUtility = calculateExpectedUtility(plan,
softgoal);
utility += preference * expectedUtility;
-
}
}
+
+ log.debug("EU[" + plan.getId() + "] = " + utility);
+
if (selectedPlan == null || maxUtility < utility) {
selectedPlan = plan;
maxUtility = utility;
bdi-jade/src/log4j.properties 3(+1 -2)
diff --git a/bdi-jade/src/log4j.properties b/bdi-jade/src/log4j.properties
index 1a4ee8a..d5b9fde 100644
--- a/bdi-jade/src/log4j.properties
+++ b/bdi-jade/src/log4j.properties
@@ -29,6 +29,5 @@ log4j.logger.org.apache.struts2=FATAL
# Spring Stuff
log4j.logger.org.springframework=FATAL
-log4j.logger.br.ufrgs.inf.bdi4jade=INFO
-log4j.logger.br.ufrgs.inf.bdi4jade.examples=DEBUG
+log4j.logger.br.ufrgs.inf.bdi4jade=DEBUG
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/AgentStarter.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/AgentStarter.java
index 51e54c6..a29db1c 100644
--- a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/AgentStarter.java
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/AgentStarter.java
@@ -36,6 +36,7 @@ import java.util.Map;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
+import org.apache.log4j.PropertyConfigurator;
import br.ufrgs.inf.bdi4jade.examples.helloworld.HelloWorldAgent;
@@ -55,6 +56,8 @@ public class AgentStarter {
};
public static void main(String[] args) {
+ PropertyConfigurator.configure(AgentStarter.class
+ .getResource("log4j.properties"));
new AgentStarter();
}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/helloworld/HelloWorldPlan.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/helloworld/HelloWorldPlan.java
index 1ce0f81..3cee61f 100644
--- a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/helloworld/HelloWorldPlan.java
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/helloworld/HelloWorldPlan.java
@@ -17,13 +17,15 @@ public class HelloWorldPlan extends OneShotBehaviour implements PlanBody {
private static final long serialVersionUID = -9039447524062487795L;
private String name;
+ private EndState endState;
public void action() {
System.out.println("Hello, " + name + "!");
+ this.endState = EndState.SUCCESSFUL;
}
public EndState getEndState() {
- return EndState.SUCCESSFUL;
+ return endState;
}
public void init(PlanInstance planInstance) {
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/log4j.properties b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/log4j.properties
new file mode 100644
index 0000000..1a4ee8a
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/log4j.properties
@@ -0,0 +1,34 @@
+#
+# Log4J Settings for log4j 1.2.x (via jakarta-commons-logging)
+#
+# The five logging levels used by Log are (in order):
+#
+# 1. DEBUG (the least serious)
+# 2. INFO
+# 3. WARN
+# 4. ERROR
+# 5. FATAL (the most serious)
+
+
+# Set root logger level to WARN and append to stdout
+log4j.rootLogger=WARN, stdout
+
+log4j.appender.stdout=org.apache.log4j.ConsoleAppender
+log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
+
+# Pattern to output the caller's file name and line number.
+log4j.appender.stdout.layout.ConversionPattern=%d{HH:mm:ss,SSS} %5p (%c{1}:%L) - %m%n
+
+# Print only messages of level ERROR or above in the package noModule.
+log4j.logger.noModule=FATAL
+
+# OpenSymphony Stuff
+log4j.logger.com.opensymphony=FATAL
+log4j.logger.org.apache.struts2=FATAL
+
+# Spring Stuff
+log4j.logger.org.springframework=FATAL
+
+log4j.logger.br.ufrgs.inf.bdi4jade=INFO
+log4j.logger.br.ufrgs.inf.bdi4jade.examples=DEBUG
+
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/ping/PongPlan.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/ping/PongPlan.java
index 420e234..8463982 100644
--- a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/ping/PongPlan.java
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/ping/PongPlan.java
@@ -43,6 +43,7 @@ public class PongPlan extends OneShotBehaviour implements PlanBody {
private Log log;
private ACLMessage pingMsg;
+ private EndState endState;
@Override
public void action() {
@@ -52,11 +53,12 @@ public class PongPlan extends OneShotBehaviour implements PlanBody {
reply.setContent(PingPongCapability.PONG);
this.myAgent.send(reply);
log.info("Pong sent to agent" + pingMsg.getSender().getName() + "!");
+ this.endState = EndState.SUCCESSFUL;
}
@Override
public EndState getEndState() {
- return EndState.SUCCESSFUL;
+ return endState;
}
@Override
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/ExperimentRunner.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/ExperimentRunner.java
new file mode 100644
index 0000000..dc64c3b
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/ExperimentRunner.java
@@ -0,0 +1,96 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import jade.BootProfileImpl;
+import jade.core.ProfileImpl;
+import jade.wrapper.AgentContainer;
+import jade.wrapper.AgentController;
+import jade.wrapper.PlatformController;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.log4j.PropertyConfigurator;
+
+import br.ufrgs.inf.bdi4jade.event.GoalEvent;
+import br.ufrgs.inf.bdi4jade.event.GoalFinishedEvent;
+import br.ufrgs.inf.bdi4jade.event.GoalListener;
+import br.ufrgs.inf.bdi4jade.examples.AgentStarter;
+
+/**
+ * @author ingrid
+ *
+ */
+public class ExperimentRunner implements GoalListener {
+
+ public static final int ITERATIONS = 5;
+
+ public static void main(String[] args) {
+ ExperimentRunner runner = new ExperimentRunner();
+ runner.run();
+ }
+
+ private ProfileImpl bootProfile;
+ private int iteration;
+ private final Log log;
+ private jade.core.Runtime runtime;
+
+ private final TransportationAgent transportationAgent;
+
+ public ExperimentRunner() {
+ PropertyConfigurator.configure(AgentStarter.class
+ .getResource("log4j.properties"));
+ this.log = LogFactory.getLog(this.getClass());
+
+ List<String> params = new ArrayList<String>();
+ params.add("-gui");
+ params.add("-detect-main:false");
+
+ log.info("Plataform parameters: " + params);
+
+ this.bootProfile = new BootProfileImpl(params.toArray(new String[0]));
+
+ this.runtime = jade.core.Runtime.instance();
+ PlatformController controller = runtime
+ .createMainContainer(bootProfile);
+
+ this.transportationAgent = new TransportationAgent();
+ try {
+ AgentController ac = ((AgentContainer) controller).acceptNewAgent(
+ transportationAgent.getClass().getSimpleName(),
+ transportationAgent);
+ ac.start();
+ } catch (Exception e) {
+ log.error(e);
+ }
+
+ this.iteration = 0;
+ }
+
+ @Override
+ public void goalPerformed(GoalEvent event) {
+ if (event instanceof GoalFinishedEvent
+ && event.getGoal() instanceof TransportationGoal) {
+ if (iteration < ITERATIONS) {
+ run();
+ } else {
+ log.info("Iterations finished!!");
+ log.info(((GenericValueFunction<?>) transportationAgent
+ .getRootCapability().getBeliefBase()
+ .getBelief(TransportationAgent.SATISFACTION).getValue())
+ .stats());
+ }
+ }
+ }
+
+ public void run() {
+ transportationAgent.updatedPreferences();
+ transportationAgent.addGoal(new TransportationGoal(), this);
+ iteration++;
+ }
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/GenericValueFunction.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/GenericValueFunction.java
new file mode 100644
index 0000000..344237c
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/GenericValueFunction.java
@@ -0,0 +1,153 @@
+/*
+ * Created on 30 Jul 2011 20:14:49
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * @author ingrid
+ *
+ */
+public class GenericValueFunction<T> {
+
+ private Double average;
+ private Pair<Double> minMax;
+ private Double standardDeviation;
+ private Double total;
+ private Map<T, Double> values;
+
+ public GenericValueFunction() {
+ this.values = new HashMap<T, Double>();
+ this.minMax = null;
+ this.total = null;
+ this.average = null;
+ this.standardDeviation = null;
+ }
+
+ public synchronized void addValue(T key, Double value) {
+ this.values.put(key, value);
+ if (minMax == null) {
+ this.minMax = new Pair<Double>(value, value);
+ } else {
+ if (minMax.getValue1() > value)
+ minMax.setValue1(value);
+ if (minMax.getValue2() < value)
+ minMax.setValue2(value);
+ }
+
+ total = null;
+ average = null;
+ standardDeviation = null;
+ }
+
+ private synchronized void calculateAverage() {
+ average = (values.size() == 0) ? null : getTotal() / values.size();
+ }
+
+ private synchronized void calculateStandardDeviation() {
+ Double variance = getVariance();
+ standardDeviation = (variance == null) ? null : Math.pow(variance, 0.5);
+ }
+
+ /**
+ * @return the average
+ */
+ public synchronized Double getAverage() {
+ if (average == null)
+ calculateAverage();
+ return average;
+ }
+
+ public int getCount() {
+ return values.size();
+ }
+
+ public Double getMax() {
+ return minMax == null ? null : minMax.getValue2();
+ }
+
+ public Double getMin() {
+ return minMax == null ? null : minMax.getValue1();
+ }
+
+ /**
+ * @return the standardDeviation
+ */
+ public synchronized Double getStandardDeviation() {
+ if (standardDeviation == null)
+ calculateStandardDeviation();
+ return standardDeviation;
+ }
+
+ /**
+ * @return the total
+ */
+ public synchronized Double getTotal() {
+ if (total == null) {
+ this.total = 0.0;
+ for (Double value : values.values()) {
+ total += value;
+ }
+ }
+ return total;
+ }
+
+ public Double getValue(T key) {
+ return values.get(key);
+ }
+
+ public synchronized Double getVariance() {
+ long n = 0;
+ double mean = 0;
+ double s = 0.0;
+
+ for (Double x : values.values()) {
+ n++;
+ double delta = x - mean;
+ mean += delta / n;
+ s += delta * (x - mean);
+ }
+ // if you want to calculate std deviation
+ // of a sample change this to (s/(n-1))
+ return n == 0 ? null : (s / n);
+ }
+
+ public Set<T> keySet() {
+ return values.keySet();
+ }
+
+ public String stats() {
+ StringBuffer sb = new StringBuffer();
+ sb.append("Total = ").append(getTotal()).append("\n");
+ sb.append("Count = ").append(getCount()).append("\n");
+ sb.append("Min = ").append(getMin()).append("\n");
+ sb.append("Max = ").append(getMax()).append("\n");
+ sb.append("Average = ").append(getAverage()).append("\n");
+ sb.append("Standard Deviation = ").append(getStandardDeviation());
+ return sb.toString();
+ }
+
+ public String toString() {
+ StringBuffer sb = new StringBuffer();
+ for (T key : values.keySet()) {
+ sb.append("R(").append(key).append(") = ").append(values.get(key))
+ .append("\n");
+ }
+ sb.append(stats());
+ return sb.toString();
+ }
+
+ public String toStringTab() {
+ StringBuffer sb = new StringBuffer();
+ sb.append("Key\tValue\n");
+ for (T key : values.keySet()) {
+ sb.append(key).append("\t").append(values.get(key)).append("\n");
+ }
+ sb.append(stats());
+ return sb.toString();
+ }
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Pair.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Pair.java
new file mode 100644
index 0000000..352e79a
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Pair.java
@@ -0,0 +1,20 @@
+/*
+ * Created on 22 Jul 2011 11:35:52
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+/**
+ * @author ingridn
+ *
+ */
+public class Pair<T> extends PairT<T, T> {
+
+ public Pair() {
+ super();
+ }
+
+ public Pair(T value1, T value2) {
+ super(value1, value2);
+ }
+
+}
\ No newline at end of file
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/PairT.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/PairT.java
new file mode 100644
index 0000000..d430660
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/PairT.java
@@ -0,0 +1,87 @@
+/*
+ * Created on 30 Jul 2011 10:29:17
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+/**
+ * @author ingrid
+ *
+ */
+public class PairT<T1, T2> {
+
+ protected T1 value1;
+ protected T2 value2;
+
+ public PairT() {
+ this.value1 = null;
+ this.value2 = null;
+ }
+
+ public PairT(T1 value1, T2 value2) {
+ this.value1 = value1;
+ this.value2 = value2;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#equals(java.lang.Object)
+ */
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj)
+ return true;
+ if (obj == null)
+ return false;
+ if (getClass() != obj.getClass())
+ return false;
+ PairT other = (PairT) obj;
+ if (value1 == null) {
+ if (other.value1 != null)
+ return false;
+ } else if (!value1.equals(other.value1))
+ return false;
+ if (value2 == null) {
+ if (other.value2 != null)
+ return false;
+ } else if (!value2.equals(other.value2))
+ return false;
+ return true;
+ }
+
+ public T1 getValue1() {
+ return value1;
+ }
+
+ public T2 getValue2() {
+ return value2;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#hashCode()
+ */
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = 1;
+ result = prime * result + ((value1 == null) ? 0 : value1.hashCode());
+ result = prime * result + ((value2 == null) ? 0 : value2.hashCode());
+ return result;
+ }
+
+ public void setValue1(T1 value1) {
+ this.value1 = value1;
+ }
+
+ public void setValue2(T2 value2) {
+ this.value2 = value2;
+ }
+
+ @Override
+ public String toString() {
+ return "<" + value1 + ", " + value2 + ">";
+ }
+
+}
\ No newline at end of file
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Plans.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Plans.java
new file mode 100644
index 0000000..cfaeeab
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Plans.java
@@ -0,0 +1,24 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+/**
+ * @author ingrid
+ *
+ */
+public interface Plans {
+
+ public static final TransportationPlan BIKE_PLAN = new TransportationPlan(
+ "Bike", 0.05, 0.20, false, 0.10, 0.20, 86, 90);
+ public static final TransportationPlan BUS_PLAN = new TransportationPlan(
+ "Bus", 0.10, 0.18, true, 0.35, 0.40, 50, 60);
+ public static final TransportationPlan CAR_PLAN = new TransportationPlan(
+ "Car", 0.15, 0.15, false, 0.90, 0.80, 20, 35);
+ public static final TransportationPlan MOTORCYCLE_PLAN = new TransportationPlan(
+ "Moto", 0.30, 0.20, false, 0.55, 0.50, 10, 20);
+
+ public static final TransportationPlan PLANS[] = { BIKE_PLAN, BUS_PLAN,
+ CAR_PLAN, MOTORCYCLE_PLAN };
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Softgoals.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Softgoals.java
new file mode 100644
index 0000000..919cfe7
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/Softgoals.java
@@ -0,0 +1,24 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import br.ufrgs.inf.bdi4jade.softgoal.NamedSoftgoal;
+import br.ufrgs.inf.bdi4jade.softgoal.Softgoal;
+
+/**
+ * @author ingrid
+ *
+ */
+public interface Softgoals {
+
+ public static final Softgoal COMFORT = new NamedSoftgoal("COMFORT");
+ public static final Softgoal COST = new NamedSoftgoal("COST");
+ public static final Softgoal PERFORMANCE = new NamedSoftgoal("PERFORMANCE");
+ public static final Softgoal SAFETY = new NamedSoftgoal("SAFETY");
+ public static final Softgoal SECURITY = new NamedSoftgoal("SECURITY");
+
+ public static final Softgoal SOFTGOALS[] = { COMFORT, COST, PERFORMANCE,
+ SAFETY, SECURITY };
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationAgent.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationAgent.java
new file mode 100644
index 0000000..580bb01
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationAgent.java
@@ -0,0 +1,68 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import java.util.Random;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+import br.ufrgs.inf.bdi4jade.belief.TransientBelief;
+import br.ufrgs.inf.bdi4jade.plan.Plan;
+import br.ufrgs.inf.bdi4jade.preference.SoftgoalPreferences;
+import br.ufrgs.inf.bdi4jade.softgoal.Softgoal;
+import br.ufrgs.inf.bdi4jade.util.agent.UtilityBasedBDIAgent;
+
+/**
+ * @author ingrid
+ *
+ */
+public class TransportationAgent extends UtilityBasedBDIAgent {
+
+ private static final long serialVersionUID = 2712019445290687786L;
+ public static final String SATISFACTION = "Satisfaction";
+
+ private final Random rand;
+ private final Log log;
+
+ public TransportationAgent() {
+ this.log = LogFactory.getLog(this.getClass());
+ this.rand = new Random(System.currentTimeMillis());
+ }
+
+ protected void init() {
+ for (Softgoal softgoal : Softgoals.SOFTGOALS) {
+ this.addSoftgoal(softgoal);
+ }
+ for (Plan plan : Plans.PLANS) {
+ this.getRootCapability().getPlanLibrary().addPlan(plan);
+ }
+ this.getRootCapability()
+ .getBeliefBase()
+ .addBelief(
+ new TransientBelief<GenericValueFunction<Integer>>(
+ SATISFACTION,
+ new GenericValueFunction<Integer>()));
+ }
+
+ public void updatedPreferences() {
+ SoftgoalPreferences preferences = (SoftgoalPreferences) this
+ .getRootCapability().getBeliefBase()
+ .getBelief(SoftgoalPreferences.NAME);
+
+ double total = 0;
+ for (Softgoal softgoal : Softgoals.SOFTGOALS) {
+ double value = rand.nextDouble();
+ total += value;
+ preferences.setPreferenceForSoftgoal(softgoal, value);
+ }
+ for (Softgoal softgoal : Softgoals.SOFTGOALS) {
+ double value = preferences.getPreferenceForSoftgoal(softgoal);
+ double normValue = value / total;
+ preferences.setPreferenceForSoftgoal(softgoal, normValue);
+ }
+ log.debug("Preferences: " + preferences);
+ }
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationGoal.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationGoal.java
new file mode 100644
index 0000000..a705405
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationGoal.java
@@ -0,0 +1,16 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import br.ufrgs.inf.bdi4jade.goal.Goal;
+
+/**
+ * @author ingrid
+ *
+ */
+public class TransportationGoal implements Goal {
+
+ private static final long serialVersionUID = 5008348479798066431L;
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationPlan.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationPlan.java
new file mode 100644
index 0000000..231a9fc
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationPlan.java
@@ -0,0 +1,135 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+
+import br.ufrgs.inf.bdi4jade.plan.PlanContribution;
+import br.ufrgs.inf.bdi4jade.softgoal.Softgoal;
+import br.ufrgs.inf.bdi4jade.util.plan.SimplePlan;
+
+/**
+ * @author ingrid
+ *
+ */
+public class TransportationPlan extends SimplePlan {
+
+ public static final double MAX_TIME_TAKEN = 90;
+
+ private double beingRobbedProbability;
+ private double comfort;
+ private double cost;
+ private boolean costConstant;
+ private double crashProbability;
+ private int maxTime;
+ private int minTime;
+
+ public TransportationPlan(String id, double crashProbability,
+ double beingRobbedProbability, boolean costConstant, double cost,
+ double comfort, int minTime, int maxTime) {
+ super(id, TransportationGoal.class, TransportationPlanBody.class);
+
+ this.beingRobbedProbability = beingRobbedProbability;
+ this.comfort = comfort;
+ this.cost = cost;
+ this.costConstant = costConstant;
+ this.crashProbability = crashProbability;
+ this.maxTime = maxTime;
+ this.minTime = minTime;
+
+ Map<Softgoal, List<PlanContribution>> contributions = (Map<Softgoal, List<PlanContribution>>) getMetadata(DefaultMetadata.CONTRIBUTIONS);
+
+ List<PlanContribution> sgContributions = new ArrayList<PlanContribution>();
+ sgContributions.add(new PlanContribution(Softgoals.SAFETY,
+ crashProbability, 0.0));
+ sgContributions.add(new PlanContribution(Softgoals.SAFETY,
+ 1 - crashProbability, 1.0));
+ contributions.put(Softgoals.SAFETY, sgContributions);
+
+ sgContributions = new ArrayList<PlanContribution>();
+ if (costConstant) {
+ sgContributions.add(new PlanContribution(Softgoals.COST, 1.0,
+ 1 - cost));
+ } else {
+ sgContributions.add(new PlanContribution(Softgoals.COST,
+ crashProbability, 0.0));
+ sgContributions.add(new PlanContribution(Softgoals.COST,
+ 1 - crashProbability, 1 - cost));
+ }
+ contributions.put(Softgoals.COST, sgContributions);
+
+ sgContributions = new ArrayList<PlanContribution>();
+ sgContributions.add(new PlanContribution(Softgoals.COMFORT, 1.0,
+ comfort));
+ contributions.put(Softgoals.COMFORT, sgContributions);
+
+ sgContributions = new ArrayList<PlanContribution>();
+ sgContributions.add(new PlanContribution(Softgoals.SECURITY,
+ beingRobbedProbability, 0.0));
+ sgContributions.add(new PlanContribution(Softgoals.SECURITY,
+ 1 - beingRobbedProbability, 1.0));
+ contributions.put(Softgoals.SECURITY, sgContributions);
+
+ sgContributions = new ArrayList<PlanContribution>();
+ sgContributions.add(new PlanContribution(Softgoals.PERFORMANCE,
+ crashProbability, 0.0));
+ sgContributions.add(new PlanContribution(Softgoals.PERFORMANCE,
+ (1 - crashProbability) * 0.5, 1 - (minTime / MAX_TIME_TAKEN)));
+ sgContributions.add(new PlanContribution(Softgoals.PERFORMANCE,
+ (1 - crashProbability) * 0.5, 1 - (maxTime / MAX_TIME_TAKEN)));
+ contributions.put(Softgoals.PERFORMANCE, sgContributions);
+ }
+
+ /**
+ * @return the beingRobbedProbability
+ */
+ public double getBeingRobbedProbability() {
+ return beingRobbedProbability;
+ }
+
+ /**
+ * @return the comfort
+ */
+ public double getComfort() {
+ return comfort;
+ }
+
+ /**
+ * @return the cost
+ */
+ public double getCost() {
+ return cost;
+ }
+
+ /**
+ * @return the crashProbability
+ */
+ public double getCrashProbability() {
+ return crashProbability;
+ }
+
+ /**
+ * @return the maxTime
+ */
+ public int getMaxTime() {
+ return maxTime;
+ }
+
+ /**
+ * @return the minTime
+ */
+ public int getMinTime() {
+ return minTime;
+ }
+
+ /**
+ * @return the costConstant
+ */
+ public boolean isCostConstant() {
+ return costConstant;
+ }
+
+}
diff --git a/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationPlanBody.java b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationPlanBody.java
new file mode 100644
index 0000000..0a21531
--- /dev/null
+++ b/bdi-jade-test/src/br/ufrgs/inf/bdi4jade/examples/planselection/TransportationPlanBody.java
@@ -0,0 +1,133 @@
+/**
+ *
+ */
+package br.ufrgs.inf.bdi4jade.examples.planselection;
+
+import jade.core.behaviours.OneShotBehaviour;
+
+import java.util.Random;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+import br.ufrgs.inf.bdi4jade.belief.TransientBelief;
+import br.ufrgs.inf.bdi4jade.plan.PlanBody;
+import br.ufrgs.inf.bdi4jade.plan.PlanInstance;
+import br.ufrgs.inf.bdi4jade.plan.PlanInstance.EndState;
+import br.ufrgs.inf.bdi4jade.preference.SoftgoalPreferences;
+
+/**
+ * @author ingrid
+ *
+ */
+public class TransportationPlanBody extends OneShotBehaviour implements
+ PlanBody {
+
+ class Scenario {
+
+ Double comfort;
+ Double cost;
+ Boolean crashed;
+ Random rand;
+ Boolean robbed;
+ Double timeTaken;
+
+ public Scenario() {
+ this.rand = new Random(System.currentTimeMillis());
+ this.crashed = occurred(rand, plan.getCrashProbability());
+ this.comfort = plan.getComfort();
+ this.timeTaken = TransportationPlan.MAX_TIME_TAKEN;
+ this.cost = plan.getCost();
+ if (!crashed) {
+ this.timeTaken = new Double(rand.nextInt(plan.getMaxTime()
+ - plan.getMinTime())
+ + plan.getMinTime());
+ } else {
+ if (!plan.isCostConstant())
+ this.cost = 1.0;
+ }
+ this.robbed = occurred(rand, plan.getBeingRobbedProbability());
+ }
+
+ public Double getSatisfaction() {
+ double safetySatisfaction = crashed ? 0.0 : 1.0;
+ log.debug("safetySatisfaction = " + safetySatisfaction);
+
+ double costSatisfaction = 1 - cost;
+ log.debug("costSatisfaction = " + costSatisfaction);
+
+ double comfortSatisfaction = comfort;
+ log.debug("comfortSatisfaction = " + comfortSatisfaction);
+
+ double performanceSatisfaction = crashed ? 0.0
+ : 1 - (timeTaken / TransportationPlan.MAX_TIME_TAKEN);
+ log.debug("performanceSatisfaction = " + performanceSatisfaction);
+
+ double securitySatisfaction = robbed ? 0.0 : 1.0;
+ log.debug("securitySatisfaction = " + securitySatisfaction);
+
+ double satisfaction = preferences
+ .getPreferenceForSoftgoal(Softgoals.SAFETY)
+ * safetySatisfaction
+ + preferences.getPreferenceForSoftgoal(Softgoals.COST)
+ * costSatisfaction
+ + preferences.getPreferenceForSoftgoal(Softgoals.COMFORT)
+ * comfortSatisfaction
+ + preferences
+ .getPreferenceForSoftgoal(Softgoals.PERFORMANCE)
+ * performanceSatisfaction
+ + preferences.getPreferenceForSoftgoal(Softgoals.SECURITY)
+ * securitySatisfaction;
+ log.debug("Total Satisfaction = " + satisfaction);
+ return satisfaction;
+ }
+
+ private boolean occurred(Random rand, double probability) {
+ double number = rand.nextDouble();
+ return (number < probability);
+ }
+
+ @Override
+ public String toString() {
+ StringBuffer sb = new StringBuffer();
+ sb.append("[ crashed = ").append(crashed).append(", cost = ")
+ .append(cost).append(", time taken = ").append(timeTaken)
+ .append(", robbed = ").append(robbed).append(" ]");
+ return sb.toString();
+ }
+
+ }
+
+ private static final long serialVersionUID = -9039447524062487795L;
+
+ private Log log;
+ private TransportationPlan plan;
+ private SoftgoalPreferences preferences;
+ private GenericValueFunction<Integer> satisfaction;
+ private EndState endState = null;
+
+ public void action() {
+ log.debug("Plan executed: " + this.plan.getId());
+ Scenario scenario = new Scenario();
+ double satisfaction = scenario.getSatisfaction();
+ this.satisfaction.addValue(this.satisfaction.getCount() + 1,
+ satisfaction);
+ log.debug("Plan finished!");
+ this.endState = EndState.SUCCESSFUL;
+ }
+
+ public EndState getEndState() {
+ return endState;
+ }
+
+ @SuppressWarnings("unchecked")
+ public void init(PlanInstance planInstance) {
+ this.log = LogFactory.getLog(this.getClass());
+ this.plan = (TransportationPlan) planInstance.getPlan();
+ this.satisfaction = ((TransientBelief<GenericValueFunction<Integer>>) planInstance
+ .getBeliefBase().getBelief(TransportationAgent.SATISFACTION))
+ .getValue();
+ this.preferences = (SoftgoalPreferences) planInstance.getBeliefBase()
+ .getBelief(SoftgoalPreferences.NAME);
+ }
+}