Ruby Singleton
require 'singleton' class Aardvark include Singleton endThat's it. Mixing in the Singleton module makes the "new" method private and creates an "instance" method that returns the sole instance of Aardvark. (So you'd access the Aardvark by saying "Aardvark.instance".) It also takes care of thread safety.
For educational purposes, this is how you would implement it without the use of the standard library:
class Aardvark
          private_class_method :new
          @@instance = new
          def Aardvark.instance
            @@instance
          end
end
Or, if you want it to be lazy-loading:
class Aardvark
          private_class_method :new
          def Aardvark.instance
            @@instance = new unless @@instance
            @@instance
          end
end
The following is an implementation of a module (MixIn) that will turn a class into a thread-safe, lazy-loading singleton.
      module ThreadSafeSingleton
        def self.append_features(clazz)
          require 'thread'
          clazz.module_eval { 
            private_class_method :new
            @instance_mutex = Mutex.new
            def self.instance 
              @instance_mutex.synchronize {
                @instance = new unless @instance
                @instance
              }
            end
          }
        end
      end
 # For further educational enjoyment, the following provides a test for
 # thread-safeness and a contrasting non-thread-safe implementation
      require 'test/unit'
      module SimpleSingleton
        def self.append_features(clazz)
          clazz.module_eval { 
            private_class_method :new
            def self.instance 
              @instance = new unless @instance
              @instance
            end
          }
        end
      end
      class SimpleSingletonClass
        include SimpleSingleton
        def initialize
          sleep 1
        end
      end
      class ThreadSafeSingletonClass
        include ThreadSafeSingleton
        def initialize
          sleep 1
        end
      end
      class TestSingleton < Test::Unit::TestCase
        def testSimpleIsNotThreadSafe
          threads = Array.new(101) { Thread.new { SimpleSingletonClass.instance }}
          assert(threads.collect { |t| t.value }.uniq.size > 1)
        end
        def testThreadSafeIsThreadSafe
          threads = Array.new(101) { Thread.new { ThreadSafeSingletonClass.instance }}
          assert_equal(1, threads.collect { |t| t.value }.uniq.size)
        end
      end
Compare with PerlSingleton and PythonSingleton
 EditText of this page
(last edited March 12, 2010)
or FindPage with title or text search