Mariano Reingart: A new web2py online python debugger
I've finished a new online debugger, based on my previous work on qdb module (bdb/pdb enhancement):
Roberto Alsina: Sacar la basura trae sus problemas
Una continuación rapidita de The problem is is, is it not? Esto no es mío, lo saqué de reddit
Esto no debería sorprenderte:
>>> a = [1,2] >>> b = [3,4] >>> a is b False >>> a == b False >>> id(a) == id(b) False
Después de todo, a y b son cosas distintas. Sin embargo:
>>> [1,2] is [3,4] False >>> [1,2] == [3,4] False >>> id([1,2]) == id([3,4]) True
Resulta que si uno usa literales, una de esas cosas no es como las demás.
Primero la explicación. Cuando uno no tiene más referencias a un dato, va a ser "garbage collected", la memoria se libera para que se pueda usar para otra cosa.
En el primer caso, las variables a y b guardan referencia a las listas. Es decir que tienen que existir todo el tiempo, ya que yo podría decir print a y python tiene que poder responderme con el valor de a.
En el segundo caso, uso literales, lo que quiere decir que no hay referencias a las listas después de que se usan. Cuando python evalúa id([1,2]) == id([3,4]) evalúa primero el lado izquierdo del ==. Después de que termina con eso, no hace falta mantener el [1,2] a mano, así que se borra. Entonces, al evaluar el lado derecho, crea [3,4].
Por pura casualidad, lo pone en exactamente el mismo lugar en que estaba el [1,2], asi que id devuelve el mismo valor. Esto sirve para recordar dos cosas:
Roberto Alsina: Gente haciendo cosas útiles con mis juguetes
Hace cosa de un año escribí un pequeño web browser llamado De Vicenzo un poco en joda.
¡Pero de golpe alguien fué y lo hizo hacer algo útil! Específicamente, para tener previews cuando edita documentos en sphinx
Está bueno :)
Roberto Alsina: PyQt Quickie: QTimer
QTimer es una clase sencillita: la usás cuando querés que algo pase "dentro de un rato" o "cada tanto".
El primer caso es así:
# llamar f() en 3 segundos QTimer.singleShot(3000, f)
El segundo es así:
# Creamos un QTimer timer = QTimer() # Lo conectamos a f timer.timeout.connect(f) # Llamamos a f() cada 5 segundos timer.start(5000)
¿Fácil, no? Bueno, sí, pero tiene un par de trampas.
Hay que guardar la referencia a timer
Si no, lo recoge el basurero, y nunca se llama a f()
Capaz que son más de 5 segundos
Va a llamar a f() más o menos cada 5 segundos después de que entre al event loop. Tal vez eso no sea enseguida después de que arrancás el timer!
Capaz que se pisan las llamadas
Si f() tarda mucho en terminar, y vuelve a entrar al event loop (por ejemplo, llamando a processEvents) tal vez timer se dispare antes que f() termine, y la llame de nuevo. Eso casi nunca es buena idea.
Una alternativa:
def f(): try: # Hacé cosas finally: QTimer.singleShot(5000, f) f()
Ese fragmento llama a f() una sola vez, pero ella misma se pone en cola para correr en 5 segundos. Ya que lo hace en un finally lo va a hacer aún si las cosas se rompen.
O sea, no se va a pisar. También quiere decir que no son 5 segundos, sino 5 más lo que tarde f. Y no hace falta guardar referencias al QTimer.
Último tipo: podés usar QTimer para que algo se haga "apenas estés en el event loop"
QTimer.singleShot(0, f)
¡Ojalá sirva!
Administración y hosting cortesía de Net Managers SRL
Tema por Andrés Antista
Banner por Joaquín Sorianello