diff --git a/transition_machine/include/Action.hpp b/transition_machine/include/Action.hpp
index 02203443873739db7fc9d3ed80e8a8357603d279..322c7f63e0ca40fcde1c3ee574deea74a2161d0a 100644
--- a/transition_machine/include/Action.hpp
+++ b/transition_machine/include/Action.hpp
@@ -32,7 +32,8 @@ class Action
       Push,
       Pop,
       Write,
-      Back
+      Back,
+      MoveHead
     };
 
     /// @brief The type of this BasicAction.
diff --git a/transition_machine/include/ActionBank.hpp b/transition_machine/include/ActionBank.hpp
index c1bdc26071b99ab541157a7a9d508b5869a4aeda..bb44dc6fbc8ee12598a414f6c40413e7ee5d7d3b 100644
--- a/transition_machine/include/ActionBank.hpp
+++ b/transition_machine/include/ActionBank.hpp
@@ -79,6 +79,41 @@ class ActionBank
   /// @param rule The rule to apply.
   /// @param relativeIndex The index of the column that will be read and written into, relatively to the head of the Config.
   static void writeRuleResult(Config & config, const std::string & fromTapeName, const std::string & targetTapeName, const std::string & rule, int relativeIndex);
+
+  /// \brief Write something on the buffer
+  ///
+  /// \param tapeName The tape we will write to
+  /// \param value The value we will write
+  /// \param relativeIndex The write index relmative to the buffer's head
+  ///
+  /// \return A BasicAction doing all of that
+  static Action::BasicAction bufferWrite(std::string tapeName, std::string value, int relativeIndex);
+
+  /// \brief Move the buffer's head
+  ///
+  /// \param movement The relative movement of the buffer's head
+  ///
+  /// \return A BasicAction moving the head
+  static Action::BasicAction moveHead(int movement);
+
+  /// \brief Write something on the buffer
+  ///
+  /// \param tapeName The tape we will write to
+  /// \param value The value we will write
+  /// \param stackIndex The stack index of the buffer index
+  ///
+  /// \return A BasicAction doing all of that
+  static Action::BasicAction stackWrite(std::string tapeName, std::string value, int stackIndex);
+
+  /// \brief Push the head of the buffer into the stack
+  ///
+  /// \return The corresponding BasicAction
+  static Action::BasicAction pushHead();
+
+  /// \brief Pop the stack
+  ///
+  /// \return The corresponding BasicAction
+  static Action::BasicAction stackPop(bool checkGov);
 };
 
 #endif
diff --git a/transition_machine/src/Action.cpp b/transition_machine/src/Action.cpp
index aec28111e50b61dd5334c7c2f9d44a44503d8650..85a6cdaa45510daec0d620d10a0663cf9302a78b 100644
--- a/transition_machine/src/Action.cpp
+++ b/transition_machine/src/Action.cpp
@@ -124,6 +124,10 @@ std::string Action::BasicAction::to_string()
     return "pop " + data;
   else if(type == Type::Write)
     return "write " + data;
+  else if(type == Type::Back)
+    return "back " + data;
+  else if(type == Type::MoveHead)
+    return "moveHead " + data;
 
   return "null";
 }
diff --git a/transition_machine/src/ActionBank.cpp b/transition_machine/src/ActionBank.cpp
index c66201134a9e565a0443223d581a19e67344eb24..a0a0ebc09c7df42d98e71a67b2ce1928f252bc82 100644
--- a/transition_machine/src/ActionBank.cpp
+++ b/transition_machine/src/ActionBank.cpp
@@ -3,6 +3,105 @@
 #include "util.hpp"
 #include "ProgramParameters.hpp"
 
+Action::BasicAction ActionBank::moveHead(int movement)
+{
+  auto apply = [movement](Config & c, Action::BasicAction &)
+    {c.moveHead(movement);};
+  auto undo = [movement](Config & c, Action::BasicAction &)
+    {c.moveHead(-movement);};
+  auto appliable = [movement](Config &, Action::BasicAction &)
+    {return true;};
+  Action::BasicAction basicAction =
+    {Action::BasicAction::Type::MoveHead, "", apply, undo, appliable};
+
+  return basicAction;
+}
+
+Action::BasicAction ActionBank::bufferWrite(std::string tapeName, std::string value, int relativeIndex)
+{
+  auto apply = [tapeName, value, relativeIndex](Config & c, Action::BasicAction &)
+    {
+      simpleBufferWrite(c, tapeName, value, relativeIndex);
+    };
+  auto undo = [tapeName, relativeIndex](Config & c, Action::BasicAction &)
+    {
+      simpleBufferWrite(c, tapeName, "", relativeIndex);
+    };
+  auto appliable = [tapeName, relativeIndex](Config & c, Action::BasicAction &)
+    {
+      return simpleBufferWriteAppliable(c, tapeName, relativeIndex);
+    };
+  Action::BasicAction basicAction =
+    {Action::BasicAction::Type::Write, value, apply, undo, appliable};
+
+  return basicAction;
+}
+
+Action::BasicAction ActionBank::stackWrite(std::string tapeName, std::string value, int stackIndex)
+{
+  auto apply = [tapeName, value, stackIndex](Config & c, Action::BasicAction &)
+    {
+      int bufferIndex = c.stackGetElem(stackIndex);
+      int relativeIndex = bufferIndex - c.getHead();
+      simpleBufferWrite(c, tapeName, value, relativeIndex);
+    };
+  auto undo = [tapeName, stackIndex](Config & c, Action::BasicAction &)
+    {
+      int bufferIndex = c.stackGetElem(stackIndex);
+      int relativeIndex = bufferIndex - c.getHead();
+      simpleBufferWrite(c, tapeName, "", relativeIndex);
+    };
+  auto appliable = [tapeName, stackIndex](Config & c, Action::BasicAction &)
+    {
+      if (!c.stackHasIndex(stackIndex))
+        return false;
+      int bufferIndex = c.stackGetElem(stackIndex);
+      int relativeIndex = bufferIndex - c.getHead();
+      return simpleBufferWriteAppliable(c, tapeName, relativeIndex);
+    };
+
+  Action::BasicAction basicAction =
+    {Action::BasicAction::Type::Write, value, apply, undo, appliable};
+
+  return basicAction;
+}
+
+Action::BasicAction ActionBank::pushHead()
+{
+    auto apply = [](Config & c, Action::BasicAction &)
+      {c.stackPush(c.getHead());};
+    auto undo = [](Config & c, Action::BasicAction &)
+      {c.stackPop();};
+    auto appliable = [](Config & c, Action::BasicAction &)
+      {return !(c.stackSize() >= ProgramParameters::maxStackSize) && (!c.endOfTapes());};
+    Action::BasicAction basicAction =
+      {Action::BasicAction::Type::Push, "", apply, undo, appliable};
+
+    return basicAction;
+}
+
+Action::BasicAction ActionBank::stackPop(bool checkGov)
+{
+  auto apply = [](Config & c, Action::BasicAction & ba)
+    {ba.data = std::to_string(c.stackTop());
+     c.stackPop();};
+  auto undo = [](Config & c, Action::BasicAction & ba)
+    {c.stackPush(std::stoi(ba.data));};
+  auto appliable = [checkGov](Config & c, Action::BasicAction &)
+    {
+      if (c.stackEmpty())
+        return false;
+      if (!checkGov)
+        return true;
+
+      return !c.getTape("GOV").getHyp(c.stackTop()-c.getHead()).empty();
+    };
+  Action::BasicAction basicAction =
+    {Action::BasicAction::Type::Pop, "", apply, undo, appliable};
+
+  return basicAction;
+}
+
 std::vector<Action::BasicAction> ActionBank::str2sequence(const std::string & name)
 {
   auto invalidNameAndAbort = [&](const char * errInfo)
@@ -34,57 +133,12 @@ std::vector<Action::BasicAction> ActionBank::str2sequence(const std::string & na
     if (object.size() != 2)
       invalidNameAndAbort(ERRINFO);
 
-    if (object[0] == "b")
-    {
-      int relativeIndex = std::stoi(object[1]);
+    int relativeIndex = std::stoi(object[1]);
 
-      auto apply = [tapeName, value, relativeIndex](Config & c, Action::BasicAction &)
-        {
-          simpleBufferWrite(c, tapeName, value, relativeIndex);
-        };
-      auto undo = [tapeName, relativeIndex](Config & c, Action::BasicAction &)
-        {
-          simpleBufferWrite(c, tapeName, "", relativeIndex);
-        };
-      auto appliable = [tapeName, relativeIndex](Config & c, Action::BasicAction &)
-        {
-          return simpleBufferWriteAppliable(c, tapeName, relativeIndex);
-        };
-      Action::BasicAction basicAction =
-        {Action::BasicAction::Type::Write, value, apply, undo, appliable};
-
-      sequence.emplace_back(basicAction);
-    }
+    if (object[0] == "b")
+      sequence.emplace_back(bufferWrite(tapeName, value, relativeIndex));
     else if (object[0] == "s")
-    {
-       auto apply = [tapeName, value, object](Config & c, Action::BasicAction &)
-        {
-          int stackIndex = std::stoi(object[1]);
-          int bufferIndex = c.stackGetElem(stackIndex);
-          int relativeIndex = bufferIndex - c.getHead();
-          simpleBufferWrite(c, tapeName, value, relativeIndex);
-        };
-      auto undo = [tapeName, object](Config & c, Action::BasicAction &)
-        {
-          int stackIndex = std::stoi(object[1]);
-          int bufferIndex = c.stackGetElem(stackIndex);
-          int relativeIndex = bufferIndex - c.getHead();
-          simpleBufferWrite(c, tapeName, "", relativeIndex);
-        };
-      auto appliable = [tapeName, object](Config & c, Action::BasicAction &)
-        {
-          int stackIndex = std::stoi(object[1]);
-          if (!c.stackHasIndex(stackIndex))
-            return false;
-          int bufferIndex = c.stackGetElem(stackIndex);
-          int relativeIndex = bufferIndex - c.getHead();
-          return simpleBufferWriteAppliable(c, tapeName, relativeIndex);
-        };
-      Action::BasicAction basicAction =
-        {Action::BasicAction::Type::Write, value, apply, undo, appliable};
-
-      sequence.emplace_back(basicAction);     
-    }
+      sequence.emplace_back(stackWrite(tapeName, value, relativeIndex));     
   }
   else if(std::string(b1) == "MULTIWRITE")
   {
@@ -99,21 +153,7 @@ std::vector<Action::BasicAction> ActionBank::str2sequence(const std::string & na
     auto splits = split(name);
 
     for(int i = startRelIndex; i <= endRelIndex; i++)
-    {
-      std::string & value = splits[4+i-startRelIndex];
-
-      auto apply = [tapeName, value, i](Config & c, Action::BasicAction &)
-        {simpleBufferWrite(c, tapeName, value, i);};
-      auto undo = [tapeName, i](Config & c, Action::BasicAction &)
-        {simpleBufferWrite(c, tapeName, "", i);};
-      auto appliable = [tapeName, i](Config & c, Action::BasicAction &)
-        {return simpleBufferWriteAppliable(c, tapeName, i);};
-
-      Action::BasicAction basicAction =
-        {Action::BasicAction::Type::Write, value, apply, undo, appliable};
-
-      sequence.emplace_back(basicAction);
-    }
+      sequence.emplace_back(bufferWrite(tapeName, splits[4+i-startRelIndex], i));
   }
   else if(std::string(b1) == "RULE")
   {
@@ -175,30 +215,13 @@ std::vector<Action::BasicAction> ActionBank::str2sequence(const std::string & na
   }
   else if(std::string(b1) == "SHIFT")
   {
-    auto apply = [](Config & c, Action::BasicAction &)
-      {c.stackPush(c.getHead());};
-    auto undo = [](Config & c, Action::BasicAction &)
-      {c.stackPop();};
-    auto appliable = [](Config & c, Action::BasicAction &)
-      {return !(c.stackSize() >= ProgramParameters::maxStackSize) && (!c.endOfTapes());};
-    Action::BasicAction basicAction =
-      {Action::BasicAction::Type::Push, "", apply, undo, appliable};
+    sequence.emplace_back(pushHead());
 
-    sequence.emplace_back(basicAction);
+    sequence.emplace_back(moveHead(+1));
   }
   else if(std::string(b1) == "REDUCE")
   {
-    auto apply = [](Config & c, Action::BasicAction & ba)
-      {ba.data = std::to_string(c.stackTop());
-       c.stackPop();};
-    auto undo = [](Config & c, Action::BasicAction & ba)
-      {c.stackPush(std::stoi(ba.data));};
-    auto appliable = [](Config & c, Action::BasicAction &)
-      {return !c.stackEmpty() && (c.endOfTapes() || !c.getTape("GOV")[c.stackTop()-c.getHead()].empty());};
-    Action::BasicAction basicAction =
-      {Action::BasicAction::Type::Pop, "", apply, undo, appliable};
-
-    sequence.emplace_back(basicAction);
+    sequence.emplace_back(stackPop(true));
   }
   else if(std::string(b1) == "LEFT")
   {
@@ -255,25 +278,7 @@ std::vector<Action::BasicAction> ActionBank::str2sequence(const std::string & na
       sequence.emplace_back(basicAction2);
     }
 
-    auto apply3 = [](Config & c, Action::BasicAction & ba)
-      {
-        ba.data = std::to_string(c.stackTop());
-        c.stackPop();
-      };
-    auto undo3 = [](Config & c, Action::BasicAction & ba)
-      {
-        c.stackPush(std::stoi(ba.data));
-      };
-    auto appliable3 = [](Config & c, Action::BasicAction &)
-      {
-        if (c.stackEmpty())
-          return false;
-        return !c.isFinal() && !c.endOfTapes();
-      };
-    Action::BasicAction basicAction3 =
-      {Action::BasicAction::Type::Pop, b1, apply3, undo3, appliable3};
-
-    sequence.emplace_back(basicAction3);
+    sequence.emplace_back(stackPop(false));
   }
   else if(std::string(b1) == "RIGHT")
   {
@@ -316,22 +321,9 @@ std::vector<Action::BasicAction> ActionBank::str2sequence(const std::string & na
       sequence.emplace_back(basicAction2);
     }
 
-    auto apply3 = [](Config & c, Action::BasicAction &)
-      {
-        c.stackPush(c.getHead());
-      };
-    auto undo3 = [](Config & c, Action::BasicAction &)
-      {
-        c.stackPop();
-      };
-    auto appliable3 = [](Config & c, Action::BasicAction &)
-      {
-        return (!c.isFinal()) && (!c.endOfTapes()) && !(c.stackSize() >= ProgramParameters::maxStackSize);
-      };
-    Action::BasicAction basicAction3 =
-      {Action::BasicAction::Type::Push, b1, apply3, undo3, appliable3};
+    sequence.emplace_back(pushHead());
 
-    sequence.emplace_back(basicAction3);
+    sequence.emplace_back(moveHead(+1));
   }
   else if(std::string(b1) == "EOS")
   {
diff --git a/transition_machine/src/Config.cpp b/transition_machine/src/Config.cpp
index 56aa64f49241ab2797cf0794a1b2ec7825f5654e..5c0e72250f1b2faaea76833b52ec57bee18a894b 100644
--- a/transition_machine/src/Config.cpp
+++ b/transition_machine/src/Config.cpp
@@ -652,10 +652,8 @@ float Config::Tape::getScore()
   float res = 0.0;
 
   for (int i = 0; i < refSize(); i++)
-  {
     if (getRef(i-head) == getHyp(i-head))
       res += 1;
-  }
 
   return 100.0*res / refSize();
 }
diff --git a/transition_machine/src/Oracle.cpp b/transition_machine/src/Oracle.cpp
index cce65937aec591dd8b0af2574ab2f548f696e884..9237a1494bf1320c30f7070a38541cbbb75a64a3 100644
--- a/transition_machine/src/Oracle.cpp
+++ b/transition_machine/src/Oracle.cpp
@@ -494,6 +494,9 @@ void Oracle::createDatabase()
     }
     else if (parts[0] == "REDUCE")
     {
+      if (stackGov == 0)
+        cost++;
+
       for (int i = head; i <= sentenceEnd; i++)
       {
         int otherGov = 0;
@@ -507,6 +510,9 @@ void Oracle::createDatabase()
     }
     else if (parts[0] == "LEFT")
     {
+      if (stackGov == 0)
+        cost++;
+
       if (eos.getRef(stackHead-head) == ProgramParameters::sequenceDelimiter)
         cost++;