Method with yield via send

Hi!

The following, of course, works fine:

class C
  def foo
   yield * 2
  end
end

C.new.foo {5}
=> 10

but if I do:

foop = proc { yield * 2 }

then

foop.call {5}

doesn't pass the block to yield, and if I define c as:

c = Class.new
c.send(:define_method,:foo,foop)

then

c.new.foo {5}

neither works.

Is there a way to define a method like the foo of C in the
c.send(:define_method,...) way?

Thanks,

···

--
Csaba

"There's more to life, than books, you know but not much more..."
[The Smiths]
***
If you want to send me a mail, see it in the mailto link at
http://www.renyi.hu/~ekho/egyelore.html

Hi,

The main problem here, I think, is the context of the blocks you are passing. They are bound into the current context. When you say 'foop = proc { yield * 2 }', the yield is for the current context, where there is no block to yield to.

Here's an example of the strange way contexts work when you define methods using blocks/procs:

   # set some variables
   foo, bar, baz = 23, 42, 93
     ==>[23, 42, 93]
   # create a class, define a method which shows the values of foobarbaz
   c = Class.new
     ==>#<Class:0x713c4>
   c.send :define_method, :inspect, lambda{"foo=#{foo}; bar=#{bar}; baz=#{baz}"}
     ==>#<Proc:0x0006149c@(irb):8>
   #inspect it:
   c.new
     ==>foo=23; bar=42; baz=93
   #change a value
   baz = 144
     ==>144
   c.new
     ==>foo=23; bar=42; baz=144

In Ruby 2.0, you will be able to do something like this:

   c = Class.new
   foop = lambda {|&b| b.call * 5 }
   c.send(:define_method, :foo, foop)

But, currently, I think there is no way to do that. I suppose you could do this:

   c=Class.new
     ==>#<Class:0x8c5ac>
   def foop() yield*2 end
     ==>nil
   c.send(:define_method, :foo, method(:foop))
     ==>#<Method: Object#foop>
   c.new.foo{5}
     ==>10

... But I get the feeling you are looking for a way to define methods using only methods.

cheers,
Mark

···

On Jun 9, 2004, at 3:53 AM, Csaba Henk wrote:

Hi!

The following, of course, works fine:

class C
  def foo
   yield * 2
  end
end

C.new.foo {5}
=> 10

but if I do:

foop = proc { yield * 2 }

then

foop.call {5}

doesn't pass the block to yield, and if I define c as:

c = Class.new
c.send(:define_method,:foo,foop)

then

c.new.foo {5}

neither works.

Is there a way to define a method like the foo of C in the
c.send(:define_method,...) way?

Hi,

At Thu, 10 Jun 2004 05:24:21 +0900,
Mark Hubbart wrote in [ruby-talk:102995]:

In Ruby 2.0, you will be able to do something like this:

   c = Class.new
   foop = lambda {|&b| b.call * 5 }
   c.send(:define_method, :foo, foop)

It has been implemented in 1.9.

···

Tue May 25 11:54:13 2004 Nobuyoshi Nakada <nobu@ruby-lang.org>

  * eval.c (rb_yield_0, proc_invoke, proc_arity): allow passing a block
    to a Proc. [ruby-dev:23533]

  * parse.y (block_par, block_var): ditto.

--
Nobu Nakada

Well, then, that's a great reason for me to upgrade...

On a related note, it's a little difficult for me to find out when these different things are implemented... What's the best way for a person to see all the features that have been implemented since their last update of the 1.9 build?

cheers,
Mark

···

On Jun 9, 2004, at 6:02 PM, nobu.nokada@softhome.net wrote:

Hi,

At Thu, 10 Jun 2004 05:24:21 +0900,
Mark Hubbart wrote in [ruby-talk:102995]:

In Ruby 2.0, you will be able to do something like this:

   c = Class.new
   foop = lambda {|&b| b.call * 5 }
   c.send(:define_method, :foo, foop)

It has been implemented in 1.9.

Tue May 25 11:54:13 2004 Nobuyoshi Nakada <nobu@ruby-lang.org>

  * eval.c (rb_yield_0, proc_invoke, proc_arity): allow passing a block
    to a Proc. [ruby-dev:23533]

  * parse.y (block_par, block_var): ditto.

That's cool, thanks!

···

In article <200406100102.i5A12ooG027348@sharui.nakada.niregi.kanuma.tochigi.jp>, nobu.nokada@softhome.net wrote:

Mark Hubbart wrote in [ruby-talk:102995]:

In Ruby 2.0, you will be able to do something like this:

   c = Class.new
   foop = lambda {|&b| b.call * 5 }
   c.send(:define_method, :foo, foop)

It has been implemented in 1.9.

Tue May 25 11:54:13 2004 Nobuyoshi Nakada <nobu@ruby-lang.org>

  * eval.c (rb_yield_0, proc_invoke, proc_arity): allow passing a block
    to a Proc. [ruby-dev:23533]

  * parse.y (block_par, block_var): ditto.

--
Csaba

"There's more to life, than books, you know but not much more..."
[The Smiths]
***
If you want to send me a mail, see it in the mailto link at
http://www.renyi.hu/~ekho/egyelore.html

Hi,

At Thu, 10 Jun 2004 14:16:14 +0900,
Mark Hubbart wrote in [ruby-talk:103045]:

On a related note, it's a little difficult for me to find out when
these different things are implemented... What's the best way for a
person to see all the features that have been implemented since their
last update of the 1.9 build?

We provide a wiki for commentary about changes in Japanese. At
least you could read original commit log and so on.

  http://rrr.jin.gr.jp/rwiki?cmd=view;name=ruby-cvs

···

--
Nobu Nakada