I think programmer sanity is probably helped by not having such a
`feature'. Reusing variables for different purposes is not at all what
[not] `typing' is about, and as David suggested, you possibly mean class,
not type. (singleton methods/whatever-you-want-to-call-them, for example?
are they part of the type? or something else?)
The point of duck typing is that you don't need to/you shouldn't document
the 'types', seeing no purpose to restrict your definition of what's
considered valid input. Surely if the object responds in all the ways you
ask it to, it's fit for the task?
Maybe I'm not in the correct mindset of dynamic programming. I've always
found it difficult to remember return values/parameter-types (i.e. classes)
for a large number of methods.
I find I have this problem less the more readable (as English) my code is.
Compare:
h = Hash.new 0
ARGF.each_line do |l|
h[l] += 1
end
puts h.sort_by { |k,v| v }.first(10).map { |k,v| "#{v}\t#{k}" }
With:
counts = Hash.new 0
ARGF.each_line do |line|
counts[line] += 1
end
top = counts.sort_by { |_, count| count }.first 10
puts top.map { |line, count| "#{count}\t#{line}" }
In the first example looking at any individual call or expression doesn't tell you anything about any of the surrounding code. You have to trace back and follow types around to understand it.
In the second example, the types are objects. If you look at just the last line, you can understand what I intend without reading any of the preceding lines.
Most of the expressiveness of the code sample above comes from Ruby's expressive and consistent core library, more so that choosing good names. Unfortunately there are libraries that do not share the consistency of the core library.
Don't get me wrong, I would much rather use
Ruby at work than Java, but with a good IDE, Java's entire API is available
in pop-up windows AS YOU TYPE. While developing in ruby, I have several
rdoc's open in my web browser, files open in several terminal windows, and
an IRB session open, all for reference purposes when I'm working with
unfamiliar APIs.
If an API is unfamiliar to me I'll use gem server or ri for hints, but once it becomes familiar I usually don't need it anymore. If I always have to refer to API documentation, it's a sign of a poor API.
Surely if the object responds in all the ways you ask it to, it's fit for the task?
Consider the common case of something like DataStructure#remove(). Does
remove take an index or the object to be removed? Usually the API developer
supports one use case or another but not both. You should not have to read
the code to figure out which it is.
That API developer should be beaten with a stick. Matz programmed my brain to expect this as the way to remove elements from a data structure by object:
$ ri Hash#delete
------------------------------------------------------------ Hash#delete
hsh.delete(key) => value
$ ri Array#delete
----------------------------------------------------------- Array#delete
array.delete(obj) -> obj or nil
And this as the way to remove elements from a data structure by index:
$ ri Array#delete_at
-------------------------------------------------------- Array#delete_at
array.delete_at(index) -> obj or nil
I realize this was just an example, but APIs for third-party packages should exclusively follow the core library's examples. This makes it easier for everyone to write code that they expect to work.
(When wrapping, say libxml, tk, etc., it is ok to exclusively follow the wrapped library's examples. Mixing is always bad.)
···
On Apr 30, 2008, at 14:00 PM, Joe K wrote: