RubyTapas #205 - #210
205 Comparable
★
- identity, equivalence
- case equality
- and hash equality
- comparison operator
>
,==
,<
- spaceship operator
<=>
- .sort
- include Comparable
>
,==
,<
不要
206 Coercion
?
- arithmetic operations
+
,-
,*
,/
順番変えるとエラー
Feet.new(50) * 23 # => #<Feet:1150.0> 23 * Feet.new(50) # => # ~> -:3:in `*': Feet can't be coerced into Fixnum (TypeError) # ~> from -:3:in `<main>'
Rational.coerce
Rational(2, 3).coerce(10) # => [(10/1), (2/3)] Rational(10, 1) * Rational(2, 3) # => (20/3) 10 * Rational(2, 3) # => (20/3)
def coerce(other) unless other.is_a?(Numeric) raise TypeError, "Can't coerce #{other}" end [Feet.new(other), self] end
207 Conversion Function
★★
conversion method returns 0, whereas the function raises an error
"ham sandwich".to_i # => 0 Integer("ham sandwich") # => # ~> -:2:in `Integer': invalid value for Integer(): "ham sandwich" (ArgumentError) # ~> from -:2:in `<main>' nil.to_i # => 0 Integer(nil) # => # ~> -:2:in `Integer': can't convert nil into Integer (TypeError) # ~> from -:2:in `<main>'
conversion function
def Feet(value) case value when Feet then value else value = Float(value) Feet.new(value) end end
module Quantities class Feet # ... end ... module_function :Feet end include Quantities Feet(1234) # or: Quantities.Feet(1234)
208 Lenient Conversions
★
#to_i
are conventionally- lenient 情け深い、大目に見る
#to_f
is idiomatic to mean "please try your best to give me a Float, but don't worry about it if you can't"
strict conversion, lenient explicit conversion
The lenient conversion methods are particularly useful when we are dealing with messy data and a few extra zeroes won't hurt anything.
The strict conversion functions, on the other hand, are a great way to "fail fast" when bad data finds its way into a critical method.
209 Explicit Conversion
★
class Feet # ... alias_method :to_f, :magnitude def to_i to_f.to_i end
210 Implicit Conversion
★
Month = Struct.new(:name, :index) do def to_s name end def to_i index end alias_method :to_int, :to_i end
#to_int
- if it responds to the #to_int message, Ruby will send it the #to_int
- interchangeably 区別しない、同じ意味で
Ruby supports the idea of both explicit and implicit conversion methods
However, this is a technique that should be used sparingly and with careful consideration