diff --git a/src/example/philosophes/MainPhilosophe.java b/src/example/philosophes/MainPhilosophe.java
index a93df0dd843def93b87de90d7e81f05337458cb1..d228b7adcbb1569e9ca62be46c49a11d01c24d16 100644
--- a/src/example/philosophes/MainPhilosophe.java
+++ b/src/example/philosophes/MainPhilosophe.java
@@ -1,9 +1,7 @@
 package example.philosophes;
 
 import mas.core.Cyclable;
-import mas.core.ThreeStepCyclable;
-import mas.implementation.schedulers.FairCycling;
-import mas.implementation.schedulers.ThreeStepCycling;
+import mas.implementation.schedulers.MonoThreadedCycling;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -12,19 +10,19 @@ public class MainPhilosophe {
 
     public static void main(String[] args) {
 
-        class MyFairCycling extends FairCycling<Cyclable> {
+        class MyFairCycling extends MonoThreadedCycling<Cyclable> {
 
             long startTimeCycle = 0;
 
             List<Long> cycleTime = new ArrayList<>();
 
-            public MyFairCycling(ThreeStepCyclable... _cyclables){
+            public MyFairCycling(Cyclable... _cyclables){
                 super(_cyclables);
             }
 
             @Override
             public boolean stopCondition() {
-                return nbOfCycles == 100;
+                return nbOfCycles == 1000;
             }
 
             @Override
@@ -44,7 +42,7 @@ public class MainPhilosophe {
         }
 
         int nAgents = 100;
-        int nbCycles = 100;
+        int nbCycles = 1000;
 
         Philosopher[] philosophers = new Philosopher[nAgents];
         Fork[] forks = new Fork[nAgents];
@@ -92,33 +90,8 @@ public class MainPhilosophe {
 
         scheduler.start();
 
-        /*try {
-            Thread.sleep(2000);
-        } catch (InterruptedException e) {
-            throw new RuntimeException(e);
-        }
-        scheduler.pause();
-
-        try {
-            Thread.sleep(2000);
-        } catch (InterruptedException e) {
-            throw new RuntimeException(e);
-        }
-
-        scheduler.resume();
-
-
-        try {
-            Thread.sleep(5000);
-        } catch (InterruptedException e) {
-            throw new RuntimeException(e);
-        }
-
-        scheduler.stop();*/
-
         scheduler.waitUntilFinish();
 
-
         final long endTime = System.nanoTime();
         System.out.println("AMAk : Total execution time: " + (endTime / 1000 - startTime / 1000) + " microseconds");
         System.out.println("\tCycle moyen : " + scheduler.getCycleTime() / 1000 + " microseconds");
diff --git a/src/example/philosophes/Philosopher.java b/src/example/philosophes/Philosopher.java
index 23c6b04a167798297df9768832c8969e532c24d8..555c9ba1f51ae34c00c5d0a6b76de7a5856a27d5 100644
--- a/src/example/philosophes/Philosopher.java
+++ b/src/example/philosophes/Philosopher.java
@@ -1,7 +1,7 @@
 package example.philosophes;
 
 import mas.core.Agent;
-import mas.core.Schedulable;
+import mas.core.Scheduler;
 
 import java.util.*;
 
@@ -30,7 +30,7 @@ public class Philosopher extends Agent {
      */
     private int id;
 
-    private Schedulable scheduler;
+    private Scheduler scheduler;
 
     /**
      * States philosophers can be in
@@ -121,7 +121,7 @@ public class Philosopher extends Agent {
     public void act() {
         //System.out.println("Philosopher num " + id + " act");
         fibonacciRecursion(23);
-        //scheduler.addCyclable(new Waste(id));
+        scheduler.addCyclable(new Waste(id));
     }
 
     public int fibonacciRecursion(int n){
@@ -218,11 +218,11 @@ public class Philosopher extends Agent {
         this.rightPhilosopher = rightPhilosopher;
     }
 
-    public void setScheduler(Schedulable scheduler) {
+    public void setScheduler(Scheduler scheduler) {
         this.scheduler = scheduler;
     }
 
-    public Schedulable getScheduler() {
+    public Scheduler getScheduler() {
         return scheduler;
     }
 
diff --git a/src/example/philosophes/Waste.java b/src/example/philosophes/Waste.java
index 01670d571216ede3aebfe4013b1b74c5cc43e7dc..8d0f84ee99f8d496efd68adb0021563ff4c1ec53 100644
--- a/src/example/philosophes/Waste.java
+++ b/src/example/philosophes/Waste.java
@@ -1,13 +1,13 @@
 package example.philosophes;
 
 import mas.core.Cyclable;
-import mas.core.Schedulable;
+import mas.core.Scheduler;
 
 public class Waste implements Cyclable {
 
     private int id;
 
-    Schedulable scheduler = null;
+    Scheduler scheduler = null;
 
     public Waste(int _id){
         id = _id;
@@ -24,7 +24,7 @@ public class Waste implements Cyclable {
     }
 
     @Override
-    public void setScheduler(Schedulable _scheduler) {
+    public void setScheduler(Scheduler _scheduler) {
         scheduler = _scheduler;
     }
 
diff --git a/src/mas/core/Agent.java b/src/mas/core/Agent.java
index 7afaba6edf962d432880234491e5f93aeb3326af..378da89dc191f36e3505b882228448a505c841ab 100644
--- a/src/mas/core/Agent.java
+++ b/src/mas/core/Agent.java
@@ -8,7 +8,7 @@ public class Agent implements ThreeStepCyclable{
     /**
      * The scheduler of the agent.
      */
-    protected Schedulable scheduler;
+    protected Scheduler scheduler;
 
     @Override
     public void perceive() {
@@ -31,7 +31,7 @@ public class Agent implements ThreeStepCyclable{
     }
 
     @Override
-    public void setScheduler(Schedulable _scheduler) {
+    public void setScheduler(Scheduler _scheduler) {
         scheduler = _scheduler;
     }
 }
diff --git a/src/mas/core/Cyclable.java b/src/mas/core/Cyclable.java
index c5785b331ffbd843648ce177059d04f6c66d6c2d..93c6b22bf5b66bd64c33a08ba8ad7555703e1f00 100644
--- a/src/mas/core/Cyclable.java
+++ b/src/mas/core/Cyclable.java
@@ -1,7 +1,7 @@
 package mas.core;
 
 /**
- * A cyclable objet. This objet must be scheduled by a {@link Schedulable}.
+ * A cyclable objet. This objet must be scheduled by a {@link Scheduler}.
  */
 public interface Cyclable {
 
@@ -23,5 +23,5 @@ public interface Cyclable {
      * @param _scheduler
      *         The scheduler in which the cyclable is going to be scheduled.
      */
-    void setScheduler(Schedulable _scheduler);
+    void setScheduler(Scheduler _scheduler);
 }
diff --git a/src/mas/core/Schedulable.java b/src/mas/core/Scheduler.java
similarity index 86%
rename from src/mas/core/Schedulable.java
rename to src/mas/core/Scheduler.java
index acad3b2747290ed0ab9ea61174264586161fb345..72510533fede1869807e9055ce69b414294468c1 100644
--- a/src/mas/core/Schedulable.java
+++ b/src/mas/core/Scheduler.java
@@ -3,7 +3,7 @@ package mas.core;
 /**
  * A schedulable object. Made to code schedulers.
  */
-public interface Schedulable {
+public interface Scheduler<T extends Cyclable> {
 
     /**
      * Launch the scheduler if it is not running.
@@ -31,7 +31,7 @@ public interface Schedulable {
      * @param cyclable
      *      The cyclable to add
      */
-    void addCyclable(Cyclable cyclable);
+    void addCyclable(T cyclable);
 
 
     /**
@@ -51,7 +51,7 @@ public interface Schedulable {
     /**
      * Pause the execution until the executor has finished.
      *
-     * This function needs to be called after a call to {@link Schedulable#stop()} or with the redefinition of {@link Schedulable#stopCondition()}.
+     * This function needs to be called after a call to {@link Scheduler#stop()} or with the redefinition of {@link Scheduler#stopCondition()}.
      */
     void waitUntilFinish();
 }
diff --git a/src/mas/implementation/schedulers/AsyncCycling.java b/src/mas/implementation/schedulers/AsyncCycling.java
index a99e26539a1fa1b91aaa69afa6b27baefacb417c..650f45575296a1e699768d242dd9b43d361f7723 100644
--- a/src/mas/implementation/schedulers/AsyncCycling.java
+++ b/src/mas/implementation/schedulers/AsyncCycling.java
@@ -1,10 +1,11 @@
 package mas.implementation.schedulers;
 
 import mas.core.Cyclable;
-import mas.core.Schedulable;
+import mas.core.Scheduler;
 import mas.core.Sleepable;
 
 import java.util.LinkedHashSet;
+import java.util.Queue;
 import java.util.Set;
 import java.util.concurrent.*;
 
@@ -13,12 +14,12 @@ import java.util.concurrent.*;
  *
  * @author David Antunes
  */
-public class AsyncCycling implements Schedulable, Sleepable {
+public class AsyncCycling<T extends Cyclable> implements Scheduler<T>, Sleepable {
 
     /**
      * The cyclable objects handled by the scheduler.
      */
-    protected final Set<Cyclable> cyclables = new LinkedHashSet<>();
+    protected final Queue<T> cyclables = new ConcurrentLinkedDeque<>();
 
     /**
      * Time between two cycles. Default time in {@link Sleepable#DEFAULT_SLEEP}.
@@ -41,9 +42,10 @@ public class AsyncCycling implements Schedulable, Sleepable {
      * @param _cyclables
      *          The corresponding cyclables
      */
-    public AsyncCycling(Cyclable... _cyclables){
+    @SafeVarargs
+    public AsyncCycling(T... _cyclables){
 
-        for(Cyclable cyclable : _cyclables){
+        for(T cyclable : _cyclables){
             cyclables.add(cyclable);
             cyclable.setScheduler(this);
         }
@@ -51,7 +53,7 @@ public class AsyncCycling implements Schedulable, Sleepable {
 
     @Override
     public void start() {
-        for (Cyclable cyclable : cyclables){
+        for (T cyclable : cyclables){
             executor.execute(() -> manageCyclable(cyclable));
         }
     }
@@ -60,11 +62,6 @@ public class AsyncCycling implements Schedulable, Sleepable {
     public void stop() {
         mustStop = true;
         executor.shutdown();
-        try {
-            executor.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
-        } catch (InterruptedException e) {
-            throw new RuntimeException(e);
-        }
     }
 
     @Override
@@ -78,7 +75,7 @@ public class AsyncCycling implements Schedulable, Sleepable {
     }
 
     @Override
-    public void addCyclable(Cyclable cyclable) {
+    public void addCyclable(T cyclable) {
         cyclables.add(cyclable);
         cyclable.setScheduler(this);
 
@@ -131,7 +128,7 @@ public class AsyncCycling implements Schedulable, Sleepable {
      * @param cyclable
      *          The cyclable
      */
-    protected void manageCyclable(Cyclable cyclable){
+    protected void manageCyclable(T cyclable){
         cyclable.cycle();
 
         doSleep();
diff --git a/src/mas/implementation/schedulers/FairCycling.java b/src/mas/implementation/schedulers/FairCycling.java
index b31efae3b1e75573c9553c5f9e4b35f45b80f820..be6ec918730eaca5af34bfde60835c26d8fbf510 100644
--- a/src/mas/implementation/schedulers/FairCycling.java
+++ b/src/mas/implementation/schedulers/FairCycling.java
@@ -1,7 +1,7 @@
 package mas.implementation.schedulers;
 
 import mas.core.Cyclable;
-import mas.core.Schedulable;
+import mas.core.Scheduler;
 import mas.core.Sleepable;
 
 import java.util.*;
@@ -11,9 +11,12 @@ import java.util.concurrent.*;
  * The FairCycling scheduler schedules tasks using a {@link Executors#newCachedThreadPool()}.
  * Every cyclable executes its cycle once every system's cycle.
  *
+ * @param <T>
+ *          Extended class of {@link Cyclable}
+ *
  * @author David Antunes
  */
-public class FairCycling<T extends Cyclable> implements Schedulable, Sleepable {
+public class FairCycling<T extends Cyclable> implements Scheduler<T>, Sleepable {
 
     /**
      * The cyclable objects handled by the scheduler.
@@ -21,7 +24,7 @@ public class FairCycling<T extends Cyclable> implements Schedulable, Sleepable {
     protected Set<T> cyclables = new LinkedHashSet<>();
 
     /**
-     * The cyclables that must be add in the next cycle.
+     * The cyclables that must be added in the next cycle.
      */
     protected Queue<T> pendingToAddCyclables = new ConcurrentLinkedQueue<>();
 
@@ -98,6 +101,12 @@ public class FairCycling<T extends Cyclable> implements Schedulable, Sleepable {
         }
     }
 
+    @Override
+    public void addCyclable(T cyclable) {
+        cyclable.setScheduler(this);
+        pendingToAddCyclables.add(cyclable);
+    }
+
     @Override
     public boolean stopCondition(){
         return false;
@@ -117,12 +126,6 @@ public class FairCycling<T extends Cyclable> implements Schedulable, Sleepable {
         }
     }
 
-    @Override
-    public void addCyclable(Cyclable cyclable){
-        cyclable.setScheduler(this);
-        pendingToAddCyclables.add((T) cyclable);
-    }
-
     @Override
     public int getSleep() {
         return sleep;
diff --git a/src/mas/implementation/schedulers/FairPosCycling.java b/src/mas/implementation/schedulers/FairPosCycling.java
index 283d615177a94b26e50400a5207a96443a0048f5..c87a5e12a99b6d9f03749749b7e0fe2da1f87abc 100644
--- a/src/mas/implementation/schedulers/FairPosCycling.java
+++ b/src/mas/implementation/schedulers/FairPosCycling.java
@@ -1,13 +1,13 @@
 package mas.implementation.schedulers;
 
 import mas.core.Cyclable;
-import mas.core.Schedulable;
+import mas.core.Scheduler;
 import mas.core.Sleepable;
 
 /**
- * Même que fair + equitable sur position des Round Robin
+ * Même que MonoThreadedCycling + equitable sur position des Round Robin
  */
-public class FairPosCycling implements Schedulable, Sleepable {
+public class FairPosCycling implements Scheduler, Sleepable {
     @Override
     public void start() {
 
diff --git a/src/mas/implementation/schedulers/MonoThreadedCycling.java b/src/mas/implementation/schedulers/MonoThreadedCycling.java
new file mode 100644
index 0000000000000000000000000000000000000000..15af4a5214136da13d95396eff7437d2d57f15e8
--- /dev/null
+++ b/src/mas/implementation/schedulers/MonoThreadedCycling.java
@@ -0,0 +1,223 @@
+package mas.implementation.schedulers;
+
+import mas.core.Cyclable;
+import mas.core.Scheduler;
+import mas.core.Sleepable;
+
+import java.util.LinkedHashSet;
+import java.util.Queue;
+import java.util.Set;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.concurrent.CountDownLatch;
+
+/**
+ * The MonoThreadedCycling scheduler schedules tasks using a {@link Thread}. The execution is sequential.
+ * This scheduler is very efficient with low complexity cyclables.
+ * Every cyclable executes its cycle once every system's cycle.
+ *
+ * @param <T>
+ *          Extended class of {@link mas.core.Cyclable}
+ *
+ * @author David Antunes
+ */
+public class MonoThreadedCycling<T extends Cyclable> implements Scheduler<T>, Sleepable {
+
+    /**
+     * The cyclable objects handled by the scheduler.
+     */
+    protected Set<T> cyclables = new LinkedHashSet<>();
+
+    /**
+     * The cyclables that must be added in the next cycle.
+     */
+    protected Queue<T> pendingToAddCyclables = new ConcurrentLinkedQueue<>();
+
+    /**
+     * Time between two cycles. Default time in {@link Sleepable#DEFAULT_SLEEP}.
+     */
+    protected int sleep = DEFAULT_SLEEP;
+
+    /**
+     * Number of system cycles.
+     */
+    protected int nbOfCycles = 0;
+
+    /**
+     * Condition to know if the scheduler must be stopped.
+     */
+    protected boolean mustStop = false;
+
+    /**
+     * Condition to know if the scheduler must be paused.
+     */
+    protected boolean mustPause = false;
+
+    /**
+     * Object used to pause the scheduler.
+     */
+    protected CountDownLatch pauseLatch;
+
+    /**
+     * The thread which executes the cycle.
+     */
+    Thread executionThread = new Thread(this::doCycle);
+
+    /**
+     * Constructor which set the initial cyclables.
+     *
+     * @param cyclables
+     *          The corresponding cyclables
+     */
+    @SafeVarargs
+    public MonoThreadedCycling(T... cyclables){
+        for (T cyclable : cyclables) {
+            addCyclable(cyclable);
+        }
+    }
+
+    @Override
+    public void start() {
+        executionThread.start();
+    }
+
+    @Override
+    public void stop() {
+        mustStop = true;
+    }
+
+    @Override
+    public void pause() {
+        if(pauseLatch == null || pauseLatch.getCount() == 0){
+            pauseLatch = new CountDownLatch(1);
+        }
+        mustPause = true;
+    }
+
+    @Override
+    public void resume() {
+        if(pauseLatch != null){
+            pauseLatch.countDown();
+        }
+    }
+
+    @Override
+    public void addCyclable(T cyclable) {
+        cyclable.setScheduler(this);
+        pendingToAddCyclables.add(cyclable);
+    }
+
+    @Override
+    public boolean stopCondition() {
+        return false;
+    }
+
+    @Override
+    public boolean isFinished() {
+        return !executionThread.isAlive();
+    }
+
+    @Override
+    public void waitUntilFinish() {
+        try {
+            executionThread.join();
+        } catch (InterruptedException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    @Override
+    public int getSleep() {
+        return sleep;
+    }
+
+    @Override
+    public void setSleep(int sleep) {
+        this.sleep = sleep;
+    }
+
+    @Override
+    public void doSleep() {
+        if (getSleep() != 0) {
+            try {
+                Thread.sleep(sleep);
+            } catch (final InterruptedException e) {
+                e.printStackTrace();
+            }
+        }
+    }
+
+    /**
+     * Executes {@link #step()} until the scheduler must stop.
+     */
+    protected void doCycle(){
+        while(!mustStop){
+            step();
+            if(stopCondition()){
+                this.stop();
+            }
+
+            if(mustPause){
+                try{
+                    pauseLatch.await();
+                } catch (InterruptedException e){
+                    throw new RuntimeException(e);
+                }
+            }
+        }
+    }
+
+    /**
+     * Executes a system's cycle.
+     */
+    protected void step(){
+        onCycleStarts();
+
+        treatPendingCyclables();
+
+        for(T cyclable : cyclables){
+            cyclable.cycle();
+            if(!cyclable.terminate()){
+                pendingToAddCyclables.add(cyclable);
+            }
+        }
+
+        doSleep();
+
+        onCycleEnds();
+
+        cyclables.clear();
+
+        nbOfCycles++;
+    }
+
+    /**
+     * Add the cyclables that are going to be scheduled on the current cycle.
+     */
+    protected void treatPendingCyclables() {
+        cyclables.addAll(pendingToAddCyclables);
+        pendingToAddCyclables.clear();
+    }
+
+    /**
+     * This method is called at the end of every system's cycle.
+     */
+    protected void onCycleEnds() {
+
+    }
+
+    /**
+     * This method is called at the start of every system's cycle.
+     */
+    protected void onCycleStarts(){
+
+    }
+
+    /**
+     * Getter for the number of cycles.
+     *
+     * @return the number of cycles performed by the system
+     */
+    public int getNbOfCycles() {
+        return nbOfCycles;
+    }
+}
diff --git a/src/mas/implementation/schedulers/ThreeStepCycling.java b/src/mas/implementation/schedulers/ThreeStepCycling.java
index 100923c8b14e3d0ab389504ac45e241f614b6336..44edf77e456e37f4154562c4f7becef03396d585 100644
--- a/src/mas/implementation/schedulers/ThreeStepCycling.java
+++ b/src/mas/implementation/schedulers/ThreeStepCycling.java
@@ -36,7 +36,7 @@ public class ThreeStepCycling extends FairCycling<ThreeStepCyclable> {
     protected void step() {
         onCycleStarts();
 
-        treatPendingCyclables();
+        //treatPendingCyclables();
 
         cycleLatch = new CountDownLatch(cyclables.size());
         perceptionLatch = new CountDownLatch(cyclables.size());
@@ -56,7 +56,7 @@ public class ThreeStepCycling extends FairCycling<ThreeStepCyclable> {
                 threeStepCyclable.act();
 
                 if(threeStepCyclable.terminate()){
-                    pendingToAddCyclables.add(threeStepCyclable);
+                    //pendingToAddCyclables.add(threeStepCyclable);
                 }
                 cycleLatch.countDown();
             });
diff --git a/src/mas/implementation/schedulers/variations/TwoDCycling.java b/src/mas/implementation/schedulers/variations/TwoDCycling.java
index d08bb542e4a5aaf47657cb19a2e7c772ed5278d7..ce906a2991cebdf7284fe8bea372f56b4464313a 100644
--- a/src/mas/implementation/schedulers/variations/TwoDCycling.java
+++ b/src/mas/implementation/schedulers/variations/TwoDCycling.java
@@ -129,7 +129,7 @@ public class TwoDCycling extends FairCycling<Cyclable> {
     @Override
     public void pause() {
         state = State.IDLE;
-        if(pauseLatch == null){
+        if(pauseLatch == null || pauseLatch.getCount() == 0){
             pauseLatch = new CountDownLatch(1);
         }
         mustPause = true;