Thursday, December 20, 2012

Python Metaprogramming: Dynamically Adding Methods to Classes

Dynamic addition of methods and attributes to classes and instances.

Dynamic Class Method Addition

Occasionally you may need dynamically add a function as a method to a class.  This is easily accomplished by assigning the function as an attribute of the class.

def fn(self):
  return id(self), self, type(self)

# Traditional Class Definition
class A_Class(object):
  def method_a(self):
    return id(self), self, type(self)

instance = A_Class()

# Modify the class and add fn as a method
setattr(A_Class, 'method_b', fn)

# Call the traditionally defined method
# Call the dynamically added method

Dynamic Instance Method Addition

When you add the method to a class all instances can access it.  If you only want a particular instance to have a method do this:

from types import MethodType

instance2 = A_Class()
setattr(instance, fn.__name__, MethodType(fn, instance, type(instance)))

# Calls the fn method attached to the instance

# Throws an exception