def get_Interseccion_De_Pilas(obj_Pila_1, Obj_Pila_2): elemento = None obj_aux_Pila = Pila() obj_aux_Pila_2 = Pila() obj_Interseccion_Pila = Pila() while (not obj_Pila_1.pila_vacia()): while (not Obj_Pila_2.pila_vacia()): elemento = Obj_Pila_2.desapilar() obj_aux_Pila_2.apilar(elemento) if (elemento == obj_Pila_1.elemento_cima()): obj_Interseccion_Pila.apilar(elemento) obj_aux_Pila.apilar(obj_Pila_1.desapilar()) #Devuelvo elementos a la pila 2 para devolverla a como estaba while (not obj_aux_Pila_2.pila_vacia()): Obj_Pila_2.apilar(obj_aux_Pila_2.desapilar()) #Devuelvo elementos a la pila 1 para devolverla a como estaba while (not obj_aux_Pila.pila_vacia()): obj_Pila_1.apilar(obj_aux_Pila.desapilar()) return obj_Interseccion_Pila
def sumar_pilas(pila1, pila2): """ DOC: Completar """ pila1_invertida = Pila() pila2_invertida = Pila() pila_final = Pila() while not pila1.esta_vacia() or not pila2.esta_vacia(): n1 = pila1.desapilar() if not pila1.esta_vacia() else 0 n2 = pila2.desapilar() if not pila2.esta_vacia() else 0 pila1_invertida.apilar(n1) if not n1 == 0 else None pila2_invertida.apilar(n2) if not n2 == 0 else None while not pila1_invertida.esta_vacia or not pila2_invertida.esta_vacia(): numero_anterior = pila_final.desapilar( ) if not pila_final.esta_vacia() else 0 n1 = pila1_invertida.desapilar( ) if not pila1_invertida.esta_vacia() else 0 n2 = pila2_invertida.desapilar( ) if not pila2_invertida.esta_vacia() else 0 print(n1, n2) suma = n1 + n2 suma += numero_anterior proximo_numero = suma // 10 suma = suma % 10 pila_final.apilar(suma) pila_final.apilar(proximo_numero) if not proximo_numero == 0 else None return pila_final
def analizar_secuencia(instrucciones, codificaciones): """ Recibe un string con instrucciones y un diccionario que contiene la codificación para algunas instrucciones variables. Devuelve un set de trazos correspondientes al análisis del string, la distancia máxima y la distancia mínima con la que ha de crearse el svg. """ coordenada_min = Vector() coordenada_max = Vector() pila_de_tortugas = Pila() pila_de_tortugas.apilar(Tortuga()) tortuga_tope = pila_de_tortugas.ver_tope() profundidad = len(pila_de_tortugas) trazos = set() for c in instrucciones: if c == "[": nueva_tortuga = tortuga_tope.clonar() pila_de_tortugas.apilar(nueva_tortuga) tortuga_tope = pila_de_tortugas.ver_tope() profundidad = len(pila_de_tortugas) elif c == "]": pila_de_tortugas.desapilar() tortuga_tope = pila_de_tortugas.ver_tope() profundidad = len(pila_de_tortugas) elif c == "F": ultima_posicion = tortuga_tope.conseguir_posicion() tortuga_tope.avanzar(DISTANCIA_BASE * (FACTOR_EXPANSION**profundidad)) nueva_posicion = tortuga_tope.conseguir_posicion() coordenada_min = calcular_min(coordenada_min, nueva_posicion) coordenada_max = calcular_max(coordenada_max, nueva_posicion) nuevo_trazo = Trazo(ultima_posicion, nueva_posicion, tortuga_tope.conseguir_grosor(), tortuga_tope.conseguir_color()) trazos.add(nuevo_trazo) elif c == "f": tortuga_tope.levantar_pluma() tortuga_tope.avanzar(DISTANCIA_BASE * (FACTOR_EXPANSION**profundidad)) tortuga_tope.bajar_pluma() elif c in "+-|": tortuga_tope.girar(codificaciones[c]) elif c in COLORS: tortuga_tope.cambiar_color_pluma(COLORS[c]) elif c in "0123456789": print(c) tortuga_tope.cambiar_grosor_pluma(c) return trazos, coordenada_min + Vector(-50, -50), coordenada_max + Vector( 50, 50)
def calculadora_polaca(elementos): """ Dada una lista de elementos que representan las componentes de una expresion en notacion polaca inversa, evalua dicha expresion. Si la expresion esta mal formada, levanta ValueError """ p = Pila() for elemento in elementos: print(f"\nDEBUG: entra {elemento}") # Intenta convertirlo a numero try: numero = float(elemento) p.apilar(numero) print(f"DEBUG: apila {numero}") # si no se puede convertir, deberia ser un operando except ValueError: if elemento not in ('+', '-', '/', '*'): raise ValueError("Operando inválido") # Si es un operando válido, intenta desapilar y operar try: a1 = p.desapilar() print(f"\nDEBUG: desapila {a1}") a2 = p.desapilar() print(f"\nDEBUG: desapila {a2}") except IndexError: raise ValueError("Faltan operandos..") if elemento == "+": resultado = a2 + a1 if elemento == "-": resultado = a2 - a1 if elemento == "/": resultado = a2 / a1 if elemento == "*": resultado = a2 * a1 print(f"\nDEBUG: apila {resultado}") p.apilar(resultado) # Al final el resultado debe ser lo unico en la pila resultado = p.desapilar() if not p.esta_vacia(): raise ValueError("Sobran operandos") return resultado
def es_Palindromo(palabra_pila): pila_Inversa = Pila() pila_Inversa = invertir_Pila_Sin_Perder_Elementos(palabra_pila) while ((not palabra_pila.pila_vacia()) and (palabra_pila.elemento_cima() == pila_Inversa.elemento_cima())): palabra_pila.desapilar() pila_Inversa.desapilar() if (palabra_pila.pila_vacia()): return True else: return False
def insertar_El_Numero_Menor_al_Mayor_En_Pila(obj_Pila_A_Insertar_Numero, numero): obj_Numeros_Mayores_Pila = Pila() #Si se ingresa mas de 1 numero entro aqui if (not obj_Pila_A_Insertar_Numero.pila_vacia()): #Si es mayor lo inserto de una if (numero >= obj_Pila_A_Insertar_Numero.elemento_cima()): obj_Pila_A_Insertar_Numero.apilar(numero) else: # Evaluo todos los menores al numero incluyendo los iguales y los apilo # En la pila auxiliar obj_Numeros_Mayores_Pila # Despues cuando se rompa el bucle doy por hecho que llego a que # Numero es mayor al elemento de la cima o que no encontro ninguno while ((not obj_Pila_A_Insertar_Numero.pila_vacia()) and (numero < obj_Pila_A_Insertar_Numero.elemento_cima())): elemento = obj_Pila_A_Insertar_Numero.desapilar() obj_Numeros_Mayores_Pila.apilar(elemento) obj_Pila_A_Insertar_Numero.apilar(numero) #Coloco todos los numeros que eran mayores al numero ingresado while (not obj_Numeros_Mayores_Pila.pila_vacia()): obj_Pila_A_Insertar_Numero.apilar( obj_Numeros_Mayores_Pila.desapilar()) else: #Si no hay nada le inserto el primer numero esto para cuando se hace el primer bucle obj_Pila_A_Insertar_Numero.apilar(numero)
def ejercicio_16(): obj_Pila = Pila() obj_Pila2 = Pila() obj_Interseccion_Pila = Pila() personajes_Star_Wars_EP_V = [ 'Luke Skywalker', 'Han Solo', 'Darth Vader', 'Leia Organa', 'Yoda', 'Capitán Needan', 'Almirante Ozzel', 'Lando Calrissian' ] personajes_Star_Wars_EP_VII = [ 'Kylo Ren', 'Rey', 'Han Solo', 'Luke Skywalker', 'C3PO', 'Leia Organa', 'Chewbacca', ' Poe Dameron' ] for i in range(0, len(personajes_Star_Wars_EP_V)): obj_Pila.apilar(personajes_Star_Wars_EP_V[i]) for i in range(0, len(personajes_Star_Wars_EP_VII)): obj_Pila2.apilar(personajes_Star_Wars_EP_VII[i]) obj_Interseccion_Pila = get_Interseccion_De_Pilas(obj_Pila, obj_Pila2) while (not obj_Interseccion_Pila.pila_vacia()): print('El personaje ', obj_Interseccion_Pila.desapilar(), ' esta en ambas peliculas')
def main(): # Inicializar el estado del juego niveles = archivos.cargar_niveles('niveles.txt') acciones = archivos.cargar_accion_de_tecla('teclas.txt') estados = Pila() pistas = None grilla, nivel = juego_inicializar(niveles) x, y = soko.dimensiones(grilla) gamelib.resize(x * PIXELES_GIF, y * PIXELES_GIF) while gamelib.is_alive(): gamelib.draw_begin() mostrar_interfaz(grilla) if pistas != None: gamelib.draw_text('Pista encontrada', PIXELES_GIF, PIXELES_GIF // 2, size=12, fill='#00FF00') gamelib.draw_end() ev = gamelib.wait(gamelib.EventType.KeyPress) if not ev: break tecla = ev.key accion = procesar_tecla_presionada(tecla, acciones) grilla, estados, pistas = juego_actualizar(grilla, nivel, niveles, accion, estados, pistas) if not grilla: break if soko.juego_ganado(grilla): while not estados.esta_vacia(): estados.desapilar() pistas = None nivel, grilla = juego_pasar_nivel(nivel, niveles) if not grilla: break
def ejercicio_2(): obj_Pila = Pila() for i in range(0, 100): num = randint(1, 10) obj_Pila.apilar(num) obj_Pila = sacar_Impares_De_Pila(obj_Pila) for i in range(0, obj_Pila.tamanio()): print(obj_Pila.desapilar())
def calculadora_polaca(elementos): """Dada una lista de elementos que representan componentes de una expresion en notacion polaca inversa, evalua dicha expresion. Si la expresion esta mal formada, levanta ValueError""" p = Pila() for elemento in elementos: print("DEBUG:", elemento) try: numero = float(elemento) p.apilar(numero) print("DEBUG: apila ", numero) except ValueError: if elemento not in "+-*/ %" or len(elemento) != 1: raise ValueError("Operador Invalido") try: a1 = p.desapilar() print("DEBUG: desapila ", a1) a2 = p.desapilar() print("DEBUG: desapila ", a2) except ValueError: print("DEBUG: error pila faltan openandos") raise ValueError("Faltan openrandos") if elemento == '+': resultado = a2 + a1 elif elemento == '-': resultado = a2 - a1 elif elemento == '*': resultado = a2 * a1 elif elemento == '/': resultado = a2 / a1 elif elemento == '%': resultado = a2 % a1 print("DEBUG: apila ", resultado) p.apilar(resultado) res = p.desapilar() if p.es_vacia(): return res else: print("DEBUG: error pila sobran openrandos") raise ValueError("Sobran operandos") print(elementos)
def _min_seguimientos(grafo, origen, destino): distancia, padre = biblioteca.camino_minimo_bfs(grafo, origen, destino) if destino not in distancia: return None p = Pila() aux = destino while aux != origen: p.apilar(aux) aux = padre[aux] p.apilar(origen) camino = [] while not p.esta_vacia(): camino.append(p.desapilar()) return camino
def main(): niveles = cargar_niveles() nivel = 1 teclas = cargar_teclas() juego = setear_juego(niveles, nivel) movimientos = Pila() soluciones = Pila() mensaje = "" while gamelib.is_alive(): gamelib.draw_begin() dibujar(juego) gamelib.draw_end() gamelib.draw_text(mensaje,15,15,anchor="w") ev = gamelib.wait(gamelib.EventType.KeyPress) if not ev: break tecla = ev.key if tecla in teclas: if teclas[tecla] == "REINICIAR": juego = reiniciar(juego, niveles, nivel, soluciones) elif teclas[tecla] == "SALIR": break elif teclas[tecla] == "DESHACER": if movimientos.tope: juego = deshacer(movimientos, juego) elif teclas[tecla] == "AYUDA": if soluciones.esta_vacia(): gamelib.draw_text("Pensando...", 15, 15, anchor="w") gamelib.get_events() #Utilizo .get_events() como una especie de mutex para evitar que el usuario interactúe solucion_encontrada, soluciones = solver.buscar_solucion(juego, DIRECCIONES) gamelib.get_events() if solucion_encontrada: mensaje = "Hay pista disponible" else: mensaje = "No hay chance" else: movimientos.apilar(juego) juego = soko.mover(juego, soluciones.desapilar()) else: movimientos.apilar(juego) juego = soko.mover(juego, DIRECCIONES[teclas[tecla]]) if tecla and not teclas[tecla] == "AYUDA": soluciones = Pila() mensaje = "" if soko.juego_ganado(juego): nivel = nivel + 1 juego = setear_juego(niveles, nivel) movimientos = Pila()
def analisis(lista): for x in lista: for ch in x: if (not verDiccionario(diccionario, ch)): error.append("Error caracter no válido " + ch) if (not (len(error) > 0)): pila = Pila() for x in lista: if (not (len(error) > 0)): analisisSintactico(x) for ch in x: if (not (len(error) > 0)): pila.apilar(ch) if (ch == "="): pila.desapilar() elif ((ch.isalpha) and (not (ch.isdigit())) and (not (esOperador(diccionario, ch)))): if (ch == x[len(x) - 2]): pila.desapilar() if (len(pila.items) > 1): error.append("Error no hay operador") else: variables[ch] = pila.desapilar() else: if (estaAsignada(ch)): pila.desapilar() pila.apilar(variables[ch]) else: error.append( "Error variable inexistente " + ch) elif ((len(pila.items) > 2) and (esOperador(diccionario, ch))): signo = pila.desapilar() num2 = pila.desapilar() num1 = pila.desapilar() pila.apilar(resolver(num1, num2, signo)) else: print(error) else: print(error) print(variables) else: print(error)
def get_Total_Personas_Capturadas(obj_Pila): obj_Aux_Pila = Pila() contador = 0 while (not obj_Pila.pila_vacia()): obj_Aux_Pila.apilar(obj_Pila.desapilar()) if (obj_Aux_Pila.elemento_cima()[2] != 'Fallo'): contador += 1 while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return contador
def get_Dinero_Total(obj_Pila): obj_Aux_Pila = Pila() Vector = None total = 0.0 while (not obj_Pila.pila_vacia()): Vector = obj_Pila.desapilar() obj_Aux_Pila.apilar(Vector) total += Vector[1] while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return total
def construirArbol(self, posfijo): posfijo.pop() variable = posfijo.pop() pilaOperador = Pila() for caracter in posfijo: if (caracter == '+' or caracter == '-' or caracter == '*' or caracter == '/'): arbol = Nodo(caracter) arbol.der = pilaOperador.desapilar() arbol.izq = pilaOperador.desapilar() pilaOperador.apilar(arbol) else: arbol = Nodo(caracter) pilaOperador.apilar(arbol) self.evaluarSintaxis(arbol) arbol = pilaOperador.desapilar() self.addDiccionario(variable, self.evaluar(arbol)) arbol1 = Nodo("=") arbol1.izq = arbol arbol1.der = Nodo(variable) self.evaluarSintaxis(arbol1.der) self.evaluarSintaxis(arbol1) return self.evaluar(arbol)
def invertir_Pila_Sin_Perder_Elementos(pila_a_invertir): pila_Inversa = Pila() aux_Pila = Pila() #me da la pila invertida while (not pila_a_invertir.pila_vacia()): elemento = pila_a_invertir.desapilar() pila_Inversa.apilar(elemento) aux_Pila.apilar(elemento) #le devuelvo los elementos que desapile a la pila original while (not aux_Pila.pila_vacia()): pila_a_invertir.apilar(aux_Pila.desapilar()) return pila_Inversa
def get_Numero_Mision_Boba_Capturo_A_Han(obj_Pila): obj_Aux_Pila = Pila() Vector = None Mision = 1 while ((not obj_Pila.pila_vacia()) and (obj_Pila.elemento_cima()[2] != 'Han Solo')): Mision += 1 Vector = obj_Pila.desapilar() obj_Aux_Pila.apilar(Vector) while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return Mision
def get_Cantidad_Peliculas_En_La_Que_Aparece_Black_Widow(obj_Pila): obj_Aux_Pila = Pila() cant_peliculas = 0 while ((not obj_Pila.pila_vacia()) and (obj_Pila.elemento_cima()[0] != 'Black Widow')): obj_Aux_Pila.apilar(obj_Pila.desapilar()) if (obj_Pila.elemento_cima()[0] == 'Black Widow'): cant_peliculas = len(obj_Pila.elemento_cima()) - 1 while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return cant_peliculas
def ejercicio_14(): obj_Pila = Pila() opcion = 'y' numero = None elemento = None while (opcion == 'y'): numero = int(input('Ingrese un numero: ')) insertar_El_Numero_Menor_al_Mayor_En_Pila(obj_Pila, numero) opcion = input('¿Volver a ingresar un numero? (Y/N): ').lower() while (not obj_Pila.pila_vacia()): print(obj_Pila.desapilar())
def reemplazar(pila, valor_nuevo, valor_viejo): pila_aux = Pila() while not pila.esta_vacia(): elemento = pila.desapilar() if elemento == valor_viejo: elemento = valor_nuevo pila_aux.apilar(elemento) while not pila_aux.esta_vacia(): pila.apilar(pila_aux.desapilar())
def get_Nombres_Que_Empiezan_Con_C_D_And_G(obj_Pila): obj_Aux_Pila = Pila() indice = 0 Vector = [] while (not obj_Pila.pila_vacia()): obj_Aux_Pila.apilar(obj_Pila.desapilar()) if (obj_Aux_Pila.elemento_cima()[0][0] in ['C', 'D', 'G']): Vector.insert(indice, obj_Aux_Pila.elemento_cima()[0]) indice += 1 while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return Vector
def invertir_Cola(contenedor): obj_Cola = Cola() obj_Pila = Pila() for i in range(0, len(contenedor)): obj_Cola.arribo(contenedor[i]) while(not obj_Cola.cola_vacia()): obj_Pila.apilar(obj_Cola.atencion()) while(not obj_Pila.pila_vacia()): obj_Cola.arribo(obj_Pila.desapilar()) for i in range(0, obj_Cola.tamanio()): contenedor[i] = obj_Cola.atencion() return contenedor
def es_Palindromo(palabra): obj_Cola = Cola() obj_Pila = Pila() letra = None for i in range(0, len(palabra)): letra = palabra[i].lower() obj_Cola.arribo(letra) obj_Pila.apilar(letra) mitad = len(palabra)//2 for i in range(0, mitad): if(obj_Pila.desapilar() != obj_Cola.atencion()): return False return True
def existe_Leila_O_Boba_En_Pila(personajes_star_wars): Estado = None aux_Pila = Pila() while ((not personajes_star_wars.pila_vacia()) and (not (personajes_star_wars.elemento_cima() in ('Boba Fet', 'Leia Organa')))): aux_Pila.apilar(personajes_star_wars.desapilar()) if (personajes_star_wars.pila_vacia()): Estado = False else: Estado = True while (not aux_Pila.pila_vacia()): personajes_star_wars.apilar(aux_Pila.desapilar()) return Estado
def get_Pos_Groot_And_Roket(obj_Pila): obj_Aux_Pila = Pila() indice = obj_Pila.tamanio() - 1 posicion_Groot = None posicion_Roket = None while ((not obj_Pila.pila_vacia()) and ((posicion_Groot == None) or (posicion_Roket == None))): obj_Aux_Pila.apilar(obj_Pila.desapilar()) if (obj_Aux_Pila.elemento_cima()[0] == 'Groot'): posicion_Groot = indice elif (obj_Aux_Pila.elemento_cima()[0] == 'Rocket Raccoon'): posicion_Roket = indice indice -= 1 while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return posicion_Groot, posicion_Roket
class _IteradorListaEnlazada: """ Modela el iterador para la clase ListaEnlazada. """ def __init__(self, elemento): """ Inicializa el iterador a partir del nodo parametrizado. """ self.actual = elemento self.anteriores = Pila() def __next__(self): """ Devuelve el próximo elemento de la lista (la información del nodo siguiente). Si el nodo es el último, termina con la iteración. """ if not self.actual: raise StopIteration() dato = self.actual.dato self.anteriores.apilar(self.actual) self.actual = self.actual.prox return dato def anterior(self): """ Devuelve el anterior elemento de la lista (la información del nodo anterior). Si el nodo es el primero, termina con la iteración. """ if self.anteriores.esta_vacia(): raise StopIteration() nodo = self.anteriores.desapilar() self.actual = nodo return nodo.dato
def eliminar_repetidos_consecutivos(pila): if pila.esta_vacia(): return pila_aux = Pila() dato1 = pila.desapilar() pila_aux.apilar(dato1) while not pila.esta_vacia(): dato2 = pila.desapilar() if dato1 != dato2: pila_aux.apilar(dato2) dato1 = dato2 while not pila_aux.esta_vacia(): pila.apilar(pila_aux.desapilar())
def get_Personajes_Que_Aparecen_En_Mas_De_5_Peliculas_And_La_Cantidad( obj_Pila): obj_Aux_Pila = Pila() cant_peliculas = None indice = 0 Vector = None Mat = [[]] while (not obj_Pila.pila_vacia()): obj_Aux_Pila.apilar(obj_Pila.desapilar()) cant_peliculas = len(obj_Aux_Pila.elemento_cima()) - 1 if (cant_peliculas > 5): Mat.insert(indice, (obj_Aux_Pila.elemento_cima()[0], cant_peliculas)) indice += 1 while (not obj_Aux_Pila.pila_vacia()): obj_Pila.apilar(obj_Aux_Pila.desapilar()) return Mat
def invertir(self): pila = Pila() if self.prim is None: return nodo = self.pop() #utilizo self.pop porque el enunciado no indica que se necesite recorrer la lista una sola vez. while nodo is not None: pila.apilar(nodo) nodo = self.pop() proximo = None while not pila.esta_vacia(): nodo_nuevo = _Nodo() nodo_nuevo.dato = pila.desapilar() nodo_nuevo.prox = proximo proximo = nodo_nuevo self.prim = proximo
class ColaDeReproduccion: """Clase que representa la cola de reproduccion del reproductor. Permite agregar y remover canciones, ademas de poder hacer y deshacer estas acciones. Las canciones se guardan en la cola como objetos de clase Cancion.""" AGREGADA = 1 REMOVIDA = 0 def __init__(self, lista_canciones=[]): """ Recibe una lista de objetos de clase Cancion con las canciones que se quieren reproducir.""" lista = ListaEnlazada() for cancion in lista_canciones: lista.insert(cancion) self.lista_canciones = lista self.acciones_tomadas = Pila() self.acciones_deshechas = Pila() self.actual = 0 def cancion_actual(self): """ Devuelve un objeto de clase Cancion que corresponde a la cancion actual, o None si no hay canciones cargadas en la cola.""" if self.lista_canciones.esta_vacia(): return None try: cancion = self.lista_canciones.get_elemento(self.actual) except IndexError: return return cancion def cancion_siguiente(self): """ Devuelve un objeto de clase Cancion que corresponde a la cancion siguiente en la cola, o None si no hay mas canciones.""" if len(self.lista_canciones) < 1: return None try: cancion = self.lista_canciones.get_elemento(self.actual + 1) self.actual += 1 except IndexError: return return cancion def cancion_anterior(self): """ Devuelve un objeto de clase Cancion que corresponde a la cancion anterior en la cola, o None si no hay canciones en la misma o la actual es la primera de la cola.""" if len(self.lista_canciones) < 1: return None try: cancion = self.lista_canciones.get_elemento(self.actual - 1) self.actual -= 1 except IndexError: #No hay cancion anterior return return cancion def agregar_cancion(self, ruta_cancion): """ Agrega una Cancion a la cola a partir de su ruta. Devuelve True si se agrego correctamente, False en caso contrario. Esta accion puede deshacerse y rehacerse.""" try: self.agregar_cancion_sin_guardar(ruta_cancion) self.guardar_accion(ruta_cancion, self.AGREGADA) return True except (TinyTagException, LookupError, OSError): return False def remover_cancion(self, ruta_cancion): """ Remueve una Cancion de la cola a partir de su ruta. Devuelve True si se removio correctamente, False en caso contrario. Esta accion puede deshacerse y rehacerse.""" try: resultado = self.remover_cancion_sin_guardar(ruta_cancion) self.guardar_accion(ruta_cancion, self.REMOVIDA) return resultado except (TinyTagException, LookupError, OSError): return False def deshacer_modificacion(self): """ Deshace la ultima accion realizada. Devuelve True si pudo deshacerse, False en caso contrario.""" try: ruta_ultima_cancion, ultima_accion = self.acciones_tomadas.desapilar() if ultima_accion == self.AGREGADA: self.remover_cancion_sin_guardar(ruta_ultima_cancion) self.acciones_deshechas.apilar((ruta_ultima_cancion, self.AGREGADA)) return True self.agregar_cancion_sin_guardar(ruta_ultima_cancion) self.acciones_deshechas.apilar((ruta_ultima_cancion, self.REMOVIDA)) return True except (ValueError, IndexError): return False def rehacer_modificacion(self): """ Rehace la ultima accion que se deshizo. Devuelve True si pudo rehacerse, False en caso contrario.""" try: ruta_ultima_cancion, ultima_accion = self.acciones_deshechas.desapilar() if ultima_accion == self.AGREGADA: self.agregar_cancion_sin_guardar(ruta_ultima_cancion) self.acciones_tomadas.apilar((ruta_ultima_cancion, self.AGREGADA)) return True self.remover_cancion_sin_guardar(ruta_ultima_cancion) self.acciones_tomadas.apilar((ruta_ultima_cancion, self.REMOVIDA)) return True except (ValueError, IndexError): return False def obtener_n_siguientes(self, n_canciones): """ Devuelve una lista con las siguientes n canciones. Si en la cola de reproduccion quedan menos canciones que las pedidas, la lista contendra menos elementos que los pedidos.""" if self.lista_canciones.esta_vacia(): return None lista = [] for i in range(n_canciones): try: lista.append(self.lista_canciones.get_elemento(self.actual + 1 + i)) except IndexError: return lista return lista def __str__(self): return str(self.lista_canciones) def guardar_accion(self, ruta_cancion, accion): """Guarda la accion como una tupla (ruta_cancion, accion).""" self.acciones_tomadas.apilar((ruta_cancion, accion)) def agregar_cancion_sin_guardar(self, ruta_cancion): """Agrega la cancion a la lista de reproduccion.""" cancion = Cancion(ruta_cancion) self.lista_canciones.insert(cancion) def remover_cancion_sin_guardar(self, ruta_cancion): """Remueve la cancion de la lista de reproduccion. Devuelve True en caso que sea exitoso y False en caso contrario.""" cancion = Cancion(ruta_cancion) posicion = self.lista_canciones.index(cancion) if posicion: self.lista_canciones.pop(posicion) return True return False