略微加速

PHP官方手册 - 互联网笔记

PHP - Manual: sleep

2024-11-14

sleep

(PHP 4, PHP 5, PHP 7, PHP 8)

sleep延缓执行

说明

sleep(int $seconds): int

程序延迟执行指定的 seconds 的秒数。

参数

seconds

暂停的秒数。

返回值

成功时返回 0,错误时返回 false

如果函数的调用被一个信号中止,sleep() 会返回一个非零的值。在Windows上,该值总是 192(即Windows API常量WAIT_IO_COMPLETION的值)。其他平台上,该返回值是剩余未sleep的秒数。

错误/异常

如果指定的 seconds 是负数,该函数会产生一个 E_WARNING 级别的错误。

范例

示例 #1 sleep() 的例子

<?php

// current time
echo date('h:i:s') . "\n";

// sleep for 10 seconds
sleep(10);

// wake up !
echo date('h:i:s') . "\n";

?>

该例子会在休眠10秒后输出。

05:31:23
05:31:33

参见

add a noteadd a note

User Contributed Notes 24 notes

up
387
linus at flowingcreativity dot net
16 years ago
This may seem obvious, but I thought I would save someone from something that just confused me: you cannot use sleep() to sleep for fractions of a second. This:

<?php sleep(0.25) ?>

will not work as expected. The 0.25 is cast to an integer, so this is equivalent to sleep(0). To sleep for a quarter of a second, use:

<?php usleep(250000) ?>
up
51
ash b
8 years ago
re: "mitigating the chances of a full bruit force attack by a limit of 30 lookups a minute."

Not really - the attacker could do 100 requests. Each request might take 2 seconds but it doesn't stop the number of requests done. You need to stop processing more than one request every 2 seconds rather than delay it by 2 seconds on each execution.
up
10
Anonymous
4 years ago
Diego Andrade's msleep function is not compatible with php7's `strict_types`, cast the usleep parameter to int, and it will be,
usleep((int)($time * 1000000));
up
19
Diego Andrade
6 years ago
Maybe obvious, but this my function to delay script execution using decimals for seconds (to mimic sleep(1.5) for example):

<?php
/**
* Delays execution of the script by the given time.
* @param mixed $time Time to pause script execution. Can be expressed
* as an integer or a decimal.
* @example msleep(1.5); // delay for 1.5 seconds
* @example msleep(.1); // delay for 100 milliseconds
*/
function msleep($time)
{
   
usleep($time * 1000000);
}
?>
up
36
barlow at fhtsolutions dot com
10 years ago
You should put sleep into both the pass and fail branches, since an attacker can check whether the response is slow and use that as an indicator - cutting down the delay time. But a delay in both branches eliminates this possibility.
up
31
MPHH
18 years ago
Note: The set_time_limit() function and the configuration directive max_execution_time only affect the execution time of the script itself. Any time spent on activity that happens outside the execution of the script such as system calls using system(), the sleep() function, database queries, etc. is not included when determining the maximum time that the script has been running.
up
2
Anonymous
8 years ago
If you are having issues with sleep() and usleep() not responding as you feel they should, take a look at session_write_close()

as noted by anonymous on comments;
"If the ajax function doesn't do session_write_close(), then your outer page will appear to hang, and opening other pages in new tabs will also stall."
up
13
hartmut at six dot de
21 years ago
it is a bad idea to use sleep() for delayed output effects as

1) you have to flush() output before you sleep

2) depending on your setup flush() will not work all the way to the browser as the web server might apply buffering of its own or the browser might not render output it thinks not to be complete

netscape for example will only display complete lines and will not show table parts until the </table> tag arrived

so use sleep if you have to wait  for events and don't want to burn  to much cycles, but don't use it for silly delayed output effects!
up
0
Anonymous
9 months ago
I wrote a simple method for sleeping with a float, which also allows you to do milliseconds (via fractional seconds).

<?php
 
function sleepFloatSecs($secs) {
   
$intSecs = intval($secs);
   
$microSecs = ($secs - $intSecs) * 1000000;

    if(
$intSecs > 0) {
     
sleep($intSecs);
    }
    if(
$microSecs > 0) {
     
usleep($microSecs);
    }
  }
?>

And testing on my machine it works perfectly:

<?php
  $x
= [0.100,0.250,0.5,1.0,1.5,2.0,2.5];

  foreach(
$x as $secs) {
   
$t = microtime(true);
   
sleepFloatSecs($secs);
   
$t = microtime(true) - $t;
    echo
"$secs \t => \t $t\n";
  }
?>

Output:

<?php
  0.1    
=>    0.10017800331116
  0.25   
=>    0.25016593933105
  0.5    
=>    0.50015211105347
  1      
=>    1.0001430511475
  1.5    
=>    1.5003218650818
  2      
=>    2.000167131424
  2.5    
=>    2.5002470016479
?>
up
0
smcbride at msn dot com
1 year ago
An example of using sleep to run a set of functions at different intervals.  This is not a replacement for multi-threading, but it could help someone that wants to do something cheap.  You don't have to use eval().  It is just used as an example.  This is different than running a standard 1 second sleep loop, due to sleeping longer does not consume as much CPU.

<?php

// current time
echo date('h:i:s') . "\n";

// Some example functions
function function_a() { echo 'function_a called @ ' . date('h:i:s') . PHP_EOL; }
function
function_b() { echo 'function_b called @ ' . date('h:i:s') . PHP_EOL; }
function
function_c() { echo 'function_c called @ ' . date('h:i:s') . PHP_EOL; }

// Add some timers (in seconds) with function calls
$sleeptimers = array();
$sleeptimers['5'][0]['func'] = 'function_a();';
$sleeptimers['10'][0]['func'] = 'function_b();';
$sleeptimers['15'][0]['func'] = 'function_c();';

// Process the timers
while(true) {
   
$currenttime = time();
   
reset($sleeptimers);
   
$mintime = key($sleeptimers);
    foreach(
$sleeptimers as $SleepTime => $Jobs) {
        foreach(
$Jobs as $JobIndex => $JobDetail) {
            if(!isset(
$JobDetail['lastrun'])) {
               
$sleeptimers[$SleepTime][$JobIndex]['lastrun'] = time();
                if(
$SleepTime < $mintime) $mintime = $SleepTime;
            } elseif((
$currenttime - $JobDetail['lastrun']) >= $SleepTime) {
                eval(
$JobDetail['func']);
               
$lastrun = time();
               
$sleeptimers[$SleepTime][$JobIndex]['lastrun'] = $lastrun;
               
$mysleeptime = $SleepTime - ($currenttime - $lastrun);
                if(
$mysleeptime < 0) $mysleeptime = 0;
                if((
$currenttime - $JobDetail['lastrun']) < $mintime) $mintime = $mysleeptime// account for length of time function runs
               
echo 'Sleep time for function ' . $JobDetail['func'] . ' = ' . $mysleeptime . PHP_EOL;
            }
        }
    }
    echo
'Sleeping for ' . $mintime . ' seconds' . PHP_EOL;
   
sleep($mintime);
}

?>
up
-7
joshmeister at gmail dot com
9 years ago
Here is a simplified way to flush output to browser before completing sleep cycle.  Note the buffer must be "filled" with 4096 characters (bytes?) for ob_flush() to work before sleep() occurs.
<?php
ob_implicit_flush
(true);
$buffer = str_repeat(" ", 4096);
echo
"see this immediately.<br>";
echo
$buffer;
ob_flush();
sleep(5);
echo
"some time has passed";
?>
up
-6
jimmy at powerzone dot dk
12 years ago
Notice that sleep() delays execution for the current session, not just the script. Consider the following sample, where two computers invoke the same script from a browser, which doesn't do anything but sleep.

PC 1 [started 14:00:00]: script.php?sleep=10 // Will stop after 10 secs
PC 1 [started 14:00:03]: script.php?sleep=0 // Will stop after 7 secs

PC 2 [started 14:00:05]: script.php?sleep=0 // Will stop immediately

http://php.net/session_write_close may be used to address this problem.
up
-4
LVT
8 years ago
Always close your SQL connection and free the memory before using sleep( ) or you will be needlessly holding a SQL connection for [xx] seconds, remember that a shared hosting environment only allows max 30 SQL connections at the same time.
up
-8
Anonymous
13 years ago
This will allow you to use negative values or valuer below 1 second.

<?php slaap(0.5); ?>

<?php
function slaap($seconds)
{
   
$seconds = abs($seconds);
    if (
$seconds < 1):
      
usleep($seconds*1000000);
    else:
      
sleep($seconds);
    endif;   
}
?>
up
-13
f dot schima at ccgmbh dot de
12 years ago
Remember that sleep() means "Let PHP time to do some other stuff".
That means that sleep() can be interrupted by signals. That is important if you work with pcntl_signal() and friends.
up
-15
toddjt78 at msn dot com
12 years ago
Simple function to report the microtime since last called or the microtime since first called.

<?php
function stopWatch($total = false,$reset = true){
    global
$first_called;
    global
$last_called;
   
$now_time = microtime(true);
    if (
$last_called === null) {
       
$last_called = $now_time;
       
$first_called = $now_time;
    }
    if (
$total) {
       
$time_diff = $now_time - $first_called;
    } else {
       
$time_diff = $now_time - $last_called;
    }
    if (
$reset)
       
$last_called = $now_time;
    return
$time_diff;
}
?>

$reset  - if true, resets the last_called value to now
$total - if true, returns the time since first called otherwise returns the time since last called
up
-19
code {@} ashleyhunt [dot] co [dot] uk
10 years ago
A really simple, but effective way of majorly slowing down bruit force attacks on wrong password attempts.

In my example below, if the end-user gets the password correct, they get to log in at full speed, as expected. For every incorrect password attempt, the users response is delayed by 2 seconds each time; mitigating the chances of a full bruit force attack by a limit of 30 lookups a minute.

I hope this very simple approach will help make your web applications that little bit more secure.

Ashley

<?php
public function handle_login() {
    if(
$uid = user::check_password($_REQUEST['email'], $_REQUEST['password'])) {
        return
self::authenticate_user($uid);
    }
    else {
       
// delay failed output by 2 seconds
        // to prevent bruit force attacks
       
sleep(2);
        return
self::login_failed();
    }
}
?>
up
-6
sergio at inbep dot com dot br
6 years ago
To use float or int numbers

function pause($seconds)
{
    usleep($seconds * 1000000);
}

pause(0.25);
up
-24
soulhunter1987 at post dot ru
11 years ago
Since sleep() can be interrupted by signals i've made a function which can also be interrupted, but will continue sleeping after the signal arrived (and possibly was handled by callback). It's very useful when you write daemons and need sleep() function to work as long as you 'ordered', but have an ability to accept signals during sleeping.

<?php
function my_sleep($seconds)
{
   
$start = microtime(true);
    for (
$i = 1; $i <= $seconds; $i ++) {
        @
time_sleep_until($start + $i);
    }
}
?>
up
-13
LVT
8 years ago
Another reason for not to abuse sleep( ) is that along with the maximum of 30 sql connections, a shared hosting environment usually limits the number of processes to 20, if your website has many users online and you put sleep( ) everywhere in the code, your server will throw a 508 error (resource limit reached) and will stop serving your website.
up
-28
webseos at gmail dot com
13 years ago
This is a critical thing to use time delay function as sleep() Because a beginner can find that this is not working and he/she will see that all output appearing at a time.

A good way to implement this is by using the function -  ob_implicit_flush() then you don't need to use flush() function explicitly.

A sample code :
<?php
ob_implicit_flush
(true);
for(
$i=0;$i<5;$i++)
{
$dis=<<<DIS
<div style="width:200px; background-color:lime;border:1px; text-align:center;text-decoration:blink;">
$i
</div>
DIS;
echo
$dis;

sleep(5);
//flush();
}
up
-40
mohd at Bahrain dot Bz
12 years ago
I hope this code will help somebody to solve the problem of not being able to flush or output the buffer to the browser (I use IE7).
It may work for you with just [ echo str_repeat(".", 4096); ] and without even using ob_... and flush.

<?php
ob_start
();

ob_implicit_flush(true);
//[ OR ] echo "..."; ob_flush(); flush();

set_time_limit(0);

function
sleep_echo($secs) {
   
$secs = (int) $secs;
   
$buffer = str_repeat(".", 4096);
   
//echo $buffer."\r\n<br />\r\n";
   
for ($i=0; $i<$secs; $i++) {
        echo
date("H:i:s", time())." (".($i+1).")"."\r\n<br />\r\n".$buffer."\r\n<br />\r\n";
       
ob_flush();
       
flush();
       
sleep(1);
       
//usleep(1000000);
   
}
}

sleep_echo(30);

ob_end_flush();
?>
up
-52
marpetr at gmail dot com
14 years ago
Very useful to prevent password brute forcing! Simply add few seconds timeout to login script and the probability to guess the password decreases a lot!
up
-1
manu7772 at gmail dot com
1 year ago
Sleep method with parameter in milliseconds :

public static function ms_sleep($milliseconds = 0) {
    if($milliseconds > 0) {
        $test = $milliseconds / 1000;
        $seconds = floor($test);
        $micro = round(($test - $seconds) * 1000000);
        if($seconds > 0) sleep($seconds);
        if($micro > 0) usleep($micro);
    }
}

官方地址:https://www.php.net/manual/en/function.sleep.php

北京半月雨文化科技有限公司.版权所有 京ICP备12026184号-3