Ducktype, right?

  • Thread starter Mills Thomas (app1tam)
  • Start date
M

Mills Thomas (app1tam)

I checked out some of the new Ruby features at theluckystiff.net and saw
'ducktype'ing. It sounds uber cool. Is this what is meant by ducktype?
(The code may be inelegant; I don't know; I'm still a Ruby Nuby). Please
correct me if I got it wrong.

######################################################################
#
# ducktype
#
# This method accepts two parameters. The first is an array of
#strings. The second is anything. As long as every string in x is the
#name of one of the methods provided by y, the method will return
#true. I grunged the return value to make sure it only returns true
#or false.
#

def ducktype (x, y)
!(!( x.map{|f| break false if !y.respond_to?(f) }))
end

#####################################################################


This is sort of like having a discovered mixin. Neat.

BTW, thanks Matz and all the contribs. This is fun!

Drew
 
M

Martin DeMello

Mills Thomas (app1tam) said:
I checked out some of the new Ruby features at theluckystiff.net and saw
'ducktype'ing. It sounds uber cool. Is this what is meant by ducktype?
(The code may be inelegant; I don't know; I'm still a Ruby Nuby). Please
correct me if I got it wrong.

def ducktype (x, y)
!(!( x.map{|f| break false if !y.respond_to?(f) }))
end

More elegantly in 1.8

x.all? {|f| y.respond_to?(f)}

martin
 
F

Florian Frank

On 2003-08-08 07:27:08 +0900, Martin DeMello wrote:
[...]
x.all? {|f| y.respond_to?(f)}

Some time ago I came up with a very similiar idea to check the interface
of an object in a case statement without using its class constant. The
advantage is that you can bind the created interface to a variable and
pass it around.

module Kernel

def Interface(*selectors)
interface = Object.new
interface.instance_eval do
@selectors = selectors
def ===(obj) @selectors.all? { |s| obj.respond_to?(s) } end
end
interface
end

end

has_split = Interface:)split)
[ %w[foo], "bar", "baz", 23 ].each do |thingy|
print "#{thingy}: "
case thingy
when Interface:)join, :to_a)
puts "join & to_a"
when "baz"
puts "is baz"
when has_split
puts "split"
else
puts "nothing"
end
end

This prints:
foo: join & to_a
bar: split
baz: is baz
23: nothing
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,020
Latest member
GenesisGai

Latest Threads

Top