python response slow when running external DLL
jfong at ms4.hinet.net
jfong at ms4.hinet.net
Tue Dec 1 22:58:15 EST 2015
Peter Otten at 2015/12/1 UTC+8 7:01:55PM wrote:
> While the var_status.set() invoked from the second thread modifies some
> internal data the main thread could kick in and modify (parts of) that same
> data, thus bringing tkinter into an broken state. A simple example that
> demonstrates the problem:
>
> import random
> import threading
> import time
>
> account = 70
>
> def withdraw(delay, amount):
> global account
> if account >= amount:
> print("withdrawing", amount)
> account -= amount
> else:
> print("failed to withdraw", amount)
>
> threads = []
> for i in range(10):
> t = threading.Thread(
> target=withdraw,
> kwargs=dict(delay=.1,
> amount=random.randrange(1, 20)))
> threads.append(t)
> t.start()
>
> for t in threads:
> t.join()
It's a simple and vivid example. You must be in the banking business:-)
In this exercise, I can just use update_idletasks() method to solve the deferred display problem of tkinter, and forget all about thread. But what if I really want to use thread for the long-running DLL function in the download hander? I didn't figure out a correct way of doing it at this moment. Maybe queue is the answer but I am not familiar with it yet.
def download():
var_status.set(...) #showing a start-up message
result = SayHello() #this is a long-running function
if result.... #according to the result, display more messages
....
>
> Before every withdrawal there seems to be a check that ensures that there is
> enough money left, but when you run the script a few times you will still
> sometimes end with a negative balance. That happens when thread A finds
> enough money, then execution switches to thread B which also finds enough
> money, then both threads perform a withdrawal -- oops there wasn't enough
> money for both.
>
> >> Another complication that inevitably comes with concurrency: what if the
> >> user triggers another download while one download is already running? If
> >> you don't keep track of all downloads the message will already switch to
> >> "Download OK" while one download is still running.
> >
> > Hummm...this thought never comes to my mind. After take a quick test I
> > found, you are right, a second "download" was triggered immediately.
> > That's a shock to me. I suppose the same event shouldn't be triggered
> > again, or at least not triggered immediately, before its previous handler
> > was completed. ...I will take a check later on Borland C++ builder to see
> > how it reacts!
> >
> > Anyway to prevent this happens? if Python didn't take care it for us.
>
> A simple measure would be to disable the button until the download has
> ended.
Good! simple and work.
I shouldn't say "Python should take care of it", but "tk" should do. It's annoying the widget's command was re-triggered before it was finished. (my personal opinion:-)
More information about the Python-list
mailing list