Ruby | 範囲を扱うクラスを自作する #ruby
概要
範囲を扱うクラスを自作します。
Ruby で範囲( Range )を扱うためには、
<=>
と succ
の二つのメソッドを実装する必要があります。
仕様
年齢を扱うクラスを範囲で扱えるようにします。
サンプルコード
require 'tbpgr_utils'
class Age
attr_accessor :age
def initialize(age)
@age = age
end
def adult?
!!(age >= 20)
end
def minor?
!adult?
end
def succ
copy = self.dup
copy.age += 1
copy
end
def <=>(other)
age <=> other.age
end
end
bulk_puts_eval binding, <<-EOS
(Age.new(18)..Age.new(22)).to_a
Range.new(Age.new(18), Age.new(22)).to_a
(Age.new(18)...Age.new(22)).to_a
Range.new(Age.new(18), Age.new(22), true).to_a
(Age.new(18)..Age.new(22)).min
(Age.new(18)..Age.new(22)).max
EOS
(Age.new(18)..Age.new(22)).each do |a|
bulk_puts_eval binding, <<-EOS
a.age
a.adult?
a.minor?
EOS
end
__END__
下記はTbpgrUtils gemの機能
bulk_puts_eval
https://rubygems.org/gems/tbpgr_utils
https://github.com/tbpgr/tbpgr_utils
出力
(Age.new(18)..Age.new(22)).to_a
# => [#<Age:0x00000600cb5b28 @age=18>, #<Age:0x00000600cb5a60 @age=19>, #<Age:0x00000600cb5a38 @age=20>, #<Age:0x00000600cb5a10 @age=21>, #<Age:0x00000600cb59e8 @age=22>]
Range.new(Age.new(18), Age.new(22)).to_a
# => [#<Age:0x00000600cb5358 @age=18>, #<Age:0x00000600cb5290 @age=19>, #<Age:0x00000600cb5268 @age=20>, #<Age:0x00000600cb5240 @age=21>, #<Age:0x00000600cb5218 @age=22>]
(Age.new(18)...Age.new(22)).to_a
# => [#<Age:0x00000600cb4c28 @age=18>, #<Age:0x00000600cb4b60 @age=19>, #<Age:0x00000600cb4b38 @age=20>, #<Age:0x00000600cb4b10 @age=21>]
Range.new(Age.new(18), Age.new(22), true).to_a
# => [#<Age:0x00000600cb44a8 @age=18>, #<Age:0x00000600cb43e0 @age=19>, #<Age:0x00000600cb43b8 @age=20>, #<Age:0x00000600cb4390 @age=21>]
(Age.new(18)..Age.new(22)).min # => #<Age:0x00000600bf2448 @age=18>
(Age.new(18)..Age.new(22)).max # => #<Age:0x00000600bf1fe8 @age=22>
a.age # => 18
a.adult? # => false
a.minor? # => true
a.age # => 19
a.adult? # => false
a.minor? # => true
a.age # => 20
a.adult? # => true
a.minor? # => false
a.age # => 21
a.adult? # => true
a.minor? # => false
a.age # => 22
a.adult? # => true
a.minor? # => false