diff --git a/AMOEBAonAMAK/src/agents/context/Context.java b/AMOEBAonAMAK/src/agents/context/Context.java
index fb9f6cd7621d11556c28e6b77e824eb110ba7bb3..12cd0844ba5f2f9792200aaa004eb94e2131c1e8 100644
--- a/AMOEBAonAMAK/src/agents/context/Context.java
+++ b/AMOEBAonAMAK/src/agents/context/Context.java
@@ -150,8 +150,7 @@ public class Context extends AmoebaAgent {
 		// world.trace(new ArrayList<String>(Arrays.asList(this.getName(),"NEW EXP",
 		// firstPoint.toString())));
 
-		localModel.updateModel(this.getCurrentExperiment(), getAmas().data.learningSpeed,
-				getAmas().data.numberOfPointsForRegression);
+		localModel.updateModel(this.getCurrentExperiment(), getAmas().data.learningSpeed);
 		getAmas().addAlteredContext(this);
 		this.setName(String.valueOf(this.hashCode()));
 
@@ -212,7 +211,7 @@ public class Context extends AmoebaAgent {
 			Double[] coef = ((LocalModelMillerRegression) fatherContext.localModel).getCoef();
 			((LocalModelMillerRegression) this.localModel).setCoef(coef);
 			this.actionProposition = ((LocalModelMillerRegression) fatherContext.localModel)
-					.getProposition(fatherContext);
+					.getProposition();
 		}
 
 		getAmas().addAlteredContext(this);
@@ -274,13 +273,12 @@ public class Context extends AmoebaAgent {
 			Double[] coef = ((LocalModelMillerRegression) bestNearestContext.localModel).getCoef();
 			((LocalModelMillerRegression) this.localModel).setCoef(coef);
 			this.actionProposition = ((LocalModelMillerRegression) bestNearestContext.localModel)
-					.getProposition(bestNearestContext);
+					.getProposition();
 		}
 		
 		localModel.setFirstExperiments(new ArrayList<Experiment>(bestNearestContext.getLocalModel().getFirstExperiments()));
 
-		localModel.updateModel(this.getCurrentExperiment(), getAmas().data.learningSpeed,
-				getAmas().data.numberOfPointsForRegression);
+		localModel.updateModel(this.getCurrentExperiment(), getAmas().data.learningSpeed);
 
 		getAmas().addAlteredContext(this);
 		this.setName(String.valueOf(this.hashCode()));
@@ -446,37 +444,6 @@ public class Context extends AmoebaAgent {
 		return maxExpansions;
 	}
 
-	// ---------
-	// TODO these methods look very similar, maybe factorization is possible ?
-	public void updateRequestNeighborState() { // faire le update dans le head attention partial et full
-		if (nonValidNeightborPercepts.size() == 0) {
-
-			getAmas().getHeadAgent().addRequestNeighbor(this);
-		} else {
-			getAmas().getHeadAgent().removeRequestNeighbor(this);
-		}
-	}
-
-	public void updateActivatedContexts() { // faire le update dans le head attention partial et full
-		if (nonValidPercepts.size() == 0) {
-
-			getAmas().getHeadAgent().addActivatedContext(this);
-		} else {
-			getAmas().getHeadAgent().removeActivatedContext(this);
-		}
-	}
-
-	public void updateActivatedContextsCopyForUpdate() { // faire le update dans le head attention partial et full
-		if (nonValidPercepts.size() == 0) {
-
-			getAmas().getHeadAgent().addActivatedContextCopy(this);
-		} else {
-			getAmas().getHeadAgent().removeActivatedContextCopy(this);
-		}
-
-	}
-	// --------
-
 	public void clearNonValidPerceptNeighbors() {
 		nonValidNeightborPercepts.clear();
 	}
@@ -543,7 +510,7 @@ public class Context extends AmoebaAgent {
 		((LocalModelMillerRegression) this.localModel).setCoef(coef);
 
 		this.actionProposition = ((LocalModelMillerRegression) betterContext.getLocalModel())
-				.getProposition(betterContext);
+				.getProposition();
 	}
 
 	public void analyzeResults3(Head head, Context closestContextToOracle) {
@@ -606,7 +573,7 @@ public class Context extends AmoebaAgent {
 		
 		lastDistanceToModel = getLocalModel().distance(this.getCurrentExperiment());
 		lastAverageRegressionPerformanceIndicator = head.getAverageRegressionPerformanceIndicator();
-		if(lastDistanceToModel < lastAverageRegressionPerformanceIndicator) {
+		if(lastDistanceToModel <= lastAverageRegressionPerformanceIndicator) {
 		//if(getLocalModel().distance(this.getCurrentExperiment()) < head.getAverageRegressionPerformanceIndicator()) {
 		//if (head.getCriticity(this) < head.getErrorAllowed()) {
 			confidence++;
@@ -959,14 +926,6 @@ public class Context extends AmoebaAgent {
 		return exp;
 	}
 
-	private boolean tryNewExperiment2() {
-		if (localModel.distance(getCurrentExperiment()) < 10.0) {
-			localModel.updateModelWithExperimentAndWeight(getCurrentExperiment(), 0.5, 100);
-			return true;
-		}
-		return false;
-	}
-
 	public double sumOfRangesLengths() {
 		double sum = 0;
 
@@ -1821,56 +1780,6 @@ public class Context extends AmoebaAgent {
 			activations++;
 			getAmas().getHeadAgent().proposition(this);
 		}
-	}
-	
-	private void onActOld() {
-
-		if (nonValidPercepts.size() == 0) {
-
-			getAmas().getHeadAgent().proposition(this);
-
-//			for (Percept pct : getAmas().getPercepts()) {
-//				getAmas().getHeadAgent().addPartiallyActivatedContextInNeighbors(pct, this);
-//			}
-
-		} else if (nonValidPercepts.size() == 1) {
-			//getAmas().getHeadAgent().addPartiallyActivatedContext(nonValidPercepts.get(0), this);
-		}
-
-		if (nonValidNeightborPercepts.size() == 0) {
-
-			getAmas().getHeadAgent().addRequestNeighbor(this);
-		} else if (nonValidNeightborPercepts.size() == 1) {
-			//getAmas().getHeadAgent().addPartialRequestNeighborContext(nonValidNeightborPercepts.get(0), this);
-		}
-
-		if ((nonValidNeightborPercepts.size() == 0) && (nonValidPercepts.size() == 1)) {
-
-			//getAmas().getHeadAgent().addPartiallyActivatedContextInNeighbors(nonValidPercepts.get(0), this);
-
-		}
-
-		this.activations = 0;
-		//this.valid = false;
-
-		// Reset percepts validities
-		for (Percept percept : perceptValidities.keySet()) {
-			perceptValidities.put(percept, false);
-			perceptNeighborhoodValidities.put(percept, false);
-		}
-		
-	}
-	
-	public void computeContextNeighborsValidity() {
-
-		
-		if (nonValidNeightborPercepts.size() == 1) {
-			getAmas().getHeadAgent().addPartiallyActivatedContextInNeighbors(nonValidNeightborPercepts.get(0), this);
-		}
-
-
-
-		
 	}
 
 	/**
@@ -1910,8 +1819,8 @@ public class Context extends AmoebaAgent {
 		s += "Context : " + getName() + "\n";
 		s += "Model : ";
 		s += this.localModel.getCoefsFormula() + "\n";	
-		s += "Max Prediction " + getLocalModel().getMaxProposition(this) + "\n";
-		s += "Min Prediction " + getLocalModel().getMinProposition(this) + "\n";
+		s += "Max Prediction " + getLocalModel().getMaxProposition() + "\n";
+		s += "Min Prediction " + getLocalModel().getMinProposition() + "\n";
 		return s;
 	}
 	
@@ -1922,8 +1831,8 @@ public class Context extends AmoebaAgent {
 		for(int i =1;i<localModel.getCoef().length;i++) {
 			array.add(""+localModel.getCoef()[i]);
 		}
-		array.add(""+ getLocalModel().getMinProposition(this));
-		array.add(""+ getLocalModel().getMaxProposition(this));
+		array.add(""+ getLocalModel().getMinProposition());
+		array.add(""+ getLocalModel().getMaxProposition());
 
 		return array;
 	}
@@ -1951,8 +1860,8 @@ public class Context extends AmoebaAgent {
 		s += "Mean Distance To Regression " + criticalities.getCriticalityMean("distanceToRegression") + "\n";
 		s += "Distance To Regression Allowed " + regressionPerformance.getPerformanceIndicator() +"\n\n";
 		
-		s += "Max Prediction " + getLocalModel().getMaxProposition(this) + "\n";
-		s += "Min Prediction " + getLocalModel().getMinProposition(this) + "\n\n";
+		s += "Max Prediction " + getLocalModel().getMaxProposition() + "\n";
+		s += "Min Prediction " + getLocalModel().getMinProposition() + "\n\n";
 		
 		s += "ASKED REQUEST " + waitingRequests.size() + "\n";
 		for(EndogenousRequest rqt : waitingRequests) {
@@ -2076,7 +1985,7 @@ public class Context extends AmoebaAgent {
 	}
 
 	public double getActionProposal() {
-		return localModel.getProposition(this);
+		return localModel.getProposition();
 	}
 
 	public double getCenterByPercept(Percept pct) {
@@ -2133,7 +2042,7 @@ public class Context extends AmoebaAgent {
 	 */
 	public void setLocalModel(LocalModel localModel) {
 		this.localModel = localModel;
-		this.localModel.context = this;
+		this.localModel.setContext(this);
 	}
 	
 	
diff --git a/AMOEBAonAMAK/src/agents/context/Range.java b/AMOEBAonAMAK/src/agents/context/Range.java
index 082754b311e52a8b0eab6b7606df584eb60278c6..61b53491ba423c369b008b839cc336400ddf5f7b 100644
--- a/AMOEBAonAMAK/src/agents/context/Range.java
+++ b/AMOEBAonAMAK/src/agents/context/Range.java
@@ -1484,8 +1484,6 @@ public class Range implements Serializable, Comparable, Cloneable {
 				}
 			}
 
-			this.context.updateRequestNeighborState();
-
 			if (!this.contains2(percept.getValue())) {
 				if (!this.context.getNonValidPercepts().contains(this.percept)) {
 					this.context.addNonValidPercept(this.percept);
@@ -1496,10 +1494,6 @@ public class Range implements Serializable, Comparable, Cloneable {
 				}
 			}
 
-			this.context.updateActivatedContextsCopyForUpdate();
-
-			
-
 			if (!this.context.isDying() && !context.getAmas().getSpatiallyAlteredContextForUnityUI().contains(this.context)) {
 				context.getAmas().addSpatiallyAlteredContextForUnityUI(this.context);
 			}
@@ -1548,8 +1542,6 @@ public class Range implements Serializable, Comparable, Cloneable {
 				}
 			}
 
-			this.context.updateRequestNeighborState();
-
 			if (!this.contains2(percept.getValue())) {
 				if (!this.context.getNonValidPercepts().contains(this.percept)) {
 					this.context.addNonValidPercept(this.percept);
@@ -1560,10 +1552,6 @@ public class Range implements Serializable, Comparable, Cloneable {
 				}
 			}
 
-			this.context.updateActivatedContextsCopyForUpdate();
-
-			
-
 			if (!this.context.isDying() && !context.getAmas().getSpatiallyAlteredContextForUnityUI().contains(this.context)) {
 				context.getAmas().addSpatiallyAlteredContextForUnityUI(this.context);
 			}
diff --git a/AMOEBAonAMAK/src/agents/context/localModel/LocalModel.java b/AMOEBAonAMAK/src/agents/context/localModel/LocalModel.java
index a2268693f46e26bb676a1f63ed7c56b8a7ba20db..2aab80c87bae8e396c3e7eaec30e4073612fb3b9 100644
--- a/AMOEBAonAMAK/src/agents/context/localModel/LocalModel.java
+++ b/AMOEBAonAMAK/src/agents/context/localModel/LocalModel.java
@@ -1,55 +1,110 @@
 package agents.context.localModel;
 
 import java.util.ArrayList;
+import java.util.HashMap;
 
 import agents.context.Context;
 import agents.context.Experiment;
-import agents.percept.Percept;
 
 /**
- * The abstract class of all agents in charge of the generation of the output
- * from Context Agent. For the sake of simplicity, it's not scheduled as agent
- * like other of the system.
+ * A LocalModel is used by a Context to store information and generate prediction.
  */
-public abstract class LocalModel {
-
-	public Context context;
+public interface LocalModel {
 
 	/**
-	 * Instantiates a new local model agent.
+	 * Sets the context that use the LocalModel
+	 * @param context
 	 */
-	public LocalModel(Context associatedContext) {
-		context = associatedContext;
-	}
-
+	public void setContext(Context context);
+	
+	/**
+	 * gets the context that use the LocalModel
+	 * @return
+	 */
+	public Context getContext();
+	
 	/**
 	 * Gets the proposition.
 	 *
-	 * @param context the context
 	 * @return the proposition
 	 */
-	public abstract double getProposition(Context context);
-	public abstract double getProposition(Experiment experiment);
-	public abstract double getMaxProposition(Context context);
-	public abstract double getMinProposition(Context context);
+	public double getProposition();
 	
-
+	/**
+	 * Gets the proposition with the highest value possible
+	 * @return
+	 */
+	public double getMaxProposition();
+	
+	/**
+	 * Return the point (percept value) that produce the max proposition, considering some percepts are fixed.
+	 * @return a HashMap with percept names as key, and their corresponding value. The oracle is the max proposition
+	 * @see LocalModel#getMaxProposition(Context)  
+	 */
+	public HashMap<String, Double> getMaxWithConstraint(HashMap<String, Double> fixedPercepts);;
 	
-	public abstract double getProposition(ArrayList<Experiment> experimentsList, Experiment experiment);
+	/**
+	 * Gets the proposition with the lowest value possible
+	 * @return
+	 */
+	public double getMinProposition();
 
-	public abstract String getCoefsFormula();
-	
-	public abstract void updateModelWithExperiments(ArrayList<Experiment> experimentsList);
-	public abstract void updateModelWithExperimentAndWeight(Experiment newExperiment, double weight, int numberOfPointsForRegression);
-	public abstract void updateModel(Experiment newExperiment, double weight, int numberOfPointsForRegression);
-	public abstract String coefsToString();
-	public abstract double distance(Experiment experiment);
-	public abstract ArrayList<Experiment> getFirstExperiments();
-	public abstract void setFirstExperiments( ArrayList<Experiment> frstExp);
-	public abstract boolean finishedFirstExperiments();
-	
-	public abstract Double[] getCoef();
-	public abstract void setCoef(Double[] coef);
+	/**
+	 * Gets the formula of the model
+	 * @return
+	 */
+	public String getCoefsFormula();
+	
+	/**
+	 * Update the model with a new experiment.
+	 * @param newExperiment
+	 * @param weight the weight of the new experiment in the compute of the model
+	 */
+	public void updateModel(Experiment newExperiment, double weight);
+	
+	public String coefsToString();
+	
+	/**
+	 * The distance between an experiment and the model.
+	 * @param experiment
+	 * @return
+	 */
+	public double distance(Experiment experiment);
+	
+	/**
+	 * Gets the experiments used to properly initialize the model.
+	 * @return
+	 */
+	public ArrayList<Experiment> getFirstExperiments();
+	
+	/**
+	 * Sets the experiments used to properly initialize the model.
+	 * This may not trigger an update of the model.
+	 * @param frstExp
+	 */
+	public void setFirstExperiments( ArrayList<Experiment> frstExp);
+	
+	/**
+	 * Tells if the model has enough experiments to produce a good prediction.
+	 * For example, a regression need a number of experiments equals or superior to the number of dimension.
+	 * @return
+	 */
+	public boolean finishedFirstExperiments();
+	
+	/**
+	 * Gets coefficients of the model
+	 * @return
+	 */
+	public Double[] getCoef();
+	
+	/**
+	 * Sets coefficients of the model
+	 * @return
+	 */
+	public void setCoef(Double[] coef);
 
-	public abstract TypeLocalModel getType();
+	/**
+	 * Gets the {@link TypeLocalModel} corresponding to this LocalModel
+	 */
+	public TypeLocalModel getType();
 }
diff --git a/AMOEBAonAMAK/src/agents/context/localModel/LocalModelMillerRegression.java b/AMOEBAonAMAK/src/agents/context/localModel/LocalModelMillerRegression.java
index 87998fe51fe7f0fbd06036fa3e26bf74c662f8b9..1a9bcee4aa2ff7bff3472e4d74067a55d44af682 100644
--- a/AMOEBAonAMAK/src/agents/context/localModel/LocalModelMillerRegression.java
+++ b/AMOEBAonAMAK/src/agents/context/localModel/LocalModelMillerRegression.java
@@ -2,6 +2,7 @@ package agents.context.localModel;
 
 import java.util.ArrayList;
 import java.util.Arrays;
+import java.util.HashMap;
 import java.util.List;
 
 import agents.context.Context;
@@ -14,7 +15,9 @@ import utils.TRACE_LEVEL;
 /**
  * The Class LocalModelMillerRegression.
  */
-public class LocalModelMillerRegression extends LocalModel{
+public class LocalModelMillerRegression implements LocalModel{
+	
+	private Context context;
 	
 	/** The n parameters. */
 	private int nParameters;
@@ -34,7 +37,7 @@ public class LocalModelMillerRegression extends LocalModel{
 	 * @param world the world
 	 */
 	public LocalModelMillerRegression(Context associatedContext) {
-		super(associatedContext);
+		context = associatedContext;
 		ArrayList<Percept> var = associatedContext.getAmas().getPercepts();
 		this.nParameters = var.size();
 		regression = new Regression(nParameters,true);
@@ -42,7 +45,7 @@ public class LocalModelMillerRegression extends LocalModel{
 	}
 	
 	public LocalModelMillerRegression(Context associatedContext, Double[] coefsCopy, List<Experiment> fstExperiments) {
-		super(associatedContext);
+		context = associatedContext;
 		ArrayList<Percept> var = associatedContext.getAmas().getPercepts();
 		this.nParameters = var.size();
 		regression = new Regression(nParameters,true);
@@ -50,6 +53,16 @@ public class LocalModelMillerRegression extends LocalModel{
 		firstExperiments = new ArrayList<Experiment>(fstExperiments);
 	}
 	
+	@Override
+	public void setContext(Context context) {
+		this.context = context;
+	}
+	
+	@Override
+	public Context getContext() {
+		return context;
+	}
+	
 	/**
 	 * Sets the coef.
 	 *
@@ -70,7 +83,8 @@ public class LocalModelMillerRegression extends LocalModel{
 		return coefs;
 	}
 
-	public double getProposition(Context context) {
+	@Override
+	public double getProposition() {
 			
 		ArrayList<Percept> percepts = context.getAmas().getPercepts();
 		
@@ -92,11 +106,8 @@ public class LocalModelMillerRegression extends LocalModel{
 	
 	
 	
-	public double getProposition(Context context, double[] situation) {
-		
-		ArrayList<Percept> percepts = context.getAmas().getPercepts();
+	private double getProposition(Context context, double[] situation) {
 		
-			
 		double result = coefs[0];
 
 		if (coefs[0] == Double.NaN) System.exit(0);
@@ -111,28 +122,64 @@ public class LocalModelMillerRegression extends LocalModel{
 		return result;
 	}
 	
-	public double getMaxProposition(Context context) {
+	@Override
+	public double getMaxProposition() {
 		
 		ArrayList<Percept> percepts = context.getAmas().getPercepts();			
 		double result = coefs[0];
 
-		if (coefs[0] == Double.NaN) System.exit(0);
+		if (coefs[0] == Double.NaN)
+			throw new ArithmeticException("First coeficient of model cannot be NaN");
 		
 		for (int i = 1 ; i < coefs.length ; i++) {
-			
-			if (Double.isNaN(coefs[i])) coefs[i] = 0.0;
-			if(coefs[i]>0) {
-				result += coefs[i] * context.getRanges().get(percepts.get(i-1)).getEnd();
+			double coef = coefs[i];
+			if (Double.isNaN(coef)) coef = 0.0;
+			if(coef>0) {
+				result += coef * context.getRanges().get(percepts.get(i-1)).getEnd();
 			}
 			else {
-				result += coefs[i] * context.getRanges().get(percepts.get(i-1)).getStart();
+				result += coef * context.getRanges().get(percepts.get(i-1)).getStart();
 			}
 		}
 	
 		return result;
 	}
 	
-	public double getMinProposition(Context context) {
+	@Override
+	public HashMap<String, Double> getMaxWithConstraint(HashMap<String, Double> fixedPercepts){
+		ArrayList<Percept> percepts = context.getAmas().getPercepts();
+		
+		HashMap<String, Double> result = new HashMap<String, Double>();
+		result.put("oracle", coefs[0]);
+
+		if (coefs[0] == Double.NaN)
+			throw new ArithmeticException("First coeficient of model cannot be NaN");
+		
+		for (int i = 1 ; i < coefs.length ; i++) {
+			double coef = coefs[i];
+			if (Double.isNaN(coef)) coef = 0.0;
+			double pos;
+			Percept p = percepts.get(i-1);
+			if(fixedPercepts.containsKey(p.getName())) {
+				pos = fixedPercepts.get(p.getName());
+			} else {
+				if(coef>0) {
+					pos = context.getRanges().get(p).getEnd();
+				}
+				else {
+					pos = context.getRanges().get(p).getStart();
+				}
+			}
+			double value = coef * pos;
+			result.put("oracle", result.get("oracle") + value);
+			result.put(p.getName(), pos);
+		}
+		
+		return result;
+	}
+	
+	@Override
+	public double getMinProposition() {
 		
 		ArrayList<Percept> percepts = context.getAmas().getPercepts();			
 		double result = coefs[0];
@@ -153,31 +200,6 @@ public class LocalModelMillerRegression extends LocalModel{
 		return result;
 	}
 	
-	public double getProposition(ArrayList<Experiment> experimentsList, Experiment experiment) {
-		
-
-		
-		if (experimentsList.size() == 1) {
-			return experimentsList.get(0).getOracleProposition();
-		}
-		else {
-			double result = coefs[0];
-
-			if (coefs[0] == Double.NaN) System.exit(0);
-			
-			for (int i = 1 ; i < coefs.length ; i++) {
-				
-				if (Double.isNaN(coefs[i])) coefs[i] = 0.0;
-				result += coefs[i] * experiment.getValuesAsArray()[i-1];
-
-			}
-		
-			return result;
-		}
-			
-		
-	}
-	
 	public double getProposition(Experiment experiment) {
 		
 		if (coefs[0] == Double.NaN) System.exit(0);
@@ -194,6 +216,7 @@ public class LocalModelMillerRegression extends LocalModel{
 			
 	}
 	
+	@Override
 	public String getCoefsFormula() {
 		String result = "" +coefs[0];
 	//	//System.out.println("Result 0" + " : " + result);
@@ -209,47 +232,8 @@ public class LocalModelMillerRegression extends LocalModel{
 		return result;
 
 }
-	
 	@Override
-	public void updateModelWithExperiments(ArrayList<Experiment> experimentsList) {
-		
-		regression = new Regression(nParameters,true);
-	
-		for (Experiment exp : experimentsList) {
-			
-			regression.addObservation(exp.getValuesAsArray(), exp.getOracleProposition());
-			
-	
-		}
-		
-			
-		
-		while (regression.getN() < experimentsList.get(0).getValuesAsLinkedHashMap().size() + 2) { //TODO : to improve
-			
-			regression.addObservation(experimentsList.get(0).getValuesAsArray(), experimentsList.get(0).getOracleProposition());
-			
-			System.out.println("Observations " + regression.getN());
-			
-			System.out.println(experimentsList.get(0).getValuesAsLinkedHashMap().toString());
-			for (int i = 0 ; i < experimentsList.get(0).getValuesAsArray().length ; i++ ) {
-				System.out.print(experimentsList.get(0).getValuesAsArray()[i] + "   " );
-			}
-			System.out.println(experimentsList.get(0).getOracleProposition() + "   " );
-		}
-		
-
-		
-		double[] coef = regression.regress().getParameterEstimates();
-		coefs = new Double[coef.length];
-		for(int i = 0; i < coef.length; i++) {
-			coefs[i] = coef[i];
-		}
-		
-		
-	}
-	
-	
-	public void updateModel(Experiment newExperiment, double weight, int numberOfPointsForRegression) {
+	public void updateModel(Experiment newExperiment, double weight) {
 		context.getAmas().getEnvironment().trace(TRACE_LEVEL.INFORM, new ArrayList<String>(Arrays.asList(context.getName(),"NEW POINT REGRESSION", "FIRST POINTS :", ""+firstExperiments.size(), "OLD MODEL :", coefsToString()))); 
 		
 		if(firstExperiments.size()< (nParameters + 2)) {
@@ -257,7 +241,7 @@ public class LocalModelMillerRegression extends LocalModel{
 			updateModel();
 			
 		}else {
-			updateModelWithExperimentAndWeight(newExperiment, weight, numberOfPointsForRegression);
+			updateModelWithExperimentAndWeight(newExperiment, weight, context.getAmas().data.numberOfPointsForRegression);
 		}
 		
 		context.getAmas().addSpatiallyAlteredContextForUnityUI(context);
@@ -460,12 +444,8 @@ public class LocalModelMillerRegression extends LocalModel{
 		
 		return new Pair<double[][], double[]>(artificalExperiments, artificalResults);
 	}
-
-	
-	
-
-	
 	
+	@Override
 	public double distance(Experiment experiment) {
 		
 		if (coefs[0] == Double.NaN) System.exit(0);
@@ -491,14 +471,17 @@ public class LocalModelMillerRegression extends LocalModel{
 			
 	}
 	
+	@Override
 	public ArrayList<Experiment> getFirstExperiments() {
 		return firstExperiments;
 	}
 	
+	@Override
 	public void setFirstExperiments( ArrayList<Experiment> frstExp) {
 		firstExperiments = frstExp;
 	}
 	
+	@Override
 	public String coefsToString() {
 		String coefsString = "";
 		if(coefs != null) {
@@ -509,6 +492,7 @@ public class LocalModelMillerRegression extends LocalModel{
 		return coefsString;
 	}
 	
+	@Override
 	public boolean finishedFirstExperiments() {
 		return firstExperiments.size()>= (nParameters + 2);
 	}
diff --git a/AMOEBAonAMAK/src/agents/head/Head.java b/AMOEBAonAMAK/src/agents/head/Head.java
index 67ee372989737495fddef7f94a5b661bda635f0d..ead7a3283f3d085e8db40ee6ac9af6a464edf428 100644
--- a/AMOEBAonAMAK/src/agents/head/Head.java
+++ b/AMOEBAonAMAK/src/agents/head/Head.java
@@ -17,9 +17,8 @@ import agents.percept.Percept;
 import kernel.AMOEBA;
 import ncs.NCS;
 import utils.Pair;
-import utils.PickRandom;
 import utils.PrintOnce;
-import utils.Quadruplet;
+import utils.RandomUtils;
 import utils.TRACE_LEVEL;
 
 /**
@@ -32,7 +31,6 @@ public class Head extends AmoebaAgent {
 	private Context bestContext;
 	private Context lastUsedContext;
 	private Context newContext;
-	private String functionSelected;
 
 	HashMap<Percept, Double> currentSituation = new HashMap<Percept, Double>();
 
@@ -40,20 +38,8 @@ public class Head extends AmoebaAgent {
 	public Criticalities endogenousCriticalities;
 
 	private ArrayList<Context> activatedContexts = new ArrayList<Context>();
-	private ArrayList<Context> activatedContextsCopyForUpdates = new ArrayList<Context>();
 	private ArrayList<Context> activatedNeighborsContexts = new ArrayList<Context>();
 
-	private HashMap<Percept, ArrayList<Context>> partiallyActivatedContextInNeighbors = new HashMap<Percept, ArrayList<Context>>();
-	private HashMap<Percept, ArrayList<Context>> partiallyActivatedContexts = new HashMap<Percept, ArrayList<Context>>();
-	private HashMap<Percept, ArrayList<Context>> partialNeighborContexts = new HashMap<Percept, ArrayList<Context>>();
-
-	private ArrayList<Context> contextsNeighborsByInfluence = new ArrayList<Context>();
-
-	private HashMap<Percept, ContextPair<Context, Context>> requestSurroundings = new HashMap<Percept, ContextPair<Context, Context>>();
-	private HashMap<Percept, ContextPair<Context, Context>> sharedIncompetenceContextPairs = new HashMap<Percept, ContextPair<Context, Context>>();
-
-	private ArrayList<Context> contextsInCompetition = new ArrayList<Context>();
-
 	Queue<EndogenousRequest> endogenousRequests = new PriorityQueue<EndogenousRequest>(new Comparator<EndogenousRequest>(){
 		   public int compare(EndogenousRequest r1, EndogenousRequest r2) {
 			      return r2.getPriority().compareTo(r1.getPriority());
@@ -81,29 +67,6 @@ public class Head extends AmoebaAgent {
 		for(int i =0 ; i< 20;i++) {
 			getAmas().data.executionTimesSums[i]=0.0;
 		}
-		
-
-		
-		
-
-	}
-	
-	
-
-	public void addPartiallyActivatedContext(Percept nonValidPercept, Context validContextExecptOnTheNonValidPercept) {
-		partiallyActivatedContexts.get(nonValidPercept).add(validContextExecptOnTheNonValidPercept);
-
-	}
-
-	public void addPartiallyActivatedContextInNeighbors(Percept nonValidPercept,
-			Context validContextExecptOnTheNonValidPercept) {
-		partiallyActivatedContextInNeighbors.get(nonValidPercept).add(validContextExecptOnTheNonValidPercept);
-
-	}
-
-	public void addPartialRequestNeighborContext(Percept nonValidPercept, Context validContextNeighborExecptOnTheNonValidPercept) {
-		partialNeighborContexts.get(nonValidPercept).add(validContextNeighborExecptOnTheNonValidPercept);
-
 	}
 
 	/**
@@ -280,28 +243,6 @@ public class Head extends AmoebaAgent {
 
 	}
 
-	public double getSpatialGeneralizationScore() {
-		return getAmas().data.spatialGeneralizationScore;
-	}
-
-	private boolean nearestLocalNeighbor(Context ctxt1, Context ctxt2) {
-
-		boolean nearestLocalNeighborTest = false;
-
-		for (Percept pct : getAmas().getPercepts()) {
-
-			if (partiallyActivatedContextInNeighbors.get(pct).contains(ctxt1)
-					&& partiallyActivatedContextInNeighbors.get(pct).contains(ctxt2)) {
-				nearestLocalNeighborTest = nearestLocalNeighborTest
-						|| (Math.abs(partiallyActivatedContextInNeighbors.get(pct).indexOf(ctxt1)
-								- partiallyActivatedContextInNeighbors.get(pct).indexOf(ctxt2)) == 1);
-			}
-
-		}
-
-		return nearestLocalNeighborTest;
-	}
-
 	public double getMinMaxVolume() {
 		double minMaxVolume = 1;
 		for (Percept pct : getAmas().getPercepts()) {
@@ -336,7 +277,6 @@ public class Head extends AmoebaAgent {
 		} else {
 
 			getAmas().data.noBestContext = true;
-			ArrayList<Context> allContexts = getAmas().getContexts();
 			Context nearestContext = this.getNearestContext(activatedNeighborsContexts);
 			if(nearestContext != null) {
 				getAmas().data.prediction = nearestContext.getActionProposal();
@@ -346,7 +286,7 @@ public class Head extends AmoebaAgent {
 				// to limit performance impact, we limit our search on a random sample.
 				// a better way would be to increase neighborhood.
 				PrintOnce.print("Play without oracle : no nearest context in neighbors, searching in a random sample. (only shown once)");
-				List<Context> searchList = PickRandom.pickNRandomElements(getAmas().getContexts(), 100);
+				List<Context> searchList = RandomUtils.pickNRandomElements(getAmas().getContexts(), 100);
 				nearestContext = this.getNearestContext(searchList);
 				if(nearestContext != null) {
 					getAmas().data.prediction = nearestContext.getActionProposal();
@@ -386,12 +326,6 @@ public class Head extends AmoebaAgent {
 		getAmas().data.endogenousPredictionActivatedContextsSharedIncompetence = null;
 		getAmas().data.endogenousPredictionNContextsByInfluence = null;
 
-		for (Percept pcpt : getAmas().getPercepts()) {
-			requestSurroundings.get(pcpt).clear();
-			sharedIncompetenceContextPairs.get(pcpt).clear();
-		}
-		contextsInCompetition.clear();
-
 		if (uniqueActivatedContext()) {
 			getAmas().data.endogenousPredictionActivatedContextsOverlaps = activatedContexts.get(0).getActionProposal();
 			getAmas().data.endogenousPredictionActivatedContextsOverlapsWorstDimInfluence = activatedContexts.get(0)
@@ -442,6 +376,7 @@ public class Head extends AmoebaAgent {
 		getAmas().data.maxConfidence = Double.NEGATIVE_INFINITY;
 		getAmas().data.minConfidence = Double.POSITIVE_INFINITY;
 
+		ArrayList<Context> contextsNeighborsByInfluence = new ArrayList<>();
 		for (Context ctxt : getAmas().getContexts()) {
 
 			if (ctxt.getConfidence() > getAmas().data.maxConfidence) {
@@ -516,20 +451,16 @@ public class Head extends AmoebaAgent {
 		// Test if there are surrounding contexts
 		boolean testSurroudingContext = false;
 
-		for (Percept pct : getAmas().getPercepts()) {
-
-			computeNearestContextsByPercept(pct);
-
-		}
+		HashMap<Percept, ContextPair<Context, Context>> sharedIncompetenceContextPairs = getSharedIncompetenceContextPair();
 
 		// displayContexts();
 
 		for (Percept pcpt : getAmas().getPercepts()) {
 
-			requestSurroundings.get(pcpt).print(pcpt);
 			if (sharedIncompetenceContextPairs.get(pcpt) != null) {
 				if (sharedIncompetenceContextPairs.get(pcpt).containTwoContexts()) {
 					testSurroudingContext = true;
+					break;
 				}
 			}
 
@@ -538,43 +469,40 @@ public class Head extends AmoebaAgent {
 		return testSurroudingContext;
 	}
 
-	private void diplayListRanges(ArrayList<Context> list, Percept prct, String range) {
-
-		System.out.print(range + " ranges list" + "  ");
-		for (Context ctxt : list) {
-			System.out.print(ctxt.getRanges().get(prct).getRange(range) + "  ");
+	private HashMap<Percept, ContextPair<Context, Context>> getSharedIncompetenceContextPair() {
+		HashMap<Percept, ContextPair<Context, Context>> sharedIncompetenceContextPairs = new HashMap<>();
+		
+		for (Percept pct : getAmas().getPercepts()) {
+			ContextPair<Context, Context> nearestContexts = computeNearestContextsByPercept(pct);
+			if (nearestContexts.getL() != null && nearestContexts.getR() != null) {
+				sharedIncompetenceContextPairs.put(pct, nearestContexts);
+			}
 		}
-		System.out.println(" ");
-
+		
+		return sharedIncompetenceContextPairs;
 	}
 
-	private void computeNearestContextsByPercept(Percept pct) {
-		ContextPair<Context, Context> nearestContexts = new ContextPair(null, null);
+	private ContextPair<Context, Context> computeNearestContextsByPercept(Percept pct) {
+		ContextPair<Context, Context> nearestContexts = new ContextPair<>(null, null);
 		boolean startNeighbor = false;
 		boolean endNeighbor = false;
 
 		ArrayList<Context> activatedContextInOtherPercepts = getAllActivatedContextsExeptForOnePercept(pct);
-
 		if (activatedContextInOtherPercepts.size() > 0) {
 
-
-
 			CustomComparator rangeStartComparator = new CustomComparator(pct, "start");
 			Collections.sort(activatedContextInOtherPercepts, rangeStartComparator);
-			// diplayListRanges(activatedContextInOtherPercepts, pct, "start");
 
 			for (Context ctxt : activatedContextInOtherPercepts) {
 				if (ctxt.getRanges().get(pct).getRange("start") > pct.getValue() && !startNeighbor) {
 					nearestContexts.setR(ctxt);
 					startNeighbor = true;
 				}
-
 			}
 
 			CustomComparator rangeEndComparator = new CustomComparator(pct, "end");
 			Collections.sort(activatedContextInOtherPercepts, rangeEndComparator);
 			Collections.reverse(activatedContextInOtherPercepts);
-			// diplayListRanges(activatedContextInOtherPercepts, pct, "end");
 
 			for (Context ctxt : activatedContextInOtherPercepts) {
 				if (ctxt.getRanges().get(pct).getRange("end") < pct.getValue() && !endNeighbor) {
@@ -583,65 +511,26 @@ public class Head extends AmoebaAgent {
 				}
 			}
 
-			// nearestContexts.print(pct);
-			requestSurroundings.put(pct, nearestContexts);
-
-			if (nearestContexts.getL() != null && nearestContexts.getR() != null) {
-				sharedIncompetenceContextPairs.put(pct, nearestContexts);
-			}
-		} else {
-
-		}
-
-	}
-
-	private ArrayList<Context> getAllActivatedContextsExeptForOnePercept(Percept onePercept) {
-
-		return partiallyActivatedContexts.get(onePercept);
-	}
-
-	private ArrayList<Context> getAllActivatedNeighborContextsExeptForOnePercept(Percept onePercept) {
-
-		return partialNeighborContexts.get(onePercept);
-	}
-
-	public void displayPartiallyActivatedContexts() {
-		//////// System.out.println("PARTIALLY ACTIVATED CONTEXTS");
-		for (Percept pct : partiallyActivatedContexts.keySet()) {
-			//// System.out.print(pct.getName() + " : ");
-			if (partiallyActivatedContexts.get(pct).size() > 0)
-				for (Context ctxt : partiallyActivatedContexts.get(pct)) {
-					//// System.out.print(ctxt.getName() + " ; ");
-				}
-			//////// System.out.println(" ");
-		}
-	}
-
-	public void displayContexts() {
-		//////// System.out.println("CONTEXTS");
-		for (Context ctxt : getAmas().getContexts()) {
-			//// System.out.print(ctxt.getName() + " ; ");
-		}
-		//////// System.out.println(" ");
-	}
-
-	private Percept getDifferentPercept(Percept p) {
-		for (Percept pct : partiallyActivatedContexts.keySet()) {
-			if (p != pct) {
-				return pct;
-			}
 		}
-		return null;
+		return nearestContexts;
 	}
 
-	private boolean contextActivateInOtherPerceptsThan(Context ctxt, Percept p1, Percept p2) {
-		boolean test = true;
-		for (Percept prct : partiallyActivatedContexts.keySet()) {
-			if (prct != p1 && prct != p2) {
-				test = test & partiallyActivatedContexts.get(prct).contains(ctxt);
+	/**
+	 * Return a list of contexts that have been activated by all percepts except a particular one.
+	 * @param pct
+	 * @return
+	 */
+	private ArrayList<Context> getAllActivatedContextsExeptForOnePercept(Percept pct) {
+		ArrayList<Percept> percepts = new ArrayList<>(getAmas().getPercepts());
+		percepts.remove(pct);
+		ArrayList<Context> ret = new ArrayList<>(getAmas().getContexts());
+		ret.removeIf(c -> {
+			for(Percept p : percepts) {
+				if(!p.activateContext(c)) return true;
 			}
-		}
-		return test;
+			return false;
+		});
+		return ret;
 	}
 
 	private void NCS_EndogenousCompetition() {
@@ -746,6 +635,7 @@ public class Head extends AmoebaAgent {
 		double smallestDistanceBetweenContexts = Double.POSITIVE_INFINITY;
 		double currentDistance;
 
+		HashMap<Percept, ContextPair<Context, Context>> sharedIncompetenceContextPairs = getSharedIncompetenceContextPair();
 		for (Percept pct : sharedIncompetenceContextPairs.keySet()) {
 			if (sharedIncompetenceContextPairs.get(pct) != null) {
 				if (sharedIncompetenceContextPairs.get(pct).containTwoContexts()) {
@@ -826,11 +716,6 @@ public class Head extends AmoebaAgent {
 
 	}
 
-	private void NCS_EndogenousIncompetence() {
-		// Extrapolation of contexts by creating twin contexts that will give the
-		// prediction
-	}
-
 	private void NCSDetection_Create_New_Context() {
 		/* Finally, head agent check the need for a new context agent */
 
@@ -977,27 +862,16 @@ public class Head extends AmoebaAgent {
 		getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("------------------------------------------------------------------------------------"
 				+ "---------------------------------------- NCS DETECTION POTENTIAL REQUESTS")));
 		
-		
-
-		
 		if (activatedNeighborsContexts.size() > 1) {
-
 			int i = 1;
 			for (Context ctxt : activatedNeighborsContexts) {
-
 				for (Context otherCtxt : activatedNeighborsContexts.subList(i, activatedNeighborsContexts.size())) {
-
-					
 					if(!this.isDying() && !ctxt.isDying()) {
 						EndogenousRequest potentialRequest = ctxt.endogenousRequest(otherCtxt);
-						
 						if(potentialRequest != null) {
 							addEndogenousRequest(potentialRequest);
-							
 						}
 					}
-					
-
 				}
 				i++;
 			}
@@ -1005,100 +879,17 @@ public class Head extends AmoebaAgent {
 		
 		getEnvironment().trace(TRACE_LEVEL.STATE, new ArrayList<String>(Arrays.asList("ENDO REQUESTS", ""+endogenousRequests.size())));
 		for(EndogenousRequest endoRequest : endogenousRequests) {
-			
 			getEnvironment().trace(TRACE_LEVEL.STATE, new ArrayList<String>(Arrays.asList("" + endoRequest)));
-			
 		}
 		
 	}
 
-	private void selfAnalysationOfContexts2() {
-
-		if (activatedContexts.size() > 1) {
-			selfAnalysationOfContextOnSeveralActivatedContexts();
-
-		} else if (activatedContexts.size() == 1) {
-
-//			double distanceToOracleForActivatedContext = activatedContexts.get(0).getLocalModel().distance(activatedContexts.get(0).getCurrentExperiment());
-//			//System.out.println(distanceToOracleForActivatedContext + " ******************************************************************DISTANCE TO MODEL : " );
-//			if(activatedNeighborsContexts.size()>1) {
-//				
-//				Context closestContextToOracle = null;
-//				double minDistanceToOraclePredictionInNeighbors = Double.POSITIVE_INFINITY;
-//				double currentDistanceToOraclePrediction = 0.0; 
-//				for(Context contextNeighbor : activatedNeighborsContexts) {
-//					if(contextNeighbor != activatedContexts.get(0)) {
-//						currentDistanceToOraclePrediction = contextNeighbor.getLocalModel().distance(contextNeighbor.getCurrentExperiment());
-//						if(currentDistanceToOraclePrediction<minDistanceToOraclePredictionInNeighbors) {
-//							minDistanceToOraclePredictionInNeighbors = currentDistanceToOraclePrediction;
-//							closestContextToOracle = contextNeighbor;
-//						} 
-//					}
-//				}
-//				
-//				if(minDistanceToOraclePredictionInNeighbors>distanceToOracleForActivatedContext) {
-//					//System.out.println("OLD COEFS " + activatedContexts.get(0).getLocalModel().coefsToString());
-//					activatedContexts.get(0).getLocalModel().updateModel(activatedContexts.get(0).getCurrentExperiment(),learningSpeed,numberOfPointsForRegression);
-//					//System.out.println("NEW COEFS " + activatedContexts.get(0).getLocalModel().coefsToString());
-//					
-//				}else {
-//					closestContextToOracle.solveNCS_IncompetentHead(this);
-//					//activatedContexts.get(0).setLocalModel(new LocalModelMillerRegression(world, activatedContexts.get(0), closestContextToOracle.getLocalModel().getCoef(),closestContextToOracle.getLocalModel().getFirstExperiments()));
-//					//LocalModelAgent remplacementModel = new LocalModelMillerRegression(world, activatedContexts.get(0), closestContextToOracle.getLocalModel().getCoef().clone());
-//					//activatedContexts.get(0).setLocalModel(remplacementModel);
-//					
-//				}
-//
-//				
-//			}else {
-//				//System.out.println("OLD COEFS " + activatedContexts.get(0).getLocalModel().coefsToString());
-//				activatedContexts.get(0).getLocalModel().updateModel(activatedContexts.get(0).getCurrentExperiment(),learningSpeed,numberOfPointsForRegression);
-//				//System.out.println("NEW COEFS " + activatedContexts.get(0).getLocalModel().coefsToString());
-//				
-//				
-//			}
-
-			selfAnalysationOfContextOnUniqueActivatedContext();
-
-		}
-
-		for (Context ctxt : activatedNeighborsContexts) {
-
-			if (!activatedContexts.contains(ctxt)) {
-				ctxt.NCSDetection_Uselessness();
-			}
-
-		}
-	}
-
-	private void selfAnalysationOfContexts3() {
-
-		if (activatedContexts.size() > 1) {
-
-			selfAnalysationOfContextOnSeveralActivatedContexts();
-
-		} else if (activatedContexts.size() == 1) {
-
-			selfAnalysationOfContextOnUniqueActivatedContext();
-
-		}
-
-		for (Context ctxt : activatedNeighborsContexts) {
-
-			if (!activatedContexts.contains(ctxt)) {
-				ctxt.NCSDetection_Uselessness();
-			}
-
-		}
-	}
-
 	private void selfAnalysationOfContexts4() {
 
 		getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("------------------------------------------------------------------------------------"
 				+ "---------------------------------------- SELF ANALYSIS OF CTXT")));
 		
 		double currentDistanceToOraclePrediction;
-		Context closestContextToOracle = null;
 		double minDistanceToOraclePrediction = Double.POSITIVE_INFINITY;
 
 		for (Context activatedContext : activatedContexts) {
@@ -1110,21 +901,18 @@ public class Head extends AmoebaAgent {
 			getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("MODEL DISTANCE", activatedContext.getName(),
 					"" + activatedContext.getLocalModel().distance(activatedContext.getCurrentExperiment()))));
 			if (!activatedContext.getLocalModel().finishedFirstExperiments()) {
-				activatedContext.getLocalModel().updateModel(activatedContext.getCurrentExperiment(), getAmas().data.learningSpeed,
-						getAmas().data.numberOfPointsForRegression);
+				activatedContext.getLocalModel().updateModel(activatedContext.getCurrentExperiment(), getAmas().data.learningSpeed);
 				getAmas().data.contextNotFinished = true;
 			}
 
 			else if (currentDistanceToOraclePrediction < getAverageRegressionPerformanceIndicator()) {
 			//else if (currentDistanceToOraclePrediction < regressionPerformance.getPerformanceIndicator()) {
-				activatedContext.getLocalModel().updateModel(activatedContext.getCurrentExperiment(), getAmas().data.learningSpeed,
-						getAmas().data.numberOfPointsForRegression);
+				activatedContext.getLocalModel().updateModel(activatedContext.getCurrentExperiment(), getAmas().data.learningSpeed);
 
 			}
 
 			if (currentDistanceToOraclePrediction < minDistanceToOraclePrediction) {
 				minDistanceToOraclePrediction = currentDistanceToOraclePrediction;
-				closestContextToOracle = activatedContext;
 			}
 
 			if (!getAmas().data.contextNotFinished) {
@@ -1164,136 +952,6 @@ public class Head extends AmoebaAgent {
 		}
 	}
 
-	private void selfAnalysationOfContextOnUniqueActivatedContext() {
-
-		if (activatedNeighborsContexts.size() > 0) {
-			double distanceToOracleForActivatedContext = activatedContexts.get(0).getLocalModel()
-					.distance(activatedContexts.get(0).getCurrentExperiment());
-			Quadruplet<Context, Double, Context, Double> closestAndFarestContextsToPredictionWithDistance = closestAndFarestContextsToPrediction();
-
-			double distanceToMin = Math
-					.abs(distanceToOracleForActivatedContext - closestAndFarestContextsToPredictionWithDistance.getB());
-			double distanceToMax = Math
-					.abs(distanceToOracleForActivatedContext - closestAndFarestContextsToPredictionWithDistance.getD());
-
-			if (distanceToMin < distanceToMax) {
-				getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("MODEL DISTANCE",
-						activatedContexts.get(0).getName(), "" + distanceToOracleForActivatedContext)));
-				activatedContexts.get(0).getLocalModel().updateModel(activatedContexts.get(0).getCurrentExperiment(),
-						getAmas().data.learningSpeed, getAmas().data.numberOfPointsForRegression);
-
-			}
-		} else {
-			getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(
-					Arrays.asList("MODEL DISTANCE", activatedContexts.get(0).getName(), "" + activatedContexts.get(0)
-							.getLocalModel().distance(activatedContexts.get(0).getCurrentExperiment()))));
-			activatedContexts.get(0).getLocalModel().updateModel(activatedContexts.get(0).getCurrentExperiment(),
-					getAmas().data.learningSpeed, getAmas().data.numberOfPointsForRegression);
-		}
-
-		// world.trace(new ArrayList<String>(Arrays.asList("MODEL
-		// DISTANCE",activatedContexts.get(0).getName(),
-		// ""+activatedContexts.get(0).getLocalModel().distance(activatedContexts.get(0).getCurrentExperiment()))));
-		// activatedContexts.get(0).getLocalModel().updateModel(activatedContexts.get(0).getCurrentExperiment(),learningSpeed,numberOfPointsForRegression);
-		activatedContexts.get(0).analyzeResults3(this, activatedContexts.get(0));
-	}
-
-	private Pair<Context, Double> maxModelDistanceToOraclePredictionInNeighbors() {
-		Context farestContextToOracle = null;
-		double maxDistanceToOraclePredictionInNeighbors = Double.NEGATIVE_INFINITY;
-		double currentDistanceToOraclePrediction = 0.0;
-		for (Context contextNeighbor : activatedNeighborsContexts) {
-			if (contextNeighbor != activatedContexts.get(0)) {
-				currentDistanceToOraclePrediction = contextNeighbor.getLocalModel()
-						.distance(contextNeighbor.getCurrentExperiment());
-				getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("MODEL DISTANCE", contextNeighbor.getName(),
-						"" + currentDistanceToOraclePrediction)));
-				if (currentDistanceToOraclePrediction > maxDistanceToOraclePredictionInNeighbors) {
-					maxDistanceToOraclePredictionInNeighbors = currentDistanceToOraclePrediction;
-					farestContextToOracle = contextNeighbor;
-				}
-			}
-		}
-		return new Pair<Context, Double>(farestContextToOracle, maxDistanceToOraclePredictionInNeighbors);
-	}
-
-	private Pair<Context, Double> minModelDistanceToOraclePredictionInNeighbors() {
-		Context closestContextToOracle = null;
-		double minDistanceToOraclePredictionInNeighbors = Double.POSITIVE_INFINITY;
-		double currentDistanceToOraclePrediction = 0.0;
-		for (Context contextNeighbor : activatedNeighborsContexts) {
-			if (contextNeighbor != activatedContexts.get(0)) {
-				currentDistanceToOraclePrediction = contextNeighbor.getLocalModel()
-						.distance(contextNeighbor.getCurrentExperiment());
-				getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("MODEL DISTANCE", contextNeighbor.getName(),
-						"" + currentDistanceToOraclePrediction)));
-				if (currentDistanceToOraclePrediction < minDistanceToOraclePredictionInNeighbors) {
-					minDistanceToOraclePredictionInNeighbors = currentDistanceToOraclePrediction;
-					closestContextToOracle = contextNeighbor;
-				}
-			}
-		}
-		return new Pair<Context, Double>(closestContextToOracle, minDistanceToOraclePredictionInNeighbors);
-	}
-
-	private Quadruplet<Context, Double, Context, Double> closestAndFarestContextsToPrediction() {
-		Context farestContextToOracle = null;
-		double maxDistanceToOraclePredictionInNeighbors = Double.NEGATIVE_INFINITY;
-		Context closestContextToOracle = null;
-		double minDistanceToOraclePredictionInNeighbors = Double.POSITIVE_INFINITY;
-
-		double currentDistanceToOraclePrediction = 0.0;
-		for (Context contextNeighbor : activatedNeighborsContexts) {
-			if (contextNeighbor != activatedContexts.get(0)) {
-				currentDistanceToOraclePrediction = contextNeighbor.getLocalModel()
-						.distance(contextNeighbor.getCurrentExperiment());
-				getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("MODEL DISTANCE", contextNeighbor.getName(),
-						"" + currentDistanceToOraclePrediction)));
-				if (currentDistanceToOraclePrediction > maxDistanceToOraclePredictionInNeighbors) {
-					maxDistanceToOraclePredictionInNeighbors = currentDistanceToOraclePrediction;
-					farestContextToOracle = contextNeighbor;
-				}
-				if (currentDistanceToOraclePrediction < minDistanceToOraclePredictionInNeighbors) {
-					minDistanceToOraclePredictionInNeighbors = currentDistanceToOraclePrediction;
-					closestContextToOracle = contextNeighbor;
-				}
-			}
-		}
-		return new Quadruplet<Context, Double, Context, Double>(closestContextToOracle,
-				minDistanceToOraclePredictionInNeighbors, farestContextToOracle,
-				maxDistanceToOraclePredictionInNeighbors);
-	}
-
-	private void selfAnalysationOfContextOnSeveralActivatedContexts() {
-
-		Context closestContextToOracle = null;
-		double minDistanceToOraclePrediction = Double.POSITIVE_INFINITY;
-		double currentDistanceToOraclePrediction = 0.0;
-
-		for (Context activatedContext : activatedContexts) {
-			currentDistanceToOraclePrediction = activatedContext.getLocalModel()
-					.distance(activatedContext.getCurrentExperiment());
-
-			getEnvironment().trace(TRACE_LEVEL.DEBUG, new ArrayList<String>(Arrays.asList("MODEL DISTANCE", activatedContext.getName(),
-					"" + activatedContext.getLocalModel().distance(activatedContext.getCurrentExperiment()))));
-			if (currentDistanceToOraclePrediction < minDistanceToOraclePrediction) {
-				minDistanceToOraclePrediction = currentDistanceToOraclePrediction;
-				closestContextToOracle = activatedContext;
-			}
-
-		}
-
-		closestContextToOracle.getLocalModel().updateModel(closestContextToOracle.getCurrentExperiment(), getAmas().data.learningSpeed,
-				getAmas().data.numberOfPointsForRegression);
-
-		activatedContextsCopyForUpdates = new ArrayList<Context>(activatedContexts);
-		for (Context activatedContext : activatedContexts) {
-			activatedContext.analyzeResults3(this, closestContextToOracle);
-
-		}
-		activatedContexts = activatedContextsCopyForUpdates;
-	}
-
 	private void setNearestContextAsBestContext() {
 		Context nearestContext = this.getNearestContext(activatedNeighborsContexts);
 
@@ -1306,25 +964,6 @@ public class Head extends AmoebaAgent {
 		bestContext = nearestContext;
 	}
 
-	private void setNearestGoodContextAsBestContext() {
-		Context nearestContext = this.getNearestGoodContext(activatedNeighborsContexts);
-
-		if (nearestContext != null) {
-			getAmas().data.prediction = nearestContext.getActionProposal();
-		} else {
-			getAmas().data.prediction = 0.0;
-		}
-
-		bestContext = nearestContext;
-	}
-
-	/**
-	 * Endogenous feedback.
-	 */
-	private void endogenousFeedback() {
-		// bestContext.growRanges(this);
-	}
-
 	/**
 	 * Gets the nearest good context.
 	 *
@@ -1364,28 +1003,6 @@ public class Head extends AmoebaAgent {
 
 	}
 
-	/**
-	 * Gets the distance to nearest good context.
-	 *
-	 * @param allContext the all context
-	 * @return the distance to nearest good context
-	 */
-	private Pair<Context, Double> getNearestGoodContextWithDistance(ArrayList<Context> contextNeighbors) {
-		double d = Double.MAX_VALUE;
-		Context nearestGoodContext = null;
-		for (Context c : contextNeighbors) {
-			if (Math.abs((c.getActionProposal() - getAmas().data.oracleValue)) <= getAmas().data.predictionPerformance.getPerformanceIndicator()
-					&& c != newContext && !c.isDying()) {
-				if (getExternalDistanceToContext(c) < d) {
-					d = getExternalDistanceToContext(c);
-					nearestGoodContext = c;
-				}
-			}
-		}
-		return new Pair<Context, Double>(nearestGoodContext, d);
-
-	}
-	
 	private Pair<Context, Double> getbestContextInNeighborsWithDistanceToModel(ArrayList<Context> contextNeighbors) {
 		double d = Double.MAX_VALUE;
 		Context bestContextInNeighbors = null;
@@ -1464,19 +1081,6 @@ public class Head extends AmoebaAgent {
 		return d;
 	}
 
-	private double getDistanceToContext(Context context) {
-		double totalDistance = 0.0;
-		for (Percept p : getAmas().getPercepts()) {
-			double distance = context.distance(p, p.getValue());
-			if (distance > 0) {
-				totalDistance += distance;
-			}
-
-		}
-
-		return totalDistance;
-	}
-
 	/**
 	 * One of proposed context was good.
 	 *
@@ -1951,24 +1555,6 @@ public class Head extends AmoebaAgent {
 		getAmas().data.useOracle = !getAmas().data.useOracle;
 	}
 
-	/**
-	 * Gets the function selected.
-	 *
-	 * @return the function selected
-	 */
-	public String getFunctionSelected() {
-		return functionSelected;
-	}
-
-	/**
-	 * Sets the function selected.
-	 *
-	 * @param functionSelected the new function selected
-	 */
-	public void setFunctionSelected(String functionSelected) {
-		this.functionSelected = functionSelected;
-	}
-
 	/**
 	 * Gets the n propositions received.
 	 *
@@ -2076,86 +1662,6 @@ public class Head extends AmoebaAgent {
 		this.getAmas().data.prediction = prediction;
 	}
 
-	public ArrayList<Context> getPartiallyActivatedContexts(Percept pct) {
-		return partiallyActivatedContexts.get(pct);
-	}
-
-	public ArrayList<Context> getPartiallyActivatedNeighborContexts(Percept pct) {
-		return partialNeighborContexts.get(pct);
-	}
-
-	public HashMap<Percept, ContextPair<Context, Context>> getRequestSurroundings() {
-		return requestSurroundings;
-	}
-
-	public boolean requestSurroundingContains(Context ctxt) {
-
-		for (Percept pct : requestSurroundings.keySet()) {
-
-			if (requestSurroundings.get(pct).contains(ctxt)) {
-				return true;
-			}
-		}
-		return false;
-
-	}
-
-	public ArrayList<Context> getContextsInCompetition() {
-		return contextsInCompetition;
-	}
-
-	public Head clone() throws CloneNotSupportedException {
-		return (Head) super.clone();
-	}
-
-	public void addRequestNeighbor(Context ctxt) {
-		if (!activatedNeighborsContexts.contains(ctxt)) {
-
-			activatedNeighborsContexts.add(ctxt);
-		}
-	}
-
-	public void addActivatedContext(Context ctxt) {
-		if (!activatedContexts.contains(ctxt)) {
-			activatedContexts.add(ctxt);
-
-
-			for (Context cxt : activatedContexts) {
-
-			}
-		}
-	}
-
-	public void addActivatedContextCopy(Context ctxt) {
-		if (!activatedContextsCopyForUpdates.contains(ctxt)) {
-			activatedContextsCopyForUpdates.add(ctxt);
-
-
-			for (Context cxt : activatedContextsCopyForUpdates) {
-
-			}
-		}
-	}
-
-	public void removeActivatedContext(Context ctxt) {
-		if (activatedContexts.contains(ctxt)) {
-			activatedContexts.remove(ctxt);
-		}
-	}
-
-	public void removeActivatedContextCopy(Context ctxt) {
-		if (activatedContextsCopyForUpdates.contains(ctxt)) {
-			activatedContextsCopyForUpdates.remove(ctxt);
-		}
-	}
-
-	public void removeRequestNeighbor(Context ctxt) {
-		if (activatedNeighborsContexts.contains(ctxt)) {
-
-			activatedNeighborsContexts.remove(ctxt);
-		}
-	}
-
 	public ArrayList<Context> getActivatedNeighborsContexts() {
 		return activatedNeighborsContexts;
 	}
@@ -2164,34 +1670,9 @@ public class Head extends AmoebaAgent {
 		activatedNeighborsContexts = neighbors;
 	}
 
-
-	public ArrayList<Context> getContextNeighborsByInfluence() {
-		return contextsNeighborsByInfluence;
-	}
-
-	public void displayActivatedNeighborsContexts() {
-		for (Context ctxt : activatedNeighborsContexts) {
-
-		}
-	}
-
-	public void clearActivatedNeighborsContexts() {
-		activatedNeighborsContexts.clear();
-	}
-
-	public void clearContextdNeighborsByInfluence() {
-		contextsNeighborsByInfluence.clear();
-	}
-
 	public void clearAllUseableContextLists() {
 		activatedContexts.clear();
 		activatedNeighborsContexts.clear();
-		contextsNeighborsByInfluence.clear();
-		for (Percept pct : getAmas().getPercepts()) {
-			partiallyActivatedContexts.get(pct).clear();
-			partiallyActivatedContextInNeighbors.get(pct).clear();
-			partialNeighborContexts.get(pct).clear();
-		}
 	}
 
 	public Double getMaxRadiusForContextCreation(Percept pct) {
@@ -2372,21 +1853,6 @@ public class Head extends AmoebaAgent {
 		
 	}
 	
-	public void updatePartiallyActivatedNeighbors() {
-		
-		for(Percept pct: getAmas().getPercepts()) {
-			
-			pct.computeContextNeighborsValidity(activatedNeighborsContexts);
-			
-		}
-		
-		for(Context ctxt : activatedNeighborsContexts) {
-			
-			ctxt.computeContextNeighborsValidity();
-			
-		}
-	}
-	
 	public boolean isVoid(HashMap<Percept, Double> request) {
 		boolean test;
 		
@@ -2411,18 +1877,11 @@ public class Head extends AmoebaAgent {
 		int numberOfRegressions = 0;
 		if(activatedNeighborsContexts.size()>0) {
 			double meanRegressionPerformanceIndicator = 0.0;
-			
 			for(Context ctxt : activatedNeighborsContexts) {
-				
-
-				if(ctxt.regressionPerformance != null) {
 					meanRegressionPerformanceIndicator += ctxt.regressionPerformance.performanceIndicator;
 					numberOfRegressions+=1;
-				}
-				
-				
 			}
-			
+			assert numberOfRegressions != 0;
 			return meanRegressionPerformanceIndicator/numberOfRegressions;
 		}
 		else{
@@ -2430,16 +1889,8 @@ public class Head extends AmoebaAgent {
 		}
 		
 	}
-	
-	
-	
-
-	// -----------------
-	// AMOEBAonAMAK ---
-	// -----------------
 
 	public void proposition(Context c) {
-
 		activatedContexts.add(c);
 	}
 	
@@ -2449,19 +1900,8 @@ public class Head extends AmoebaAgent {
 		getAmas().data.maxConfidence = Double.NEGATIVE_INFINITY;
 		getAmas().data.minConfidence = Double.POSITIVE_INFINITY;
 
-		// getAmas().data.mappingPerformance.setPerformanceIndicator(world.getMappingErrorAllowed());//
-		// Math.pow(world.getMappingErrorAllowed(),
-		// world.getScheduler().getPercepts().size());
-
 		criticalities = new Criticalities(getAmas().data.numberOfCriticityValuesForAverage);
 		endogenousCriticalities = new Criticalities(getAmas().data.numberOfCriticityValuesForAverageforVizualisation);
 	}
-
-	public void addPercept(Percept pct) {
-		partiallyActivatedContextInNeighbors.put(pct, new ArrayList<Context>());
-		partiallyActivatedContexts.put(pct, new ArrayList<Context>());
-		partialNeighborContexts.put(pct, new ArrayList<Context>());
-		requestSurroundings.put(pct, new ContextPair<Context, Context>(null, null));
-		sharedIncompetenceContextPairs.put(pct, new ContextPair<Context, Context>(null, null));
-	}
+	
 }
diff --git a/AMOEBAonAMAK/src/agents/percept/Percept.java b/AMOEBAonAMAK/src/agents/percept/Percept.java
index 064969461e53732961f008123fc2106b850b5bfe..52c9a398ded9453bac8fb6692c977517f61b5050 100644
--- a/AMOEBAonAMAK/src/agents/percept/Percept.java
+++ b/AMOEBAonAMAK/src/agents/percept/Percept.java
@@ -53,8 +53,6 @@ public class Percept extends AmoebaAgent {
 		value = getAmas().getPerceptions(this.name);
 		ajustMinMax();
 		computeContextProjectionValidityOptimized();
-		//computeContextProjectionValidity();
-
 	}
 
 	public void computeContextProjectionValidity() {
@@ -124,7 +122,7 @@ public class Percept extends AmoebaAgent {
 		}
 		
 		for (Context c : contexts) {
-			if (contextProjections.get(c).contains(this.value)) {
+			if (activateContext(c)) {
 				validContextProjection.add(c);
 			}
 		} 
@@ -137,7 +135,7 @@ public class Percept extends AmoebaAgent {
 		}
 		
 		for (Context c : neighborsContexts) {
-			if(contextProjections.get(c).inNeighborhood()) {
+			if(inNeighborhood(c)) {
 				neighborContextProjection.add(c);
 			}
 		} 
@@ -145,6 +143,24 @@ public class Percept extends AmoebaAgent {
 		
 		logger().debug("CYCLE "+getAmas().getCycle(), "%s's valid contexts : %s", toString(), validContextProjection.toString());
 	}
+	
+	/**
+	 * Return true if the context is activated by this percept.
+	 * @param context
+	 * @return
+	 */
+	public boolean activateContext(Context context) {
+		return contextProjections.get(context).contains(this.value);
+	}
+	
+	/**
+	 * Return true if the context is in the neighborhood of this percept.
+	 * @param context
+	 * @return
+	 */
+	public boolean inNeighborhood(Context context) {
+		return contextProjections.get(context).inNeighborhood();
+	}
 
 
 	/**
diff --git a/AMOEBAonAMAK/src/experiments/F_XY_System.java b/AMOEBAonAMAK/src/experiments/F_XY_System.java
index 86a0d739f772a9e98e7c03d1aa7b10eaeb764f28..30f3fdfdf8fa9706fea2abee71c0a9307b06fc2d 100644
--- a/AMOEBAonAMAK/src/experiments/F_XY_System.java
+++ b/AMOEBAonAMAK/src/experiments/F_XY_System.java
@@ -48,7 +48,7 @@ public class F_XY_System implements StudiedSystem {
 
 		out.put("px0", x);
 		out.put("px1", y);
-		out.put("oracle", result);
+		out.put("oracle", 0.0);
 		return out;
 	}
 
diff --git a/AMOEBAonAMAK/src/experiments/MinimalMain.java b/AMOEBAonAMAK/src/experiments/MinimalMain.java
index 60218985a5ed9718f003c4cfe7f8cf21f96a65a2..b9b0bde35821831dfe658b762a50be32ceb0540a 100644
--- a/AMOEBAonAMAK/src/experiments/MinimalMain.java
+++ b/AMOEBAonAMAK/src/experiments/MinimalMain.java
@@ -1,12 +1,7 @@
 package experiments;
 
-import java.util.HashMap;
-
-import fr.irit.smac.amak.Configuration;
-import fr.irit.smac.amak.tools.Log;
 import kernel.AMOEBA;
 import kernel.StudiedSystem;
-import kernel.backup.SaveHelperDummy;
 
 /**
  * The most minimal main possible producing a functioning amoeba.
@@ -16,61 +11,12 @@ import kernel.backup.SaveHelperDummy;
 public class MinimalMain {
 
 	public static void main(String[] args) throws InterruptedException {
-		Configuration.commandLineMode = true;
-		Log.defaultMinLevel = Log.Level.INFORM;
 		// create a system to be studied
-		StudiedSystem studiedSystem = new NDimCube(50.0, 3);
+		StudiedSystem studiedSystem = new F_XY_System(50.0);
 		// create the amoeba
 		// Make sure the path to the config file is correct.
-		AMOEBA amoeba = new AMOEBA("resources/threeDimensionsLauncher.xml", studiedSystem);
-		amoeba.saver = new SaveHelperDummy();
+		AMOEBA amoeba = new AMOEBA("resources/twoDimensionsLauncher.xml", studiedSystem);
 		// a window should have appeared, allowing you to control and visualize the amoeba.
-		
-		Thread.sleep(5000);
-		
-		long start = System.currentTimeMillis();
-		long end = System.currentTimeMillis();
-		for(int i = 0; i < 10000; i++) {
-			studiedSystem.playOneStep();
-			amoeba.learn(studiedSystem.getOutput());
-			if(i%100 == 99) {
-				end = System.currentTimeMillis();
-				System.out.println("Time for 100 learn: "+(end-start)/1000.0);
-				start = System.currentTimeMillis();
-			}
-		}
-		
-		start = System.currentTimeMillis();
-		end = System.currentTimeMillis();
-		for(int i = 0; i < 1000; i++) {
-			studiedSystem.playOneStep();
-			amoeba.request(studiedSystem.getOutput());
-			if(i%100 == 99) {
-				end = System.currentTimeMillis();
-				System.out.println("Time for 100 request: "+(end-start)/1000.0);
-				start = System.currentTimeMillis();
-			}
-		}
-		
-		start = System.currentTimeMillis();
-		end = System.currentTimeMillis();
-		for(int i = 0; i < 1000; i++) {
-			studiedSystem.playOneStep();
-			HashMap<String, Double> req = studiedSystem.getOutput();
-			req.remove("px1");
-			req.remove("px2");
-			req.remove("px3");
-			req.remove("oracle");
-			amoeba.maximize(req);
-			if(i%100 == 99) {
-				end = System.currentTimeMillis();
-				System.out.println("Time for 100 maximize: "+(end-start)/1000.0);
-				start = System.currentTimeMillis();
-			}
-		}
-		
-		System.exit(0);
-		
 	}
 
 }
diff --git a/AMOEBAonAMAK/src/experiments/SimpleReinforcement.java b/AMOEBAonAMAK/src/experiments/SimpleReinforcement.java
new file mode 100644
index 0000000000000000000000000000000000000000..b63df76532b63de09980521021efc64b13d007eb
--- /dev/null
+++ b/AMOEBAonAMAK/src/experiments/SimpleReinforcement.java
@@ -0,0 +1,125 @@
+package experiments;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Random;
+
+import fr.irit.smac.amak.Configuration;
+import fr.irit.smac.amak.ui.drawables.Drawable;
+import fr.irit.smac.amak.ui.drawables.DrawableOval;
+import gui.AmoebaWindow;
+import javafx.scene.paint.Color;
+import kernel.AMOEBA;
+import utils.Pair;
+import utils.RandomUtils;
+import utils.XmlConfigGenerator;
+
+/**
+ * Train an amoeba on a simple reinforcement task.
+ * The goal of the task is to get to the center. When the position of the agent cross 0, it gets a reward of 100.
+ * The agent can only moves in 2 directions, of a distance of 1. Moving give a reward of -1.
+ * If the agent moves outside of the allowed range, it gets a reward of -100. 
+ * @author Hugo
+ *
+ */
+public class SimpleReinforcement {
+	
+	private Random rand = new Random();
+	private double x = 0;
+	private double reward = 0;
+	private Drawable pos;
+
+	public static void main(String[] args) {
+		ArrayList<Pair<String, Boolean>> sensors = new ArrayList<>();
+		sensors.add(new Pair<String, Boolean>("p1", false));
+		sensors.add(new Pair<String, Boolean>("a1", true));
+		File config;
+		try {
+			config = File.createTempFile("config", "xml");
+			XmlConfigGenerator.makeXML(config, sensors);
+		} catch (IOException e) {
+			e.printStackTrace();
+			System.exit(1);
+			return; // now compilator know config is initialized
+		}
+		
+		AMOEBA amoeba = new AMOEBA(config.getAbsolutePath(), null);
+		SimpleReinforcement env = new SimpleReinforcement();
+		
+		Random r = new Random();
+		HashMap<String, Double> state = env.reset();
+		HashMap<String, Double> state2;
+		for(int i = 0; i < 10000; i++) {
+			state.remove("oracle");
+			HashMap<String, Double> action = amoeba.maximize(state);
+			if(r.nextDouble() < 0.2 || action.get("oracle").equals(Double.NEGATIVE_INFINITY) ) {
+				System.out.println("Random action");
+				action.put("a1", (r.nextBoolean() ? 10.0 : -10.0));
+			}
+			state2 = env.step(action.get("a1"));
+			action.put("oracle", state2.get("oracle"));
+			action.put("p1", state.get("p1"));
+			System.out.println(action);
+			amoeba.learn(action);
+			state = state2;
+		}
+	}
+	
+	/**
+	 * Must be called AFTER an AMOEBA with GUI
+	 */
+	public SimpleReinforcement() {
+		Configuration.commandLineMode = false;
+		AmoebaWindow instance = AmoebaWindow.instance();
+		pos = new DrawableOval(0.5, 0.5, 1, 1);
+		pos.setColor(new Color(0.5, 0.0, 0.0, 0.5));
+		instance.mainVUI.add(pos);
+		instance.mainVUI.createAndAddRectangle(-50, -0.25, 100, 0.5);
+		instance.mainVUI.createAndAddRectangle(-0.25, -1, 0.5, 2);
+		
+		
+		
+	}
+	
+	public HashMap<String, Double> step(double action){
+		if(action == 0.0) action = rand.nextDouble();
+		if(action > 0.0) action = Math.ceil(action);
+		if(action < 0.0 ) action = Math.floor(action);
+		if(action > 1.0) action = 1.0;
+		if(action < -1.0) action = -1.0;
+		double oldX = x;
+		x = x + action;
+		if(x < -50.0 || x > 50.0) {
+			x = RandomUtils.nextDouble(rand, -50.0, Math.nextUp(50.0));
+			reward = -100.0;
+		} else if(x == 0.0 || sign(oldX) != sign(x)) {
+			// win !
+			reward = 100.0;
+			x = RandomUtils.nextDouble(rand, -50.0, Math.nextUp(50.0));
+		} else {
+			reward = -1.0;
+		}
+		HashMap<String, Double> ret = new HashMap<>();
+		ret.put("p1", x);
+		ret.put("oracle", reward);
+		pos.move(x+0.5, 0.5);
+		return ret;
+	}
+	
+	public HashMap<String, Double> reset(){
+		x = RandomUtils.nextDouble(rand, -50.0, Math.nextUp(50.0));
+		reward = 0.0;
+		
+		HashMap<String, Double> ret = new HashMap<>();
+		ret.put("p1", x);
+		ret.put("oracle", reward);
+		return ret;
+	}
+	
+	private int sign(double x) {
+		return x < 0 ? -1 : 1;
+	}
+
+}
diff --git a/AMOEBAonAMAK/src/experiments/TestingMain.java b/AMOEBAonAMAK/src/experiments/TestingMain.java
index 20332e2005b0b34e1b3965b4469a2a1362c2ad39..55bfd61be6a785e91185c2cf2eff2c396e810a15 100644
--- a/AMOEBAonAMAK/src/experiments/TestingMain.java
+++ b/AMOEBAonAMAK/src/experiments/TestingMain.java
@@ -16,7 +16,7 @@ import kernel.backup.SaveHelperDummy;
 public class TestingMain {
 
 	public static void main(String[] args) throws InterruptedException {
-		Configuration.commandLineMode = true;
+		Configuration.commandLineMode = false;
 		Log.defaultMinLevel = Log.Level.INFORM;
 		// create a system to be studied
 		StudiedSystem studiedSystem = new NDimCube(50.0, 3);
@@ -30,7 +30,7 @@ public class TestingMain {
 		
 		long start = System.currentTimeMillis();
 		long end = System.currentTimeMillis();
-		for(int i = 0; i < 10000; i++) {
+		for(int i = 0; i < 1000; i++) {
 			studiedSystem.playOneStep();
 			amoeba.learn(studiedSystem.getOutput());
 			if(i%100 == 99) {
diff --git a/AMOEBAonAMAK/src/experiments/XmlConfigGenerator.java b/AMOEBAonAMAK/src/experiments/XmlConfigGenerator.java
deleted file mode 100644
index 00f5086a85ab7d5363024529ae1cf8a115749274..0000000000000000000000000000000000000000
--- a/AMOEBAonAMAK/src/experiments/XmlConfigGenerator.java
+++ /dev/null
@@ -1,69 +0,0 @@
-package experiments;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileWriter;
-import java.io.IOException;
-
-public class XmlConfigGenerator {
-
-	public XmlConfigGenerator() {
-		
-	}
-	
-	public static String makeLineXML(String sensorName, String source) {
-		return "\t\t<Sensor Name=\""+sensorName+"\" Source=\""+source+"\"></Sensor>\n"; 
-	}
-
-	public static void makeXML(String XMLFile, int dimension) {
-		String path = "Ressources";
-	
-	    try {
-	    	File file = new File(path+"/"+XMLFile);
-	        FileWriter fw = new FileWriter(file);
-	        
-	        //Make content
-	        String str = "";
-	        str += "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" + 
-	        		"<System>\n" + 
-	        		"\n" + 
-	        		"\t<!-- General config options -->\n" + 
-	        		"\t<Configuration>\n" + 
-	        		"\t\t<Learning allowed = \"true\" creationOfNewContext = \"true\" loadPresetContext = \"false\"></Learning>	\n" + 
-	        		"\t</Configuration>\n" + 
-	        		"\n" + 
-	        		"\t<StartingAgents>\n";
-	  
-	        for(int j = 0; j < dimension; ++j) {
-	        	str += makeLineXML("px"+j,"x"+j);
-    		}
-	        
-	        str += "\t\t<Controller Name=\"Controller\" Oracle=\"test\"></Controller>\n\n";
-
-	        
-	        		
-	        str += "\t</StartingAgents>\n" + 
-	        		"\n" + 
-	        		"</System>";
-	        
-	        //Write and close file
-	        fw.write(str);
-	        fw.close();
-	      } catch (FileNotFoundException e) {
-	        e.printStackTrace();
-	      } catch (IOException e) {
-	        e.printStackTrace();
-	      }
-	}
-	
-	public static void main(String[] args) {
-		// TODO Auto-generated method stub
-
-		
-		String XMLConfigFile = "nDimensionLauncher.xml";
-		
-		XmlConfigGenerator.makeXML(XMLConfigFile, 2);
-		
-		
-	}
-}
diff --git a/AMOEBAonAMAK/src/experiments/nDimensionsLaunchers/F_N_Launcher.java b/AMOEBAonAMAK/src/experiments/nDimensionsLaunchers/F_N_Launcher.java
index 603a383547e5e06f82035c77577b7fccd3d5add9..d53742604f30df6fe706e718d4d4df127ca8bbf6 100644
--- a/AMOEBAonAMAK/src/experiments/nDimensionsLaunchers/F_N_Launcher.java
+++ b/AMOEBAonAMAK/src/experiments/nDimensionsLaunchers/F_N_Launcher.java
@@ -4,13 +4,8 @@ import java.io.File;
 import java.io.IOException;
 import java.io.Serializable;
 import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashMap;
 
-import agents.context.Context;
 import experiments.FILE;
-import experiments.F_XY_System;
-import experiments.XmlConfigGenerator;
 import fr.irit.smac.amak.Configuration;
 import gui.AmoebaWindow;
 import kernel.AMOEBA;
@@ -91,6 +86,14 @@ public class F_N_Launcher implements Serializable {
 //		}
 //		long end = System.currentTimeMillis();
 //		System.out.println("Done in : " + (end - start) );
+//		
+//		start = System.currentTimeMillis();
+//		for (int i = 0; i < nbCycle; ++i) {
+//			studiedSystem.playOneStep();
+//			amoeba.request(studiedSystem.getOutput());
+//		}
+//		end = System.currentTimeMillis();
+//		System.out.println("Done in : " + (end - start) );
 		
 		
 //		/* XP PIERRE */
diff --git a/AMOEBAonAMAK/src/gui/ContextRendererFX.java b/AMOEBAonAMAK/src/gui/ContextRendererFX.java
index cfe62c32fd7d5c9909ad1710e570cf216962df7f..75ddf4125607f21b3ef19ca0dcaaea006105be4d 100644
--- a/AMOEBAonAMAK/src/gui/ContextRendererFX.java
+++ b/AMOEBAonAMAK/src/gui/ContextRendererFX.java
@@ -83,7 +83,7 @@ public class ContextRendererFX extends RenderStrategy {
 	 */
 	public DrawableRectangle getDrawable() {
 		if (!context.isDying() && drawable == null) {
-			drawable = new DrawableContext(0, 0, 10, 10, context);
+			drawable = new DrawableContext(0, 0, 0, 0, context);
 			AmoebaWindow.instance().mainVUI.add(drawable);
 		}
 		return drawable;
diff --git a/AMOEBAonAMAK/src/kernel/AMOEBA.java b/AMOEBAonAMAK/src/kernel/AMOEBA.java
index d05843c62e72bac2fd2c9abb45de07fb06c2625c..502a41fd835f1a65aaeb864a7585496afe3a1d58 100644
--- a/AMOEBAonAMAK/src/kernel/AMOEBA.java
+++ b/AMOEBAonAMAK/src/kernel/AMOEBA.java
@@ -429,78 +429,23 @@ public class AMOEBA extends Amas<World> implements IAMOEBA {
 			if(good) pac.add(c);
 		}
 		
-		ArrayList<Pair<HashMap<String, Double>, Double>> sol = new ArrayList<>();
+		ArrayList<HashMap<String, Double>> sol = new ArrayList<>();
 		for(Context c : pac) {
-			sol.add(maximiseContext(known, percepts, unknown, c));
+			sol.add(c.getLocalModel().getMaxWithConstraint(known));
 		}
 		HashMap<String, Double> max = new HashMap<>();
-		// set default value if no solution
-		for(Percept p : unknown) {
-			max.put(p.getName(), 0.0);
-		}
+
 		Double maxValue = Double.NEGATIVE_INFINITY;
+		max.put("oracle", maxValue);
 		//find best solution
-		for(Pair<HashMap<String, Double>, Double> s : sol) {
-			if(s.getB() > maxValue) {
-				maxValue = s.getB();
-				max = s.getA();
+		for(HashMap<String, Double> s : sol) {
+			if(s.get("oracle") > maxValue) {
+				maxValue = s.get("oracle");
+				max = s;
 			}
 		}
-		max.put("oracle", maxValue);
 		return max;
 	}
-	
-	private Pair<HashMap<String, Double>, Double> maximiseDummy(HashMap<String, Double> known,
-			ArrayList<Percept> percepts, ArrayList<Percept> unknown, Context c) {
-		HashMap<String, Double> res = new HashMap<>();
-		for(Percept p : unknown) {
-			res.put(p.getName(), c.getRangeByPercept(p).getCenter());
-		}
-		HashMap<String, Double> tmpReq = new HashMap<>(res);
-		HashMap<String, Double> old = perceptions;
-		perceptions = tmpReq;
-		Pair<HashMap<String, Double>, Double> ret = new Pair<>(res, c.getActionProposal());
-		perceptions = old;
-		return ret;
-	}
-
-	//TODO tests !
-	private Pair<HashMap<String, Double>, Double> maximiseContext(HashMap<String, Double> known,
-			ArrayList<Percept> percepts, ArrayList<Percept> unknown, Context c) {
-		HashMap<String, Double> res = new HashMap<>();
-		
-		Double[] coefs = c.getLocalModel().getCoef();
-		double[] vCoefs = new double[coefs.length-1];
-		for(int i = 1; i < coefs.length; i++) {
-			vCoefs[i-1] = coefs[i];
-		}
-		LinearObjectiveFunction fct = new LinearObjectiveFunction(vCoefs, coefs[0]);
-		ArrayList<LinearConstraint> constraints = new ArrayList<>();
-		//TODO : problem : we are not sure that the order of percepts is the same as coefs
-		int i = 0;
-		for(String p : known.keySet()) {
-			double[] cf = new double[percepts.size()];
-			cf[i++] = 1.0;
-			constraints.add(new LinearConstraint(cf, Relationship.EQ, known.get(p)));
-		}
-		int unknowStart = i;
-		for(Percept p : unknown) {
-			double[] cf = new double[percepts.size()];
-			cf[i++] = 1.0;
-			constraints.add(new LinearConstraint(cf, Relationship.GEQ, c.getRangeByPercept(p).getStart()));
-			constraints.add(new LinearConstraint(cf, Relationship.LEQ, c.getRangeByPercept(p).getEnd()));
-		}
-		SimplexSolver solver = new SimplexSolver();
-		LinearConstraintSet set = new LinearConstraintSet(constraints);
-		PointValuePair sol = solver.optimize(fct, set, GoalType.MAXIMIZE);
-		for(Percept p : unknown) {
-			//TODO check if the order match
-			res.put(p.getName(), sol.getFirst()[unknowStart++]);
-		}
-		
-		Pair<HashMap<String, Double>, Double> ret = new Pair<>(res, sol.getSecond());
-		return ret;
-	}
 
 	public LocalModel buildLocalModel(Context context) {
 		switch (localModel) {
@@ -734,15 +679,6 @@ public class AMOEBA extends Amas<World> implements IAMOEBA {
 		alteredContexts.add(context);
 	}
 	
-	/**
-	 * Gets the altered contexts.
-	 *
-	 * @return the altered contexts
-	 */
-	public ArrayList<Context> getAlteredContexts() {
-		return alteredContexts;
-	}
-	
 	/**
 	 * Return the current set of valid contexts.
 	 *
@@ -832,7 +768,6 @@ public class AMOEBA extends Amas<World> implements IAMOEBA {
 	
 	public void addPercept(Percept pct) {
 		percepts = null;
-		head.addPercept(pct);
 	}
 	
 }
diff --git a/AMOEBAonAMAK/src/utils/PickRandom.java b/AMOEBAonAMAK/src/utils/RandomUtils.java
similarity index 63%
rename from AMOEBAonAMAK/src/utils/PickRandom.java
rename to AMOEBAonAMAK/src/utils/RandomUtils.java
index ae94493c4a00b50e6654ab8722eac7f98de66117..9440f17725430ccad2abcee4edb6470d61072134 100644
--- a/AMOEBAonAMAK/src/utils/PickRandom.java
+++ b/AMOEBAonAMAK/src/utils/RandomUtils.java
@@ -5,7 +5,7 @@ import java.util.List;
 import java.util.Random;
 import java.util.concurrent.ThreadLocalRandom;
 
-public class PickRandom {
+public class RandomUtils {
 	
 	/**
 	 * Pick N random element from the list. if n is bigger than the list, return the list.
@@ -40,4 +40,19 @@ public class PickRandom {
 	public static <E> List<E> pickNRandomElements(List<E> list, int n) {
 	    return pickNRandomElements(list, n, ThreadLocalRandom.current());
 	}
+	
+	/**
+	 * Generate a pseudorandom double values, conforming to the given origin (inclusive) and bound(exclusive).
+	 * @param rand
+	 * @param origin the origin (inclusive) of the random value
+	 * @param bound the bound (exclusive) of the random value
+	 * @return
+	 */
+	public static double nextDouble(Random rand, double origin, double bound) {
+		   double r = rand.nextDouble();
+		   r = r * (bound - origin) + origin;
+		   if (r >= bound) // correct for rounding
+		     r = Math.nextDown(bound);
+		   return r;
+	}
 }
diff --git a/AMOEBAonAMAK/src/utils/XmlConfigGenerator.java b/AMOEBAonAMAK/src/utils/XmlConfigGenerator.java
new file mode 100644
index 0000000000000000000000000000000000000000..3819e2af7c35df94763eab320fbacd78491f335e
--- /dev/null
+++ b/AMOEBAonAMAK/src/utils/XmlConfigGenerator.java
@@ -0,0 +1,61 @@
+package utils;
+
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Locale;
+
+public class XmlConfigGenerator {
+	
+	public static String header = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n";
+	public static String systemStart = "<System>\n";
+	public static String configurationStart = "<Configuration>\n";
+	public static String configuration = "    <Learning allowed = \"%s\" creationOfNewContext = \"%s\" loadPresetContext = \"%s\" />\n";
+	public static String configurationEnd = "</Configuration>\n";
+	public static String agentsStart = "<StartingAgents>\n";
+	public static String sensor = "    <Sensor Name=\"%s\" Enum=\"%s\" />\n";
+	public static String controller = "    <Controller Name=\"Controller\">\n" + 
+			"        <ErrorMargin ErrorAllowed=\"%f\" AugmentationFactorError=\"%f\" DiminutionFactorError=\"%f\" MinErrorAllowed=\"%f\" NConflictBeforeAugmentation=\"%d\" NSuccessBeforeDiminution=\"%d\" />\n" + 
+			"    </Controller>\n";
+	public static String agentsEnd = "</StartingAgents>\n";
+	public static String systemEnd = "</System>\n";
+	
+	private static String makeSensor(String sensorName, boolean isEnum) {
+		return String.format(sensor, sensorName, ""+isEnum);
+	}
+	
+	private static String makeConfiguration(boolean isLearningAllowed, boolean isCreationOfNewContext, boolean isLoadContext) {
+		return String.format(configuration, ""+isLearningAllowed, ""+isCreationOfNewContext, ""+isLoadContext);
+	}
+	
+	private static String makeController(double errorAllowed, double augmentationFactorError, double diminutionFactorError, double minErrorAllowed, int nConflictBeforeAugmentation, int nSuccessBeforeDiminution) {
+		return String.format(Locale.ENGLISH, controller, errorAllowed, augmentationFactorError, diminutionFactorError, minErrorAllowed, nConflictBeforeAugmentation, nSuccessBeforeDiminution);
+	}
+
+	public static void makeXML(File file, List<Pair<String, Boolean>> sensors) throws IOException {
+	    try(FileWriter fw = new FileWriter(file)){
+	    	fw.write(header);
+	    	fw.write(systemStart);
+	    	fw.write(configurationStart);
+	    	fw.write(makeConfiguration(true, true, false));
+	    	fw.write(configurationEnd);
+	    	fw.write(agentsStart);
+	    	for(Pair<String, Boolean> s : sensors) {
+	    		fw.write(makeSensor(s.getA(), s.getB()));
+	    	}
+	    	fw.write(makeController(1.0, 0.5, 0.5, 0.01, 50, 50));
+	    	fw.write(agentsEnd);
+	    	fw.write(systemEnd);
+	    }
+	}
+	
+	public static void makeXML(File file, int dimension) throws IOException {
+		ArrayList<Pair<String, Boolean>> sensors = new ArrayList<>(dimension);
+		for(int i = 1; i <= dimension; i++) {
+			sensors.add(new Pair<String, Boolean>("p"+i, false));
+		}
+		makeXML(file, sensors);
+	}
+}