NOTE: This RFC is closed; I went ahead and implemented. If you've got a problem with that, fork the project and make it better: https://github.com/yaauie/typed-array
tl;dr: Ruby does not have an Array class that enforces the type of its members; such a class can be useful, so I have created one. I would like help in determining the interface for it.
While there are partial implementations of typed arrays in libraries here and there, I could not find any that covered all interfaces that could change the contents of an Array. I created a class that handles substantially more than any existing typed-array class, with the intent of providing full coverage. I plan to release it as an MIT-licensed gem, but would first appreciate feedback from more experienced rubyists on the interface that is used to create these Arrays. Please feel free to share this gist with anyone you feel would have valuable input.
Monkeypatch a constant within Array, generate classes on the fly if/when they are needed using const_missing
# If you need an array that only accepts symbols, you would call this:
Array::Typed::Symbol.new
# If you had a class Foo and need to extend the typed array that extends it:
class Foos < Array::Typed::Foo
def analyze
# do something
end
end
# it can even easily work with classes that are deep in a hierarchy
Array::Typed::Deep::Hierarchy.new()
Advantages:
- Reads well
- Hierarchy is easy to follow
Disadvantages
- Proxy class definitions can get a little tricky. Can we easily have a typed array of typed arrays?
Array::Typed::Array::Typed::Foo.new()
- Not easy to follow gem naming configurations when you're extending core classes
The same as Option 1 except instead of monkeypatching, wrap in a module called TypedArray. Theoretically these could operate side-by-side or by require
-ing a different script.
# If you need an array that only accepts symbols, you would call this:
TypedArray::Symbol.new
# If you had a class Foo and need to extend the typed array that extends it:
class Foos < TypedArray::Foo
def analyze
# do something
end
end
# it can even easily work with classes that are deep in a hierarchy
TypedArray::Deep::Hierarchy.new()
Advantages:
- Reads well
- Hierarchy is easy to follow
- Easy to follow gem naming conventions
Disadvantages:
- Proxy class definitions can get a little tricky. Can we easily have a typed array of typed arrays?
TypedArray::TypedArray::Foo.new()
Monkeypatch Class to provide a TypedArray constant with const_missing
# If you need an array that only accepts symbols, you would call this:
Symbol::TypedArray.new
# If you had a class Foo and need to extend the typed array that extends it:
class Foos < Foo::TypedArray
def analyze
# do something
end
end
# it can even easily work with classes that are deep in a hierarchy
Deep::Hierarchy::TypedArray.new()
Advantages:
- No proxy objects needed; greatly simplifies execution timeline
- Lightweight
Disadvantages:
- Hierarchy not as easy to follow
- no known convention for gem naming
- array-of-arrays is ugly, essentially backwards:
Foo::TypedArray::TypedArray.new()
The less magic version
# If you need an array that only accepts symbols, you would call this:
TypedArray.new( Symbol )
# If you had a class Foo and need to extend the typed array that extends it:
class Foos < TypedArray::Class.new( Symbol )
def analyze
# do something
end
end
# it can even easily work with classes that are deep in a hierarchy
TypedArray.new( Deep::Hierarchy )
Advantages:
- No proxy objects needed; greatly simplifies execution timeline
- Free of monkeypatches
- No use of const_missing
Disadvantages:
- Hierarchy not as easy to follow
- Feels less ruby-ish to me