IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Python Discussion :

Programmation sequentielle - Actions parallèles


Sujet :

Python

  1. #1
    Membre éprouvé

    Homme Profil pro
    Ingénieur
    Inscrit en
    Août 2010
    Messages
    654
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2010
    Messages : 654
    Points : 1 150
    Points
    1 150
    Par défaut Programmation sequentielle - Actions parallèles
    Bonjour tout le monde.

    Ce sujet est je pense similaire à celui créé par Plaxtor (http://www.developpez.net/forums/d14...e/#post8086321) mais pas tout à fait identique.

    Je cherche à mettre en place un mécanisme simple pour lancer séquentiellement plusieurs actions (comme lancer un script python, lancer un executable windows, copier, renommer, supprimer des fichiers, etc...). En somme un ensemble de tâches répétitives tout à fait gérables avec un bon vieux .bat (ce qui est le cas jusqu'à present). Cependant l'une de ces tâches/actions peut ne pas se dérouler comme prevue. Typiquement un des executable plante pour x ou y raison et nécessite la fermeture d'une boite de dialogue pour poursuivre le reste des tâches. Comme j'ai pas souvent de bol ça intervient souvent en début de soirée, peu après être parti du boulot, foirant l'ensemble des calculs prévus pour la nuit...

    Bref, ce que je cherche à faire c'est lancer un process (n'importe lequel), soit celui-ci se termine à temps, soit on atteint un timeout et on le stop avant de poursuivre le reste (dans l'idéal conserver un log). Cela s'apparente furieusement du process concurrent où dès que l'un des process se termine, les autres sont tués.

    En grafcet, cela donnerait ceci (où action 1 serait un timer dans mon cas précis):
    Nom : Process.png
Affichages : 1027
Taille : 5,3 Ko

    Je suis parvenu à créer un mécanisme de timeout:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    import subprocess
    import psutil
    import time
     
    def process_timeout(cmd, seconds, interval=1):
        """Run process and wait to finish, or kill it after timeout"""
        start = time.time()
        end = start + seconds
        proc = subprocess.Popen(cmd, shell=True)
        p = psutil.Process(proc.pid)
        while p.is_running():
            if time.time() >= end:
                proc.terminate()
                print 'Process terminated after timeout'
                return
            time.sleep(interval)
        print 'Process finished in time'
     
    if __name__ == '__main__':
     
        command = "PING -n 2 127.0.0.1 >NUL"
        process_timeout(command, 1, interval=0.01)
        process_timeout(command, 3, interval=0.01)
    Mais je suis bien en peine de créer quelque chose de plus general (pas simplement un système de timeout). Une liste de process (pool?) concurrents dont tous les process (ainsi que leur enfants) sont tués dès que l'un se termine normalement.

    Est-ce qu'il existe quelque chose en python 2.7 pour cela? Un backport d'une bibliothèque de python 3.x compatible avec Windows?

    Merci par avance,

    Julien

  2. #2
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2015
    Messages
    42
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 27
    Localisation : France, Maine et Loire (Pays de la Loire)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2015
    Messages : 42
    Points : 54
    Points
    54
    Par défaut
    En effet ton problème ressemble un peu au mien (programmation concurrente)
    Tu cherches à tuer tous les process si l'un d'eux s'achève ? Je ne connais pas les modules que tu utilise, si j'en crois ton utilisation ça devrait donner quelque chose comme ca non ? :


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    import subprocess
    import psutil
    import time
     
    def end_process(list_of_process):
        """Kill all the process in the list of process when one of them end"""
        list_p = [psutil.Process(process.pid) for process in list_of_process]
        while not sum[not p.is_running() for p in list_p]: #Devient False quand l'un des process ne tourne plus
            pass
        for p in list_p:
            p.terminate()

  3. #3
    Membre éprouvé

    Homme Profil pro
    Ingénieur
    Inscrit en
    Août 2010
    Messages
    654
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2010
    Messages : 654
    Points : 1 150
    Points
    1 150
    Par défaut
    Merci Plaxtor, Je n'avais pas du tout songé à l'idée de tester un liste de booléens. Cependant la somme renvoie non pas un booléen mais un entire correspondant au nombre de True ou de False selon.

    La fonction suivante fonctionne (les prints sont là uniquement pour tester et le dico log juste à titre d'exemple perso):
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    import subprocess
    import psutil
     
    def concurrent_subprocess(cmds):
        log = {}
        for cmd in cmds:
            print "Process %s running" % (cmd,)
            proc = subprocess.Popen(cmd, shell=True)
            p = psutil.Process(proc.pid)
            log[p] = {'status': 'is_running', 'cmd': cmd, 'pid': proc.pid}
        while sum([p.is_running() for p in log.keys()]) == len(log.keys()):
            pass
        for p, stat_dict in log.iteritems():
            if p.is_running(): 
                stat_dict['status'] = 'aborted'
                p.terminate()
                print "Process %s aborted" % (stat_dict['cmd'],)
            else:
                stat_dict['status'] = 'finished'
                print "Process %s finished" % (stat_dict['cmd'],)
        return log
     
     
    if __name__ == '__main__':
     
        cmd_1 = "PING -n 2 127.0.0.1 >NUL"
        cmd_2 = "PING -n 4 127.0.0.1 >NUL"
        res = concurrent_subprocess((cmd_1, cmd_2))

    Je vais voir si je peux pas render tout ça plus proper et plus general.

    Ju

Discussions similaires

  1. programmer les actions de Lynx (batch?)
    Par Lcf.vs dans le forum Scripts/Batch
    Réponses: 0
    Dernier message: 07/06/2008, 16h46
  2. Programmer une action à une heure définie
    Par BakaOnigiri dans le forum API standards et tierces
    Réponses: 12
    Dernier message: 26/10/2007, 14h21
  3. programmer mon port parallèle
    Par sarrgan dans le forum C
    Réponses: 4
    Dernier message: 06/09/2007, 11h39
  4. SOS:programmation objet action script
    Par obiwan13 dans le forum Flash
    Réponses: 4
    Dernier message: 13/04/2006, 09h27
  5. [VBA-E] Toggle button: programmation des actions
    Par micknic dans le forum Macros et VBA Excel
    Réponses: 5
    Dernier message: 30/10/2005, 19h28

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo