Dynamically adding a runtime generated method to a class.

Joe Goldthwaite joe at goldthwaites.com
Thu Nov 29 17:31:43 EST 2007


I'm not sure how to even ask this question.  I'm working on a financial
reporting application.  The current system is very limited in what it can
display.  You can see reports with columns of Period, Quarter, Year to date
or you can see a yearly trend.  I'd like for the users to be able to define
the columns on the fly but I'm not sure how to do it in Python in the
cleanest most efficient manner.

The easy way would be to keep a list of class methods like this;
    #My first attempt
    class lineClass1:

        def __init__(self, desc, trend):

            self.desc = desc
            self.trend = trend

        def Ptd(self, per):
            return self.trend[per]

        def Ytd(self, per):
            return sum(self.trend[:per])

        def getLine(self, cols, per):

            # return the descriptionin the first column
            vals = [self.desc]
            for col in cols:
                vals.append(col(self, per))
            return vals

    # create the instance
    line1 = lineClass1('Some Description', [1,2,3,4,5,6,7,8,9,10,11,12])

    # Now I can get the columns out in the order I want by passing in a list
of methods
    cols = [lineClass1.Ptd, lineClass1.Ytd]
    print line1.getLine(cols, 5)

This would work and not be too terribly inefficient but I was thinking it
would be much better generate the getLine method at runtime and dynamically
add it to the class so I wouldn't have to pass the columns around and loop
through them every time;

    #Define the class with just the trend
    class lineClass2:

        def __init__(self, desc, trend):

            self.desc = desc
            self.trend = trend

        def Ptd(self, per):

            return self.trend[per]

        def Ytd(self, per):

            return sum(self.trend[:per])

        #
****************************************************************************
************
        # Here, I want to dyamically add a class method that has the return
line below defined at runtime
        #
        def getLine(self, per):
            return [self.desc, self.Ptd(per), self.Ytd(per)]

    # create a couple of instances
    line = lineClass('Some Description', [1,2,3,4,5,6,7,8,9,10,11,12])

    # try it out.
    print line.getLine(5)

Is there any way to dynamically generate the getLine function at runtime?
Can the eval statement do that?






More information about the Python-list mailing list