tan dificil es hacer o usar una clase en python?

Publicado por Daphnes Nohansen Hyrule
hace 10 años

<p>hola todos, ha pasado mucho tiempo desde que no use esta seccion, y eso es debido a que no he tenido tantas dudas programando en python.</p>

<p>pero resulta que en estos momentos estoy tratando de hacer un pequeño programa experimental con clases donde un soldado ataca mas o menos  a 2 o mas palos de guerra</p>

<p>por ahora el soldado como habilidad, tiene la capacidad de atacar, y otras 2 opciones no utiles para el soldado la verdad, pero lo que estoy tratando de hacer ahora es que cuando los palos</p>

<p>tengan 0 HP, se trate de o eliminar el objeto, o evitar de alguna forma que deje de aparecer su salud en la batalla, y por ahora el programa si hace eso, pero resulta que al otro palo creo, se le ve la el HP a 0,</p>

<p>y no supe que mas hacer la verdad, ojala pudieran ayudarme con ello y asi pudiera hacer grandes videojuegos con los experimentos ya hechos, he aqui el codigo fuente de todas formas:</p>

<pre class="prettyprint"> import os

class Milicia:

def __init__(self,hp = 60,atk = 3,df = 1):
    self.hp = hp
    self.atk = atk
    self.df = df

def atacar(self):
    palos[objetivo-1].hp -= self.atk
    print "el palo ha sufrido" ,self.atk, "de danio"

class Palodeguerra():

def __init__(self,hp = 100):
    self.hp = hp

def rendirse(self):
    print "me rindo &gt;&lt;"

def limpiar(): os.system("clear")

soldado = Milicia() palos = [Palodeguerra(),Palodeguerra()] palos[1].hp += 50 palos[0].hp -= 97 objetivo = 0 while True: for i in palos: objetivo += 1 print "salud de palo", objetivo,":",i.hp objetivo = 0 print "1: atacar" print "2: nada" print "3: salir" opcion = input() limpiar() if opcion == 1: for i in palos: objetivo += 1 print "palo:",objetivo objetivo = input() limpiar() soldado.atacar() objetivo = 0 elif opcion == 2: pass else: exit() for i in palos: objetivo = +1 if i.hp <= 0: i.rendirse() del palos[objetivo] objetivo = 0

batalla()</pre>

<p>igual seguire yo tambien buscando alguna solucion al problema, agradezco todas las respuestas posibles a mi problema.</p>

<p>saludos :D</p>

python videojuegos
Respuesta de Cristian Olaz
hace 10 años

<p>El problema está en estas líneas:</p>

<pre class="prettyprint"> for i in palos: objetivo = +1 if i.hp <= 0: i.rendirse() del palos[objetivo] objetivo = 0</pre>

<p>Lo que ocurre es lo siguiente. Cuando iniciás el ciclo <strong>for</strong> comenzás tomando el primer elemento el cual tiene el atributo "hp" en cero ( ya que decidiste "atacarlo" al comenzar el programa ). Pero lo que haces automáticamente al comenzar el ciclo for es asignarle el número 1 a la variable ojetivo.</p>

<pre class="prettyprint"> objetivo = +1</pre>

<p>El signo más puesto de esta forma, solo indicaría que es un número positivo. Supongo que tu intención no era poner eso. Pero lo que termina pasando es que en la primera ejecución del ciclo for, la variable "i" respresenta al <em><u><strong>primer</strong></u></em> "palo" ( el cual tiene hp igual a cero ) y la variable objetivo "apunta" al <em><u><strong>segundo</strong></u></em> elemento de la lista "palos", es decir, al elemento cuyo índice es uno.</p>

<p>Esto quiere decir que estas evaluando el primer elmento y eliminando el segundo.</p>

<pre class="prettyprint">

Aquí se apunta al SEGUNDO elemento

objetivo = +1

Aquí se está evaluando el PRIMER elemento!

if i.hp <= 0:

    # Y aquí se está borrando el SEGUNDO elemento
    del palos[objetivo]</pre>

<hr /><p>Entonces. Por empezar, desde los métodos no deberías acceder a variables que estén fuera de las clases, como haces en esta parte:</p>

<pre class="prettyprint"> class Milicia: def atacar(self):

    # Las variables "palos" y "objetivo" no existen dentro de la clase Milicia
    palos[ objetivo - 1 ].hp -= self.atk</pre>

<p>Esas variables deberías pasarlas como argumentos del método, o deberían ser parte de la clase.</p>

<pre class="prettyprint"> class Milicia: def atacar( self, palos, objetivo ): palos[ objetivo - 1 ].hp -= self.atk</pre>

<p>Y para poder terminar de solucionar tu problema, deberías renovar las variables que utilizas. La variable "objetivo" la usas a lo largo de muchas líneas de código, deberías utilizarla solo en pequeños fragmentos. Podés intentar aplicar esto en el código que tenés, o tratar de introducir más clases o funciones.</p>

<p>Un ejemplo con funciones podría ser el siguiente.</p>

<pre class="prettyprint"> def atacar():

aquí la variable "objetivo" se recrearía en cada llamada

objetivo = 0

if opcion == 1: atacar() elif opcion == 2: pass else: exit()</pre>

<p>De esta forma no "compartís" esa variable entre distintas estructuras de código.</p>

<p>Por último, para borrar los elementos de la lista que tengan el atributo hp igual a cero, podrías hacer lo siguiente:</p>

<pre class="prettyprint"> palos = [ palo for palo in palos if palo.hp != 0 ]</pre>

<p>Aunque en raelidad no deberías acceder a ese atributo ( hp ) sin utilizar un método ...</p>