time — функции, связанные со временем¶
Модуль time предоставляет функции для получения текущего времени и даты, измерения временных интервалов и создания задержек.
Эпоха времени: OpenMV Cam на базе Alif и i.MX RT используют эпоху POSIX 1970-01-01 00:00:00 UTC. OpenMV Cam на базе STM32 используют эпоху 2000-01-01 00:00:00 UTC. Год эпохи можно определить во время выполнения с помощью gmtime(0)[0].
Поддержание актуальной календарной даты/времени: для этого требуются часы реального времени (RTC). На OpenMV Cam системное время предоставляется объектом machine.RTC. Текущее календарное время можно установить с помощью machine.RTC().datetime(tuple), и оно поддерживается одним из следующих способов:
Резервная батарея (необязательный компонент на некоторых OpenMV Cam).
Сетевой протокол времени, например
ntptime(требует сетевого подключения).Ручная установка при каждом включении питания. RTC затем обычно поддерживается при программных сбросах, но теряется при отключении питания, если не установлена резервная батарея.
Если календарное время не поддерживается, приведённые ниже функции, обращающиеся к текущему абсолютному времени, не будут работать должным образом.
Функции¶
- time.gmtime(secs: int | None = None) Tuple[int, int, int, int, int, int, int, int]¶
- time.localtime(secs: int | None = None) Tuple[int, int, int, int, int, int, int, int]¶
Преобразует время secs, выраженное в секундах с начала эпохи (см. выше), в 8-элементный кортеж, содержащий:
(year, month, mday, hour, minute, second, weekday, yearday)Если secs не задано или равно None, то используется текущее время из RTC.Функция
gmtime()возвращает кортеж даты-времени в UTC, аlocaltime()возвращает кортеж даты-времени в локальном времени.Формат элементов 8-элементного кортежа следующий:
year включает столетие (например, 2014).
month от 1 до 12
mday от 1 до 31
hour от 0 до 23
minute от 0 до 59
second от 0 до 59
weekday от 0 до 6 для Пн-Вс
yearday от 1 до 366
- time.mktime(date_time_tuple: Tuple[int, int, int, int, int, int, int, int]) int¶
Это обратная функция к localtime. Её аргумент — полный 8-элементный кортеж, выражающий время согласно localtime. Она возвращает целое число, равное количеству секунд с начала эпохи времени.
- time.sleep(seconds: float) None¶
Приостанавливает выполнение на заданное количество секунд. seconds может быть числом с плавающей точкой для приостановки на дробное число секунд. Для более точных или целочисленных задержек используйте функции
sleep_ms()иsleep_us().Вызов
sleep(), включаяsleep(0), гарантированно вызывает ожидающие функции обратного вызова.
- time.sleep_ms(ms: int) None¶
Задержка на заданное количество миллисекунд, должна быть положительной или равной 0.
Эта функция создаёт задержку как минимум на заданное количество миллисекунд, но может занять больше времени, если требуется выполнить другую обработку, например обработчики прерываний или другие потоки. Передача 0 в ms всё равно позволит выполниться этой другой обработке. Для более точных задержек используйте
sleep_us().Вызов
sleep_ms(), включаяsleep_ms(0), гарантированно вызывает ожидающие функции обратного вызова.
- time.sleep_us(us: int) None¶
Задержка на заданное количество микросекунд, должна быть положительной или равной 0.
Эта функция пытается обеспечить точную задержку как минимум на us микросекунд, но может занять больше времени, если у системы есть другая обработка с более высоким приоритетом.
- time.ticks_ms() int¶
Возвращает возрастающий счётчик миллисекунд с произвольной точкой отсчёта, который переполняется после некоторого значения.
Значение, при котором происходит переполнение, явно не раскрывается, но для упрощения обсуждения мы будем называть его TICKS_MAX. Период значений равен TICKS_PERIOD = TICKS_MAX + 1. TICKS_PERIOD гарантированно является степенью двойки, но в остальном может отличаться от порта к порту. Одно и то же значение периода используется для всех функций
ticks_ms(),ticks_us(),ticks_cpu()(для простоты). Таким образом, эти функции возвращают значение в диапазоне [0 .. TICKS_MAX] включительно, всего TICKS_PERIOD значений. Обратите внимание, что используются только неотрицательные значения. По большей части следует рассматривать значения, возвращаемые этими функциями, как непрозрачные. Единственными доступными для них операциями являются функцииticks_diff()иticks_add(), описанные ниже.Примечание: выполнение стандартных математических операций (+, -) или операторов сравнения (<, <=, >, >=) непосредственно над этими значениями приведёт к неверному результату. Выполнение математических операций с последующей передачей их результатов в качестве аргументов в
ticks_diff()илиticks_add()также приведёт к неверным результатам этих функций.
- time.ticks_us() int¶
Как и
ticks_ms()выше, но в микросекундах.
- time.ticks_cpu() int¶
Аналогично
ticks_ms()иticks_us(), но с максимально возможным в системе разрешением. Обычно это такты процессора, поэтому функция так и названа. Но это не обязательно должны быть такты процессора, вместо этого может использоваться другой доступный в системе источник времени (например, высокоточный таймер). Точная единица измерения времени (разрешение) этой функции не определена на уровне модуляtime, но документация для конкретного порта может предоставить более конкретную информацию. Эта функция предназначена для очень точного бенчмаркинга или очень плотных циклов реального времени. Избегайте её использования в переносимом коде. Она доступна на всех OpenMV Cam.
- time.ticks_add(ticks: int, delta: int) int¶
Смещает значение тиков на заданное число, которое может быть как положительным, так и отрицательным. Имея значение ticks, эта функция позволяет вычислить значение тиков на delta тиков до или после него, следуя определению значений тиков в модульной арифметике (см.
ticks_ms()выше). Параметр ticks должен быть прямым результатом вызова функцийticks_ms(),ticks_us()илиticks_cpu()(или предыдущего вызоваticks_add()). Однако delta может быть произвольным целым числом или числовым выражением.ticks_add()полезна для вычисления крайних сроков для событий/задач. (Примечание: для работы с крайними сроками необходимо использовать функциюticks_diff().)Примеры:
# Find out what ticks value there was 100ms ago print(ticks_add(time.ticks_ms(), -100)) # Calculate deadline for operation and test for it deadline = ticks_add(time.ticks_ms(), 200) while ticks_diff(deadline, time.ticks_ms()) > 0: do_a_little_of_something() # Find out TICKS_MAX used by this port print(ticks_add(0, -1))
- time.ticks_diff(ticks1: int, ticks2: int) int¶
Измеряет разницу тиков между значениями, возвращёнными функциями
ticks_ms(),ticks_us()илиticks_cpu(), в виде знакового значения, которое может переполняться.Порядок аргументов такой же, как у оператора вычитания:
ticks_diff(ticks1, ticks2)имеет то же значение, что иticks1 - ticks2. Однако значения, возвращаемые функциямиticks_ms()и т. д., могут переполняться, поэтому прямое использование вычитания над ними даст неверный результат. Именно поэтому нужнаticks_diff()— она реализует модульную (или, более конкретно, кольцевую) арифметику для получения правильного результата даже для переполняющихся значений (при условии, что они не слишком далеки друг от друга, см. ниже). Функция возвращает знаковое значение в диапазоне [-TICKS_PERIOD/2 .. TICKS_PERIOD/2-1] (это типичное определение диапазона для знаковых двоичных целых чисел в дополнительном коде). Если результат отрицательный, это означает, что ticks1 произошёл раньше во времени, чем ticks2. В противном случае это означает, что ticks1 произошёл после ticks2. Это справедливо только в том случае, если ticks1 и ticks2 отстоят друг от друга не более чем на TICKS_PERIOD/2-1 тиков. Если это не выполняется, будет возвращён неверный результат. В частности, если два значения тиков отстоят на TICKS_PERIOD/2-1 тиков, именно это значение будет возвращено функцией. Однако если между ними прошло TICKS_PERIOD/2 тиков реального времени, функция вернёт -TICKS_PERIOD/2, то есть результирующее значение переполнится в отрицательный диапазон возможных значений.Неформальное обоснование приведённых выше ограничений: предположим, вы заперты в комнате без средств отслеживания течения времени, кроме стандартных часов с 12 делениями. Тогда, если вы посмотрите на циферблат сейчас и не будете смотреть снова в течение следующих 13 часов (например, если уснёте надолго), то, когда вы наконец взглянете снова, вам может показаться, что прошёл лишь 1 час. Чтобы избежать этой ошибки, просто смотрите на часы регулярно. Ваше приложение должно поступать так же. Метафора «слишком долгого сна» также напрямую отображается на поведение приложения: не позволяйте вашему приложению выполнять какую-либо одну задачу слишком долго. Выполняйте задачи по шагам и отслеживайте время в промежутках.
ticks_diff()разработана для поддержки различных шаблонов использования, среди которых:Опрос с тайм-аутом. В этом случае порядок событий известен, и вы будете иметь дело только с положительными результатами
ticks_diff():# Wait for GPIO pin to be asserted, but at most 500us start = time.ticks_us() while pin.value() == 0: if time.ticks_diff(time.ticks_us(), start) > 500: raise TimeoutError
Планирование событий. В этом случае результат
ticks_diff()может быть отрицательным, если событие просрочено:# This code snippet is not optimized now = time.ticks_ms() scheduled_time = task.scheduled_time() if ticks_diff(scheduled_time, now) > 0: print("Too early, let's nap") sleep_ms(ticks_diff(scheduled_time, now)) task.run() elif ticks_diff(scheduled_time, now) == 0: print("Right at time!") task.run() elif ticks_diff(scheduled_time, now) < 0: print("Oops, running late, tell task to run faster!") task.run(run_faster=true)
Примечание: не передавайте значения
time()вticks_diff(), для них следует использовать обычные математические операции. Но учтите, чтоtime()также может (и будет) переполняться. Это известно как https://en.wikipedia.org/wiki/Year_2038_problem .
- time.time() int¶
Возвращает количество секунд в виде целого числа с начала эпохи, предполагая, что базовый RTC установлен и поддерживается, как описано выше. Если RTC не установлен, эта функция возвращает количество секунд с момента специфичной для порта точки отсчёта времени (для встраиваемых плат без RTC с резервным питанием от батареи — обычно с момента включения питания или сброса). Если вы хотите разрабатывать переносимое приложение MicroPython, вам не следует полагаться на эту функцию для обеспечения точности выше одной секунды. Если вам нужна более высокая точность, абсолютные временные метки, используйте
time_ns(). Если приемлемо относительное время, используйте функцииticks_ms()иticks_us(). Если вам нужно календарное время, лучшим выбором будетgmtime()илиlocaltime()без аргумента.Отличие от CPython
В CPython эта функция возвращает количество секунд с начала эпохи Unix (1970-01-01 00:00 UTC) в виде значения с плавающей точкой, обычно с микросекундной точностью. На OpenMV Cam она возвращает целое число с точностью до одной секунды — оборудование не может одновременно представить и большой диапазон времени, и субсекундную точность в числе с плавающей точкой — и эпоха различается в зависимости от платы (см. Эпоху времени выше). Без RTC с резервным питанием от батареи, который был установлен, вместо этого она ведёт отсчёт секунд с момента включения питания/сброса.
Конструкторы¶
- class time.clock¶
Возвращает объект часов.
Методы¶
- fps() float¶
Прекращает отслеживание прошедшего времени и возвращает текущее значение FPS (кадров в секунду).
Всегда вызывайте
tickперед вызовом этой функции.