What should I implement to have a custom class behave exactly as an array?
Say I have a custom class, what should I override to get array-like behaviour? I think that supplying an each
method开发者_Go百科 won't be enough, as that won't give me acces to the []
methods?
Should I inherit the Array class? What should I overwrite in there?
For enumerable like behavior (which sounds like what you want), you should include Enumerable
to get the Enumerable
module functionality, which means you need to provide a method each
. This will give you lots of the relevant methods you want (Enumerable details).
If you want just []
like functionality, you only need the following methods, and nothing more:
def [] key
# return value for key here.
end
def []= key, value
# store value under key here.
end
Inheriting from Array makes perfect sense. You get to extend Array behavior without worrying about interactions with other users of the Array type, and you don't even need to do the trivial work to mix in Enumerable.
And if you need hooks, which you probably do, you can just call super()
to forward the current message.
If you have an actual array that stores your data, you may want to have
require "forwardable"
class CustomArray
extend Forwardable # For def_delegators
include Enumerable # Optional
def_delegators :@actual_array, :[], :[]=, :each
def initialize(actual_array)
@actual_array = actual_array
end
end
By using delegation, you only provide the methods that you know you want, rather than providing all the methods by default.
精彩评论