time_sleep_until
(PHP 5 >= 5.1.0, PHP 7)
time_sleep_until — Откладывает исполнение скрипта до заданного времени
Описание
$timestamp
)
Откладывает исполнение скрипта до заданной отметки времени, указанной в
параметре timestamp
.
Список параметров
-
timestamp
-
Отметка времени продолжения исполнения скрипта.
Возвращаемые значения
Возвращает TRUE
в случае успешного завершения или FALSE
в случае возникновения ошибки.
Список изменений
Версия | Описание |
---|---|
5.3.0 | Эта функция теперь доступна на Windows платформах. |
Ошибки
Если указанная временная отметка timestamp
просрочена,
то функция создаст исключение уровня E_WARNING
.
Примеры
Пример #1 Пример использования time_sleep_until()
<?php
//возвращает false и выводит предупреждение
var_dump(time_sleep_until(time()-1));
// может работать только на быстродействующих компьютерах, выполнение отложено до 0.2 секунд
var_dump(time_sleep_until(microtime(true)+0.2));
?>
Примечания
Замечание: Все сигналы будут доставлены после продолжения исполнения скрипта.
Смотрите также
- sleep() - Откладывает выполнение
- usleep() - Откладывает выполнение на микросекунды
- time_nanosleep() - Откладывает исполнение на заданное число секунд и наносекунд
- set_time_limit() - Ограничение времени выполнения скрипта
Коментарии
At least on my Windows machine, the time_sleep_until function appears to calculate the number of microseconds between now and the sleep-until timestamp, and it appears to use unsigned 32-bit math in this calculation. This roundoff leads to a maximum sleep time of just under 4295 seconds (1 hour, 11 minutes, 35 seconds). To get longer sleep times, while still using time_sleep_until to minimize processor overhead, the following loop may be some help to you:
<?php
$sleepuntil = strtotime("tuesday 3pm");
while (time() < $sleepuntil)
time_sleep_until($sleepuntil);
// proceed with dated processing
?>
Of course, one could use something like "cron" instead, to avoid the script doing the extended sleep. Also note that time_nanosleep appears to do similar math, but it is somewhat more intuitive that the seconds parameter has an upper limit on what it can be. Still, both functions might report a warning when waking up prematurely due to roundoff.
Not realising that this function existed, I wrote something similar, but it has the additional facility to specify a minimum pause even if the target time has already been reached, for instance in a processor-intensive loop.
It's in seconds rather than microseconds (it's intended for heavy-duty CLI scripts), but that could easily be changed by using microtime(true) and usleep if greater granularity was required.
<?php
/**
* Pause processing until the specified time, to avoid hammering a DB or service
*
* @param int $target_time Timestamp
* @param int $min_sleep Always sleep for a minimum number of seconds,
* even if the target timestamp has already passed.
* Default 0, meaning only sleep until the target timestamp is reached.
*
* @example <code>
while ( ! $finished )
{
$minimum_start_of_next_loop = time() + $min_secs_per_loop;
# DO STUFF THAT MAY OR MAY NOT TAKE VERY LONG
sleep_until( $minimum_start_of_next_loop, $min_pause_between_loops );
}
</code>
*/
function sleep_until($target_time, $min_sleep = 0)
{
$time_now = time();
$time_to_target = $target_time - $time_now;
// If we've already reached the target time, that's fine
if ( $time_to_target <= $min_sleep )
{
// If required, sleep for a bit anyway
sleep( $min_sleep );
}
else
{
// Sleep for the number of seconds until the target time
sleep( $time_to_target );
}
}
?>
if you for some reason need a constant-time implementation of realpath(), try
<?php
function realpath_constant_time(string $path, float $target_seconds, bool &$constant_time_success = null){
$start_time=microtime(true);
$ret=realpath($path);
$constant_time_success = @time_sleep_until($start_time+$target_seconds);
return $ret;
}
?>
for example, a realtime that always uses exactly 1 millisecond (should be more than enough for SSD-based servers, perhaps rotating harddrive based servers may need something closer to 10 milliseconds, i don't know):
<?php
realpath_constant_time("/path/to/../to/file.txt",0.001,$constant_time_success);
?>
and you can use $constant_time_success to see if you needed more time (and thus failed to do realpath() in constant-time), or if you succeeded.