Python Forum

Full Version: Assistance with running a few lines of code at an EXACT time
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
I'm not sure if this is the correct area, so I apologize, anyways, I'm new to learning python, for the past 2 days I've been looking for an answer to this. I want to add code that can make it so it pauses the script (not ending it) and then at an exact time it will run the few lines below it. Such as if I wanted it to pause it until 10:40 pm, I need it to be accurate to the very millisecond. Example: 2021 2 21 22 40 00 00 Year month day hour minute(s) second(s) millisecond(s)

The closest code to it that I got didn't do it accurately and most of the time had a second or more delay.
---The code
import sched
import time as time_module
def myfunc(): print("test123")

scheduler = sched.scheduler(time_module.time, time_module.sleep)
t = time_module.strptime('2021-02-21 22:25:14', '%Y-%m-%d %H:%M:%S')
t = time_module.mktime(t)
scheduler_e = scheduler.enterabs(t, 1, myfunc, ())
scheduler.run()
---
I put the rest of my code here.
I'm not sure if this is the correct area, so I apologize, anyways, I'm new to learning python, for the past 2 days I've been looking for an answer to this. I want to add code that can make it so it pauses the script (not ending it) and then at an exact time it will run the few lines below it. Such as if I wanted it to pause it until 10:40 pm, I need it to be accurate to the very millisecond. Example: 2021 2 21 22 40 00 00 Year month day hour minute(s) second(s) millisecond(s)

The closest code to it that I got didn't do it accurately and most of the time had a second or more delay.
---The code
import sched
import time as time_module
def myfunc(): print("test123")

scheduler = sched.scheduler(time_module.time, time_module.sleep)
t = time_module.strptime('2021-02-21 22:25:14', '%Y-%m-%d %H:%M:%S')
t = time_module.mktime(t)
scheduler_e = scheduler.enterabs(t, 1, myfunc, ())
scheduler.run()
---
I put the rest of my code here.
Some machines/operating systems may not schedule your process every millisecond (especially under load). So anything you do in python is dependent on the OS running your program "quickly" enough. (time.time_ns() is preferred over time.time())

But what I'd probably do to get fairly accurate while not spinning on a CPU constantly is to sleep() until a few seconds prior to the time you want. Then calculate what the target time will be in epoch time and spin in a loop until it passes.
You can expect the time to be accurate if you synchronize with some atomic clock (with some time server) BUT there might be a delay of 0.02 to 0.1 second if you are unlucky. The delay depends on network activities and scheduled computer activities with high priority. Even if you use ns precision these delays can't be calculated by any means. The method that @bowlofred suggests is OK but even sleep(n) is to be considered "sleep at least for n seconds". There might be an unlucky high priority activity scheduled at that precise moment. I wouldn't expect a higher precision than 0.1 sec.
Out of curiosity, what are you doing that is so time sensitive?
If you're not using a real-time operating system, then no language can guarantee it'll be running at a specific time. Normally (99% of the time), being "close enough" is fine. But those times you really do need extremely specific timing without any delays, it's incredibly important, like for pacemakers (offset a heart beat a bit, and you might be killing someone).

So first, you should define how important it actually is to be that accurate. If it truly is that important, you probably shouldn't be using python at all.

But if it isn't critical, time.sleep() is fine:
import time

# 1 min = 60 sec
# 1 sec = 1e9 ns
delay_for = 60 * 1e9
print("Starting...")
delay_until = time.time_ns() + delay_for
while delay_until > time.time_ns():
    time.sleep((delay_until - time.time_ns()) / 1e9)
print("1 minute(ish) has passed")