Python - Is Time.Sleep(N) Cpu Intensive

Python - is time.sleep(n) cpu intensive?

No, it isn't CPU intensive.

The documentation says:

Suspend execution for the given number of seconds.

Python can't actually guarantee that in every possible implementation, this means the OS will never schedule your process during a sleep. But on each platform, Python tries to do something appropriate to block for the specified time without using any CPU. On some platforms, that may still mean a little bit of CPU, but it's going to be as little as reasonably possible.

In particular, since you asked about linux, and presumably CPython:

On linux, and most other POSIX platforms, it will generally use select. See the 3.3 source.

The man page makes it pretty clear that select suspends until signal, timeout, or ready I/O (and in this case, there are no fds, so the latter is impossible).

You can read the kernel source for full details, but basically, unless there are any unexpected signals, you won't be scheduled at all, except possibly a tiny amount of spinning at the very start of the select (as an optimization for the cases where select can return almost immediately).


In the middle of your summary, the question changes from "is sleep CPU-intensive" to "should I use sleep, or a cron job?"

Either way, you're not burning any CPU while waiting around. There are some pros and cons, but most of them are trivial. From (roughly, and subjectively) most important to least, a cron job:

  • allows configuration—e.g., changing the schedule—without editing source code.
  • requires configuration to work.
  • means less code—meaning fewer bugs, and less for any future readers to understand.
  • will persist across system shutdown.
  • will fire again even if your script exits with an exception or a signal.
  • may fire either 0, 1 or N times if its scheduled interval is missed N times (this isn't specified, and different cron implementations do different things), instead of guaranteed 0.
  • has a better chance of handling system clock changes.
  • has to pay for process launch, interpreter startup, etc. each time it fires.
  • doesn't waste page table and process table space, because there is no process running and no memory mapped.

Is time.sleep() a CPU bound operation?

It's not. That article is misusing terminology.

A CPU-bound operation is one whose speed is limited by the speed of CPU execution, as opposed to the speed of memory access or network round trips or some other factor. time.sleep is not such an operation. A faster CPU does not make time.sleep any faster.

Does time.sleep help the processor?

TL;DR If you are polling for an event that happens once a minute, you might want to not check every nano second.

Yes, it is really true. Sleeping in a thread does reduce the CPU usage of that thread. While a thread sleeps, it hardly consumes any CPU time.

Yes, this is true for largely any language as long as the sleeping is implemented using the OS native threading API.

To think about this intuitively, let us consider a simplified version of the program from the linked question:

while end_condition_expression:
if time_based_condition_expression:
do_something()

Now, let us simplify the world, and assume that the program is the only process running on the processor.

Let us also assume, that the time based condition is true once a minute. Let us also assume that executing end_condition_expression and time_based_condition_expression costs 10 nano seconds of cpu time.

How much cpu time will this consume within a minute? Exactly one minute == 60 000 000 000 nano seconds. The cpu usage will have been 100% during the entire time. The loop will have iterated six billion times.

Now, consider this variation of the program:

while end_condition_expression:
if time_based_condition_expression:
do_something()
sleep_for_a_second()

How many times will the loop have executed within a minute? 60 iterations. How much cpu time will this consume within a minute? 60 * 10 ns = 600 ns. That is one hundred millionth of what the non-sleeping version of the program used.

In reality, there is a bit of overhead from the call to sleep, and the cpu time is shared with other processes, and a scheduler is involved, and the exact cpu usage won't exactly match my assumptions, but the idea stays the same.

Pythons' sleep() CPU usage

No, sleep() does not use CPU time in python (or in any other programming language that I've heard of). Other alternatives for achieving similar results include sched-module, twisteds LoopingCall or GLibs Timeout.

Note that any method that includes waiting for a constant amount of time (like sleep()) will in the long run drift compared to an actual timeout API (like LoopingCall or GLib Timeout) unless you keep track of how much time has passed and change the sleep length on every cycle.

How much CPU should a Python time.sleep(n) call use

1) Your sleep only gets called when there are new files.

This should be much better:

while True:
files = dict ([(f, None) for f in os.listdir(path_to_watch)])
if len(files) > 0:
print "You have %s new file/s!" % len(files)
time.sleep(20)

2) Yes, especially if using linux. Gamin would be something I'd recommend looking into.

Example:

import gamin
import time
mydir = /path/to/watch
def callback(path, event):
global mydir
try:
if event == gamin.GAMCreated:
print "New file detected: %s" % (path)
fullname = mydir + "/" + path
print "Goint to read",fullname
data = open(fullname).read()
print "Going to upload",fullname
rez = upload_file(data,path)
print "Response from uploading was",rez
except Exception,e: #Not good practice
print e
import pdb
pdb.set_trace()


mon = gamin.WatchMonitor()
mon.watch_directory(mydir, callback)
time.sleep(1)
while True:
ret = mon.handle_one_event()
mon.stop_watch(mydir)
del mon

Is using a loop to wait more CPU-intensive in python than a sleep command?

As @tobias_k mentioned in comment, try this:

import time
wakeuptime=time.time()+20 #start again exactly 20 seconds from now
UnpredictablySlowFunction()
time_left = wakeuptime -time.time()
time.sleep(time_left)

differences between time.sleep() and iterating until the seconds pass

The while True loop is called a Busy Wait [Wikipedia], because it will keep the processor running. This will probably keep 1 core at 100%.

A time.sleep() is an Idle Wait, because the processor has nothing to do. Your CPU will be at 0% if not used by something else.

And now, things will become difficult, if you want to fully understand it and it probably depends on the operating system.

  • thread scheduling in Windows happens at 1/64s, if not changed. Whatever your program does, it probably has a precision of 1/64s, because that's the interval when Windows will wake the thread up.

  • keeping the CPU busy will keep the thread priority same or even lower it.

  • keeping the CPU busy will make it warm. CPUs don't like heat and they may actually slow down or at least stop TurboBoost (or similar CPU feature)

  • keeping the CPU idle will increase the thread priority. It will use a synchronization object and call WaitForSingleObject() [MSDN] thus giving the CPU back to the operating system.

What will actually happen or which method is more precise is very hard to predict. To fully understand what happens on Windows, read the Windows Internals book [Amazon] part 1 about processes and threads.



Related Topics



Leave a reply



Submit