Skip to content

Commit 07225a3

Browse files
committed
Expound on alias vs alias_method appropriateness
Added examples of when one is more appropriate over the other, and notes about aliasing and inheritance.
1 parent 98dc6d2 commit 07225a3

File tree

1 file changed

+66
-4
lines changed

1 file changed

+66
-4
lines changed

README.md

Lines changed: 66 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2447,6 +2447,72 @@ condition](#safe-assignment-in-condition).
24472447
end
24482448
```
24492449

2450+
* <a name="alias-method-lexically"></a>
2451+
Prefer `alias` when aliasing methods in lexical class scope as the
2452+
resolution of `self` in this context is also lexical, and it communicates
2453+
clearly to the user that the indirection of your alias will not be altered
2454+
at runtime or by any subclass unless made explicit.
2455+
<sup>[[link](#alias-method-lexically)]</sup>
2456+
2457+
```Ruby
2458+
class Westerner
2459+
def first_name
2460+
@names.first
2461+
end
2462+
2463+
alias given_name first_name
2464+
end
2465+
```
2466+
2467+
Since `alias`, like `def`, is a keyword, prefer bareword arguments over
2468+
symbols or strings. In other words, do `alias foo bar`, not
2469+
`alias :foo :bar`.
2470+
2471+
Also be aware of how Ruby handles aliases and inheritance: an alias
2472+
references the method that was resolved at the time the alias was defined;
2473+
it is not dispatched dynamically.
2474+
2475+
```Ruby
2476+
class Fugitive < Westerner
2477+
def first_name
2478+
'Nobody'
2479+
end
2480+
end
2481+
```
2482+
2483+
In this example, `Fugitive#given_name` would still call the original
2484+
`Westerner#first_name` method, not `Fugitive#first_name`. To override the
2485+
behavior of `Fugitive#given_name` as well, you'd have to redefine it in the
2486+
derived class.
2487+
2488+
```Ruby
2489+
class Fugitive < Westerner
2490+
def first_name
2491+
'Nobody'
2492+
end
2493+
2494+
alias given_name first_name
2495+
end
2496+
```
2497+
2498+
* <a name="alias-method"></a>
2499+
Always use `alias_method` when aliasing methods of modules, classes, or
2500+
singleton classes at runtime, as the lexical scope of `alias` leads to
2501+
unpredictability in these cases.
2502+
<sup>[[link](#alias-method)]</sup>
2503+
2504+
```Ruby
2505+
module Mononymous
2506+
def self.included(other)
2507+
other.class_eval { alias_method :full_name, :given_name }
2508+
end
2509+
end
2510+
2511+
class Sting < Westerner
2512+
include Mononymous
2513+
end
2514+
```
2515+
24502516
## Exceptions
24512517

24522518
* <a name="fail-method"></a>
@@ -3393,10 +3459,6 @@ condition](#safe-assignment-in-condition).
33933459
Foo.bar = 1
33943460
```
33953461

3396-
* <a name="alias-method"></a>
3397-
Avoid `alias` when `alias_method` will do.
3398-
<sup>[[link](#alias-method)]</sup>
3399-
34003462
* <a name="optionparser"></a>
34013463
Use `OptionParser` for parsing complex command line options and `ruby -s`
34023464
for trivial command line options.

0 commit comments

Comments
 (0)