Adding method to object

  • Thread starter Thomas Guettler
  • Start date
T

Thomas Guettler

Hi!

How can I add a method to an object.
This code does not work:

class Foo:
def __init__(self):
self.counter=0

f=Foo()

def incr(self):
self.counter+=1

f.incr=incr

f.incr()

===> python extend.py
Traceback (most recent call last):
File "extend.py", line 12, in ?
f.incr()
TypeError: incr() takes exactly 1 argument (0 given)
 
G

Gonçalo Rodrigues

Hi!

How can I add a method to an object.
This code does not work:

class Foo:
def __init__(self):
self.counter=0

f=Foo()

def incr(self):
self.counter+=1

f.incr=incr

f.incr()

===> python extend.py
Traceback (most recent call last):
File "extend.py", line 12, in ?
f.incr()
TypeError: incr() takes exactly 1 argument (0 given)

You have to call it like

f.incr(f)

If you want to leave out the f as arg (call it like an instance
method) then
Help on class instancemethod in module __builtin__:

class instancemethod(object)
| instancemethod(function, instance, class)
|
| Create an instance method object.
|
....

And

new.instancemethod(incr, f, f.__class__)

Should do the trick.

With my best regards,
G. Rodrigues
 
P

Peter Otten

Thomas said:
How can I add a method to an object.

self is not passed automatically, if you call an instance attribute.
You can provide a default value instead:
.... def __init__(self):
.... self.counter = 0
........ self.counter += 1
....
If you have more than one instance with the same incr() method, you can wrap
it into a lambda:
2

Peter
 
M

marco

Is it possible to do the same thing for an attribut, instead of a method ?

i'd like to wrap an newAttribute to an oldAttribute one :
example:
i've got an instance "n" of an "xmlNode" class
i'd like to use "n.parentNode" instead of "n.parent" ...
 
S

Sean Ross

marco said:
Is it possible to do the same thing for an attribut, instead of a method ?

i'd like to wrap an newAttribute to an oldAttribute one :
example:
i've got an instance "n" of an "xmlNode" class
i'd like to use "n.parentNode" instead of "n.parent" ...
[snip]

# try this ...
n.parentNode = n.parent

HTH
Sean
 
M

marco

Is it possible to do the same thing for an attribut, instead of a method
?
i'd like to wrap an newAttribute to an oldAttribute one :
example:
i've got an instance "n" of an "xmlNode" class
i'd like to use "n.parentNode" instead of "n.parent" ...
[snip]

# try this ...
n.parentNode = n.parent

i'll try,
but ... it s not dynamic ....

if n.parent change .... n.parentNode will not change ... it must be
re-affected ... not ?
 
S

Sean Ross

marco said:
method
?
i'd like to wrap an newAttribute to an oldAttribute one :
example:
i've got an instance "n" of an "xmlNode" class
i'd like to use "n.parentNode" instead of "n.parent" ...
[snip]

# try this ...
n.parentNode = n.parent

i'll try,
but ... it s not dynamic ....

if n.parent change .... n.parentNode will not change ... it must be
re-affected ... not ?

You're right. Sorry about that. Maybe you could use a property?

n.__class__.parentNode = property(lambda self: self.parent, ... etc ... )

This way you can get/set/del n.parent using n.parentNode, and changes
to n.parent will be reflect in n.parentNode.

There's probably another way, but I can't think of it at the moment...

Hope that's a little more helpful than the last suggestion,
Sean
 
M

marco

Sean said:
Is it possible to do the same thing for an attribut, instead of a
method
?

i'd like to wrap an newAttribute to an oldAttribute one :
example:
i've got an instance "n" of an "xmlNode" class
i'd like to use "n.parentNode" instead of "n.parent" ...

[snip]

# try this ...
n.parentNode = n.parent

i'll try,
but ... it s not dynamic ....

if n.parent change .... n.parentNode will not change ... it must be
re-affected ... not ?


You're right. Sorry about that. Maybe you could use a property?

n.__class__.parentNode = property(lambda self: self.parent, ... etc ... )

This way you can get/set/del n.parent using n.parentNode, and changes
to n.parent will be reflect in n.parentNode.

There's probably another way, but I can't think of it at the moment...

Hope that's a little more helpful than the last suggestion,
Sean

perfect ! it works like a charm
thanx a lot !
 
D

Dave Benjamin

If you want to leave out the f as arg (call it like an instance
method) then

Help on class instancemethod in module __builtin__:

class instancemethod(object)
| instancemethod(function, instance, class)
|
| Create an instance method object.
|
...

And

new.instancemethod(incr, f, f.__class__)

Should do the trick.

I tried to bring this up several weeks ago but nobody replied, so I'm
bringing it up again. I still see people recommending "new.instancemethod",
yet "help(new)" says that the "new" module is deprecated. The seemingly
identical "types.MethodType" ought to be its replacement, even though I
think "new.instancemethod" is more clear. If you stringify types.MethodType,
it says "<type 'instancemethod'>". The help for instancemethod, above, says
that instancemethod is in the __builtin__ module, but it is neither a
builtin nor available in the __builtin__ module. This is confusing. Can we
decide on a community standard for the appropriate way to create new
instance methods, and resolve the documentation discrepancies?

Thankya kindly,
Dave
 
A

Aahz

How can I add a method to an object.
This code does not work:

class Foo:
def __init__(self):
self.counter=0

f=Foo()

def incr(self):
self.counter+=1

f.incr=incr
f.incr()

Try ``Foo.incr=incr``
 

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
474,172
Messages
2,570,933
Members
47,473
Latest member
ChristelPe

Latest Threads

Top