Module: Concurrent::Dereferenceable
- Included in:
- Agent, MVar, Obligation, TimerTask
- Defined in:
- lib/concurrent/dereferenceable.rb
Overview
Object references in Ruby are mutable. This can lead to serious problems when the #value of a concurrent object is a mutable reference. Which is always the case unless the value is a Fixnum, Symbol, or similar “primitive” data type. Most classes in this library that expose a #value getter method do so using this mixin module.
Instance Method Summary collapse
-
#init_mutex ⇒ Object
Initializes the internal
Mutex. -
#mutex ⇒ Mutex
A mutex lock used for synchronizing thread-safe operations.
-
#set_deref_options(opts = {}) ⇒ Object
Set the options which define the operations #value performs before returning data to the caller (dereferencing).
-
#value ⇒ Object
(also: #deref)
Return the value this object represents after applying the options specified by the
#set_deref_optionsmethod.
Instance Method Details
#init_mutex ⇒ Object
This method must be called from within the constructor of the including class.
Initializes the internal Mutex.
56 57 58 |
# File 'lib/concurrent/dereferenceable.rb', line 56 def init_mutex @mutex = Mutex.new end |
#mutex ⇒ Mutex
A mutex lock used for synchronizing thread-safe operations. Methods defined by Dereferenceable are synchronized using the Mutex returned from this method. Operations performed by the including class that operate on the @value instance variable should be locked with this Mutex.
45 46 47 |
# File 'lib/concurrent/dereferenceable.rb', line 45 def mutex @mutex end |
#set_deref_options(opts = {}) ⇒ Object
Most classes that include this module will call #set_deref_options
Set the options which define the operations #value performs before returning data to the caller (dereferencing).
from within the constructor, thus allowing these options to be set at object creation.
74 75 76 77 78 79 80 81 |
# File 'lib/concurrent/dereferenceable.rb', line 74 def (opts = {}) mutex.synchronize do @dup_on_deref = opts[:dup_on_deref] || opts[:dup] @freeze_on_deref = opts[:freeze_on_deref] || opts[:freeze] @copy_on_deref = opts[:copy_on_deref] || opts[:copy] @do_nothing_on_deref = ! (@dup_on_deref || @freeze_on_deref || @copy_on_deref) end end |
#value ⇒ Object Also known as: deref
Return the value this object represents after applying the options specified by the #set_deref_options method.
When multiple deref options are set the order of operations is strictly defined. The order of deref operations is:
-
:copy_on_deref -
:dup_on_deref -
:freeze_on_deref
Because of this ordering there is no need to #freeze an object created by a provided :copy_on_deref block. Simply set :freeze_on_deref to true. Setting both :dup_on_deref to true and :freeze_on_deref to +true is as close to the behavior of a “pure” functional language (like Erlang, Clojure, or Haskell) as we are likely to get in Ruby.
This method is thread-safe and synchronized with the internal #mutex.
28 29 30 31 32 |
# File 'lib/concurrent/dereferenceable.rb', line 28 def value mutex.synchronize do (@value) end end |