How come every class in Ruby inherits from Object even though you never have to specify that behavior?
You would expect something like:
class Foo < Object; end
but
class Foo; end
is enough. How does Ruby do this internally?
The question of how Ruby does this internally is not entirely meaningful since the specific mechanism is intentionally undocumented and could change with later releases despite the language spec staying the same. Additionally, there are many Ruby interpreters out there, and they could all implement this behavior differently.
For MRI, if you look at the source for Class.new you'll see that if there are no arguments it sets the super to Object:
if (argc == 0) {
super = rb_cObject;
}
rb_define_class from the C API works similarly (by passing NULL to rb_define_class_id):
if (!super) super = rb_cObject;
I have no idea which code path class Foo; end ends up taking, but it doesn't really matter.
Internally, when you define a class like this:
class Foo < Bar; end
Ruby (at least the MRI and Rubinius versions) calls a C method, very similar to this:
rb_define_class( "Foo", parent_class );
where parent_class is set to point to Bar (I don't know much about the C code that finds Bar from the bare name you specified, but that is not relevant to your question).
When you write
class Foo; end
Then the value of parent_class used is rb_cObject, which is pre-defined in the core of Ruby, and this reference is also attached to the Object constant, so it will find the same Ruby value if you specify class Foo < Object
Ultimately, this is just a standard defaulting mechanism, same as you might implement in a method definition. It is all defined in a similar way to using default values of any other parameter, just the syntax used to express it is different; deciding whether to use the default or accept your choice of base class is handled by the Ruby parser.
If you want to learn more about internals of Ruby - at least MRI Ruby and Rubinius - at this level, you could start with learning about C native extensions. This PDF covers the basics very well. The internal structure of MRI Ruby is actually a large and quite "flat" C API, which is relatively easy to code if you know only a little C. Rubinius is a bit different, but still presents the same API for compatibility with native extensions.
This is by design of the language, vide ri Object:
Object is the default root of all Ruby objects. Object inherits from
BasicObject which allows creating alternate object hierarchies. Methods on
object are available to all classes unless explicitly overridden.
Related
In the book OO Design in Ruby, Sandi Metz says that the main use of modules is to implement duck types with them and include them in every class needed. Why is the Ruby Kernel a module included in Object? As far as I know it isn't used anywhere else. What's the point of using a module?
Ideally,
Methods in spirit (that are applicable to any object), that is, methods that make use of the receiver, should be defined on the Object class, while
Procedures (provided globally), that is, methods that ignore the receiver, should be collected in the Kernel module.
Kernel#puts, for example doesn't do anything with its receiver; it doesn't call private methods on it, it doesn't access any instance variables of it, it only acts on its arguments.
Procedures in Ruby are faked by using Ruby's feature that a receiver that is equal to self can be omitted. They are also often made private to prevent them from being called with an explicit receiver and thus being even more confusing. E.g., "Hello".puts would print a newline and nothing else since puts only cares about its arguments, not its receiver. By making it private, it can only be called as puts "Hello".
In reality, due to the long history of Ruby, that separation hasn't always been strictly followed. It is also additionally complicated by the fact that some Kernel methods are documented in Object and vice versa, and even further by the fact that when you define something which looks like a global procedure, and which by the above reasoning should then end up in Kernel, it actually ends up as a private instance method in Object.
As you already pointed out: Modules provide a way to collect and structure behavior, so does the Kernel module. This module is mixed in early into the class Object so every Ruby class will provide these methods. There is only a BasicObject before in hierarchy, it's child Objects purpose is only to get extended by the Kernel methods. BasicObject has only 7 methods that very very basic like new, __send__ or __id__.
class Object < BasicObject
include Kernel # all those many default methods we appreciate :)
end
I have a typical OO pattern: one base abstract class (that defines abstract methods) and several classes that implement these abstract methods in class-specific way.
I'm used to write documentation only once in abstract methods and then it automatically propagates to several concrete classes (at least it works the following way in Javadoc, in Scaladoc, in Doxygen), i.e. I don't need to repeat the same description in all concrete classes.
However, I couldn't find how to do such propagation in YARD. I've tried, for example:
# Some description of abstract class.
# #abstract
class AbstractClass
# Some method description.
# #return [Symbol] some return description
# #abstract
def do_something
raise AbstractMethodException.new
end
end
class ConcreteClass < AbstractClass
def do_something
puts "Real implementation here"
return :foo
end
end
What I get:
Code works as expected - i.e. throws AbstractMethodException is called in abstract class, does the job in concrete class
In YARD, AbstractClass is clearly defined as abstract, ConcreteClass is normal
Method description and return type is good in AbstractClass
Method is said to throw AbstractMethodException in AbstractClass
Method has no description at all and generic Object return type in ConcreteClass, there's not a single notice of that an abstract method exists in base class.
What I expect to get:
Method's description and return type are inherited (i.e. copied) to ConcreteClass from info at AbstractClass
Ideally, this method is specified in "inherited" or "implemented" section of ConcreteClass description, with some reference link from ConcreteClass#do_something to AbstractMethod#do_something.
Is it possible to do so?
I think the issue boils down to what you're trying to do. It looks like you're trying to implement an Interface in Ruby, which makes sense if you're coming from Java or .NET, but isn't really how Ruby developers tend to work.
Here is some info about how the typical thought on Interfaces in Ruby: What is java interface equivalent in Ruby?
That said, I understand what you're trying to do. If you don't want your AbstractClass to be implemented directly, but you want to define methods that can be used in a class that behaves like the AbstractClass stipulates (as in Design by Contract), then you probably want to use a Module. Modules work very well for keeping your code DRY, but they don't quite solve your problem related to documenting overridden methods. So, at this point I think you can reconsider how you approach documentation, or at least approach it in a more Ruby-ish way.
Inheritance in Ruby is really (generally speaking from my own experience) only used for a few reasons:
Reusable code and attributes
Default behaviors
Specialization
There are obviously other edge cases, but honestly this is what inheritance tends to be used for in Ruby. That doesn't mean what you're doing won't work or violates some rule, it just isn't typical in Ruby (or most dynamically typed languages). This atypical behavior is probably why YARD (and other Ruby doc generators) doesn't do what you expect. That said, creating an abstract class that only defines the methods that must exist in a subclass really gains you very little from a code perspective. Methods not defined will result in a NoMethodError exception being thrown anyway, and you could programmatically check if an object will respond to a method call (or any message for that matter) from whatever calls the method, using #respond_to?(:some_method) (or other reflective tools for getting meta stuff). It all comes back Ruby's use of Duck Typing.
For pure documentation, why document a method that you don't actually use? You shouldn't really care about the class of the object being sent or received from calling a method, just what those objects respond to. So don't bother creating your AbstractClass in the first place if it adds no real value here. If it contains methods you actually will call directly without overriding, then create a Module, document them there, and run $ yardoc --embed-mixins to include methods (and their descriptions) defined in mixed-in Modules. Otherwise, document methods where you actually implement them, as each implementation should be different (otherwise why re-implement it).
Here is how I would something similar to what you're doing:
# An awesome Module chock-full of reusable code
module Stuff
# A powerful method for doing things with stuff, mostly turning stuff into a Symbol
def do_stuff(thing)
if thing.kind_of?(String)
return thing.to_sym
else
return thing.to_s.to_sym
end
end
end
# Some description of the class
class ConcreteClass
include Stuff
# real (and only implementation)
def do_something
puts "Real implementation here"
return :foo
end
end
an_instance = ConcreteClass.new
an_instance.do_somthing # => :foo
# > Real implementation here
an_instance.do_stuff("bar") # => :bar
Running YARD (with --embed-mixins) will include the methods mixed-in from the Stuff module (along with their descriptions) and you now know that any object including the Stuff module will have the method you expect.
You may also want to look at Ruby Contracts, as it may be closer to what you're looking for to absolutely force methods to accept and return only the types of objects you want, but I'm not sure how that will play with YARD.
Not ideal, but you can still use the (see ParentClass#method) construct (documented here). Not ideal because you have to type this manually for every overriding method.
That being said, I'm no Yard specialist but given its especially customizable architecture, I'd be surprised that there would be no easy way to implement what you need just by extending Yard, somewhere in the Templates department I guess.
As a little hobby project, I'm trying to build up my own object system. I was wondering if there is a way of changing the default inheritance of all classes from Object to my base class Entity, so that whenever I create a new class I don't have to explicitly say class Thing < Entity; ideally, I would just be able to say class Thing and have its default superclass be my Entity class.
Sure you could do this by modifying the relevant part of the Ruby source and recompiling Ruby:
VALUE
rb_define_class_id(ID id, VALUE super)
{
VALUE klass;
if (!super) super = rb_cObject; // <-- where the default is set
klass = rb_class_new(super);
// ...
But that’s a huge hassle and requires patching and running a custom Ruby and probably has a lot of gotchas and things that are hard-coded to assume Object is the default.
And, on top of that, what’s the point? If you replace Object with something else as the default superclass, every class—including those in Ruby core—will now inherit from this new default superclass. You could get the same effect (just without the different name) far more easily and without needing a custom Ruby by just changing Object itself. That’s the beauty of being able to reopen classes! For example:
class Object
def foo
'bar!'
end
end
class A; end
A.new.foo #=> 'bar!'
If you wanted to be kind you might even just put all the relevant methods in an Entity module instead of a class and then include it into Object.
No, unfortunately this is not possible in Ruby. Ruby does not have a Meta-Object Protocol like e.g. CLOS that would allow you to manipulate the core semantics of the Object Model. It would be nice, though!
Does ruby have something different to other OOP languages (eg: PHP) that makes interfaces useless? Does it have some kind of replacement for this?
Edit:
Some clarifications:
In other languages (eg: PHP), you don't "need" interfaces (they are not mandatory at code level). You use them to make a contract, to improve the architecture of the software. Therefore, the affirmation 'in ruby you don't need interfaces / in other languages you need interfaces because XXX' is false.
No, mixins are not interfaces, they are a complete different thing (PHP 5.4 implements mixins). Have you even used interfaces?
Yes, PHP is OOP. Languages evolve, welcome to the present.
Well, it's a consensus that when an object is passed in Ruby it's not type-checked. Interfaces in Java and PHP are a way to affirm that an object complies to a certain contract or "type" (so something might be Serializable, Authorizable, Sequential and whatever else that you want).
However, in Ruby there is no formalized notion of a contract for which interfaces would fulfill some meaningful role as interface conformance is not checked in method signatures. See, for example, Enumerable. When you mix it into your object you are using its functionality as opposed to declaring that your object is Enumerable. The only benefit of having your object being Enumerable is that having defined each(&blk) you automatically get map, select and friends for free. You can perfectly have an object which implements all of the methods provided by Enumerable but does not mix in the module and it would still work.
For example, for any method in Ruby that expects an IO object you could feed in something that has nothing to do with an IO, and then it would explode with an error or - if you implemented your IO stub correctly - it will work just fine even though your passed object is not declared to be "IO-ish".
The idea behind that comes from the fact that objects in Ruby are not really glorified hash tables with a tag slapped onto them (which then have some extra tags that tell the interpreter or the compiler that this object has interface X therefore it can be used in context Y) but an enclosed entity responding to messages. So if an object responds to a specific message it fullfils the contract, and if it does not respond to that message - well then an error is raised.
So the absence of interfaces is compensated partially by the presence of Modules (which can contain functionality that you reach for without doing any type promises to the caller/consumer) and partially by the tradition of message-passing as opposed to typed dicts.
You should watch some presentations by Jim Weirich since he touches on the subject extensively.
This question is kind of open-ended, but here is my take:
The purpose of an interface declaration is two things:
Declare to your future self or colleagues what methods this class must have
Declare to your computer what methods this class must have
If we take the second purpose first, Ruby source code is never compiled, so there is never an option to verify the conformance to the interface declaration and warn the developer of any failure to conform. This means that if Ruby had some built-in interface support, it wouldn't have an option to verify the conformance until runtime, where the application will crash anyway, because of the missing implementation.
So back to the first purpose. Code readability. This could make sense and a formal Ruby convention of specifying interfaces might be helpful. For now, you would probably communicate this using comments or specs or - as I would probably prefer - a declarative module inclusion. E.g.
module Shippable
# This is an interface module. If your class includes this module, make sure it responds to the following methods
# Returns an integer fixnum representing weight in grams
def weight
raise NotImplementedError.new
end
# Returns an instance of the Dimension class.
def dimensions
raise NotImplementedError.new
end
# Returns true if the entity requires special handling.
def dangerous?
raise NotImplementedError.new
end
# Returns true if the entity is intended for human consumption and thereby must abide by food shipping regulations.
def edible?
raise NotImplementedError.new
end
end
class Product
include Shippable
end
A way of enforcing this interface would be by creating a spec that creates an instance of every class that includes the Shippable module, calls the four methods and expects them to not raise NotImplementedError.
I'm a 'Ruby person', and I would like interfaces, or something like them.
Not to enforce a contract - because enforcing anything isn't very Ruby, and kind of defeats the point of a dynamic language, and anyway there's no "compilation" step to enforce it at - but to document contracts that client subclasses can choose to conform to (or not, although if they choose not to they can't complain if the code doesn't work).
When I'm faced with this problem, ie, when I'm writing a class or module I expect subclasses to provide methods for, I usually document the methods I expect subclasses to provide like this:
module Enumerable
def each
raise NotImplementedError, "Subclasses must provide this method"
end
end
It's not ideal, but it's a reasonably rare case and it works for me.
As ruby is duck-typed, no separate interface is needed, but the objects only need to implement the common methods. Look at the "classic" example below:
class Duck
def move
"I can waddle."
end
end
class Bird
def move
"I can fly."
end
end
animals = []
animals << Duck.new
animals << Bird.new
animals.each do |animal|
puts animal.move
end
In this example, the "interface" is the move method, which is implemented by both the Duck and the Bird class.
I believe it's because Ruby is dynamically typed whereas other languages are statically typed. The only reason you'd need to use an interface in PHP is when you use type hinting when passing objects around.
Ruby is very dynamic and duck-typed. Wouldn't that make interfaces kind of useless or overkill? Interfaces force classes to have certain methods available at compile time.
Review this too:
http://en.wikipedia.org/wiki/Duck_typing
Depends what you mean by interface.
If by interface you mean a concrete object that exists in your language that you inherit from or implement then no you don't use interfaces in a language like ruby.
If you mean interface as in objects have some well documented interface then yes of course, objects still have a well documented interfaces, they have attributes and methods that you expect to be there.
I'd agree that interfaces are something that exists in your mind and the documentation and not in the code as an object.
I am studying the ruby object model and have some questions. I understand the idea that an object only stores instance variables, and methods are stored in the class, which an object has a reference to. I also understand the idea of 'self' -- what it is, how it changes, etc.
However, what I don't understand is the notion that 'classes are objects.' Is there a good, intuitive explanation anywhere?
(BTW: I'm using Ruby Object Model and Metaprogramming and Metaprogramming Ruby as my two resources. If anybody can suggest something else, that would be helpful.)
Thanks.
It means precisely what it sounds like — classes are objects. Specifically, they are instances of the class Class, which is itself a subclass of the class Module, which in turn is a subclass of Object, just like every other class in Ruby. Like any other object in Ruby, a class can respond to messages, have its own instance variables, etc.
As a practical example, let's take private.
class Person
attr_accessor :name, :height
private
attr_accessor :weight
end
This gives instances of Person public methods to access the person's name and height, but the accessors for the person's weight are private. BUTBUTBUT — rather than being a keyword like in most languages, private is an ordinary method of the Module class. If we wanted, we could redefine it to do something different for a particular class hierarchy.
class RichardStallman
def self.private(*args)
puts "NO! INFORMATION WAS MEANT TO BE FREE!"
end
end
Here's my shot at one.
In Ruby, classes are objects. Usually they have class Class. For example, let's consider the class Foo.
class Foo
end
Doubtless you've seen this before, and it's not terribly exciting. But we could also have defined Foo this way:
Foo = Class.new
Just as you'd create a new Foo by calling Foo.new, you can create a new Class by calling Class.new. Then you give that class the name Foo by assigning it, just like any other variable. That's all there is to it.
The notion of "classes are objects" ( as I understand it ) implies that anything you can do with an object, you can do it with a class.
This differs from other programming languages where the class and the class definition are special artifacts different from objects and often unaccessible to the runtime.
For instance in Ruby, you can modify any object at runtime, since classes are also objects you can modify the class it self and add methods at runtime, delete methods, or add and delete attributes at runtime.
For instance:
$ irb
>> x = Object.new
=> #<Object:0x1011ce560>
>> x.to_s
=> "#<Object:0x1011ce560>"
>> undef to_s
=> nil
>> x.to_s
NoMethodError: undefined method `to_s' for #<Object:0x1011ce560>
from (irb):4
>>
That's not possible on other programming languages where a distinction between objects and classes is made.
note: Probably you should understand basic Ruby concepts before going to meta programming as it may be confusing, that what I would do.
Look at this article, you may find it helpful:
The Ruby Object Model - Structure and Semantics
Personally I learned a lot about the Ruby object model by reading about the Smalltalk one (e.g. in the Squeak documentation). And depending on how fluent you are in C, the MRI sources are quite approachable and yield the most definite answers.
When you think of it, it's completely logical for new to be a function, right? A function which creates and returns a new object. (Unlike most of other languages where new is some kind of operator or a language construct.)
Pushing it further, even more logical for this function new is that it should be a method, if we are talking about an OO language. Whose method? A method of an object, just a little bit different sort of an object that we can call "class".
So, looking it that way, classes are just special kinds of objects, objects that, among other peculiarities, have method new and know how to create other objects based on their own image.
what I don't understand is the notion that 'classes are objects.' Is there a good, intuitive explanation anywhere?
An answer to SO thread `Visual representation of Ruby Object Model' links to an excellent video on the subject.