不知道大家还记得在学校的时候体育测试时老师带的秒表吗?当枪声想起时,我们开始跑步,这时秒表启动,当我们跑过终点后,老师会按下按扭记录我们的成绩,这就是一个典型的定时器的应用。今天我们要学习的内容其实就是和这个体育测验的秒表类似的一个功能扩展,它就是 PHP 的 HRTime 扩展。
时钟节拍
首先我们要了解一下什么叫做系统的时钟节拍。当 Linux 系统启动之后,会同时启动一个时钟节拍器,以纳秒为单位进行计时,而我们的 HRTime 扩展的真实名称是 高精度时间 扩展。也就是说,它正是基于操作系统的时钟节拍器,能够以纳秒为单位进行计时。
1秒=1000毫秒=1000000微妙=1000000000纳秒,这是秒、毫秒、微秒和纳秒的关系,看出来它的精度有多高了吧。1秒等于10亿纳秒,这样我们就可以获得一个非常精确的时间间隔计数。
HRTime 扩展直接在 PECL 进行下载安装就可以了,和其他的普通扩展没有什么区别。
获取系统时钟节拍信息 Ticks
我们先来看看如何获取操作系统的时钟节拍,也就是这个 Ticks 。关于它的内容在学习操作系统的时候相信已经有不少的同学接触过了,这里我们看看使用 HRTime 扩展如何获取。
print_r(hrtime()); // Array // ( // [0] => 3758 // [1] => 407409171 // ) echo hrtime(true), PHP_EOL; // 3758407428932
hrtime() 这个函数在 PHP7 之后已经集成在默认 PHP 环境中了。它不需要 HRTime 扩展就可以使用。这个函数在没有参数的情况下返回的是一个数组,第 0 项是系统启动到现在的秒数,第 1 项就是对应的纳秒计数。如果给它的参数设置一个 true 的话,它将直接返回将秒和纳秒拼接起来的实际纳秒时间戳。
echo HRTime\PerformanceCounter::getFrequency(), PHP_EOL; // 1000000000 echo HRTime\PerformanceCounter::getTicks(), PHP_EOL; // 3758428256236 echo HRTime\PerformanceCounter::getTicksSince(1212), PHP_EOL; // 3758428257494 $a = HRTime\PerformanceCounter::getTicks(); echo HRTime\PerformanceCounter::getTicksSince($a), PHP_EOL; // 412
接下来的这三个函数就是 HRTime 扩展中的 PerformanceCounter 对象的静态函数了。PerformanceCounter 对象的意思是性能计数器,getFrequency() 表示的是计时器频率(以滴答Ticks/秒为单位),可以看出,它返回的就是纳秒单位,也就是 10亿 。getTicks() 返回的是当前的时钟节拍时间,可以看出它和 hrtime(true) 函数的结果是一样的,都是返回的系统启动后的时钟节拍时间。getTicksSince() 方法则是根据指定的纳秒数返回时间间隔,类似于 date_diff() 的感觉,其实就像我们的 time() – time() 这样的操作。通过这个方法就可以获得一段代码两次运行的时间间隔,而且是以纳秒为单位哦。
定时器功能
接下来就是我们文章的重点内容了,也就是定时器功能的实现。上面已经说过,使用 getTickSince() 其实也能做到监控一段代码的运行时间间隔,不过下面将学习到的内容将更加强大。
$c = new HRTime\StopWatch; $c->start(); for ($i = 0; $i < 1024*1024; $i++); echo 'isRunning: ', $c->isRunning(), PHP_EOL; // isRunning: 1 $c->stop(); echo 'Time NS: ', $c->getLastElapsedTime(HRTime\Unit::NANOSECOND), PHP_EOL; echo 'Time US: ', $c->getLastElapsedTime(HRTime\Unit::MICROSECOND), PHP_EOL; echo 'Time MS: ', $c->getLastElapsedTime(HRTime\Unit::MILLISECOND), PHP_EOL; echo 'Time S: ', $c->getLastElapsedTime(HRTime\Unit::SECOND), PHP_EOL; // T<em>8本文来源gao.dai.ma.com搞@代*码(网$</em><pre>搞代gaodaima码
ime NS: 6929888
// Time US: 6929.888
// Time MS: 6.929888
// Time S: 0.006929888
echo 'Ticks: ',$c->getLastElapsedTicks(), PHP_EOL;
// Ticks: 6929888
echo 'isRunning: ',$c->isRunning(), PHP_EOL;
//