简体   繁体   中英

Augmenting the methods with `alias` keyword

Having reading through The Ruby programming language I found an example of using alias keyword for augmenting the methods.

def hello                      # A nice simple method
  puts 'Hello world'           # Suppose we want to augment it...
end

alias original_hello hello     # Give the method a backup name

def hello                      # Now we define a new method with the old name
  puts "Your attention please" # That does some stuff
  original_hello               # Then calls the original method
  puts "This has been a test"  # Then does some more stuff
end

Indeed original hello preserves the old behavior even after the method the it had been referencing to was redefined.

But, to my mind, this example hardly clarifies the real benefit of this technique. Cannot the same be achieved in traditional way (eg by providing the block)? Then why applying this idiom? Can anyone provide an example from the real world when augmenting with alias really makes sense?

Rails code is full of those. Imagine the original hello method does not belong to your code base . Somewhere in 3rd-party library there is do_stuff(stuff) method declared on the class Stuffer .

You want to eg debug this method. You reopen the class, define an alias and, voilà:

class Stuffer
  alias original_do_stuff do_stuff
  def do_stuff(stuff)
    puts stuff.inspect
    original_do_stuff(stuff)
  end
end

Now all the code, including original 3rd party code you might be even not aware about, would print out the parameter passed to every single call to do_stuff .


Real-life example (don't try this at home and in the school :)

class String
  alias _inspect inspect
  def inspect
    puts "I am a string: “#{_inspect}”"
  end
end
"abc".inspect
#⇒ I am a string: “"abc"”

Can anyone provide an example from the real world when augmenting with alias really makes sense?

Not really. Today, you would do this (example taken from @mudasobwa's answer ):

 module WeirdInspectRefinement module WeirdInspectExtension def inspect "I am a string: “#{super}”" end end refine String do prepend WeirdInspectExtension end end using WeirdInspectRefinement p 'abc'.inspect #⇒ 'I am a string: “"abc"”' 

But even before Module#prepend and Refinements existed, there was never a reason to use alias for this, which leaves unused methods around polluting the namespace, and Rails abandoned it quite a while ago :

 class String old_inspect = instance_method(:inspect) define_method(:inspect) do "I am a string: “#{old_inspect.bind(self).()}”" end end 'abc'.inspect #⇒ 'I am a string: “"abc"”' 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM