Question

Je suis en train de comprendre comment puis-je faire mon code plus asynchrone en utilisant torsadé.

  • Une fonction retourne un objet différé
  • puis-je ajouter une liste des callbacks
  • le premier rappel sera appelée après la fonction différée fournit un résultat par deferred_obj.callback
  • puis, dans la chaîne de callbacks, le premier rappel fera quelque chose avec les données et appelez le deuxième rappel
  • et etc.

callbacks cependant enchaînées ne sera pas considérée comme asynchrone parce qu'ils sont enchaînées et la boucle d'événement continuer à tirer chacun d'eux en même temps jusqu'à ce qu'il n'y a pas de plus, non?

Cependant, si j'ai un objet différé, et je joins en tant que rappel le deferred_obj.callback comme dans d.addCallback(deferred_obj.callback) alors ce sera considéré comme asynchrone, car le deferred_obj attend les données, puis la méthode qui transmettre les données est en attente de données aussi bien, mais une fois que je d.callback « d » objet traite les données puis appelez deferred_obj.callback cependant, puisque cet objet est reporté, contrairement au cas des callbacks enchaînées, il exécute de manière asynchrone ... correcte?

En supposant que tout mon code est non-bloquant, cela signifie que callbacks chaînées ne sont PAS asynchrones tandis que deferreds sont enchaînées, correct?

Autres conseils

Un peu, mais il n'y a pas dans ce type concurrency de traitement des événements. Pas de nouveau rappel sera appelé jusqu'à ce que le code revient à la boucle d'événements. Ainsi, la chaîne de callbacks est synchrone. Il est seulement asynchrone dans la boucle d'événements.

Ceci est une mise en garde de ce type de programmation, les gestionnaires les plus exécutent rapidement et revenir à la boucle d'événements le plus tôt possible. Il ne devrait pas faire une tâche fastidieuse dans un gestionnaire.

L'utilisation d'un différé ne rend pas votre asynchrone de code.

import time
from twisted.internet import defer
from twisted.internet import reactor

def blocking(duration, deferred):
    print "start blocking"
    time.sleep(duration)
    print "finished blocking"
    deferred.callback(True)

def other_task():
    print "working..."
    reactor.callLater(1, other_task)

def finish(result):
    print "stopping reactor in 2sec"
    reactor.callLater(2, reactor.stop)

def failed(reason):
    print reason
    print "stopping reactor in 2sec"
    reactor.callLater(2, reactor.stop)

def main():
    d = defer.Deferred()
    d.addCallbacks(finish, failed)
    reactor.callLater(0, blocking, 5, d)

if __name__ == "__main__":
    reactor.callLater(0, other_task)
    main()
    reactor.run()

Si vous avez de longue date code synchrone, vous pouvez deferToThread ou diviser en itérations courtes en utilisant un coopérateur (twisted.internet.task)

Si vous voulez rendre votre code plus asynchrone avec une approche propre, puis vérifier ce cadre:

https://github.com/iogf/untwisted

Il a un code propre avec une documentation claire. La façon de traiter les modèles asynchrones est simple.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top