diff --git a/examples/lj.py b/examples/lj.py
index 214966e0634db3a81c9a1faf7988a23fc5751a73..b5986e5fe8024af4e3f5a21643d000e883e6833a 100644
--- a/examples/lj.py
+++ b/examples/lj.py
@@ -7,11 +7,16 @@ def lj(i, j):
     sr6 = sr2 * sr2 * sr2 * sigma6[i, j]
     apply(force, delta(i, j) * (48.0 * sr6 * (sr6 - 0.5) * sr2 * epsilon[i, j]))
 
-def euler(i):
-    linear_velocity[i] += dt * force[i] / mass[i]
+
+def initial_integrate(i):
+    linear_velocity[i] += (dt * 0.5) * force[i] / mass[i]
     position[i] += dt * linear_velocity[i]
 
 
+def final_integrate(i):
+    linear_velocity[i] += (dt * 0.5) * force[i] / mass[i]
+
+
 cmd = sys.argv[0]
 target = sys.argv[1] if len(sys.argv[1]) > 1 else "none"
 if target != 'cpu' and target != 'gpu':
@@ -25,7 +30,7 @@ sigma = 1.0
 epsilon = 1.0
 sigma6 = sigma ** 6
 
-psim = pairs.simulation("lj", [pairs.point_mass()], timesteps=200, double_prec=True, debug=True)
+psim = pairs.simulation("lj", [pairs.point_mass()], timesteps=200, double_prec=True)
 psim.add_position('position')
 psim.add_property('mass', pairs.real(), 1.0)
 psim.add_property('linear_velocity', pairs.vector())
@@ -39,8 +44,9 @@ psim.reneighbor_every(20)
 #psim.compute_half()
 psim.build_neighbor_lists(cutoff_radius + skin)
 psim.vtk_output(f"output/lj_{target}")
+psim.compute(initial_integrate, symbols={'dt': dt}, pre_step=True, skip_first=True)
 psim.compute(lj, cutoff_radius)
-psim.compute(euler, symbols={'dt': dt})
+psim.compute(final_integrate, symbols={'dt': dt}, skip_first=True)
 
 if target == 'gpu':
     psim.target(pairs.target_gpu())
diff --git a/src/pairs/mapping/funcs.py b/src/pairs/mapping/funcs.py
index 0d9300899a0562ef852ad38bd650b873bce388ea..925115623c190b2f340c832a065f0b0bd9640bea 100644
--- a/src/pairs/mapping/funcs.py
+++ b/src/pairs/mapping/funcs.py
@@ -273,7 +273,7 @@ class BuildParticleIR(ast.NodeVisitor):
         return op_class(self.sim, operand, None, BuildParticleIR.get_unary_op(node.op))
 
 
-def compute(sim, func, cutoff_radius=None, symbols={}):
+def compute(sim, func, cutoff_radius=None, symbols={}, pre_step=False, skip_first=False):
     src = inspect.getsource(func)
     tree = ast.parse(src, mode='exec')
     #print(ast.dump(ast.parse(src, mode='exec')))
@@ -318,7 +318,11 @@ def compute(sim, func, cutoff_radius=None, symbols={}):
 
             ir.visit(tree)
 
-    sim.build_module_with_statements()
+    if pre_step:
+        sim.build_pre_step_module_with_statements(skip_first=skip_first)
+
+    else:
+        sim.build_module_with_statements(skip_first=skip_first)
 
 
 def setup(sim, func, symbols={}):
diff --git a/src/pairs/sim/simulation.py b/src/pairs/sim/simulation.py
index 85b333f4a60f4d7e98a66f54875dae2c187e2cf6..86dcb610c8e6e3ccea05e54686114a83eff00e35 100644
--- a/src/pairs/sim/simulation.py
+++ b/src/pairs/sim/simulation.py
@@ -10,7 +10,7 @@ from pairs.ir.properties import Properties, ContactProperties
 from pairs.ir.symbols import Symbol
 from pairs.ir.types import Types
 from pairs.ir.variables import Variables
-from pairs.graph.graphviz import ASTGraph
+#from pairs.graph.graphviz import ASTGraph
 from pairs.mapping.funcs import compute, setup
 from pairs.sim.arrays import DeclareArrays
 from pairs.sim.cell_lists import CellLists, BuildCellLists, BuildCellListsStencil, PartitionCellLists
@@ -59,8 +59,9 @@ class Simulation:
         self._capture_statements = True
         self._block = Block(self, [])
         self.setups = Block(self, [])
-        self.setup_functions = Block(self, [])
-        self.functions = Block(self, [])
+        self.setup_functions = []
+        self.pre_step_functions = []
+        self.functions = []
         self.module_list = []
         self.kernel_list = []
         self._check_properties_resize = False
@@ -215,8 +216,8 @@ class Simulation:
         self.neighbor_lists = NeighborLists(self.cell_lists)
         return self.neighbor_lists
 
-    def compute(self, func, cutoff_radius=None, symbols={}):
-        return compute(self, func, cutoff_radius, symbols)
+    def compute(self, func, cutoff_radius=None, symbols={}, pre_step=False, skip_first=False):
+        return compute(self, func, cutoff_radius, symbols, pre_step, skip_first)
 
     def setup(self, func, symbols={}):
         return setup(self, func, symbols)
@@ -240,7 +241,7 @@ class Simulation:
             raise Exception("Two sizes assigned to same capacity!")
 
     def build_setup_module_with_statements(self):
-        self.setup_functions.add_statement(
+        self.setup_functions.append(
             Module(self,
                 name=self._module_name,
                 block=Block(self, self._block),
@@ -248,14 +249,31 @@ class Simulation:
                 check_properties_resize=self._check_properties_resize,
                 run_on_device=False))
 
-    def build_module_with_statements(self, run_on_device=True):
-        self.functions.add_statement(
-            Module(self,
-                name=self._module_name,
-                block=Block(self, self._block),
-                resizes_to_check=self._resizes_to_check,
-                check_properties_resize=self._check_properties_resize,
-                run_on_device=run_on_device))
+    def build_pre_step_module_with_statements(self, run_on_device=True, skip_first=False):
+        module = Module(self, name=self._module_name,
+                              block=Block(self, self._block),
+                              resizes_to_check=self._resizes_to_check,
+                              check_properties_resize=self._check_properties_resize,
+                              run_on_device=run_on_device)
+
+        if skip_first:
+            self.pre_step_functions.append((module, {'skip_first': True}))
+
+        else:
+            self.pre_step_functions.append(module)
+
+    def build_module_with_statements(self, run_on_device=True, skip_first=False):
+        module = Module(self, name=self._module_name,
+                              block=Block(self, self._block),
+                              resizes_to_check=self._resizes_to_check,
+                              check_properties_resize=self._check_properties_resize,
+                              run_on_device=run_on_device)
+
+        if skip_first:
+            self.functions.append((module, {'skip_first': True}))
+
+        else:
+            self.functions.append(module)
 
     def capture_statements(self, capture=True):
         self._capture_statements = capture
@@ -312,41 +330,45 @@ class Simulation:
     def generate(self):
         assert self._target is not None, "Target not specified!"
         comm = Comm(self, self._dom_part)
+        every_reneighbor_params = {'every': self.reneighbor_frequency}
 
-        timestep_procedures = [
-            (comm.exchange(), self.reneighbor_frequency),
-            (comm.borders(), comm.synchronize(), self.reneighbor_frequency),
-            (BuildCellLists(self, self.cell_lists), self.reneighbor_frequency),
-            (PartitionCellLists(self, self.cell_lists), self.reneighbor_frequency)
+        timestep_procedures = self.pre_step_functions + [
+            (comm.exchange(), every_reneighbor_params),
+            (comm.borders(), comm.synchronize(), every_reneighbor_params),
+            (BuildCellLists(self, self.cell_lists), every_reneighbor_params),
+            (PartitionCellLists(self, self.cell_lists), every_reneighbor_params)
         ]
 
         if self.neighbor_lists is not None:
-            timestep_procedures.append((BuildNeighborLists(self, self.neighbor_lists), self.reneighbor_frequency))
+            timestep_procedures.append(
+                (BuildNeighborLists(self, self.neighbor_lists), every_reneighbor_params))
 
         if self._use_contact_history:
             if self.neighbor_lists is not None:
-                timestep_procedures.append((BuildContactHistory(self, self._contact_history, self.cell_lists), self.reneighbor_frequency))
+                timestep_procedures.append(
+                    (BuildContactHistory(self, self._contact_history, self.cell_lists), every_reneighbor_params))
 
             timestep_procedures.append(ResetContactHistoryUsageStatus(self, self._contact_history))
 
-        timestep_procedures += [
-            ResetVolatileProperties(self),
-            self.functions
-        ]
+        timestep_procedures += [ResetVolatileProperties(self)] + self.functions
 
         if self._use_contact_history:
             timestep_procedures.append(ClearUnusedContactHistory(self, self._contact_history))
 
         timestep = Timestep(self, self.ntimesteps, timestep_procedures)
         self.enter(timestep.block)
-        timestep.add(VTKWrite(self, self.vtk_file, timestep.timestep() + 1, self.vtk_frequency))
+
+        if self.vtk_file is not None:
+            timestep.add(VTKWrite(self, self.vtk_file, timestep.timestep() + 1, self.vtk_frequency))
+
         self.leave()
 
+        vtk_item = [] if self.vtk_file is None else VTKWrite(self, self.vtk_file, 0, self.vtk_frequency)
         body = Block.from_list(self, [
             self.setups,
             self.setup_functions,
             BuildCellListsStencil(self, self.cell_lists),
-            VTKWrite(self, self.vtk_file, 0, self.vtk_frequency),
+            vtk_item,
             timestep.as_block()
         ])
 
diff --git a/src/pairs/sim/timestep.py b/src/pairs/sim/timestep.py
index f3c78922a275f99dcd2aea191e52807417d358eb..6b274ef56d33bd51c3f3a81009afc3804aa104f2 100644
--- a/src/pairs/sim/timestep.py
+++ b/src/pairs/sim/timestep.py
@@ -1,6 +1,6 @@
 from pairs.ir.scalars import ScalarOp
 from pairs.ir.block import Block
-from pairs.ir.branches import Branch
+from pairs.ir.branches import Branch, Filter
 from pairs.ir.loops import For
 
 
@@ -8,22 +8,30 @@ class Timestep:
     def __init__(self, sim, nsteps, item_list=None):
         self.sim = sim
         self.block = Block(sim, [])
-        self.timestep_loop = For(sim, 0, nsteps + 1, self.block)
+        self.timestep_loop = For(sim, 0, nsteps, self.block)
 
         if item_list is not None:
             for item in item_list:
                 if isinstance(item, tuple):
-                    if len(item) >= 3:
-                        self.add(item[0], item[2], item[1])
-                    else:
-                        self.add(item[0], item[1])
+                    stmt_else = None
+
+                    if len(item) == 2:
+                        stmt, params = item
+
+                    if len(item) == 3:
+                        stmt, stmt_else, params = item
+
+                    exec_every = 0 if 'every' not in params else params['every']
+                    skip_first = False if 'skip_first' not in params else params['skip_first']
+                    self.add(stmt, exec_every, stmt_else, skip_first)
+
                 else:
                     self.add(item)
 
     def timestep(self):
         return self.timestep_loop.iter()
 
-    def add(self, item, exec_every=0, item_else=None):
+    def add(self, item, exec_every=0, item_else=None, skip_first=False):
         assert exec_every >= 0, "exec_every parameter must be higher or equal than zero!"
         stmts = item if not isinstance(item, Block) else item.statements()
         stmts_else = None
@@ -37,6 +45,10 @@ class Timestep:
             self.block.add_statement(
                 Branch(self.sim, ScalarOp.inline(ScalarOp.cmp(ts % exec_every, 0)), True if stmts_else is None else False,
                 Block(self.sim, stmts), None if stmts_else is None else Block(self.sim, stmts_else)))
+
+        elif skip_first:
+            self.block.add_statement(Filter(self.sim, ScalarOp.inline(ts > 0), Block(self.sim, stmts)))
+
         else:
             self.block.add_statement(stmts)