Home > Software design >  Calling class function saved as attribute
Calling class function saved as attribute

Time:10-31

I have two classes, and a "use" class function that preforms multiple actions using the various attributes as the inputs so that i can just call the one function and get different results based on which class object is referenced. Where I am getting stuck is that I want to have part of the use function check the 'effect' attribute and call the function found there. currently, function named in effect is called when the object c is defined, and everything i have tried within the use function has no effect or returns 'none' since i dont have a return statement in the add and sub functions. Provided simplified example code below. C has 9 attributes, and 10 different class functions i would want to use in the effect spot.I plan on having 50 different c objects, so not having to write out specific functions for each one would be spectacular.

in this example, the print(p.h) at the end returns 101, showing that designing the c object calls the add function i put in the attribute

M= []
class P:
    def __init__(p, h, s):
        p.h= h
        p.s=s
class C:
    def __init__(y, name, d, f effect,):
        y.name= name
        y.effect= effect
        y.d= d
        y.f= f
    
    def use(c):
        M.append(c)
        p.h -= p. y.d
        p.s  = y.f
        effect
    def add(c, x):
        p.h  = x
    def sub(c, x):
        p.h -=x
p= P(100)   
c= C('test1', add(1), 1)
print(p.h)

I have tried the add and sub functions as both class and standalone which didnt seem to make a different, calling y.effect as though it were a function which just returns 'none' as mentioned, and adding the property decorator which threw an error probably because i dont quite understand what that is supposed to do yet.

CodePudding user response:

When accessing methods of classes C and P, you will only be able to access them from the class namespace. C.add will work, but add will not.

Furthermore if you call c.add(4) it will be the same thing as calling C.add(c, 4) because it will implicitly pass the instance c into the class (C) method C.add. You cannot call add(1) or c.add(1) before your instance c is initialized by the __init__ method.

Typically when writing python, it is most clear to always name the first argument to your class method self to make it clear that self refers to the instance and that it will automatically get passed into the function.

Furthermore, because you do not instantiate p until after you define your class C, you won't be able to access p from inside your C class unless you pass p into the function or save it as an attribute of c.

Not totally sure what you are going for here but I made some modifications which might help.

#!/usr/bin/env python
M = []


class P:
    def __init__(self, h, s):
        # self refers to your instance of p
        self.h = h
        self.s = s


class C:
    def __init__(self, name, p, d, f, effect):
        # self refers to your instance of c
        self.p = p  # save an instance of p as an attribute of your instance of c
        self.name = name
        self.effect = effect
        self.d = d
        self.f = f

    def use(self):
        M.append(self)
        self.p.h -= self.d
        self.p.s  = self.f
        return self.effect

    def add(self, x):
        # self refers to your instance of c and gets implicitly passed in as the first argument
        # when c.add(2) is called
        self.p.h  = x

    def sub(self, x):
        self.p.h -= x


p = P(100, 50)
c = C('test1', p, d=2, f=1, effect="a")
c.add(1)
print(p.h)
<script src="https://modularizer.github.io/pyprez/pyprez.min.js"></script>

CodePudding user response:

This code isn't runnable as-is, so there may be other problems with your real code that aren't possible to discern from this example, but when you say:

function named in effect is called when the object c is defined

that's happening not because of what's inside your C class, but the line where you construct your C:

c= C('test1', add(1), 1)

The expression add(1) isn't passing the add function, it's calling the add function and passing its result. To pass a function as an argument, just pass the function itself without the ():

c = C('test1', add, 1)

Note that in the code you provided there is no function called add in the current scope, and your C.use does not call effect, which is a different problem.

  • Related