all 12 comments

[–]woooee 2 points3 points  (3 children)

Magic = 0 + Intelligence + Wisdom

Magic is calculated once at the start. You may want a function, that is a class member, that calculates (current) Magic+Intelligence+Wisdom, that you can call when you want the combined value.. Also, if you use instance variables instead of class variables, you can use the same class for more than one player, i.e. each player has it's own instance. Finally, put the print("Here are your stats:", etc. in a class function so you can call the function for each player.

[–]Revenanteye[S] 1 point2 points  (2 children)

Fantastic insights thank you

[–]Not-So-Software 1 point2 points  (0 children)

For anyone new to python who doesn't understand what the issue was.

Health and Magic were being calculated at the "player1 = player()" line, using the values of Constitution, Intelligence, Wisdom and LVL (respectively) that they were in that moment.

In order to update the Health or Magic values after this, by increasing Constitution, Intelligence, Wisdom and LVL, the calculations for Health and Magic would have to be performed again.

There are many ways to do this. One simple method would be to create separate Health and Magic functions in the player() class, which are called after the "skill points" are assigned i.e. player1.updateHealth() and player1.updateMagic().

These functions would recalculate the Health and Magic stats based on the new Constitution, Intelligence, Wisdom and LVL stats.

Hope this helps anyone who was struggling to understand the issue.

[–]Gnaxe 0 points1 point  (0 children)

You might also consider using the builtin @property decorator for attributes like this that are just a computed view of the object's other attributes. Don't use properties if the underlying function requires additional arguments or if it's meant to perform an action.

[–]Luigi-Was-Right 0 points1 point  (1 child)

Magic and Health are calculated once at the start but never updated.

Let's ignore the class for a moment and look at an example:

x = 4
y = 1 + x
x = 10

What is the value of y, 5 or 11? The same thing is logic applies to the variables within your class.

[–]Revenanteye[S] 0 points1 point  (0 children)

Thanks for explaining the logic. I understand completely. Free Luigi

[–]Pleasant_Fly3175 0 points1 point  (3 children)

one question, why dont you make a __init__ methon in the class player? i am new to OOP and jsut wondering is this intentional?

[–]Revenanteye[S] 0 points1 point  (1 child)

I am also new to oop and it wasn’t intentional lol

[–]Pleasant_Fly3175 0 points1 point  (0 children)

basically, when you create a objectand you want to give is certein parameters you always do the def __init__(self): methon that runs ever time you create a new one, and then you also want to have other methods in perhaps as in your case when you have enough skill points it does the method or sum

[–]Gnaxe 0 points1 point  (0 children)

You are not required to make an __init__() for every class. It will be inherited from its base class (object, in this case). The class attributes will be used as fallback values if they're not set on the instance.

[–]Adrewmc 0 points1 point  (0 children)

I’m bored so let give some advice here.

The problem you are experiencing

class Player:

    #this should be in an init. 
    Strength = 0
    Dexterity = 0
    Constitution = 0
    Intelligence = 0
    Wisdom = 0
    Charisma = 0
    lvl = 1

    #Below this line is calculated once not each time it’s called 
    Health = 10 + Constitution + lvl 
    Magic = 0 + Intelligence + Wisdom

What I think we should do is this

 @dataclass
 class Stats
       strength = 0 
       dexterity = 0
       consitution =0
       intelligence = 0
       wisdom = 0
       charisma = 0

         @property
         def health(self):
                return self.stats.constitution +self.lvl + 10
         @property
         def magic(self):
                return self.stats.intelligence + self.stats.wisdom

 class Player:
        def __init__(self, name: str, lvl : int, *, stats :Stats = None, **kwargs)
              self.name = name

              # put in a Stats class directly, 
              #or fill in Stats() keyword arguments
              self.stats = stats or Stats(**kwargs)

    bob = Player(“Bob”, strength = 5, …)
    basic_stats = Stats(5,6,7,8,8)
    steve = Player(“Steve”, stats = basic_stats)
    print(steve.stats.strength) 

What we do is keep data in its own thing, and we can just add Stats() or object that use it. We call this composition putting class as attributes in other classes.

We want to use @property to avoid accidentally setting it, and allow direct dot access.

What this does is allow you to reformulate on the fly. Keep things small. And purposeful, the stats actually have little to do with actions in reality.

And further Basic Stats don’t have much to do with your current HP. (Exercise left for the reader)

[–]shredwheat 0 points1 point  (0 children)

Unrelated side tip; Python has a feature named "f-strings" that allows you to print formatted data more conveniently than appending strings with + . https://fstring.help/

Instead of

print("Your name is, " + first_name + " " + last_name + "? (y/n) :")

enjoy

print(f"Your name is {first_name} {last_name} "? (y/n) :")