comments? storing a function in an object
Francesco Bochicchio
bieffe62 at gmail.com
Mon Jul 20 13:44:16 EDT 2009
On Jul 20, 6:22 pm, Esmail <ebo... at hotmail.com> wrote:
> Hello all,
>
> I am trying to store a function and some associated information in an
> object so that I can later have series of functions in a list that I can
> evaluate one at a time.
>
> Right now I am only storing the function itself, the number of
> arguments it expects and its string representation. I may add other
> information such as the acceptable range for the parameters or other
> characteristics such as maximum or minimum.
>
> I wonder if anyone could comment on my implementation and offer
> suggestions or constructive criticisms?
>
> The 'loading' of the functions is a bit tedious and of course care
> has to be taken to make sure the string representation corresponds to
> the actual function computed. It would be nice if there was an
> automatic way to convert the function to its string representation.
>
> Comments or problems with the approach I have taken?
>
> Thanks,
> Esmail
>
> --
>
> #!/usr/bin/env python
>
> #
> # store and represent functions
> #
>
> import math
>
> class FunctionException(Exception):
> """ custom exception """
> def __init__(self, value):
> self.parameter = value
>
> def __str__(self):
> return repr(self.parameter)
>
> class Function(object):
> """ class to represent a function """
>
> def __init__(self, fn, fn_str, num_vars):
> """
> the function, its string representation, and the number of variables
> """
> self.fn = fn
> self.fn_str = fn_str
> self.num_vars = num_vars
>
> def eval_fn(self, variables):
> """ size of variables should equal num_vars .. else problem """
> if len(variables) == self.num_vars:
> result = self.fn(*variables)
> return result
> else:
> raise FunctionException('invalid number of args provided - '+
> 'received %d, expected %d'
> %(len(variables), self.num_vars))
>
> def str(self):
> """ return string representation of function """
> return self.fn_str
>
> def funct1(x):
> ''' small test function '''
> return x * x
>
> def funct2(x, y):
> ''' small test function '''
> return x + y
>
> def funct3(x):
> ''' small test function '''
> return 1000 + (x*x + x) * math.cos(x)
>
> def main():
> """ main method """
> print 'in main'
>
> fn1 = Function(funct1, 'x * x', 1)
> fn2 = Function(funct2, 'x + y', 2)
> fn3 = Function(funct3, '1000 + (x*x + x) * cos(x)', 1)
>
> for i in range(-10, 10):
> try:
>
> print 'f(', [i],') =',
> print fn3.str(), ' => ',
> print fn3.eval_fn([i])
>
> except FunctionException, (ex):
> print ex.parameter
>
> if __name__ == '__main__':
> main()
I can offer some small suggestions: it is up to you to evaluate if
they make sense for your app:
1. use __doc__ function standard attribute for function description
(your fn_str); this meanst that
you do not need fm_str in the constructor and you have to do e.g. :
def funct2(x, y):
''' x + y '''
return x + y
then funct2.__doc__ becomes the string you want to associate to the
function
2. Use __call__ instead of eval_fn : this way, the instance of your
Function became a 'callable' and can be used
everywhere a function is needed. You can do:
f = Function(...)
f( some_args )
3. If you call a python function with wrong number of arguments, it
already raises a TypeError exception which contains
- with different wording - the same information of your
FunctionException : consider removing the check and using the
python error instead
HTH
Ciao
------
FB
More information about the Python-list
mailing list