[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Forums >

comp.lang.ruby

method_added/define_method infinite loop

Trans

11/13/2007 2:25:00 PM

What's the best way to avoid the classic method_added/define_method
infinite loop?

class X
def self.method_added(name)
p name
define_method(name)
# do something else
end
end

def foo; end
end

This will, of course, print "foo" forever.

As an aside, anyone else think method_added should also receive a
block of the method definition? E.g. this would be a "push" (less the
infinite loop issue):

def self.method_added(name, &block)
define_method(name, &block)
end

Thanks!
T.


7 Answers

ara.t.howard

11/13/2007 8:37:00 PM

0


On Nov 13, 2007, at 7:24 AM, Trans wrote:

> What's the best way to avoid the classic method_added/define_method
> infinite loop?
>
> class X
> def self.method_added(name)
> p name
> define_method(name)
> # do something else
> end
> end
>
> def foo; end
> end
>
> This will, of course, print "foo" forever.
>
> As an aside, anyone else think method_added should also receive a
> block of the method definition? E.g. this would be a "push" (less the
> infinite loop issue):
>
> def self.method_added(name, &block)
> define_method(name, &block)
> end
>
> Thanks!
> T.
>
>



cfp:~ > cat a.rb
class X
class << self
def ignoring_added_methods
ignoring_added_methods = @ignoring_added_methods
@ignoring_added_methods = true
yield
ensure
@ignoring_added_methods = ignoring_added_methods
end

def ignoring_added_methods?
defined? @ignoring_added_methods and @ignoring_added_methods
end

def method_added name
return if ignoring_added_methods?
ignoring_added_methods do
p name
define_method(:bar){}
end
end
end

def foo
end
end



cfp:~ > ruby a.rb
:foo


a @ http://codeforp...
--
it is not enough to be compassionate. you must act.
h.h. the 14th dalai lama




Trans

11/14/2007 3:13:00 AM

0



On Nov 13, 3:36 pm, "ara.t.howard" <ara.t.how...@gmail.com> wrote:
> On Nov 13, 2007, at 7:24 AM, Trans wrote:
>
>
>
> > What's the best way to avoid the classic method_added/define_method
> > infinite loop?
>
> > class X
> > def self.method_added(name)
> > p name
> > define_method(name)
> > # do something else
> > end
> > end
>
> > def foo; end
> > end
>
> > This will, of course, print "foo" forever.
>
> > As an aside, anyone else think method_added should also receive a
> > block of the method definition? E.g. this would be a "push" (less the
> > infinite loop issue):
>
> > def self.method_added(name, &block)
> > define_method(name, &block)
> > end
>
> > Thanks!
> > T.
>
> cfp:~ > cat a.rb
> class X
> class << self
> def ignoring_added_methods
> ignoring_added_methods = @ignoring_added_methods
> @ignoring_added_methods = true
> yield
> ensure
> @ignoring_added_methods = ignoring_added_methods
> end
>
> def ignoring_added_methods?
> defined? @ignoring_added_methods and @ignoring_added_methods
> end
>
> def method_added name
> return if ignoring_added_methods?
> ignoring_added_methods do
> p name
> define_method(:bar){}
> end
> end
> end
>
> def foo
> end
> end
>
> cfp:~ > ruby a.rb
> :foo

nice. i like the way you did that. thanks ara.

only question i have is about thread safety --could the instance var
pose a potential problem with that?

T.


Phrogz

11/14/2007 3:36:00 AM

0

On Nov 13, 1:36 pm, "ara.t.howard" <ara.t.how...@gmail.com> wrote:
> def ignoring_added_methods?
> defined? @ignoring_added_methods and @ignoring_added_methods
> end

What was your motivation for the above code instead of simply
def ignoring_added_methods?
@ignoring_added_methods
end



Chris Carter

11/14/2007 4:16:00 AM

0

On Nov 13, 2007 8:24 AM, Trans <transfire@gmail.com> wrote:
> This will, of course, print "foo" forever.
>
> As an aside, anyone else think method_added should also receive a
> block of the method definition? E.g. this would be a "push" (less the
> infinite loop issue):
>
> def self.method_added(name, &block)
> define_method(name, &block)
> end

I might be missing something, but I cannot think of a practical use
for that. It re-defined the method with the same name and
content....Why?

>
> Thanks!
> T.
>
>
>



--
Chris Carter
concentrationstudios.com
brynmawrcs.com

ara.t.howard

11/14/2007 5:44:00 AM

0


On Nov 13, 2007, at 8:40 PM, Phrogz wrote:

> On Nov 13, 1:36 pm, "ara.t.howard" <ara.t.how...@gmail.com> wrote:
>> def ignoring_added_methods?
>> defined? @ignoring_added_methods and @ignoring_added_methods
>> end
>
> What was your motivation for the above code instead of simply
> def ignoring_added_methods?
> @ignoring_added_methods
> end
>
>
>
>

cfp:~ > ruby -d -e ' def foo() defined? @foo and @foo end; foo() '


cfp:~ > ruby -d -e ' def foo() @foo end; foo() '
-e:1: warning: instance variable @foo not initialized


been trying to get the habit... it's tough! ;-)

cheers.

a @ http://codeforp...
--
share your knowledge. it's a way to achieve immortality.
h.h. the 14th dalai lama



ara.t.howard

11/14/2007 5:49:00 AM

0


On Nov 13, 2007, at 8:12 PM, Trans wrote:

> only question i have is about thread safety --could the instance var
> pose a potential problem with that?

probably. maybe (untested):

cfp:~ > cat a.rb
class X
class << self
def ignoring_added_methods
ignoring_added_methods = @ignoring_added_methods
@ignoring_added_methods = true
yield
ensure
@ignoring_added_methods = ignoring_added_methods
end

def ignoring_added_methods?
defined? @ignoring_added_methods and @ignoring_added_methods
end

def method_added name
Thread.critical = true
return if ignoring_added_methods?
ignoring_added_methods do
p name
define_method(:bar){}
end
ensure
Thread.critical = false
end
end

def foo
end
end

cheers.


a @ http://codeforp...
--
it is not enough to be compassionate. you must act.
h.h. the 14th dalai lama




Trans

11/14/2007 11:49:00 AM

0



On Nov 13, 11:16 pm, "Chris Carter" <cdcar...@gmail.com> wrote:
> On Nov 13, 2007 8:24 AM, Trans <transf...@gmail.com> wrote:
>
> > This will, of course, print "foo" forever.
>
> > As an aside, anyone else think method_added should also receive a
> > block of the method definition? E.g. this would be a "push" (less the
> > infinite loop issue):
>
> > def self.method_added(name, &block)
> > define_method(name, &block)
> > end
>
> I might be missing something, but I cannot think of a practical use
> for that. It re-defined the method with the same name and
> content....Why?

I'm impractical ? ;)

meta-programming. In this instance, I was working on a Traits idea. I
need to rename every method defined and keep track of it and replace
it with a method that weaves together these renamed methods.

T.