From: php at richardneill dot org Operating system: Linux PHP version: 6CVS-2009-07-07 (CVS) PHP Bug Type: Performance problem Bug description: strtotime() seems surprisingly slow (3x worse than preg_match).
Description: ------------ I've just been troubleshooting a script whose job is to fix logfiles. Each line of the logfile has a timestamp, but only HH:MM:SS and it's missing the date. My script has to fix this. For a 500,000 line file, this takes about 2 minutes, so I investigated further. I found that strtotime() was really quite a lot slower than I expected, and that using preg_match() instead doubled the script execution speed. Is this really to be expected, or could strtotime() be optimised? Reproduce code: --------------- #!/usr/bin/php <? //This demonstrates that strtotime() is really rather slow. The //example is quite contrived, but surely it should be possible to //make strtotime() much faster than an entire regular-expression //match, rather than 3 times slower? $time1=microtime(1); $timestamp1="05:03:02"; $timestamp2="03:05:07"; for ($i=0;$i<1E6;$i++){ $seconds = strtotime($timestamp1) - strtotime($timestamp2); #echo "$seconds\n"; //Do something with $seconds } $time2=microtime(1); for ($i=0;$i<1E6;$i++){ //preg_match lets us both check that this IS a valid //timestamp and split it into parts. preg_match('/^(\d\d):(\d\d):(\d\d)(\.\d+)?$/', $timestamp1, $matches1); preg_match('/^(\d\d):(\d\d):(\d\d)(\.\d+)?$/', $timestamp2, $matches2); $seconds = ( 3600 * intval($matches1[1]) + 60 * intval($matches1[2]) + intval($matches1[3]) ) - ( 3600 * intval($matches2[1]) + 60 * intval($matches2[2]) + intval($matches2[3]) ); #echo "$seconds\n"; //Do something with $seconds } $time3=microtime(1); # 42.8 on 2.4GHz CPU echo "Each pair of calls to strtotime() took:".($time2 - $time1 )." microseconds \n"; # 16.6. echo "Each pair of calls to preg_match() etc took:".($time3 - $time2 )." microseconds \n"; ?> Expected result: ---------------- I expect strtotime(), which is designed specifically for the purpose, to be faster than preg_match, which is more general-purpose. Actual result: -------------- strtotime() takes about 3 x longer than the brute-force approach using a regular-expression + array maths. Is that really expected? date() isn't very fast either. 42us means 100,000 CPU cycles! -- Edit bug report at http://bugs.php.net/?id=48828&edit=1 -- Try a CVS snapshot (PHP 5.2): http://bugs.php.net/fix.php?id=48828&r=trysnapshot52 Try a CVS snapshot (PHP 5.3): http://bugs.php.net/fix.php?id=48828&r=trysnapshot53 Try a CVS snapshot (PHP 6.0): http://bugs.php.net/fix.php?id=48828&r=trysnapshot60 Fixed in CVS: http://bugs.php.net/fix.php?id=48828&r=fixedcvs Fixed in CVS and need be documented: http://bugs.php.net/fix.php?id=48828&r=needdocs Fixed in release: http://bugs.php.net/fix.php?id=48828&r=alreadyfixed Need backtrace: http://bugs.php.net/fix.php?id=48828&r=needtrace Need Reproduce Script: http://bugs.php.net/fix.php?id=48828&r=needscript Try newer version: http://bugs.php.net/fix.php?id=48828&r=oldversion Not developer issue: http://bugs.php.net/fix.php?id=48828&r=support Expected behavior: http://bugs.php.net/fix.php?id=48828&r=notwrong Not enough info: http://bugs.php.net/fix.php?id=48828&r=notenoughinfo Submitted twice: http://bugs.php.net/fix.php?id=48828&r=submittedtwice register_globals: http://bugs.php.net/fix.php?id=48828&r=globals PHP 4 support discontinued: http://bugs.php.net/fix.php?id=48828&r=php4 Daylight Savings: http://bugs.php.net/fix.php?id=48828&r=dst IIS Stability: http://bugs.php.net/fix.php?id=48828&r=isapi Install GNU Sed: http://bugs.php.net/fix.php?id=48828&r=gnused Floating point limitations: http://bugs.php.net/fix.php?id=48828&r=float No Zend Extensions: http://bugs.php.net/fix.php?id=48828&r=nozend MySQL Configuration Error: http://bugs.php.net/fix.php?id=48828&r=mysqlcfg