PHP进程通信基础之信号


Posted in PHP onFebruary 19, 2017

使用信号通信。可以使用kill -l 来查看当前系统的信号类型。
每个信号所代表的的详细含义,请查看我的这篇文章:https://3water.com/article/106040.htm
使用信号的时候可以通过php --version 来查看当前PHP的版本。已决定使用哪种方式来进行进程间的信号通信。

[root@roverliang ipc]# php --version

PHP 5.6.24 (cli) (built: Aug 15 2016 19:14:02)
Copyright (c) 1997-2016 The PHP Group
Zend Engine v2.6.0, Copyright (c) 1998-2016 Zend Technologies

使用pcntl_signal_dispatch 函数 需要PHP 版本(PHP 5 >= 5.3.0, PHP 7)

如果PHP版本小于5.3.一些大公司可能会低于这个版本。这个时候会使用 declare(ticks=1),意思为每执行一条低级指令,
就会去检测是否出现该信号。详细的介绍可以查看 https://3water.com/article/48340.htm

官网解释如下:Tick(时钟周期)是一个在 declare 代码段中解释器每执行 N 条可计时的低级语句就会发生的事件。N 的值是在 declare 中的 directive 部分用 ticks=N 来指定的。

那么什么是低级语句呢:如下代码所示:

for ($i = 0; $i < 3; $i++) {
    echo $i.PHP_EOL;
  }

那么这个for 循环中就含有三条低级指令。每输出一条$i。就会去检测下是否发生了已注册的事件,可想而知,这样效率是比较低的。所以如果检测到自己的PHP大于等于5.3 。就使用pcntl_singal_dispath 来进行信号派送。

主进程在启动的时候注册一些信号处理函数。

/**
 * @param $signal 信号
 */
function signalHandal($signal)
{
  switch ($signal) {
    case SIGINT:
      //do something
      break;
    case SIGHUP:
      //do something
      break;
    default :
      //do something
      break;
  }
}

然后将信号处理器与信号处理函数绑定:

//根据不同的信号,安装不同的信号处理器
pcntl_signal(SIGINT, 'signalHandal');
pcntl_signal(SIGHUP, 'signalHandal');
pcntl_signal(SIGUSR1, 'signalHandla');

在子进程监听信号,如果出现该信号,就调用预安装的信号处理函数

//分配信号。
pcntl_signal_dispatch($signal);

我们来整理下思路:
1、定义信号发生所需要处理事件的函数
2、将信号和信号处理函数绑定,称为信号安装。
3、信号监听或者分发,出现信号调用已安装的信号。

理解好上面的信号概念,我们来看一个demo:

<?php
$parentpid = posix_getpid();
echo "parent progress pid:{$parentpid}\n";

//定义一个信号处理函数

function sighandler($signal) {
  if ($signal == SIGINT) {
    $pid = getmypid();
    exit("{$pid} process, Killed!".PHP_EOL);
  }
}

//php version < 5.3 .每执行一条低级指令,就检查一次是否出现该信号。效率损耗很大。
//declare(ticks=1);
$child_list = [];
//注册一个信号处理器。当发出该信号的时候对调用已定义的函数
pcntl_signal(SIGINT, 'sighandler');



for($i = 0; $i < 3; $i++) {
  $pid = pcntl_fork();
  if ($pid == 0) {
    //子进程
    while (true) {
      //调用已安装的信号信号处理器,为了检测是否有新的信号等待dispatching
      pcntl_signal_dispatch();
      echo "I am child: ".getmypid(). " and i am running !".PHP_EOL;
      sleep(rand(1,3));
    }
  } elseif($pid > 0) {
    $child_list[] = $pid;
  } else {
    die('fork fail!'.PHP_EOL);
  }
}

sleep(5);
foreach ($child_list as $key => $pid) {
  posix_kill($pid, SIGINT);
}

sleep(2);
echo "{$parentpid} parent is end".PHP_EOL;
PHP 相关文章推荐
php中删除字符串中最先出现某个字符的实现代码
Feb 03 PHP
php批量上传的实现代码
Jun 09 PHP
深入解析PHP的引用计数机制
Jun 14 PHP
php 删除目录下N分钟前创建的所有文件的实现代码
Aug 10 PHP
PHP中round()函数对浮点数进行四舍五入的方法
Nov 19 PHP
yiic命令时提示“php.exe”不是内部或外部命令的解决方法
Dec 18 PHP
PHP 的Opcache加速的使用方法
Dec 29 PHP
PHP实现打包zip并下载功能
Jun 12 PHP
PHP数字金额转换成中文大写显示
Jan 05 PHP
PHP添加PNG图片背景透明水印操作类定义与用法示例
Mar 12 PHP
为你的 Laravel 验证器加上多验证场景的实现
Apr 07 PHP
THINKPHP5.1 Config的配置与获取详解
Jun 08 PHP
PHP 信号管理知识整理汇总
Feb 19 #PHP
php 三大特点:封装,继承,多态
Feb 19 #PHP
PHP实现大数(浮点数)取余的方法
Feb 18 #PHP
Zend Framework基于Command命令行建立ZF项目的方法
Feb 18 #PHP
完美解决php 导出excle的.csv格式的数据时乱码问题
Feb 18 #PHP
Zend Framework数据库操作技巧总结
Feb 18 #PHP
php基于ob_start(ob_gzhandler)实现网页压缩功能的方法
Feb 18 #PHP
You might like
使用PHP编写发红包程序
2015/07/22 PHP
PHP获取访问页面HTTP状态码的实现代码
2016/11/03 PHP
Avengerls vs KG BO3 第二场2.18
2021/03/10 DOTA
共享自己写一个框架DreamScript
2007/01/20 Javascript
Jquery Ajax的Get方式时需要注意URL地方
2011/04/07 Javascript
详谈javascript中的cookie
2015/06/03 Javascript
jquery.gridrotator实现响应式图片展示画廊效果
2015/06/23 Javascript
全面解析Bootstrap表单使用方法(表单控件状态)
2015/11/24 Javascript
浅析AngularJs HTTP响应拦截器
2015/12/28 Javascript
JS实现图片平面旋转的方法
2016/03/01 Javascript
JavaScript 监控微信浏览器且自带返回按钮时间
2016/11/27 Javascript
Bootstrap面板(Panels)的简单实现代码
2017/03/17 Javascript
JS实现留言板功能[楼层效果展示]
2017/12/27 Javascript
利用不到200行代码写一款属于你自己的js类库
2019/07/08 Javascript
JavaScript基础之this和箭头函数详析
2019/09/05 Javascript
微信小程序实现吸顶特效
2020/01/08 Javascript
vue-router之解决addRoutes使用遇到的坑
2020/07/19 Javascript
[01:01:35]Optic vs paiN 2018国际邀请赛小组赛BO2 第二场 8.19
2018/08/21 DOTA
Python单元测试框架unittest简明使用实例
2015/04/13 Python
Python实现约瑟夫环问题的方法
2016/05/03 Python
Python面向对象编程中关于类和方法的学习笔记
2016/06/30 Python
django创建自定义模板处理器的实例详解
2017/08/14 Python
Python使用wget实现下载网络文件功能示例
2018/05/31 Python
python ipset管理 增删白名单的方法
2019/01/14 Python
Python中整数的缓存机制讲解
2019/02/16 Python
Myprotein芬兰官网:欧洲第一运动营养品牌
2019/05/05 全球购物
沃尔玛加拿大:Walmart.ca
2020/03/02 全球购物
金融行业务员的自我评价
2013/12/13 职场文书
会计核算科岗位职责
2014/03/19 职场文书
2014银行授权委托书样本
2014/10/04 职场文书
银行贷款收入证明
2014/10/17 职场文书
办公室务虚会发言材料
2014/10/20 职场文书
2015年读书月活动总结
2015/03/26 职场文书
利用javaScript处理常用事件详解
2021/04/14 Javascript
比较几种Redis集群方案
2021/06/21 Redis
剑指Offer之Java算法习题精讲二叉树专项训练
2022/03/21 Java/Android