简体   繁体   中英

Execute Function Every X Seconds On Class Init

I have created a jabberbot class that I would like to broadcast scheduled messages. I don't have much experience with threads (in any language) but I am having an especially hard time grasping the concept with python.

My lattest attempt was using threading.timer something like this:

class myBot(JabberBot):
     def __init__( self, jid, password, res = none):
         autoNotify()

      def autoNotify():
           #Send timed message
           self.send('someuser@jabber.example.com','cooool message text!')
           #set/reset timer
           t = Timer(05,self.autoNotify)
           t.start()

The problem with this is that it continuously spawns new threads until it eventually dies. I've read numerous examples on SO using third party libraries, messaging queues, and twisted, but my question is simply this - Is there really no easy way to spawn a single asynchronous thread?

Yes, there is .

However, you should really not spawn a thread in a constructor. Instead, provide a run method and inherit from threading.Thread , this will make a public start method available that can be used to start the notification loop. Something like this:

import threading
import time

class myBot(JabberBot, threading.Thread):
  def __init__( self, jid, password, res = none):
    threading.Thread.__init__(self)

  def run(self):
    while True:
      self.autoNotify()
      time.sleep(5) # wait 4 seconds

  def autoNotify(self):
    self.send('someuser@jabber.example.com','cooool message text!')

Use like this:

 myBot(...).start()

If you can't or don't want to use multiple inheritance for some reason, you can also do something like this:

class myBot(JabberBot):
  def start(self):
    threading.Thread(target=self.autoNotifyLoop).start()

  def autoNotifyLoop(self):
    while True:
      self.autoNotify()
      time.sleep(5) # wait 4 seconds

  def autoNotify(self):
    self.send('someuser@jabber.example.com','cooool message text!')

You can also create a function for that, for maximum "convenience":

def call_async(func, *args, **kw):
  threading.Thread(target=func, args=args, kwargs=kw).start()

def do_something(msg):
  print msg

call_async(do_something, "Don't overuse threads!")

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM