php操作共享内存shmop类及简单使用测试(代码)
SimpleSHM 是一个较小的抽象层,用于使用 PHP 操作共享内存,支持以一种面向对象的方式轻松操作内存段。在编写使用共享内存进行存储的小型应用程序时,这个库可帮助创建非常简洁的代码。可以使用 3 个方法进行处理:读、写和删除。从该类中简单地实例化一个对象,可以控制打开的共享内存段。
类对象和测试代码
<?php
//类对象
namespace Simple\SHM; class Block
{
/**
* Holds the system id for the shared memory block
*
* @var int
* @access protected
*/
protected $id; /**
* Holds the shared memory block id returned by shmop_open
*
* @var int
* @access protected
*/
protected $shmid; /**
* Holds the default permission (octal) that will be used in created memory blocks
*
* @var int
* @access protected
*/
protected $perms = ; /**
* Shared memory block instantiation
*
* In the constructor we'll check if the block we're going to manipulate
* already exists or needs to be created. If it exists, let's open it.
*
* @access public
* @param string $id (optional) ID of the shared memory block you want to manipulate
*/
public function __construct($id = null)
{
if($id === null) {
$this->id = $this->generateID();
} else {
$this->id = $id;
} if($this->exists($this->id)) {
$this->shmid = shmop_open($this->id, "w", , );
}
} /**
* Generates a random ID for a shared memory block
*
* @access protected
* @return int System V IPC key generated from pathname and a project identifier
*/
protected function generateID()
{
$id = ftok(__FILE__, "b");
return $id;
} /**
* Checks if a shared memory block with the provided id exists or not
*
* In order to check for shared memory existance, we have to open it with
* reading access. If it doesn't exist, warnings will be cast, therefore we
* suppress those with the @ operator.
*
* @access public
* @param string $id ID of the shared memory block you want to check
* @return boolean True if the block exists, false if it doesn't
*/
public function exists($id)
{
$status = @shmop_open($id, "a", , );
return $status;
} /**
* Writes on a shared memory block
*
* First we check for the block existance, and if it doesn't, we'll create it. Now, if the
* block already exists, we need to delete it and create it again with a new byte allocation that
* matches the size of the data that we want to write there. We mark for deletion, close the semaphore
* and create it again.
*
* @access public
* @param string $data The data that you wan't to write into the shared memory block
*/
public function write($data)
{
$size = mb_strlen($data, 'UTF-8'); if($this->exists($this->id)) {
shmop_delete($this->shmid);
shmop_close($this->shmid);
$this->shmid = shmop_open($this->id, "c", $this->perms, $size);
shmop_write($this->shmid, $data, );
} else {
$this->shmid = shmop_open($this->id, "c", $this->perms, $size);
shmop_write($this->shmid, $data, );
}
} /**
* Reads from a shared memory block
*
* @access public
* @return string The data read from the shared memory block
*/
public function read()
{
$size = shmop_size($this->shmid);
$data = shmop_read($this->shmid, , $size); return $data;
} /**
* Mark a shared memory block for deletion
*
* @access public
*/
public function delete()
{
shmop_delete($this->shmid);
} /**
* Gets the current shared memory block id
*
* @access public
*/
public function getId()
{
return $this->id;
} /**
* Gets the current shared memory block permissions
*
* @access public
*/
public function getPermissions()
{
return $this->perms;
} /**
* Sets the default permission (octal) that will be used in created memory blocks
*
* @access public
* @param string $perms Permissions, in octal form
*/
public function setPermissions($perms)
{
$this->perms = $perms;
} /**
* Closes the shared memory block and stops manipulation
*
* @access public
*/
public function __destruct()
{
shmop_close($this->shmid);
}
}
<?php
//测试使用代码
namespace Simple\SHM\Test; use Simple\SHM\Block; class BlockTest extends \PHPUnit_Framework_TestCase
{
public function testIsCreatingNewBlock()
{
$memory = new Block;
$this->assertInstanceOf('Simple\\SHM\\Block', $memory); $memory->write('Sample');
$data = $memory->read();
$this->assertEquals('Sample', $data);
} public function testIsCreatingNewBlockWithId()
{
$memory = new Block();
$this->assertInstanceOf('Simple\\SHM\\Block', $memory);
$this->assertEquals(, $memory->getId()); $memory->write('Sample 2');
$data = $memory->read();
$this->assertEquals('Sample 2', $data);
} public function testIsMarkingBlockForDeletion()
{
$memory = new Block();
$memory->delete();
$data = $memory->read();
$this->assertEquals('Sample 2', $data);
} public function testIsPersistingNewBlockWithoutId()
{
$memory = new Block;
$this->assertInstanceOf('Simple\\SHM\\Block', $memory);
$memory->write('Sample 3');
unset($memory); $memory = new Block;
$data = $memory->read();
$this->assertEquals('Sample 3', $data);
}
}
额外说明
<?php $memory = new SimpleSHM;
$memory->write('Sample');
echo $memory->read(); ?>
请注意,上面代码里没有为该类传递一个 ID。如果没有传递 ID,它将随机选择一个编号并打开该编号的新内存段。我们可以以参数的形式传递一个编号,供构造函数打开现有的内存段,或者创建一个具有特定 ID 的内存段,如下
<?php $new = new SimpleSHM();
$new->write('Sample');
echo $new->read(); ?>
神奇的方法 __destructor
负责在该内存段上调用 shmop_close
来取消设置对象,以与该内存段分离。我们将这称为 “SimpleSHM 101”。现在让我们将此方法用于更高级的用途:使用共享内存作为存储。存储数据集需要序列化,因为数组或对象无法存储在内存中。尽管这里使用了 JSON 来序列化,但任何其他方法(比如 XML 或内置的 PHP 序列化功能)也已足够。如下
<?php require('SimpleSHM.class.php'); $results = array(
'user' => 'John',
'password' => '',
'posts' => array('My name is John', 'My name is not John')
); $data = json_encode($results); $memory = new SimpleSHM;
$memory->write($data);
$storedarray = json_decode($memory->read()); print_r($storedarray); ?>
我们成功地将一个数组序列化为一个 JSON 字符串,将它存储在共享内存块中,从中读取数据,去序列化 JSON 字符串,并显示存储的数组。这看起来很简单,但请想象一下这个代码片段带来的可能性。您可以使用它存储 Web 服务请求、数据库查询或者甚至模板引擎缓存的结果。在内存中读取和写入将带来比在磁盘中读取和写入更高的性能。
使用此存储技术不仅对缓存有用,也对应用程序之间的数据交换也有用,只要数据以两端都可读的格式存储。不要低估共享内存在 Web 应用程序中的力量。可采用许多不同的方式来巧妙地实现这种存储,惟一的限制是开发人员的创造力和技能。
php操作共享内存shmop类及简单使用测试(代码)的更多相关文章
- Linux进程IPC浅析[进程间通信SystemV共享内存]
Linux进程IPC浅析[进程间通信SystemV共享内存] 共享内存概念,概述 共享内存的相关函数 共享内存概念,概述: 共享内存区域是被多个进程共享的一部分物理内存 多个进程都可把该共享内存映射到 ...
- php简单使用shmop函数创建共享内存减少服务器负载
在之前的一篇博客[了解一下共享内存的概念及优缺点]已经对共享内存的概念做了说明.下面就来简单使用共享内存(其实也可以用其他工具,比如redis) PHP做内存共享有两套接口.一个是shm,它实际上是变 ...
- PHP共享内存的应用shmop系列
简单的说明 可能很少情况会使用PHP来操控共享内存,一方面在内存的控制上,MC已经提供了一套很好的方式,另一方面,自己来操控内存的难度较大,内存的读写与转存,包括后面可能会用到的存储策略,要是没有一定 ...
- System V IPC 之共享内存
IPC 是进程间通信(Interprocess Communication)的缩写,通常指允许用户态进程执行系列操作的一组机制: 通过信号量与其他进程进行同步 向其他进程发送消息或者从其他进程接收消息 ...
- PHP共享内存详解
前言 在PHP中有这么一族函数,他们是对UNIX的V IPC函数族的包装. 它们很少被人们用到,但是它们却很强大.巧妙的运用它们,可以让你事倍功半. 它们包括: 信号量(Semaphores) 共享内 ...
- Linux 程序设计1:深入浅出 Linux 共享内存
笔者最近在阅读Aerospike 论文时,发现了Aerospike是利用了Linux 共享内存机制来实现的存储索引快速重建的.这种方式比传统利用索引文件进行快速重启的方式大大提高了效率.(减少了磁盘 ...
- C 共享内存封装
引言 - 背景 2016 年写过一篇关于 linux 共享内存 shm api 扫盲文. C扩展 从共享内存shm到memcache外部内存 比较简单. 没有深入分析(能力有限, 也深入分析不了). ...
- PHP共享内存
如何使用 PHP shmop 创建和操作共享内存段,使用它们存储可供其他应用程序使用的数据. 1. 创建内存段 共享内存函数类似于文件操作函数,但无需处理一个流,您将处理一个共享内存访问 ID.第一个 ...
- Akka系列(四):Akka中的共享内存模型
前言...... 通过前几篇的学习,相信大家对Akka应该有所了解了,都说解决并发哪家强,JVM上面找Akka,那么Akka到底在解决并发问题上帮我们做了什么呢? 共享内存 众所周知,在处理并发问题上 ...
随机推荐
- maven项目中添加Tomcat启动插件
在pom.xml文件中添加如下配置: <!-- 配置tomcat插件,pom.xml里配置 --> <build> <plugins> <plugin> ...
- mac 安装geckodriver和chromedriver
Last login: Fri Apr :: on ttys000 (base) localhost:~ ligaijiang$ env TERM_PROGRAM=Apple_Terminal SHE ...
- Count(广工14届竞赛)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6470 这道题目题解就扔了个矩阵快速幂啥都没写.....这题解是太看得懂我这个弱鸡了. 既然是矩阵快速幂 ...
- vector erase的错误用法
直接写 a.erase(it)是错误的,一定要写成it=a.erase(it)这个错误编译器不会报错.而且循环遍历删除的时候,删除了一个元素,容器里会自动向前移动,删除一个元素要紧接着it--来保持位 ...
- OAuth2.0标准类库汇总
转载官网: https://oauth.net/code/ https://www.w3cschool.cn/oauth2/5ghz1jab.html 服务端类库 .NET .NET DotNetOp ...
- node.js初识03
node中的url var http = require("http"); var url = require("url"); var server = htt ...
- HDU 2276 Kiki & Little Kiki 2(矩阵位运算)
Kiki & Little Kiki 2 转载自:点这里 [题目链接]Kiki & Little Kiki 2 [题目类型]矩阵位运算 &题意: 一排灯,开关状态已知,每过一秒 ...
- hive-drop-import-delims选项对oracle的clob无效
工作过程中发现了用sqoop将oracle中的数据导入到hive时,会因为oracle中类型为clob的字段中存在换行时,会造成hive的数据错位.即使加上了 --hive-drop-import-d ...
- linux如何在不重新登录用户的情况下使用户加入的组生效
这个问题在很早之前就遇到了,之前的解决方法是登出用户再登录用户.今天在配置virtualbox的过程中又遇到了同样的问题.于是又进行了一番搜索. 找到了如下答案: https://stackoverf ...
- vss使用笔记
一.四大代码/文档管理软件 (1) git:具有PR(push request)特性,推送请求.需要负责人审核后才能推送.另外,在推送过程中,git会预编译(合并),分布式代码管理(客户端本地 ...