Suppose a class needs to load an external library which takes some time to load and thus should be loaded only once. Two natural solutions to this would be to use the singleton pattern or the monostate pattern. Is there any advantage to either of these solutions in this particular context in Ruby?
For example:
# Using a Singleton class
require 'singleton'
class Parser
include Singleton
def initialize
#parser = load_external_library
end
def parse(sentence)
#parser.parse(sentence)
end
end
# Then calling using...
Parser.instance.parse(sentence)
Versus:
# Using a Monostate class
class Parser
def self.parse(sentence)
##parser ||= load_external_library
##parser.parse(sentence)
end
end
# Then calling using...
Parser.parse(sentence)
Since the second syntax is much cleaner, are there any advantages to using the Singleton in Ruby?
The singleton pattern structurally enforces the fact that you can never have more than one instance of a class at a time, and it is obvious to the developers that they are dealing with a singleton.
The monostate enforces the behavior of a singleton without the structure of the monostate.
You might find situations where you still need instance data. Therefore a monostate would be better. You can create the instance, use methods to affect instance data and still have access to the static data. With a singleton, you cannot have instance data.
Besides, If you plan on deriving classes from the singleton and you want those classes to be singletons, your better choice is monostate. That’s because all classes derived from a monostate are monostates. Classes derived singleton classes are not singletons by default. You would have to add the static method and attribute to each derived class.
Related
In MRI Ruby, when is a singleton class allocated?
I just found out that a singleton class can also have its own singleton class.
Thusly, it's possible to call
Object.singleton_class.singleton_class.singleton_class.singleton_class...
until the end of time itself. Obviously all of these singleton classes aren't allocated by the virtual machine by default.
Exactly when does a singleton class get allocated by the Ruby virtual machine? Does an object have a singleton class at all if I don't define any methods on it and don't call Object#singleton_class?
From the point of view of a Ruby program, every object always has a singleton class. Including classes. Including singleton classes.
However, as you guessed, some Ruby Implementations optimize this by not allocating all singleton classes in advance.
Here's what YARV does (to the best of my knowledge):
Singleton classes are allocated lazily. They are only created when you either try to access it, or open it, or define a method or constant or variable in it. This is a memory optimization.
However, this lazy allocation has some overhead. Since modules and classes often have singleton methods, for classes and modules, this is different: for classes and modules, YARV creates a singleton class as soon as the (class / module) object is instantiated. This is a speed optimization.
Of course, as you said in your question, this leads to an infinite recursion. So, #2 is only applied to "normal" classes, not to singleton classes.
So: singleton classes are instantiated lazily. The exception are classes and modules. The exception from the exception are singleton classes.
However, let me repeat what I wrote at the beginning: this is a private internal implementation detail of YARV. Other Ruby Implementations may or may not behave the same.
In Ruby, a singleton class always exists for every object, including singleton classes.
TL;DR according to my experiment, at least for YARV 2.6.5, all singleton classes are lazily allocated.
Before experiment
ObjectSpace.each_object(type) returns an enumerator that iterates over all the objects that .is_a?(type), as long as it is not garbage collected yet.
Experiment 1: defining an empty class
Open an irb, and do following steps. Note that the absolute number of objects may vary on your computer, but it's the diff that matters.
ObjectSpace.each_object(Class).count #=> 649
class A; end
ObjectSpace.each_object(Class).count #=> 650
Defining an empty class only allocates 1 class object, so the singleton class is not allocated.
Experiment 2: defining a class containing only instance methods
class B
def foo; end
def bar; end
end
ObjectSpace.each_object(Class).count #=> 651
Creating such classes does not create singleton classes either.
Experiment 3: defining a class containing class methods
class C
def self.foo; end
end
ObjectSpace.each_object(Class).count #=> 653
This time, 2 classes are created, one is the class C itself, the other is C's singleton class.
Experiment 4: new objects
a = A.new
ObjectSpace.each_object(Class).count #=> 653
So instantiation does not create singleton classes.
Experiment 5: adding singleton methods
def a.foo; end
ObjectSpace.each_object(Class).count #=> 654
As expected, adding singleton methods does create singleton classes.
Experiment 6: inheritance
class D; end
class E < D
def self.foo; end
end
ObjectSpace.each_object(Class).count #=> 658
This time, 4 classes are allocated, 2 of which are the "normal" classes, the other 2 are singleton classes. Because we proved that creating empty classes do not allocate singleton classes on the fly, D's singleton class must be allocated when defining singleton methods in E. So the conclusion is, when a singleton class must be created, its parent class (also a singleton class) must already be there. If not, it's created on the fly.
You can do the experiments for modules by yourself.
What are the differences between
module Logging
def self.log
if #logger.nil?
#logger = Logger.new STDOUT
end
#logger
end
end
and this?
class Logging
def self.log
if #logger.nil?
#logger = Logger.new STDOUT
end
#logger
end
end
They both appear to do the same thing. Why would I choose one over the other?
tl;dr: There are no class methods and module methods in Ruby, only instance methods. Considering that they are both just instance methods, and thus the same thing, there cannot possibly be any difference.
There is no such thing as a "class method" or a "module method" in Ruby. Ruby has exactly one kind of method: instance methods.
We sometimes use the word "class method" or "module method" out of convenience when talking about a certain pattern of using instance methods, but there is no such concept in Ruby. "Class methods" and "module methods" are really just singleton methods of an object which just happens to be an instance of the Module class or the Class class. There is absolutely no difference whatsoever between a singleton method of an object which happens to be an instance of Class, Module, String, Array, Hash, Object, Foo, Bar, Whatever, or Garbledigookidoo.
Oh. Did I mention? Singleton methods don't exist, either. Again, it is a word we use for certain kinds of usages of methods, but they are really just regular boring old instance methods of the singleton class of an object.
However, "instance method of the singleton class of foo" and "instance method of the singleton class of Foo, where Foo is an instance of Class" are really long, and so we shorten them to "singleton method of foo" and "class method of Foo" out of convenience, knowing full well that those are fictions that don't actually exist in the language.
Unlike Java, which has three different kinds of methods (instance methods, static methods, and constructors (which are kinda-sorta like methods)), Ruby has exactly one kind of method: instance methods. No class methods, no module methods, no global methods, no top-level methods, no static methods, no constructors. It does, however, have three kinds of classes: regular classes, singleton classes, and include classes (the latter being classes that get synthesized and injected into the inheritance hierarchy when you call include or prepend). These classes differ mainly in whether methods like Object#class, Class#superclass, and Class#ancestors display them or suppress them. Singleton classes are suppressed by all of them, include classes by the first two, but shown by ancestors.
Jörg Mittag is correct that there technically are no class methods or module methods. However, I will assume by "class method" you meant "an instance method defined on the singleton class of a Class instance" and by "module method" you meant "an instance method defined on the singleton class of a Module instance".
There is no functional difference between the two. Both define a method within a namespace.
In practice, you'll see that they tend to be used for different purposes. For example, class methods are often to specify different ways to construct an object, e.g. Puzzle.from_textfile. Module methods are just global functions that are put into a single namespace because they are logically related, e.g. Math.sin and Math.abs.
It's also important to note that Ruby also has the concept of a "module function", which is unrelated to this question. The term "module function" refers an class method on a module which has an identical private instance method. These can be created programmatically using Module.module_function, and are useful when a module is intended to be used as both a namespace and a mixin (e.g. Math).
Modules are about providing methods that you can use across multiple classes - think about them as "libraries" (as you would see in a Rails app). Classes are about objects; modules are about functions
See this
Modules are similar to classes in that they hold a collection of methods, constants, and other module and class definitions. Unlike classes, you cannot create objects based on modules.
Modules serve two purposes. First, they act as a namespace, letting you define methods whose names will not clash with those defined elsewhere. Second, they allow you to share functionality between classes—if a class mixes in a module, that module’s instance methods become available as if they had been defined in the class. Multiple classes can mix in the same module, sharing the module’s functionality without using inheritance. You can also mix multiple modules into a single class.
Classes are to create objects.
I understand that all classes in ruby are instances of metaclass Class. And that "regular" objects are instances of these classes (the instances of metaclass Class).
But I keep wondering, I mean classes are root of objects, classes are themselves instances of Class (called metaclass because its instances are classes). I saw in some blogs some overriding of method new, of class Class.
So Class behaves as a class, but its instances are classes. So it seems we have a circle, it looks likes class Class is an instance of itself.
I'm clearly missing a point here. What is the origin of class Class?
Here's an example that's confusing me:
class Class
def new
#something
end
end
But keyword class implies an instance of class Class. So how do this work?
how do this work
Easy: it doesn't. Not in Ruby, anyway.
Just like in most other languages, there are some core entities that are simply assumed to exist. They fall from the sky, materialize out of thin air, magically appear.
In Ruby, some of those magic things are:
Object doesn't have a superclass, but you cannot define a class with no superclass, the implicit direct superclass is always Object. [Note: there may be implementation-defined superclasses of Object, but eventually, there will be one which doesn't have a superclass.]
Object is an instance of Class, which is a subclass of Object (which means that indirectly Object is an instance of Object itself)
Class is a subclass of Module, which is an instance of Class
Class is an instance of Class
None of these things can be explained in Ruby.
BasicObject, Object, Module and Class all need to spring into existence at the same time because they have circular dependencies.
Just because this relationship cannot be expressed in Ruby code, doesn't mean the Ruby Language Specification can't say it has to be so. It's up to the implementor to figure out a way to do this. After all, the Ruby implementation has a level of access to the objects that you as a programmer don't have.
For example, the Ruby implementation could first create BasicObject, setting both its superclass pointer and its class pointer to null.
Then, it creates Object, setting its superclass pointer to BasicObject and its class pointer to null.
Next, it creates Module, setting its superclass pointer to Object and its class pointer to null.
Lastly, it creates Class, setting its superclass pointer to Module and its class pointer to null.
Now, we can overwrite BasicObject's, Object's, Module's, and Class's class pointer to point to Class, and we're done.
This is easy to do from outside the system, it just looks weird from the inside.
Once they do exist, however, it is perfectly possible to implement most of their behavior in plain Ruby. You only need very barebones versions of those classes, thanks to Ruby's open classes, you can add any missing functionality at a later time.
In your example, the class Class is not creating a new class named Class, it is reopening the existing class Class, which was given to us by the runtime environment.
So, it is perfectly possible to explain the default behavior of Class#new in plain Ruby:
class Class
def new(*args, &block)
obj = allocate # another magic thing that cannot be explained in Ruby
obj.initialize(*args, &block)
return obj
end
end
[Note: actually, initialize is private, so you need to use obj.send(:initialize, *args, &block) to circumvent the access restriction.]
BTW: Class#allocate is another one of those magic things. It allocates a new empty object in Ruby's object space, which is something that cannot be done in Ruby. So, Class#allocate is something that has to be provided by the runtime system as well.
There is a meta-circularity given by the "twist" link. It is the built-in superclass link from the root's eigenclass to the Class class. This can be expressed by
BasicObject.singleton_class.superclass == Class
A clue to understanding the .class map is seeing this map as derived from the eigenclass and superclass links: for an object x, x.class is the first class in the superclass chain of x's eigenclass. This can be expressed by
x.class == x.eigenclass.superclass(n)
where eigenclass is a "conceptual alias" of singleton_class
(resistant to issues with immediate values), y.superclass(i) means i-th superclass of y and n is smallest such that x.eigenclass.superclass(n) is a class. Equivalently, eigenclasses in the superclass chain of x.eigenclass are skipped (see rb_class_real which also reveals that in MRI, even superclass links are implemented indirectly – they arise by skipping "iclasses").
This results in that the class of every class (as well as of every eigenclass) is constantly the Class class.
A picture is provided by this diagram.
The metaclass confusion has 2 main sources:
Smalltalk. The Smalltalk-80 object model contains conceptual inconsistencies that are rectified by the Ruby object model. In addition, Smalltalk literature uses dialectics in terminology, which unfortunately has not been sufficiently remedied in the Ruby literature.
The definition of metaclass. At present, the definition states that metaclasses are classes of classes. However, for so called "implicit metaclasses" (the case of Ruby and Smalltalk-80) a much more fitting definition would be that of meta-objects of classes.
Yes, Class is an instance of itself. It's a subclass of Module, which is also an instance of class, and Module is a subclass of Object, which is also an instance of Class. It is indeed quite circular — but this is part of the core language, not something in a library. The Ruby runtime itself doesn't have the same limits thast you or I do when we're writing Ruby code.
I've never heard the word "metaclass" used to talk about Class, though. It isn't used much in Ruby at all, but when it is, it's usually a synonym for what's officially called a "singleton class of an object," which is an even more confusing topic than Object-Module-Class triangle.
Though it is a little out of date, this article by _why may help in understanding the behavior. You can find an even deeper dive into the subject in Paolo Perrotta's Metaprogramming Ruby.
I understand that singleton methods live in singleton classes (or eigenclasses). My first question is:
Why can't they live inside objects? I know that in ruby, an object can
only hold instance variables. But I cannot see why singleton methods
weren't designed to be in objects.
Next,
If objects can only contain instance variables, how come classes,
which are objects of Class, are able to store methods?
I am just confused at conceptual level. I have read many times that ruby object model is consistent.
Ad 1, they indeed do live inside an object. Singleton class, in fact, is just a mental construct. 'Singleton' here means, that, by definition, the class has only one instance - that object. So the identity of the object and the singleton class is intextricably the same.
Ad 2, the answer is, because Matz decided so. More precisely, not classes, but modules (Module class) store methods, and Class < Module.
It might be of interest to you, that a singleton class of an object is not instantiated by default. Until you try to access it, it simply does not exist. This is because if all the singleton classes were immediately instantiated, you would have an infinite chain of singleton classes:
o = Object.new
o.singleton_class
o.singleton_class.singleton_class
o.singleton_class.singleton_class.singleton_class
...
The goal of singleton pattern is to ensure, that only one object of a particular class will live within a system.
So the methods still live in a class, but you just can't create another instance of that class.
A class is an object, but because it serves as a template for other objects, its own instances, it keeps their instance methods inside its module. But if you treat a class as an ordinary object, for example call #object_id on it, it gives you all the behavior expected of normal objects.
Continuing from our discussion in comments: Strictly speaking, the ability to store methods (and constants) is a buit-in special ability of modules (Module class). Class class happens to be a subclass of Module class, which makes it inherit modules' ability to store methods, but you are free to create other objects (not just classes) with that ability:
class MyPetObjectThatCanStoreMethods < Module
def greet; puts "Bow, wow!" end
end
Fred = MyPetObjectThatCanStoreMethods.new
So, Fred is not exactly a module, but decsends from Module and has thus ability to store methods and constants:
module Fred # this is allowed!
LENGTH = 19
def rise; puts "I'm rising!" end
end
You can't do this with normal objects, only with module descendants!
Fred::LENGTH #=> 19
Fred.greet
#=> Bow, wow!
Fred.rise
#=> NoMethodError
That's because Fred stores #rise method, just like modules do, but unlike #greet method, #rise is not its instance method! To gain access to it, we will have to include Fred in a suitable class:
o = Object.new
o.rise
#=> NoMethodError
class << o # Including Fred in the metaclass of o
include Fred
end
o.rise
#=> I'm rising!
If objects can only contain instance variables, how come classes, which are objects of Class, are able to store methods?
class Foo
def suprim;end
end
Foo.instance_methods(true).grep(/^sup/)
#=> [:suprim]
I searched for Class's instance method superclass ,but didn't appear,as Foo is an instance of Class,so it should not store the
instance methods of Class. But yes,Foo returns only the methods of its instances to be used. Which is natural.Look below now:
Class.instance_methods(true).grep(/^sup/)
#=>[:superclass]
In the Ruby Standard Library we have the Singleton class:
http://ruby-doc.org/stdlib/libdoc/singleton/rdoc/index.html
We can make any class a singleton by including this class inside. I just rarely see this used. When would it make sense to use this Singleton class vs. just using plain old class methods - also known as singleton methods?
Said in another way: Which Singleton coding-convention are the best and why? Here are three ways I could think of:
require 'singleton'
class Foo
include Singleton
# method definitions go here...
end
Foo.instance.do_something!
Versus
class Foo
class << self
# method definitions go here...
end
end
Foo.do_something!
Versus
module Foo
class << self
# method definitions go here...
end
end
Foo.do_something!
WARNING: Opinions ahead!
If you just need a single object, just use a single object:
class << (Foo = Object.new)
# method definitions go here...
end
Foo.do_something!
Modules are for sharing behavior between objects. Classes are factories for objects. Note the plural: if you have only one object, you need neither a facility for sharing behavior nor a factory for producing multiple copies.
Whether or not this is considered idiomatic Ruby depends largely on which "Ruby" you are talking about: are you talking about Ruby as used by Rails programmers, Ruby as used by Smalltalk programmers, Ruby as used by Java programmers or Ruby as used by Ruby programmers? There are significant differences in the styles used by these different communities.
For example, old time Rubyists like David Alan Black tend to start always with just objects and singleton methods. Only if they later on discover duplicated behavior between objects will they extract that behavior into a mixin and extend the objects with it. (Note that at this stage, there still aren't any classes!)
Classes are created, again, only by refactoring, not by upfront design, when and only when there is duplicated structure between objects.
The most common approach I've seen is neither a singleton nor a class that you never instantiate. The most common and idiomatic way to do this is a module.