¿Cómo ejecutar el programa Python para siempre?


83

Necesito ejecutar mi programa Python para siempre en un bucle infinito.

Actualmente lo estoy ejecutando así:

#!/usr/bin/python

import time

# some python code that I want 
# to keep on running


# Is this the right way to run the python program forever?
# And do I even need this time.sleep call?
while True:
    time.sleep(5)

¿Hay alguna forma mejor de hacerlo? ¿O incluso necesito time.sleepllamar? ¿Alguna idea?


Esa sería la forma correcta de hacerlo. No necesita time.sleep(5), siempre que tenga un código sangrado debajo de la while True:línea (puede ser passcomo mínimo)
Holy Mackerel

1
Es bueno agregar una condición de interrupción: "cierre de gancho", si desea salir, en lugar de matar el proceso.
user3020494

7
Pero si no duerme, o hace algo que duerme por un evento externo (como escuchar conexiones o datos en un socket), su programa usará el 100% de la CPU, también conocido como busywait . Esto no es cortés :)
qris

Python 3.5 puede usar asyncio y enlazar funciones a eventos. El programa con GUI puede manejar el bucle de eventos ui (por ejemplo, gtk.main ())
eri

Esto parece un duplicado de esta pregunta: stackoverflow.com/questions/3226628/non-blocking-wait-in-python
dllahr

Respuestas:


100

Sí, puede utilizar un while True:bucle que nunca se interrumpa para ejecutar código Python de forma continua.

Sin embargo, deberá colocar el código que desea ejecutar continuamente dentro del ciclo:

#!/usr/bin/python

while True:
    # some python code that I want 
    # to keep on running

Además, time.sleepse utiliza para suspender el funcionamiento de un script durante un período de tiempo. Entonces, dado que desea que el suyo se ejecute continuamente, no veo por qué lo usaría.


mientras que True no parece funcionar al iniciar código python a través de un archivo .bat
BarryMahnly

1
¿Puede time.sleepmejorar el rendimiento esperando, por ejemplo, 1 ms en lugar de correr a su velocidad máxima?
538ROMEO

35

¿Que tal este?

import signal
signal.pause()

Esto permitirá que su programa duerma hasta que reciba una señal de algún otro proceso (o de sí mismo, en otro hilo), haciéndole saber que es hora de hacer algo.


2
La señal detendrá el hilo. El título se trata de correr para siempre. Como servicio del sistema o demonio.
horario del

1
¿detendría eso solo el hilo principal, permitiendo que otros hilos se ejecuten indefinidamente?
David V.24 de

@David Sí, esto detiene solo el hilo principal. Solo probé para confirmar.
Samuel

9

dormir es una buena manera de evitar la sobrecarga en la CPU

No estoy seguro de si es realmente inteligente, pero suelo usar

while(not sleep(5)):
    #code to execute

El método sleep siempre devuelve None.


votado en contra sin comentarios? Me gustó esta solución cuando la leí, porque tiene buena legibilidad / mantenibilidad. Un lector interesado de este código no necesita desplazarse para encontrar el intervalo de bucle.
Matt

1
@mustafa ¿cuál? explíquese, funciona perfectamente bien.
Porunga

1
¿no duerme antes de la primera ejecución? No creo que sea un comportamiento deseado en general
noonex

6

Sé que este es un hilo demasiado antiguo, pero ¿por qué nadie mencionó esto?

#!/usr/bin/python3
import asyncio 

loop = asyncio.get_event_loop()
try:
    loop.run_forever()
finally:
    loop.close()

1
Siempre uso esto cuando intento que mi programa se ejecute para siempre. No sé por qué nadie mencionó esto tampoco
madladzen

5

para sistemas operativos que admiten select:

import select

# your code

select.select([], [], [])

5

Aquí está la sintaxis completa,

#!/usr/bin/python3

import time 

def your_function():
    print("Hello, World")

while True:
    your_function()
    time.sleep(10) #make function to sleep for 10 seconds

1

Tengo un pequeño script interruptableloop.py que ejecuta el código en un intervalo (predeterminado 1 segundo), envía un mensaje a la pantalla mientras se está ejecutando y captura una señal de interrupción que puede enviar con CTL-C:

#!/usr/bin/python3
from interruptableLoop import InterruptableLoop

loop=InterruptableLoop(intervalSecs=1) # redundant argument
while loop.ShouldContinue():
   # some python code that I want 
   # to keep on running
   pass

Cuando ejecuta el script y luego lo interrumpe, verá esta salida (los puntos se bombean en cada paso del ciclo):

[py36]$ ./interruptexample.py
CTL-C to stop   (or $kill -s SIGINT pid)
......^C
Exiting at  2018-07-28 14:58:40.359331

interruptableLoop.py :

"""
    Use to create a permanent loop that can be stopped ...

    ... from same terminal where process was started and is running in foreground: 
        CTL-C

    ... from same user account but through a different terminal 
        $ kill -2 <pid> 
        or $ kill -s SIGINT <pid>

"""
import signal
import time
from datetime import datetime as dtt
__all__=["InterruptableLoop",]
class InterruptableLoop:
    def __init__(self,intervalSecs=1,printStatus=True):
        self.intervalSecs=intervalSecs
        self.shouldContinue=True
        self.printStatus=printStatus
        self.interrupted=False
        if self.printStatus:
            print ("CTL-C to stop\t(or $kill -s SIGINT pid)")
        signal.signal(signal.SIGINT, self._StopRunning)
        signal.signal(signal.SIGQUIT, self._Abort)
        signal.signal(signal.SIGTERM, self._Abort)

    def _StopRunning(self, signal, frame):
        self.shouldContinue = False

    def _Abort(self, signal, frame):
        raise 

    def ShouldContinue(self):
        time.sleep(self.intervalSecs)
        if self.shouldContinue and self.printStatus: 
            print( ".",end="",flush=True)
        elif not self.shouldContinue and self.printStatus:
            print ("Exiting at ",dtt.now())
        return self.shouldContinue

¿No sería mucho más fácil (y más Pythonic) captar las excepciones KeyboardInterrupty SystemExiten el código del cliente, en lugar de tener una clase dedicada para ello?
Matthew Cole

Lo uso para encapsular y me gusta la forma en que se lee. Obviamente, la implementación de interruptableloop no pasa por mi mente cuando lo estoy usando.
Riaz Rizvi
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.