Discussion:
Stop Thread (Detener hilo)
Manuel Kaufmann
2006-11-07 00:05:31 UTC
Permalink
Hola gente de PyAr, logré hacer un system tray con algunas consultas
que les hice a ustedes y algo que he leído por ahí (desde ya gracias a
todos). Pero ahora me encuentro con un problema, el cual pude
"solucionar" una gran parte.

El problema es el siguiente, cuando lanzo mi aplicación KDE (clase
KApplication) y el SystemTray (clase KSystemTray) funciona todo
correctamente. Ahora cuando por ejemplo presiono botón derecho en el
TrayIcon y selecciono una de las funciones, si esta demora un tiempo
considerable el TrayIcon se queda tildado y no puedo seguir elegiendo
opciones (funciones) del programa.

Esto lo solucioné ejecutando esa función en un hilo que se llama
cuando el KSystemTray (en realidad es la clase KPopupMenu, que es la
que desplega el menú) envía una señal; y en la función esta puse lo
siguiente:

def iniciarDemonio():
from threading import Thread
global DEMONIO

class TestThr(Thread):
def __init__(self):
Thread.__init__(self)

#redefino el metodo run
def run(self):
while 1:
print time.ctime()
#hago algo
funcion_x()
#y duermo el demonio
time.sleep(TIEMPO_ESPERA)
#¿esto está bien? [*1*]
if DEMONIO == False:
#demonio en ejecucion
DEMONIO = True
thread = TestThr()
# lo seteo como demonio para que cuando cierre la aplicacion principal
# termine con este hilo tambien
thread.setDaemon(1)
thread.start()
else:
print 'El demonio ya esta en ejecucion'

[*1*]: ¿esto está bien hecho así, o hay alguna forma más pythónica de
hacerlo? Si está bien así, luego ¿cómo hago para parar el demonio
desde otra función, por ejemplo cuando presiono en el menú (de botón
derecho en el TrayIcon), "Detener demonio"?

Perdón si son demasiadas preguntas y gracias a todos!

Saludos!
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-07 18:00:53 UTC
Permalink
Estuve buscando información y leyendo hoy a la mañana sobre Threads y
encontré esta página
"http://www.commandprompt.com/community/pyqt/x3738" en la que leí lo
siguiente:

"Killing or stopping threads from outside the threads is not supported
in Python, but you can create a global variable, stop, to circumvent
this. In the threads themselves, you then check whether stop is true."

¿Esto es realmente así? ¿La única forma de detener un hilo es haciendo
una verificación con una variable global?
Post by Manuel Kaufmann
Hola gente de PyAr, logré hacer un system tray con algunas consultas
que les hice a ustedes y algo que he leído por ahí (desde ya gracias a
todos). Pero ahora me encuentro con un problema, el cual pude
"solucionar" una gran parte.
El problema es el siguiente, cuando lanzo mi aplicación KDE (clase
KApplication) y el SystemTray (clase KSystemTray) funciona todo
correctamente. Ahora cuando por ejemplo presiono botón derecho en el
TrayIcon y selecciono una de las funciones, si esta demora un tiempo
considerable el TrayIcon se queda tildado y no puedo seguir elegiendo
opciones (funciones) del programa.
Esto lo solucioné ejecutando esa función en un hilo que se llama
cuando el KSystemTray (en realidad es la clase KPopupMenu, que es la
que desplega el menú) envía una señal; y en la función esta puse lo
from threading import Thread
global DEMONIO
Thread.__init__(self)
#redefino el metodo run
print time.ctime()
#hago algo
funcion_x()
#y duermo el demonio
time.sleep(TIEMPO_ESPERA)
#¿esto está bien? [*1*]
#demonio en ejecucion
DEMONIO = True
thread = TestThr()
# lo seteo como demonio para que cuando cierre la aplicacion principal
# termine con este hilo tambien
thread.setDaemon(1)
thread.start()
print 'El demonio ya esta en ejecucion'
[*1*]: ¿esto está bien hecho así, o hay alguna forma más pythónica de
hacerlo? Si está bien así, luego ¿cómo hago para parar el demonio
desde otra función, por ejemplo cuando presiono en el menú (de botón
derecho en el TrayIcon), "Detener demonio"?
Perdón si son demasiadas preguntas y gracias a todos!
Saludos!
--
Kaufmann Manuel
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alberto Bertogli
2006-11-07 19:10:40 UTC
Permalink
Post by Manuel Kaufmann
Estuve buscando información y leyendo hoy a la mañana sobre Threads y
encontré esta página
"http://www.commandprompt.com/community/pyqt/x3738" en la que leí lo
"Killing or stopping threads from outside the threads is not supported
in Python, but you can create a global variable, stop, to circumvent
this. In the threads themselves, you then check whether stop is true."
¿Esto es realmente así? ¿La única forma de detener un hilo es haciendo
una verificación con una variable global?
Si y no.

Es realmente asi porque no tenes mecanismo "built-in" para detener hilos
en Python.

Pero por otro lado, podes usar un monton de cosas para hacerlo vos,
ademas de una variable global. Podrias, por ejemplo, usar colas de
mensajes, semaforos o mutexes; el mecanismo depende de lo que necesites
y de como este diseñada tu aplicacion.

Saludos,
Alberto



---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-07 19:21:01 UTC
Permalink
Post by Alberto Bertogli
Post by Manuel Kaufmann
Estuve buscando información y leyendo hoy a la mañana sobre Threads y
encontré esta página
"http://www.commandprompt.com/community/pyqt/x3738" en la que leí lo
"Killing or stopping threads from outside the threads is not supported
in Python, but you can create a global variable, stop, to circumvent
this. In the threads themselves, you then check whether stop is true."
¿Esto es realmente así? ¿La única forma de detener un hilo es haciendo
una verificación con una variable global?
Si y no.
Es realmente asi porque no tenes mecanismo "built-in" para detener hilos
en Python.
No sé qué es un mecanismo "built-in" :(
Post by Alberto Bertogli
Pero por otro lado, podes usar un monton de cosas para hacerlo vos,
ademas de una variable global. Podrias, por ejemplo, usar colas de
mensajes, semaforos o mutexes; el mecanismo depende de lo que necesites
y de como este diseñada tu aplicacion.
Gracias por la recomendación Alberto, esto de semáforos y colas de
mensajes lo dí el año pasado en la facultad y nunca entedí nada ya que
el "profesor" iba cuando quería... ¿Asique para esto sirve? Es un buen
momento ponerme a leer el libro!

Saludos!
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alberto Bertogli
2006-11-07 19:46:03 UTC
Permalink
Post by Manuel Kaufmann
Post by Manuel Kaufmann
Post by Manuel Kaufmann
¿Esto es realmente así? ¿La única forma de detener un hilo es
haciendo
Post by Manuel Kaufmann
una verificación con una variable global?
Si y no.
Es realmente asi porque no tenes mecanismo "built-in" para detener hilos
en Python.
No sé qué es un mecanismo "built-in" :(
Me referia a algun mecanismo que venga incorporado ya en el modulo de
threads de Python.
Post by Manuel Kaufmann
Post by Manuel Kaufmann
Pero por otro lado, podes usar un monton de cosas para hacerlo vos,
ademas de una variable global. Podrias, por ejemplo, usar colas de
mensajes, semaforos o mutexes; el mecanismo depende de lo que necesites
y de como este diseñada tu aplicacion.
Gracias por la recomendación Alberto, esto de semáforos y colas de
mensajes lo dí el año pasado en la facultad y nunca entedí nada ya que
el "profesor" iba cuando quería... ¿Asique para esto sirve? Es un buen
momento ponerme a leer el libro!
Sirven para muchas cosas mas aparte de esto eh! De hecho este ni
siquiera es uno de los usos mas comunes (aunque tampoco es algo loco ni
descabellado). Si vas a hacer cosas con hilos, deberias saber que son
esas cosas, porque las vas a necesitar =)

Gracias,
Alberto



---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
franzag
2006-11-07 21:41:06 UTC
Permalink
En mi primer mensaje a la lista hice una clase basada en
threading.Thread, descubri que en esta clase tiene una funcion
"privada?" _Thread_stop, que dtiene el hilo.
class threadx(threading.Thread):
def run(self):
# ...
pass
def stop(self):
self._Thread__stop()

http://mx.grulic.org.ar/lurker/message/20060925.021634.04f29bd7.es.html
Post by Alberto Bertogli
Post by Manuel Kaufmann
Post by Manuel Kaufmann
Post by Manuel Kaufmann
¿Esto es realmente así? ¿La única forma de detener un hilo es
haciendo
Post by Manuel Kaufmann
una verificación con una variable global?
Si y no.
Es realmente asi porque no tenes mecanismo "built-in" para detener hilos
en Python.
No sé qué es un mecanismo "built-in" :(
Me referia a algun mecanismo que venga incorporado ya en el modulo de
threads de Python.
Post by Manuel Kaufmann
Post by Manuel Kaufmann
Pero por otro lado, podes usar un monton de cosas para hacerlo vos,
ademas de una variable global. Podrias, por ejemplo, usar colas de
mensajes, semaforos o mutexes; el mecanismo depende de lo que necesites
y de como este diseñada tu aplicacion.
Gracias por la recomendación Alberto, esto de semáforos y colas de
mensajes lo dí el año pasado en la facultad y nunca entedí nada ya que
el "profesor" iba cuando quería... ¿Asique para esto sirve? Es un buen
momento ponerme a leer el libro!
Sirven para muchas cosas mas aparte de esto eh! De hecho este ni
siquiera es uno de los usos mas comunes (aunque tampoco es algo loco ni
descabellado). Si vas a hacer cosas con hilos, deberias saber que son
esas cosas, porque las vas a necesitar =)
Gracias,
Alberto
---------------------------------------------------------------------
PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
--
franzag-***@public.gmane.org
http://franzag.googlepages.com

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alberto Bertogli
2006-11-07 21:48:03 UTC
Permalink
Post by franzag
En mi primer mensaje a la lista hice una clase basada en
threading.Thread, descubri que en esta clase tiene una funcion
"privada?" _Thread_stop, que dtiene el hilo.
# ...
pass
self._Thread__stop()
Esto no te sirve para parar el thread, sirve solo para el join() (y lo
vas a estar engañando) segun parece de una vista muy rapida del codigo.

Yo no te recomendaria para nada que lo uses.

Gracias,
Alberto



---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
franzag
2006-11-07 21:56:40 UTC
Permalink
asi es, una descripcion mas academica para el que se quedo ....
http://mail.python.org/pipermail/python-list/2006-June/348738.html
Y como caramba paras un thread dese afuera de la clase?
Post by Alberto Bertogli
Post by franzag
En mi primer mensaje a la lista hice una clase basada en
threading.Thread, descubri que en esta clase tiene una funcion
"privada?" _Thread_stop, que dtiene el hilo.
# ...
pass
self._Thread__stop()
Esto no te sirve para parar el thread, sirve solo para el join() (y lo
vas a estar engañando) segun parece de una vista muy rapida del codigo.
Yo no te recomendaria para nada que lo uses.
Gracias,
Alberto
---------------------------------------------------------------------
PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
--
franzag-***@public.gmane.org
http://franzag.googlepages.com

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Facundo Batista
2006-11-07 21:59:04 UTC
Permalink
Post by franzag
asi es, una descripcion mas academica para el que se quedo ....
http://mail.python.org/pipermail/python-list/2006-June/348738.html
Y como caramba paras un thread dese afuera de la clase?
No lo matás, le decís que se muera.

Yo lo que hago siempre, como tengo una Queue con el thread para darle
info, le mando un "quit", y el tipo se deja morir...

Slds.
--
. Facundo

Blog: http://www.taniquetil.com.ar/plog/
PyAr: http://www.python.org/ar/

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Pablo Ziliani
2006-11-07 22:04:07 UTC
Permalink
Post by Facundo Batista
Post by franzag
asi es, una descripcion mas academica para el que se quedo ....
http://mail.python.org/pipermail/python-list/2006-June/348738.html
Y como caramba paras un thread dese afuera de la clase?
No lo matás, le decís que se muera.
Yo lo que hago siempre, como tengo una Queue con el thread para darle
info, le mando un "quit", y el tipo se deja morir...
Saturday Night Ninja[1], the dissapearing threads
Perdón, no lo pude resistir.

[1] http://www.pyweek.org/e/pycor/

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-07 23:18:50 UTC
Permalink
Post by Facundo Batista
Post by franzag
Y como caramba paras un thread dese afuera de la clase?
No lo matás, le decís que se muera.
Yo lo que hago siempre, como tengo una Queue con el thread para darle
info, le mando un "quit", y el tipo se deja morir...
¿Como le digo al "tipo" que se muera, o mejor dicho, se deje morir? :)
No encontré un método que se llame "quit".
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alberto Bertogli
2006-11-07 23:30:02 UTC
Permalink
Post by Manuel Kaufmann
Post by Facundo Batista
Post by franzag
Y como caramba paras un thread dese afuera de la clase?
No lo matás, le decís que se muera.
Yo lo que hago siempre, como tengo una Queue con el thread para darle
info, le mando un "quit", y el tipo se deja morir...
¿Como le digo al "tipo" que se muera, o mejor dicho, se deje morir? :)
No encontré un método que se llame "quit".
A ver, lo haces en dos pasos.

El primer paso es hacerle llegar al thread de alguna forma el mensaje
que se tiene que morir. Esto lo haces con una variable global, un mutex,
una cola de mensajes, o de la manera que mas te guste y te convenga.

Despues, cuando recibis el mensaje, tenes que hacer que la funcion
principal del thread haga un return, que eso "finaliza" el thread.

Me explico?

Queres que te arme un codigo de ejemplo, que quizas sea mas entendible?

Gracias,
Alberto



---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-07 23:40:34 UTC
Permalink
Post by Alberto Bertogli
Post by Manuel Kaufmann
¿Como le digo al "tipo" que se muera, o mejor dicho, se deje morir? :)
No encontré un método que se llame "quit".
A ver, lo haces en dos pasos.
El primer paso es hacerle llegar al thread de alguna forma el mensaje
que se tiene que morir. Esto lo haces con una variable global, un mutex,
una cola de mensajes, o de la manera que mas te guste y te convenga.
Despues, cuando recibis el mensaje, tenes que hacer que la funcion
principal del thread haga un return, que eso "finaliza" el thread.
Perfecto! Esto lo venía haciedo (o intentando hacer) así, lo único que
si yo duermo el hilo con un time.sleep(x*60) con x=20, osea 20
minutos, el hilo no se muere hasta que no se termine de ejecutar ese
time.sleep() logicamente.

Y lo que hice fué meter en un for la comprobación de que si el hilo se
debe morir o no, y hacer un intervalo de tiempo más chico, pero no me
gustó mucho eso. Y hasta pensé que estaba MAL hecho.

Gracias a todos por molestarse!
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alberto Bertogli
2006-11-08 00:07:00 UTC
Permalink
Post by Manuel Kaufmann
Post by Alberto Bertogli
Post by Manuel Kaufmann
¿Como le digo al "tipo" que se muera, o mejor dicho, se deje morir? :)
No encontré un método que se llame "quit".
A ver, lo haces en dos pasos.
El primer paso es hacerle llegar al thread de alguna forma el mensaje
que se tiene que morir. Esto lo haces con una variable global, un mutex,
una cola de mensajes, o de la manera que mas te guste y te convenga.
Despues, cuando recibis el mensaje, tenes que hacer que la funcion
principal del thread haga un return, que eso "finaliza" el thread.
Perfecto! Esto lo venía haciedo (o intentando hacer) así, lo único que
si yo duermo el hilo con un time.sleep(x*60) con x=20, osea 20
minutos, el hilo no se muere hasta que no se termine de ejecutar ese
time.sleep() logicamente.
Claro.
Post by Manuel Kaufmann
Y lo que hice fué meter en un for la comprobación de que si el hilo se
debe morir o no, y hacer un intervalo de tiempo más chico, pero no me
gustó mucho eso. Y hasta pensé que estaba MAL hecho.
Y... no es lo mas lindo que digamos, no.

O sea, funciona, pero ya hablando a nivel un poco mas "estructural" no
esta muy bueno que tengas que hacer eso. En general te conviene buscar
algun mecanismo dado que cuando tu hilo no tiene nada que hacer, no se
quede iterando haciendo sleep() y despues viendo si tiene trabajo, y
asi.

Una de las consecuencias de esto que vos hiciste es que la latencia de
respuesta del hilo aumenta: desde que vos le pones trabajo hasta que se
"aviva" puede pasar un rato (el tiempo que le dijiste que haga sleep()).
Esto hace que el hilo use mas CPU, baja la performance y no es muy
prolijo que digamos.

En cambio vos podrias pasarle las cosas usando una Queue, mas o menos
asi:


import threading
import Queue

def worker(q):
while True:
# Obtenemos un item de la cola. Si esta vacia, se queda
# esperando a que alguien haga un put
i = q.get()
if i == 'quit':
# si nos llega el string "quit", salimos
break
else:
# sino procesamos el elemento que vino, en este
# ejemplo imprimimos nomas
print i
print 'saliendo'
return


def main():
# por esta cola le vamos a pasar el trabajo al worker
q = Queue.Queue()

# este objeto representa al hilo del worker
w1 = threading.Thread(target = worker, args = (q,))

# arrancamos el hilo
w1.start()

# le mandamos cosas para hacer
q.put("hola")
q.put("mandamos trabajo")

# y ahora le decimos que se muera
q.put("quit")

# despues hacemos un join, que hace que este hilo espere a que el otro
# muera realmente
w1.join()

# y salimos
return


El chiste es que cuando el hilo esta en el q.get(), si no hay ningun
mensaje (ponele porque tu main() hace un sleep en el medio), se queda
esperando sin usar CPU ni nada. Y ni bien entra un mensaje se
"despierta" de forma bastante bastante rapida.

Me explico?


Gracias,
Alberto



---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-09 04:45:26 UTC
Permalink
Post by Alberto Bertogli
El chiste es que cuando el hilo esta en el q.get(), si no hay ningun
mensaje (ponele porque tu main() hace un sleep en el medio), se queda
esperando sin usar CPU ni nada. Y ni bien entra un mensaje se
"despierta" de forma bastante bastante rapida.
Me explico?
Muchas gracias por la explicación detalla que me diste. Todavía no he
tenido el tiempo necesario para leer la doc de Queue; porque estoy con
el tema del viaje a CaFeCONF y la facultad me ha tenido bastante
ocupado también.

Cuando pruebe todo esto nuevo para mí, les comento como me fué. Pero
desde ya estoy muy agredecido por sus respuestas! El ejemplo lo
entendí perfectamente!
Post by Alberto Bertogli
Post by Manuel Kaufmann
Y lo que hice fué meter en un for la comprobación de que si el hilo se
debe morir o no, y hacer un intervalo de tiempo más chico, pero no me
gustó mucho eso. Y hasta pensé que estaba MAL hecho.
Y... no es lo mas lindo que digamos, no.
O sea, funciona, pero ya hablando a nivel un poco mas "estructural"...
Tal cual, funciona... Pero no me gustó para nada desde el primer
momento y por eso pedí ayuda a los que más saben de esto, que son Uds!

Saludos y gracias nuevamente!
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-14 19:12:55 UTC
Permalink
Post by Alberto Bertogli
Una de las consecuencias de esto que vos hiciste es que la latencia de
respuesta del hilo aumenta: desde que vos le pones trabajo hasta que se
"aviva" puede pasar un rato (el tiempo que le dijiste que haga sleep()).
Esto hace que el hilo use mas CPU, baja la performance y no es muy
prolijo que digamos.
En cambio vos podrias pasarle las cosas usando una Queue
Hola Alberto!, implenté lo que me dijiste pero tengo un problema. Lo
de la Queue funciona correctamente (MUY buen ejemplo); pero el
problema que tengo yo es que se tiene que ejecutar una función en un
determinado lapso de tiempo, por ejemplo cada 30 min. y no cuando el
usuario haga "click" en algún botón. Por lo tanto no encuentro otra
forma de no hacer esto sin un time.sleep(); pero el problema que tengo
acá es que si este tiempo se quiere cambiar a mitad del sleep(),
supongamos que va por los 15 min. y quiero setearlo a 5 min (hay una
opción para hacer esto) tengo que esperar a que termine ese sleep()
para iniciar otro con 5 min.

Ese es mi problema y no sé como solucionarlo, quiero interrumpir en
cualquier momento este tiempo.

¿Es muy complicado lo que quiero hacer?

Gracias a todos y saludos!

PD: Tengo problemas al mandar los mails a la lista, he tenido que
mandarlos dos veces a cada uno, ¿a alguien le pasa algo similar?
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Facundo Batista
2006-11-14 19:52:02 UTC
Permalink
Post by Manuel Kaufmann
Ese es mi problema y no sé como solucionarlo, quiero interrumpir en
cualquier momento este tiempo.
¿Es muy complicado lo que quiero hacer?
No hagas un sleep() de 30 minutos, hacé 30*12 sleeps de 5 segundos,
con un buclecito.

Slds.
--
. Facundo

Blog: http://www.taniquetil.com.ar/plog/
PyAr: http://www.python.org/ar/

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-14 19:58:44 UTC
Permalink
Post by Facundo Batista
Post by Manuel Kaufmann
Ese es mi problema y no sé como solucionarlo, quiero interrumpir en
cualquier momento este tiempo.
¿Es muy complicado lo que quiero hacer?
No hagas un sleep() de 30 minutos, hacé 30*12 sleeps de 5 segundos,
con un buclecito.
Esto es lo que estaba haciendo y me parecía que estaba mal, incluso me
dijeron en la lista de una forma muy educada que estaba mal, por eso
es que quise cambiar todo e implementar Queue.

Saludos, y un gusto haberte conocido
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-14 19:20:46 UTC
Permalink
---------- Forwarded message ----------
From: Manuel Kaufmann <humitos-***@public.gmane.org>
Date: 14-nov-2006 16:09
Subject: Re: [pyar] Re: Stop Thread (Detener hilo)
Post by Alberto Bertogli
Una de las consecuencias de esto que vos hiciste es que la latencia de
respuesta del hilo aumenta: desde que vos le pones trabajo hasta que se
"aviva" puede pasar un rato (el tiempo que le dijiste que haga sleep()).
Esto hace que el hilo use mas CPU, baja la performance y no es muy
prolijo que digamos.
En cambio vos podrias pasarle las cosas usando una Queue
Hola Alberto!, implenté lo que me dijiste pero tengo un problema. Lo
de la Queue funciona correctamente (MUY buen ejemplo); pero el
problema que tengo yo es que se tiene que ejecutar una función en un
determinado lapso de tiempo, por ejemplo cada 30 min. y no cuando el
usuario haga "click" en algún botón. Por lo tanto no encuentro otra
forma de no hacer esto sin un time.sleep(); pero el problema que tengo
acá es que si este tiempo se quiere cambiar a mitad del sleep(),
supongamos que va por los 15 min. y quiero setearlo a 5 min (hay una
opción para hacer esto) tengo que esperar a que termine ese sleep()
para iniciar otro con 5 min.

Ese es mi problema y no sé como solucionarlo, quiero interrumpir en
cualquier momento este tiempo.

¿Es muy complicado lo que quiero hacer?

Gracias a todos y saludos!

PD: tengo problemas al enviar mails a la lista, me los rebota.
¿alguien tiene el mismo problema?

--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Roberto Alsina
2006-11-14 19:29:18 UTC
Permalink
Post by Manuel Kaufmann
---------- Forwarded message ----------
Date: 14-nov-2006 16:09
Subject: Re: [pyar] Re: Stop Thread (Detener hilo)
Post by Alberto Bertogli
Una de las consecuencias de esto que vos hiciste es que la latencia de
respuesta del hilo aumenta: desde que vos le pones trabajo hasta que se
"aviva" puede pasar un rato (el tiempo que le dijiste que haga sleep()).
Esto hace que el hilo use mas CPU, baja la performance y no es muy
prolijo que digamos.
En cambio vos podrias pasarle las cosas usando una Queue
Hola Alberto!, implenté lo que me dijiste pero tengo un problema. Lo
de la Queue funciona correctamente (MUY buen ejemplo); pero el
problema que tengo yo es que se tiene que ejecutar una función en un
determinado lapso de tiempo, por ejemplo cada 30 min. y no cuando el
usuario haga "click" en algún botón. Por lo tanto no encuentro otra
forma de no hacer esto sin un time.sleep(); pero el problema que tengo
acá es que si este tiempo se quiere cambiar a mitad del sleep(),
supongamos que va por los 15 min. y quiero setearlo a 5 min (hay una
opción para hacer esto) tengo que esperar a que termine ese sleep()
para iniciar otro con 5 min.
Mirá el segundo argumento de Queue.get():

get( [block[, timeout]])
Remove and return an item from the queue. If optional args block is true and
timeout is None (the default), block if necessary until an item is available.
If timeout is a positive number, it blocks at most timeout seconds and raises
the Empty exception if no item was available within that time. Otherwise
(block is false), return an item if one is immediately available, else raise
the Empty exception (timeout is ignored in that case).
New in version 2.3: the timeout parameter.
--
 ("\''/").__..-''"`-. .         Roberto Alsina
 `9_ 9  )   `-. (    ).`-._.`)  ralsina-***@public.gmane.org
 (_Y_.)' ._   ) `._`.  " -.-'   KDE Developer (MFCH)
  _..`-'_..-_/ /-'_.'
(l)-'' ((i).' ((!.'   Buenos Aires - Argentina
Feynman's problem solving algorithm: write down the problem->
think very hard -> write down the answer.

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-14 19:56:47 UTC
Permalink
Post by Roberto Alsina
get( [block[, timeout]])
Remove and return an item from the queue. If optional args block is true and
timeout is None (the default), block if necessary until an item is available.
If timeout is a positive number, it blocks at most timeout seconds and raises
the Empty exception if no item was available within that time. Otherwise
(block is false), return an item if one is immediately available, else raise
the Empty exception (timeout is ignored in that case).
New in version 2.3: the timeout parameter.
Estuve leyendo la documentación otra vez, y aunque mi inglés es
realmente malo, entendí lo siguiente (puede ser que esté MUY
equivocado) la parte que me interesa, la del "timeout":

"Si 'timeout' es un número positivo, espera 'timeout' segundos hasta
que halla algo el la Queue y si no encuentra nada, devuelve la
excepcion Empty"

Ahora, si en la Queue se ingresa algo (distinto de 'quit', por
ejemplo) antes que se cumpla ese tiempo, la función se ejecuta igual.

Lo probré y funciona así, no es que espera 'timeout' segundos para
fijarse si hay algo o no, sino que si hay algo lo procesa y si no hay
nada espera 'timeout' como máximo antes de tirar la excepción.

Saludos y gracias por tu respuesta,
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Roberto Alsina
2006-11-14 20:38:31 UTC
Permalink
Post by Manuel Kaufmann
Post by Roberto Alsina
get( [block[, timeout]])
Remove and return an item from the queue. If optional args block is true
and timeout is None (the default), block if necessary until an item is
available. If timeout is a positive number, it blocks at most timeout
seconds and raises the Empty exception if no item was available within
that time. Otherwise (block is false), return an item if one is
immediately available, else raise the Empty exception (timeout is ignored
in that case).
New in version 2.3: the timeout parameter.
Estuve leyendo la documentación otra vez, y aunque mi inglés es
realmente malo, entendí lo siguiente (puede ser que esté MUY
"Si 'timeout' es un número positivo, espera 'timeout' segundos hasta
que halla algo el la Queue y si no encuentra nada, devuelve la
excepcion Empty"
Ahora, si en la Queue se ingresa algo (distinto de 'quit', por
ejemplo) antes que se cumpla ese tiempo, la función se ejecuta igual.
Lo probré y funciona así, no es que espera 'timeout' segundos para
fijarse si hay algo o no, sino que si hay algo lo procesa y si no hay
nada espera 'timeout' como máximo antes de tirar la excepción.
Sí, exacto.

No es que la cola está continuamente recibiendo cosas, no?

La ponés a esperar suponete un minuto. O le llega el quit (y cortás el hilo) o
pasa un minuto.

Lo metés adentro de un loop con un contador.

Te fijás si pasaron suficientes minutos como para que tengas que correr la
tarea que tenés pendiente. La corrés o no.

O no entendí lo que querés hacer? Perfectamente probable ;-)

 
--
 ("\''/").__..-''"`-. .         Roberto Alsina
 `9_ 9  )   `-. (    ).`-._.`)  ralsina-***@public.gmane.org
 (_Y_.)' ._   ) `._`.  " -.-'   KDE Developer (MFCH)
  _..`-'_..-_/ /-'_.'
(l)-'' ((i).' ((!.'   Buenos Aires - Argentina
Feynman's problem solving algorithm: write down the problem->
think very hard -> write down the answer.

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alejandro J. Cura
2006-11-15 20:53:38 UTC
Permalink
Post by Manuel Kaufmann
Post by Alberto Bertogli
En cambio vos podrias pasarle las cosas usando una Queue
Hola Alberto!, implenté lo que me dijiste pero tengo un problema. Lo
de la Queue funciona correctamente (MUY buen ejemplo); pero el
problema que tengo yo es que se tiene que ejecutar una función en un
determinado lapso de tiempo, por ejemplo cada 30 min. y no cuando el
usuario haga "click" en algún botón. Por lo tanto no encuentro otra
forma de no hacer esto sin un time.sleep(); pero el problema que tengo
acá es que si este tiempo se quiere cambiar a mitad del sleep(),
supongamos que va por los 15 min. y quiero setearlo a 5 min (hay una
opción para hacer esto) tengo que esperar a que termine ese sleep()
para iniciar otro con 5 min.
Lo que aca estas planteando es un mecanismo similar al "callLater" de twisted.

Lo que tenes que hacer es asi como le mandas un mensaje "quit" por el
queue a tu thread, tambien podes mandarle un mensaje
"callLater(segundos, accion)", que le diga dentro de cuanto tiempo
tiene que hacer la accion deseada.

Dentro del thread, cuando recibis el callLater, lo gardas dentro de
una lista de eventos pendientes, que podes armar como una tupla de
(tiempo actual+segundos, accion). Y esa lista la ordenas por el
instante en que tiene que ser ejecutado.
Y luego te quedas durmiendo, esperando un evento por el queue, pero
solamente el tiempo que te falta hasta el primer "evento".

Cuando llega algo por el queue (o se va por timeout) comparas el
tiempo actual con el tiempo de los items de la lista, y si ya llego
ese instante, entonces ejecutas la respectiva accion. Si todavia no
llego el instante (porque por ejemplo te llego un nuevo mensaje
callLater, o algo asi) entonces volves a dormir por el tiempo que te
falta hasta el primer evento de la lista.

Avisame si no se entiende bien y trato de armar un ejemplo.

PD: al final, cuando uno se pone a programar con threads, termina
implementando una version ad-hoc, informalmente especificada, llena de
bugs de la mitad de twisted :-)

Saludos,
--
alecu

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-16 20:41:12 UTC
Permalink
Post by Alejandro J. Cura
Post by Manuel Kaufmann
Post by Alberto Bertogli
En cambio vos podrias pasarle las cosas usando una Queue
Hola Alberto!, implenté lo que me dijiste pero tengo un problema. Lo
de la Queue funciona correctamente (MUY buen ejemplo); pero el
problema que tengo yo es que se tiene que ejecutar una función en un
determinado lapso de tiempo, por ejemplo cada 30 min. y no cuando el
usuario haga "click" en algún botón. Por lo tanto no encuentro otra
forma de no hacer esto sin un time.sleep(); pero el problema que tengo
acá es que si este tiempo se quiere cambiar a mitad del sleep(),
supongamos que va por los 15 min. y quiero setearlo a 5 min (hay una
opción para hacer esto) tengo que esperar a que termine ese sleep()
para iniciar otro con 5 min.
Lo que aca estas planteando es un mecanismo similar al "callLater" de twisted.
Lo que tenes que hacer es asi como le mandas un mensaje "quit" por el
queue a tu thread, tambien podes mandarle un mensaje
"callLater(segundos, accion)", que le diga dentro de cuanto tiempo
tiene que hacer la accion deseada.
Dentro del thread, cuando recibis el callLater, lo gardas dentro de
una lista de eventos pendientes, que podes armar como una tupla de
(tiempo actual+segundos, accion). Y esa lista la ordenas por el
instante en que tiene que ser ejecutado.
Y luego te quedas durmiendo, esperando un evento por el queue, pero
solamente el tiempo que te falta hasta el primer "evento".
Cuando llega algo por el queue (o se va por timeout) comparas el
tiempo actual con el tiempo de los items de la lista, y si ya llego
ese instante, entonces ejecutas la respectiva accion. Si todavia no
llego el instante (porque por ejemplo te llego un nuevo mensaje
callLater, o algo asi) entonces volves a dormir por el tiempo que te
falta hasta el primer evento de la lista.
Avisame si no se entiende bien y trato de armar un ejemplo.
Si no es te es mucha molestia, te agradecería mucho que me armes algún
ejemplito porque todavía estoy "carburando" con respecto a lo que me
dijiste y estoy bastante mareado, hay muchas cosas nuevas para mí acá.

Saludos y MUCHAS GRACIAS
Post by Alejandro J. Cura
PD: al final, cuando uno se pone a programar con threads, termina
implementando una version ad-hoc, informalmente especificada, llena de
bugs de la mitad de twisted :-)
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Alejandro J. Cura
2006-11-24 01:30:08 UTC
Permalink
Post by Manuel Kaufmann
Post by Alejandro J. Cura
Post by Manuel Kaufmann
Post by Alberto Bertogli
En cambio vos podrias pasarle las cosas usando una Queue
Hola Alberto!, implenté lo que me dijiste pero tengo un problema. Lo
de la Queue funciona correctamente (MUY buen ejemplo); pero el
problema que tengo yo es que se tiene que ejecutar una función en un
determinado lapso de tiempo, por ejemplo cada 30 min. y no cuando el
usuario haga "click" en algún botón. Por lo tanto no encuentro otra
forma de no hacer esto sin un time.sleep(); pero el problema que tengo
acá es que si este tiempo se quiere cambiar a mitad del sleep(),
supongamos que va por los 15 min. y quiero setearlo a 5 min (hay una
opción para hacer esto) tengo que esperar a que termine ese sleep()
para iniciar otro con 5 min.
Lo que aca estas planteando es un mecanismo similar al "callLater" de twisted.
Lo que tenes que hacer es asi como le mandas un mensaje "quit" por el
queue a tu thread, tambien podes mandarle un mensaje
"callLater(segundos, accion)", que le diga dentro de cuanto tiempo
tiene que hacer la accion deseada.
Dentro del thread, cuando recibis el callLater, lo gardas dentro de
una lista de eventos pendientes, que podes armar como una tupla de
(tiempo actual+segundos, accion). Y esa lista la ordenas por el
instante en que tiene que ser ejecutado.
Y luego te quedas durmiendo, esperando un evento por el queue, pero
solamente el tiempo que te falta hasta el primer "evento".
Cuando llega algo por el queue (o se va por timeout) comparas el
tiempo actual con el tiempo de los items de la lista, y si ya llego
ese instante, entonces ejecutas la respectiva accion. Si todavia no
llego el instante (porque por ejemplo te llego un nuevo mensaje
callLater, o algo asi) entonces volves a dormir por el tiempo que te
falta hasta el primer evento de la lista.
Avisame si no se entiende bien y trato de armar un ejemplo.
Si no es te es mucha molestia, te agradecería mucho que me armes algún
ejemplito porque todavía estoy "carburando" con respecto a lo que me
dijiste y estoy bastante mareado, hay muchas cosas nuevas para mí acá.
Saludos y MUCHAS GRACIAS
Post by Alejandro J. Cura
PD: al final, cuando uno se pone a programar con threads, termina
implementando una version ad-hoc, informalmente especificada, llena de
bugs de la mitad de twisted :-)
Je, me quedo picando. Bueno, tarde un rato mas, pero me quedo algo
bastante prolijo. :-) Lo mando attachado.

Saludos,
--
alecu
Manuel Kaufmann
2006-11-24 02:54:20 UTC
Permalink
Post by Alejandro J. Cura
Post by Manuel Kaufmann
Si no es te es mucha molestia, te agradecería mucho que me armes algún
ejemplito porque todavía estoy "carburando" con respecto a lo que me
dijiste y estoy bastante mareado, hay muchas cosas nuevas para mí acá.
Saludos y MUCHAS GRACIAS
Post by Alejandro J. Cura
PD: al final, cuando uno se pone a programar con threads, termina
implementando una version ad-hoc, informalmente especificada, llena de
bugs de la mitad de twisted :-)
Je, me quedo picando. Bueno, tarde un rato mas, pero me quedo algo
bastante prolijo. :-) Lo mando attachado.
La verdad te pasaste! Muchas gracias de verdad, nunca me imaginé que tenía que
hacer algo como eso. Estoy intentando entender el código, hay muchas cosas
que no conocía. No te entendía a qué te referías antes con lo de callLater,
pero ahora veo como es la cosa. No era tan fácil lo que había que hacer.

Saludos y gracias, me voy a poner con esto ahora. Un abrazo!
--
Kaufmann Manuel
Alejandro J. Cura
2006-11-24 03:02:48 UTC
Permalink
Post by Manuel Kaufmann
La verdad te pasaste! Muchas gracias de verdad, nunca me imaginé que tenía que
hacer algo como eso. Estoy intentando entender el código, hay muchas cosas
que no conocía. No te entendía a qué te referías antes con lo de callLater,
pero ahora veo como es la cosa. No era tan fácil lo que había que hacer.
Saludos y gracias, me voy a poner con esto ahora. Un abrazo!
Se aceptan consultas y sugerencias. Criticas tambien :-)

saludos,
--
alecu
Facundo Batista
2006-11-07 21:53:10 UTC
Permalink
Post by franzag
En mi primer mensaje a la lista hice una clase basada en
threading.Thread, descubri que en esta clase tiene una funcion
"privada?" _Thread_stop, que dtiene el hilo.
Si en la doc te dice que no hay, y el método es privado, lo único que
vas a ganar usándolo es quilombos...

Slds.
--
. Facundo

Blog: http://www.taniquetil.com.ar/plog/
PyAr: http://www.python.org/ar/

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Daniel F. Moisset
2006-11-08 03:11:54 UTC
Permalink
Post by Alberto Bertogli
Post by Manuel Kaufmann
Estuve buscando información y leyendo hoy a la mañana sobre Threads y
encontré esta página
"http://www.commandprompt.com/community/pyqt/x3738" en la que leí lo
"Killing or stopping threads from outside the threads is not supported
in Python, but you can create a global variable, stop, to circumvent
this. In the threads themselves, you then check whether stop is true."
¿Esto es realmente así? ¿La única forma de detener un hilo es haciendo
una verificación con una variable global?
Si y no.
Es realmente asi porque no tenes mecanismo "built-in" para detener hilos
en Python.
No hay forma de parar un hilo en python?

Ahora entiendo porque 15, 20 mails en un hilo de PC vs Mac....

/me ducks


---------------------------------------------------------------------
Para dar de baja la suscripci�n, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Manuel Kaufmann
2006-11-08 03:20:39 UTC
Permalink
Post by Daniel F. Moisset
No hay forma de parar un hilo en python?
Ahora entiendo porque 15, 20 mails en un hilo de PC vs Mac....
Yo sigo sin entender porqué se armó esa "discusión" :(
Post by Daniel F. Moisset
/me ducks
--
Kaufmann Manuel

---------------------------------------------------------------------
Para dar de baja la suscripción, mande un mensaje a:
pyar-unsubscribe-***@public.gmane.org

Para obtener el resto de direcciones-comando, mande un mensaje a:
pyar-help-***@public.gmane.org

PyAr - Python Argentina - Sitio web: http://www.python.com.ar/
Loading...