Commits

Stefan Scherfke  committed 44e2bef

Went over the SimPy intro, fixed a few things and "finalized" it.

  • Participants
  • Parent commits 76ddd3c

Comments (0)

Files changed (7)

File docs/simpy_intro/basic_concepts.rst

 Basic Concepts
 ==============
 
-A thing that has a state and a behaviour that changes its state over time is
-called *process*. All processes live in an *environment*. They may interact
-with the environment and with each other via *events*.
+SimPy is a discrete-event simulation library. The behavior of active components
+(like vehicles, customers or messages) is modeled by *processes*. All processes
+live in an *environment*. They interact with the environment and with each
+other via *events*.
 
 Processes are described by simple Python `generators
 <http://docs.python.org/3/reference/expressions.html#yieldexpr>`_. You can call
 them *process function* or *process method*, depending on whether it is
-a normal function or method of a class.  During their life time, they create
-events and ``yield`` them to wait for them to happen.
+a normal function or method of a class. During their life time, they create
+events and ``yield`` them in order to wait for them to be triggered.
 
 When a process yields an event, the process gets *suspended*. SimPy *resumes*
-the process, when the event occurs (we say that the event is *activated*).
+the process, when the event occurs (we say that the event is *triggered*).
 Multiple processes can wait for the same event. SimPy resumes them in the same
 order in which they yielded that event.
 
 An important event type is the :class:`Timeout`. Events of this type are
-activated after a certain amount of (simulated) time has passed. They allow
-a process to to sleep (or hold its state) for the given duration.
-A :class:`Timeout` and all other events can be created by calling the
-appropriate method of the :class:`Environment` that the process lives in
-(:meth:`Environment.timeout()` for example).
+triggered after a certain amount of (simulated) time has passed. They allow
+a process to sleep (or hold its state) for the given time. A :class:`Timeout`
+and all other events can be created by calling the appropriate method of the
+:class:`Environment` that the process lives in (:meth:`Environment.timeout()`
+for example).
 
 
 Our First Process
     ...         trip_duration = 2
     ...         yield env.timeout(trip_duration)
 
-Our *car* process requires a reference to an :class:`Environment` (``env``) to
-create new events. The *car*'s behaviour is described in an infinite loop.
-Remember, this function is a generator. Though it will never terminate, it will
-pass the control flow back to the simulation once a ``yield`` statement is
-reached. Once the yielded event is activate ("it occurs"), the simulation will
-resume the function at this statement.
-
+Our *car* process requires a reference to an :class:`Environment` (``env``) in
+order to create new events. The *car*'s behaviour is described in an infinite
+loop. Remember, this function is a generator. Though it will never terminate,
+it will pass the control flow back to the simulation once a ``yield`` statement
+is reached. Once the yielded event is triggered ("it occurs"), the simulation
+will resume the function at this statement.
 
 As I said before, our car switches between the states *parking* and *driving*.
 It announces its new state by printing a message and the current simulation
     >>> import simpy
     >>> env = simpy.Environment()
     >>> env.start(car(env))
-    Process(car)
+    <Process(car) object at 0x...>
     >>> simpy.simulate(env, until=15)
     Start parking at 0
     Start driving at 5
     Start driving at 12
     Start parking at 14
 
-First thing we need to do is to create an instance of :class:`Environment`.
+The first thing we need to do is to create an instance of :class:`Environment`.
 This instance is passed into our *car* process function. Calling it creates
-a *process generator (PG)* that needs to be started and added to the
-environment via :meth:`Environment.start()`.
+a *process generator* that needs to be started and added to the environment via
+:meth:`Environment.start()`.
 
-Note, that at this time, none of the code in your PEM is being executed. It's
-execution is merely scheduled at the current simulation time.
+Note, that at this time, none of the code of our process function is being
+executed. It's execution is merely scheduled at the current simulation time.
 
 The :class:`Process` returned by :meth:`~Environment.start()` can be used for
 process interactions (we will cover that in the next section, so we will ignore
 Finally, we start the simulation by calling :func:`simulate()` and passing the
 environment as well as an end time to it.
 
+
 What's Next?
 ============
 

File docs/simpy_intro/how_to_proceed.rst

+==============
+How to Proceed
+==============
+
+If you are not certain yet if SimPy fulfills your requirements or if you want
+to see more features in action, you should take a look at the various
+:doc:`examples <../examples/index>` we provide.
+
+If you are looking for a more detailed description of a certain aspect or
+feature of SimPy, the :doc:`Topical Guides <../topical_guides/index>` section
+might help you.
+
+Finally, there is an :doc:`API Reference <../api_reference/index>` that
+describes all functions and classes in full detail.

File docs/simpy_intro/index.rst

 ===================
 
 
-In this section, you'll learn the basics of SimPy in just a few minutes. You
-will be able to implement a simple simulation using SimPy and you'll be able
-to make an educated decision if SimPy is what you need. We'll also give you
-some hints on how to proceed to implement more complex simulations.
+In this section, you'll learn the basics of SimPy in just a few minutes.
+Afterwards, you will be able to implement a simple simulation using SimPy and
+you'll be able to make an educated decision if SimPy is what you need. We'll
+also give you some hints on how to proceed to implement more complex
+simulations.
 
 .. toctree::
    :maxdepth: 1
    basic_concepts
    process_interaction
    shared_resources
+   how_to_proceed
 
 ..     monitoring
-..     how_to_proceed

File docs/simpy_intro/installation.rst

 
 You can now optionally run SimPy's tests to see if everything works fine. You
 need `pytest <http://pytest.org>`_ and `mock
-<http://www.voidspace.org.uk/python/mock/>`_ for this.
+<http://www.voidspace.org.uk/python/mock/>`_ for this:
 
 .. code:: bash
 

File docs/simpy_intro/process_interaction.rst

 Waiting for a Process
 =====================
 
-As it happens, a SimPy :class:`Process` can be used like an event( technically,
-a process actually *is* an event). If you yield
-it, you are resumed once the process has finished. Imagine a car-wash
-simulation where cars enter the car-wash and wait for the washing process to
-finish. Or an airport simulation where passengers have to wait until a security
-check finishes.
+As it happens, a SimPy :class:`Process` can be used like an event (technically,
+a process actually *is* an event). If you yield it, you are resumed once the
+process has finished. Imagine a car-wash simulation where cars enter the
+car-wash and wait for the washing process to finish. Or an airport simulation
+where passengers have to wait until a security check finishes.
 
 Lets assume that the car from our last example magically became an electric
 vehicle. Electric vehicles usually take a lot of time charing their batteries
     ...         while True:
     ...             print('Start parking and charging at %d' % env.now)
     ...             charge_duration = 5
-    ...             # We yield the process that start() returns to wait for
-    ...             # it to finish
+    ...             # We yield the process that start() returns
+    ...             # to wait for it to finish
     ...             yield env.start(self.charge(charge_duration))
     ...
-    ...             # The charge process has finished and we can start driving
-    ...             # again.
+    ...             # The charge process has finished and
+    ...             # we can start driving again.
     ...             print('Start driving at %d' % env.now)
     ...             trip_duration = 2
     ...             yield env.timeout(trip_duration)
     ...         yield self.env.timeout(duration)
 
 When you compare the output of this simulation with the previous example,
-you'll notice that the car no starts driving at time ``3`` instead of ``5``::
+you'll notice that the car now starts driving at time ``3`` instead of ``5``::
 
     >>> env = simpy.Environment()
     >>> car = Car(env)
     >>> env.start(driver(env, car))
-    Process(driver)
+    <Process(driver) object at 0x...>
     >>> simpy.simulate(env, until=15)
     Start parking and charging at 0
     Was interrupted. Hope, the battery is full enough ...

File docs/simpy_intro/shared_resources.rst

 Basic Resource Usage
 ====================
 
-We'll slightly modify our elctric vehicle process ``car`` that we introduced in
+We'll slightly modify our electric vehicle process ``car`` that we introduced in
 the last sections.
 
 The car will now drive to a *battery charging station (BCS)* and request one of
     ...
     ...     # Request one of its charging spots
     ...     print('%s arriving at %d' % (name, env.now))
-    ...     with bsc.request() as req:
+    ...     with bcs.request() as req:
     ...         yield req
     ...
-    ...         # Charge the battery and release the resource afterwards
+    ...         # Charge the battery
     ...         print('%s starting to charge at %s' % (name, env.now))
     ...         yield env.timeout(charge_duration)
     ...         print('%s leaving the bcs at %s' % (name, env.now))
 
 The resource's :meth:`~simpy.resources.resource.Resource.request()` method
 generates an event that lets you wait until the resource becomes available
-again.  If you are resumed, you "own" the resource until you *release* it.
+again. If you are resumed, you "own" the resource until you *release* it.
 
 If you use the resource with the ``with`` statement as shown above, the
-resource is automatically being released. If you call ``release()`` without
+resource is automatically being released. If you call ``request()`` without
 ``with``, you are responsible to call
-:meth:`~simpy.resources.resource.Resource.release()` with the event once you
-are done using the resource.
+:meth:`~simpy.resources.resource.Resource.release()` once you are done using
+the resource.
 
 When you release a resource, the next waiting process is resumed and now "owns"
-one of the resource's slots.
+one of the resource's slots. The basic
+:class:`~simpy.resources.resource.Resource` sorts waiting processes in a *FIFO
+(first in---first out)* way.
 
-SimPy lets you choose the type of the queue used for waiters (e.g., *First in
--- first out (FIFO)* which is the default or *Last in -- first out (LIFO)*).
-Appart from the optional queue type, a resource needs a reference to an
-:class:`~simpy.core.Environment` and a *capacity* when it is created::
+A resource needs a reference to an :class:`~simpy.core.Environment` and
+a *capacity* when it is created::
 
     >>> import simpy
     >>> env = simpy.Environment()
-    >>> bcs = simpy.Resource(env, capacity=2)  # A LIFO queue is used by default
+    >>> bcs = simpy.Resource(env, capacity=2)
 
 We can now create the ``car`` processes and pass a reference to our resource as
 well as some additional parameters to them::
 
     >>> for i in range(4):
     ...     env.start(car(env, 'Car %d' % i, bcs, i*2, 5))
-    Process(car)
-    Process(car)
-    Process(car)
-    Process(car)
+    <Process(car) object at 0x...>
+    <Process(car) object at 0x...>
+    <Process(car) object at 0x...>
+    <Process(car) object at 0x...>
 
 Finally, we can start the simulation. Since the car processes all terminate on
 their own in this simulation, we don't need to specify an *until* time---the
 What's Next
 ===========
 
-The last part of this tutorial will demonstrate, how you can collect data from
-your simulation.
+.. The last part of this tutorial will demonstrate, how you can collect data from
+.. your simulation.
 
-Since this feature is not implemented yet, you should take a look at the
-:doc:`../examples/index` or the :doc:`../api_reference/index`.
+You should now be familiar with SimPy's basic concepts. The :doc:`next section
+<how_to_proceed>` shows you how you can proceed with using SimPy from here on.

File simpy/core.py

     except EmptySchedule:
         pass
 
-    return until.value if until.triggered else PENDING
+    return until.value if until.triggered else None
 
 
 def _describe_frame(frame):