From: Alexander Presber Date: 2007-06-22T02:00:30+09:00 Subject: Re: Behaviour of Enumerables reject vs. select mixed into Hash >> module Enumerable >> def select(&blk) >> o = self.class.new >> each{|*e| o << e if blk[*e]} >> end >> end >> >> class Hash >> def <<(e) >> self[e[0]] = e[1] >> end >> end >> >> The downside here is, it is less efficient and breaks backward >> compatibility. > > It is a conceptional beauty but it really sucks for performance Why is that? Isn't the current implementation doing something similar, but more like def select(&blk) o = new Array each{|*e| o << e if blk[*e]} end > there is *no* solution to our problem that is backward compatible, we > explicitly ask for backward compatibility unless we go for a choosable > Enum Mixin. > Something like > class Hash > include TomsEnum > end Obviously breaking compatibilty is a very bad thing. But without knowing for sure, I imagine Enumerables implementation should have been something more along the lines of the above from the beginning. (I know, this is a bold claim and I'd like to see more opinions on that. But transfires approach is exactly what I was thinking of when bringing this up.) Making Enumerable behave more agnostic to the class it is mixed in (by letting the class itself provide a method to add an "element" to an instance of itself, Enumerable becomes truly mixable into anything that provides "each" and "<<". Then doing reject on any class that mixes in Enumerable will yield a filtered instance of that class, not Array. That said - I think there should be no such thing as TomsEnum or any special implementation. Enumerable is the place to define methods for all things containing enumerable elements. >> >> The other option would require an #each_assoc method (maybe assoc >> isn't the best term, but anyhow...) >> >> module Enumerable >> def select_assoc(&blk) >> h = {} >> each_assoc{|k,v| h[k]=v if blk[k,v]} >> h >> end >> end >> >> The downside here of course, is twice the number of Enumerable >> methods. > And although I cannot imagine a case, how do we know that there are > not Enumerables that take three or fourtytwo params ;). > After all Enumerable is a Mixin and we have to be prepared that it be > mixed in, right? Yes, one could impossibly provide for all possible Mixees like this. Yours, Alex