This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

Author terry.reedy
Recipients Ludovic.Gasc, Maxime S, gvanrossum, serhiy.storchaka, terry.reedy, yselivanov
Date 2016-07-27.00:36:20
SpamBayes Score -1.0
Marked as misclassified Yes
Message-id <1469579785.96.0.0405833241709.issue27546@psf.upfronthosting.co.za>
In-reply-to
Content
> wasting battery power ?!  We live in slightly different computing universes ;-).  But I get the point.  The last two files I uploaded use call_later and I should stick with that.  I should also add a note that the innermost asyncio loop function sleeps when there is nothing to do and that the tk updater wakes it up, if necessary, to check for gui events even when there are none.  Updater is polling rather than interrupt based.  Or in other words, it interrupts asyncio to poll tk.

I should also say that the update interval is passed in to the class so one can make an instance-specific tradeoff between overhead and responsiveness and display update frequency.  A read-only display might be updated just once a minute.

If loop.call_later(0.1, tk_update) is actually a problem on a system, then IDLE would likely be twice as bad, as it also has a busy loop in the user process, polling both the socket connection and calling tk update 20 times a second.  There are also loops in the IDLE process.


I agree on the ideal solution and on the key component, which is to sleep until there is a ready Task or file event.  _run_once does this in the select call by adjusting the timeout to the minimum time to the next ready task (possibly 0).

Tcl has such a component, with the addition of simultaneously waiting for window events -- but it only only includes file events on unix.  (It took a brave and talented group to try to reconcile the Unix and Windows models.)

Here is a simplified Python version of Tcl_DoOneEvent. http://www.tcl.tk/man/tcl8.6/TclLib/DoOneEvent.htm  

Tcl has window, file, timer, and idle events.  Window events include user key and mouse events and other from the graphics system.  The first three types all go in one ready queue. Idle events are those that affect what the user sees on the screen and go in a separate, lower-priority queue.

def do_one_event(sleep_ok):
    if ready:
        process(ready.pop())
        return True
    load_ready()
    if ready:
        process(ready.pop())
        return True
    if idle:
        for event in idle:
            process(event)
        return True
    if sleep_ok:
        sleep_until_event()  # the hard part
        load_ready()
        process(ready.pop())
        return True
    else:
        return False

def load_ready():
    # In some unspecified order
    ready.extend(get_window_events)  # graphics system
    ready.extend(get_file_events)  # select
    ready.extend(get_timer_events)  # priority queue pops

Update processes all events available without sleeping. http://www.tcl.tk/man/tcl8.6/TclCmd/update.htm
Mainloop continues (with sleeps) while there are toplevels and not stopped.

def update():
    while(do_one_event(sleep_ok=False)): pass

def mainloop():
    while toplevels and not stop:
        do_one_event()

Sleep_ok is actually a dont_sleep bit flag. DoOneEvent has other flags to select which types of event to process.  Hence

def update_idletasks()  # all currently ready
    do_one_event(dont_sleep | idletasks)

It is possible for the idle queue to get starved for attention.  Hence the existence of update_idletasks and recommendations to call it in certain situations.


It would also be possible to call (from Python, via tcl) do_one_event(dont_sleep | gui_events) IF it were known that a gui event was ready to be retrieved.  It is knowing that, without polling in a 'busy loop' that is hard to impossible.  If it were possible, an extra call to do idletasks would also be needed..

In summary, I see this as a situation where practicality beats a possibly unattainable purity.
History
Date User Action Args
2016-07-27 00:36:26terry.reedysetrecipients: + terry.reedy, gvanrossum, Ludovic.Gasc, serhiy.storchaka, yselivanov, Maxime S
2016-07-27 00:36:25terry.reedysetmessageid: <1469579785.96.0.0405833241709.issue27546@psf.upfronthosting.co.za>
2016-07-27 00:36:25terry.reedylinkissue27546 messages
2016-07-27 00:36:21terry.reedycreate