定时器实现延时处理

Posted 王大西

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了定时器实现延时处理相关的知识,希望对你有一定的参考价值。

<?php
/**
 * 定时器
 * User: wangdaxi
 * Date: 2018/3/2
 * Time: 上午10:53
 */
set_time_limit(0);
Newretail_Timer::run();
while(true) {
    pcntl_signal_dispatch();
}

class Newretail_Timer
{
    /**
     * @var array 任务数组
     */
    //可以把任务存储到redis里
    public static $task = [
        1 => [
            ‘uid‘ => 695,
            ‘uname‘ => ‘王大西‘
        ],
        3 => [
            ‘uid‘ => 698,
            ‘uname‘ => ‘王3西‘
        ],
        6 => [
            ‘uid‘ => 699,
            ‘uname‘ => ‘王6西‘
        ],
        9 => [
            ‘uid‘ => 700,
            ‘uname‘ => ‘王9西‘
        ],
    ];

    /**
     * @var int 环形队列的当前指针
     */
    public static $currentIndex = 0;

    /**
     * @var int 定时间隔
     */
    public static $time = 1;

    /**
     * @var string 任务记录
     */
    public static $taskRecord = ‘‘;

    /**
     * 开启服务
     * @param null $time
     */
    public static function run($time = null)
    {
        if (!is_null($time)) {
            self::$time = intval($time);
        }

        self::registerHandler();

        pcntl_alarm(self::$time);
    }

    /**
     * 注册信号处理函数
     */
    public static function registerHandler()
    {
        pcntl_signal(SIGALRM, [‘Newretail_Timer‘, ‘signalHandler‘]);
    }


    /**
     * 信号处理函数
     */
    public static function signalHandler()
    {
        //接收到信号,代表环指针移动一次
        self::$currentIndex++;
        if (self::$currentIndex > 59) {
            self::$currentIndex = 0;
        }

        self::task();

        //一次信号事件执行完成后,再触发下一次
        pcntl_alarm(self::$time);
    }

    /**
     * 执行任务处理
     */
    public static function task()
    {


        if (empty(self::$task)) {
            return false;
        }


        foreach (self::$task as $index => $arr) {
            if ($index != self::$currentIndex) {
                continue;
            }

            //执行当前任务
             $strRecord = sprintf(
                    "当前时间[%s],当前索引为[%s],用户信息为uid[%s],uname[%s]\n",
                    date("Y-m-d H:i:s"),
                    $index,
                    $arr[‘uid‘],
                    $arr[‘uname‘]
                );
            echo $strRecord;

            self::recordTask($strRecord);

            //不删除当前任务
            //unset(self::$task[self::$currentIndex]);
        }
    }

    public static function recordTask($strRecord = "")
    {
        if (empty($strRecord)) {
            return false;
        }
        $fp = fopen("/tmp/recordtask", "a");
        fwrite($fp, $strRecord);
        fclose($fp);
        return true;
    }
}

 

以上是关于定时器实现延时处理的主要内容,如果未能解决你的问题,请参考以下文章

怎么用定时器写延时函数

IOS开发定时器延时的探究

单片机中用写delay函数做延时和用定时器做延时有啥区别?

使用系统定时器SysTick实现精确延时微秒和毫秒函数

节流和防抖的实现

基于RabbitMQ实现分布式延时任务调度