anchor.diff:  === Basic Tuning Options
   
   Using the above approach will work functionally in the widest set of deployment scenarios.
  -However, if you able to make certain assumptions about the hardware and software environment that the Disruptor will run in then you can take advantage of a number of tuning options to improve performance.
  -There are 2 main options for tuning, single vs. multiple producers and alternative wait strategies.
  -
  -==== Single vs. Multiple Producers
  -
  -One of the best ways to improve performance in concurrent systems is to adhere to the http://mechanical-sympathy.blogspot.co.nz/2011/09/single-writer-principle.html[Single Writer Principle], this applies to the Disruptor.
  -If you are in the situation where there will only ever be a single thread producing events into the Disruptor, then you can take advantage of this to gain additional performance.
  -
  -.Using a single producer
  +However, there are a number of tuning options that can be used to improve performance.
  +
  +The two main options for tuning are:
  +
  +- <<_single_vs_multiple_producers, Single vs. multiple producers>>, _and_
  +- <<_alternative_wait_strategies, Alternative wait strategies>>.
  +
  +Both of these options are set when constructing a Disruptor:
  +
  +.Tuning the Disruptor
   [source,java]
   ----
   public class LongEventMain
  
positive.code: | Run 6 | Disruptor=81,699,346 ops/sec
  |===
  
  ==== Alternative Wait Strategies
  
  The default wait strategy used by the Disruptor is the `BlockingWaitStrategy`.
  Internally the `BlockingWaitStrategy` uses a typical lock and condition variable to handle thread wake-up.
  The `BlockingWaitStrategy` is the slowest of the available wait strategies, but is the most conservative with the respect to CPU usage and will give the most consistent behaviour across the widest variety of deployment options.
  However, again knowledge of the deployed system can allow for additional performance.
  
  - **SleepingWaitStrategy** ->
  
  --
  Like the `BlockingWaitStrategy` the `SleepingWaitStrategy` it attempts to be conservative with CPU usage, by using a simple busy wait loop, but uses a call to link:http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/locks/LockSupport.html#parkNanos(long)[`LockSupport.parkNanos(1)`^] in the middle of the loop.
  On a typical Linux system this will pause the thread for around 60µs.
  However it has the benefit that the producing thread does not need to take any action other increment the appropriate counter and does not require the cost of signalling a condition variable.
  However, the mean latency of moving the event between the producer and consumer threads will be higher.
  It works best in situations where low latency is not required, but a low impact on the producing thread is desired.
  A common use case is for asynchronous logging.
  --
  
negative.code: - **YieldingWaitStrategy** ->
  
  --
  The `YieldingWaitStrategy` is one of two ``WaitStrategy``s that can be use in low-latency systems.
  It is designed for cases where there is the option to burn CPU cycles with the goal of improving latency.
  
  The `YieldingWaitStrategy` will busy spin, waiting for the sequence to increment to the appropriate value.
  Inside the body of the loop `Thread#yield()` will be called allowing other queued threads to run.
  
  This is the recommended wait strategy when you need very high performance, and the number of `EventHandler` threads is lower than the total number of logical cores, e.g. you have hyper-threading enabled.
  --
  
  - **BusySpinWaitStrategy** ->
  
  --
  The `BusySpinWaitStrategy` is the highest performing `WaitStrategy`.
  Like the `YieldingWaitStrategy`, it can be used in low-latency systems, but puts the highest constraints on the deployment environment.
  
  This wait strategy should only be used if the number of `EventHandler` threads is lower than the number of physical cores on the box, e.g. hyper-threading should be disabled.
  --
  
  === Clearing Objects From the Ring Buffer
  
  When passing data via the Disruptor, it is possible for objects to live longer than intended.
  To avoid this happening it may be necessary to clear out the event after processing it.
  
  If you have a single event handler, clearing out the value within the same handler is sufficient.
  If you have a chain of event handlers, then you may need a specific handler placed at the end of the chain to handle clearing out the object.
  
  .Example `ObjectEvent`
  