
Sinnvolle Aufteilung in Klassen
Dann muss ich eben doch noch nachsitzen. (Sollte ja eigentlich nur ein kleine Skizze werden...)
yipyip
Code: Alles auswählen
def ask_attributes(attributes, max_points=100):
available = max_points
length = len(attributes)
attr_points = dict.fromkeys(attributes, 0)
for i, attr in enumerate(attributes):
while True:
try:
points = int(raw_input("Attribute %s (max=%d, %d. from %d) -> " %
(attr, available, i+1, length)))
if points < 0:
print "That's to little!"
continue
if available < points:
print "That's to much!"
else:
break
except ValueError:
print "Hu?"
attr_points[attr] = points
available -= points
if not available:
print 'No more points!'
break
return attr_points
my_attributes = ['Smartness', 'Stamina', 'Strength', 'Intelligence', 'Humor']
print ask_attributes(my_attributes)

yipyip
Wenn du schon dabei bist, dann möchtest du aus dem einen if ein elif machen und das überflüssige continue entfernen ^^yipyip hat geschrieben:Dann muss ich eben doch noch nachsitzen.
Das Leben ist wie ein Tennisball.
Danke euch allen, ich werd mir die Sachen mal anschaun und wer das mal versuchen auf mich anzupassen und ins Script einzubaun. Werde das Script dann wieder posten 
Den schliesslich habe ich auf seine Kritik hin mich mit der Schleife versucht.

Mich nimmt jedoch immer noch wunder wie das den Xynon1 gelöst hätteXynon1 hat geschrieben: 3. Wieso schreibst du die Abfragen doppelt und dreifach, nutze dafür doch einfach eine Schleife

Ich würde Datenmodell und Programmlogik besser trennen. Vielleicht so:
Stefan
Code: Alles auswählen
#!/opt/local/bin/python2.7
class Character:
def __init__(self):
self.name = "Anonymous"
self.strength = 0
self.agility = 0
self.stamina = 0
self.intelligence = 0
def compute_secondary_attributes(self):
self.health = self.stamina * 6 + 100
def points_spent(self):
return self.strength + self.agility + self.stamina + self.intelligence
def set(self, attribute, value):
if attribute == "str": self.strength = value
elif attribute == "agi": self.agility = value
elif attribute == "sta": self.stamina = value
elif attribute == "int": self.intelligence = value
else: raise ValueError
def __str__(self):
return "%s (strength=%d, agility=%d, stamina=%d, intelligence=%d)" % (
self.name, self.strength, self.agility, self.stamina, self.intelligence)
def create_character(points_to_spend):
ch = Character()
ch.name = raw_input('Name: ')
while True:
print "Now distribute %s skill points to attributes." % points_to_spend
print "You have %s points left." % (points_to_spend - ch.points_spent())
attribute = raw_input("Which attribute (str/agi/sta/int): ")
if not attribute:
return ch
try:
ch.set(attribute, int(raw_input("Value: ")))
except ValueError:
print "Invalid input. Please try again."
print create_character(25)
@sma: Ich finde ja die `set()`-Methode unschön. Man könnte die Attribute auch mit `setattr()` von aussen ändern. Wahrscheinlich hätte ich in der `__init__()` die Werte entgegen genommen und da ein vom Benutzer befülltes Dictionary mit ``**``-Syntax übergeben.
Mit class habe ich noch nicht so gearbeitet. Verstehe es auch noch nicht ganz. Aber danke für deine Idee, deinen Ansatz. Werde ich mir auch mal anschaun.sma hat geschrieben:Ich würde Datenmodell und Programmlogik besser trennen. Vielleicht so:StefanCode: Alles auswählen
#!/opt/local/bin/python2.7 class Character: def __init__(self): self.name = "Anonymous" self.strength = 0 self.agility = 0 self.stamina = 0 self.intelligence = 0 def compute_secondary_attributes(self): self.health = self.stamina * 6 + 100 def points_spent(self): return self.strength + self.agility + self.stamina + self.intelligence def set(self, attribute, value): if attribute == "str": self.strength = value elif attribute == "agi": self.agility = value elif attribute == "sta": self.stamina = value elif attribute == "int": self.intelligence = value else: raise ValueError def __str__(self): return "%s (strength=%d, agility=%d, stamina=%d, intelligence=%d)" % ( self.name, self.strength, self.agility, self.stamina, self.intelligence) def create_character(points_to_spend): ch = Character() ch.name = raw_input('Name: ') while True: print "Now distribute %s skill points to attributes." % points_to_spend print "You have %s points left." % (points_to_spend - ch.points_spent()) attribute = raw_input("Which attribute (str/agi/sta/int): ") if not attribute: return ch try: ch.set(attribute, int(raw_input("Value: "))) except ValueError: print "Invalid input. Please try again." print create_character(25)
Nach deinem gestrigen Ansatz hätte ich es etwa so gehabt, allerdings ist ein Character Objekt wesentlich schöner.heal.p hat geschrieben:Mich nimmt jedoch immer noch wunder wie das den Xynon1 gelöst hätteDen schliesslich habe ich auf seine Kritik hin mich mit der Schleife versucht.
Code: Alles auswählen
#!/usr/bin/env python
# -*- coding: cp1252 -*-
from collections import defaultdict
def set_skill(name, skillpoints):
print("\nDir stehen {0} Skillpunkte zur Verfügung.".format(skillpoints))
question = "Wieviele Punkte sollen in {0} investiert werden? ".format(name)
while True:
try:
points = int(raw_input(question))
if 0 <= points <= skillpoints:
return points
else:
print "Zuwenig Skillpunkte verfügbar."
except ValueError:
print "Deine Eingabe ist ungültig."
if __name__ == "__main__":
skillpoints = 25
alternate_name = "Namenloser"
attributes = defaultdict.fromkeys(["Stärke", "Beweglichkeit", "Ausdauer",
"Intelligenz"], 0)
name = raw_input("Welchen Namen soll der Charakter tragen? ")
if name == "":
name = alternate_name
print("Willkommen {0}, du kannst nun folgende Fertigkeiten trainieren:" \
"\n{1}".format(name, "\n".join(attributes)))
while skillpoints > 0:
for attribute_name in attributes:
points = set_skill(attribute_name, skillpoints)
attributes[attribute_name] += points
skillpoints -= points
if skillpoints == 0:
break
weapon = None
hp = 100 + (attributes["Ausdauer"] * 6)
Mhh. Was ich immernoch nicht ganz begriffen habe ist wasXynon1 hat geschrieben:Nach deinem gestrigen Ansatz hätte ich es etwa so gehabt, allerdings ist ein Character Objekt wesentlich schöner.heal.p hat geschrieben:Mich nimmt jedoch immer noch wunder wie das den Xynon1 gelöst hätteDen schliesslich habe ich auf seine Kritik hin mich mit der Schleife versucht.
Code: Alles auswählen
if __name__ == "__main__":

Jedoch versteh ich deinen Ansatz am besten. Die Vorschläge von sma und yipyip verwirren mich noch zusehr. Bin noch nicht so fortgeschritten in Python.

Prüft lediglich ob das Modul, naja nicht importiert wurde, also das aktuelle ist.
Also der Text darunter wird nur aufgerufen wenn du den Script direkt ausführst,
wenn du das Modul von wo anders importierst wird alles darunter ignoriert.
Also der Text darunter wird nur aufgerufen wenn du den Script direkt ausführst,
wenn du das Modul von wo anders importierst wird alles darunter ignoriert.
Zuletzt geändert von Xynon1 am Donnerstag 6. Januar 2011, 13:37, insgesamt 1-mal geändert.
@heal.p: `__name__` wird von Python an den Namen des Moduls gebunden, also der Dateiname ohne `.py` am Ende. Mit einer Ausnahme: Das Modul was man als Programm gestartet hat, bekommt den Namen '__main__' -- egal wie die Datei heisst. Wenn Du das Modul also als Programm startest, wird der ``if``-Zweig ausgeführt. Wenn man das Modul dagegen in einer Python-Shell oder einem anderen Modul importiert, dann wird der ``if``-Zweig nicht ausgeführt, weil `__name__` dann ja nicht '__main__' ist.
Und was habe ich davon für einen Nutzen? Das ich die Funktion nicht einfach so starten kann?Xynon1 hat geschrieben:Prüft lediglich ob das Modul, naja nicht importiert wurde, also das aktuelle ist.
Also der Text darunter wird nur aufgerufen wenn du den Script direkt ausführst,
wenn du das Modul von wo anders importierst wird alles darunter ignoriert.
Edit: Oke dank BlackJack wurde es mir noch klarer was es macht, jedoch ist mir immer noch nicht ganz klar, was es für einen Nutzen haben soll.
Würde soetwas Sinn machen?
Code: Alles auswählen
hp = 100 + (attributes["Ausdauer"] * 6)
stre = attributes["Stärke"]
agi = attributes["Beweglichkeit"]
stam = attributes["Ausdauer"]
intel = attributes["Intelligenz"]
Wenn du nicht mit Modulen arbeitest macht es für dich keinen Unterschied.heal.p hat geschrieben:Und was habe ich davon für einen Nutzen? Das ich die Funktion nicht einfach so starten kann?
Du könntest es auch so machen:
Code: Alles auswählen
...
attribute_names = ["Stärke", "Beweglichkeit", "Ausdauer", "Intelligenz"]
attributes = defaultdict.fromkeys(attribute_names, 0)
stre, agi, stam, intel = [attributes[name] for name in attribute_names]
...
Wie viele Attribute siehst du eigentlich vor ?
Ööhm, mit Modulen arbeiten wäre wohl besser? Sollte ich mich wohl mal drüber infomieren.Xynon1 hat geschrieben:Wenn du nicht mit Modulen arbeitest macht es für dich keinen Unterschied.heal.p hat geschrieben:Und was habe ich davon für einen Nutzen? Das ich die Funktion nicht einfach so starten kann?
Aber so würdest du eine doppelte Verwaltung der Attribute haben, also auch nicht schön, denn wenn du "stre" änderst, ändert sich nicht die Dictionary.
Wie viele Attribute siehst du eigentlich vor ?
Attribute sehe ich eigentlich bis jetzt folgende vor: Stärke, Beweglichkeit, Ausdauer, Intelligenz, Leben, Schaden und evt Abgewehrter Schaden.
Die Attribute Leben, Schaden und Abgewehrter Schaden sollen jenachdem wieviele Punkte ich auf Stärke, Beweglichkeit, Ausdauer und Intelligenz habe skalieren. Da ich jetzt mal ne Lösung habe und diese auch verstehe, versuche ich mich jetzt mal dran gegen einen Gegner zu kämpfen. Bzw die Funktionen Schaden zu machen zu schreiben usw.
Edit: Vll später noch Erfahrung und Level.
Wenn du diesen Ansatz wirklich weiter ausbauen willst solltest du noch etwas Zeit in OOP investieren.
Was brauchst du denn bei einem Kampf ?
1. Ein Charakter
2. Ein Gegner
Wie willst du einen Kampf berechnen ?
1. Anhand der Attribute
2. Etwas Zufall
Schlußfolgerung, dein Gegner braucht auch Attribute.
Willst du nun wirklich überall einzelne Dictionaries rumschwirren lassen mit Attibuten und hp, (max_hp), ...
Denk über eine Characterklasse nach, denn eine Instanz von dieser, kann sowohl dein Hero als auch jeder Gegner sein, damit sparst du dir viel Arbeit und man kann einen Überblick behalten.
Was brauchst du denn bei einem Kampf ?
1. Ein Charakter
2. Ein Gegner
Wie willst du einen Kampf berechnen ?
1. Anhand der Attribute
2. Etwas Zufall
Schlußfolgerung, dein Gegner braucht auch Attribute.
Willst du nun wirklich überall einzelne Dictionaries rumschwirren lassen mit Attibuten und hp, (max_hp), ...
Denk über eine Characterklasse nach, denn eine Instanz von dieser, kann sowohl dein Hero als auch jeder Gegner sein, damit sparst du dir viel Arbeit und man kann einen Überblick behalten.
Auch wenn man erst einmal mit nur einem Modul arbeitet, kann das ``if __name__ ...`` Sinn machen. Man kann das dann importieren, ohne dass es als Programm ausgeführt wird, und einzelne Funktionen testen, zum Beispiel um einen Fehler zu suchen. Automatisierte Tests sind auch möglich.
Mhh. Ich werd mich mal ins Thema einlesen und versuchen zum zusetzen. Ist der Code von sma OOP gerecht geschrieben, oder ist das nochmal was ganz anderes? Den seinen Code verstehe ich nur zum Teil.Xynon1 hat geschrieben:Wenn du diesen Ansatz wirklich weiter ausbauen willst solltest du noch etwas Zeit in OOP investieren.
Was brauchst du denn bei einem Kampf ?
1. Ein Charakter
2. Ein Gegner
Wie willst du einen Kampf berechnen ?
1. Anhand der Attribute
2. Etwas Zufall
Schlußfolgerung, dein Gegner braucht auch Attribute.
Willst du nun wirklich überall einzelne Dictionaries rumschwirren lassen mit Attibuten und hp, (max_hp), ...
Denk über eine Characterklasse nach, denn eine Instanz von dieser, kann sowohl dein Hero als auch jeder Gegner sein, damit sparst du dir viel Arbeit und man kann einen Überblick behalten.
Hast du eventuell noch eine gute Seite wo mir erklärt wird wie ich das mit den Klassen aufbaun muss, bzw richtig verwende?
Ein gutes Tutorial ist immer das offizielle http://docs.python.org/tutorial/classes ... ss-objects
Ansonsten würde ich noch dringend vom Python GalileoComputing Openbook abraten.
Ansonsten würde ich noch dringend vom Python GalileoComputing Openbook abraten.
Das offizielle gabs doch auch auf Deutsch? Denke das würde mir beim Verstehen leichterfallen.Xynon1 hat geschrieben:Ein gutes Tutorial ist immer das offizielle http://docs.python.org/tutorial/classes ... ss-objects
Ansonsten würde ich noch dringend vom Python GalileoComputing Openbook abraten.
Was ist den beim GalileoComputing Openbook nicht gut?