From the Module
Module#append_features(mod) → mod => When this module is included in another, Ruby calls append_features in this module, passing it the receiving module in mod. Ruby’s default implementation is to add the constants, methods, and module variables of this module to mod if this module has not already been added to mod or one of its ancestors.
Module#prepend_features(mod) → mod => When this module is prepended in another, Ruby calls prepend_features in this module, passing it the receiving module in mod. Ruby’s default implementation is to overlay the constants, methods, and module variables of this module to mod if this module has not already been added to mod or one of its ancestors.
Can anyone help me to understand the below questions:
What more features of Module
are defined as append
and prepend
except those default?
How they differ functionally?
When to use append_features
and when prepend_features
?
what is the difference between two bold lines as above?
Available since Ruby 2, prepend is a bit less known to Rubyists than its two other friends. It actually works like include , except that instead of inserting the module between the class and its superclass in the chain, it will insert it at the bottom of the chain, even before the class itself.
In simple words, the difference between include and extend is that 'include' is for adding methods only to an instance of a class and 'extend' is for adding methods to the class but not to its instance.
included is called when you include module into a class, it is used for defining relations, scopes, validations, ... It gets called before you even have created object from that class.
What is the difference between a class and a module? Modules are collections of methods and constants. They cannot generate instances. Classes may generate instances (objects), and have per-instance state (instance variables).
As specified in the text you quoted:
the constants, methods, and module variables
Both add methods of the mixed-in module to the passed module (class). The difference is in the lookup order of these methods, in case that the target class already has them defined:
include
behaves as if the target class inherited mixed-in module:
module FooBar def say puts "2 - Module" end end class Foo include FooBar def say puts "1 - Implementing Class" super end end Foo.new.say # => # 1 - Implementing Class # 2 - Module
prepend
makes the methods from the mixed in module "stronger" and executes them first:
module FooBar def say puts "2 - Module" super end end class Foo prepend FooBar def say puts "1 - Implementing Class" end end Foo.new.say # => # 2 - Module # 1 - Implementing Class
The example kindly ripped off from here: http://blog.crowdint.com/2012/11/05/3-killer-features-that-are-coming-on-ruby-2-0.html
Use prepend
when you want to keep methods of the target module (class) at the end of the method lookup chain.
Some real-world examples can be found by searching SO for ruby
, module
and prepend
:
(Note: I am mentioning only methods, as they are easiest to picture when it comes to inheritance and mixing-in, but the same applies to other features.)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With