如何使用PHP清除共享内存?

时间:2014-06-20 04:37:56

标签: php shared-memory

我想问一下为什么在我使用shmop_delete($ shmid)和shmop_close($ shmid)之后没有什么事情发生?第一个字符串仍然存在。

这是我的PHP代码:     $ key = 864;     $ mode =' c&#39 ;;     $ permission = 0644;     $ size = 1024;

$shmid = shmop_open($key, $mode, $permission, 1024);

$string = "Hello World !!!";

shmop_write($shmid, $string, 0);

$size = shmop_size($shmid);
echo shmop_read($shmid, 0, $size);

shmop_delete($shmid);
shmop_close($shmid);

第一个结果: Hello World !!!

然后我改变$ string =" TEST"。

之后我再次使用结果运行代码: TESTo World !!! (不需要的结果)。 我想要的结果是: TEST

为什么这个世界!!!'虽然我已经做了shmop_delete和shmop_close,但仍然附着?以及如何从共享内存中删除它? THX ...

2 个答案:

答案 0 :(得分:0)

当你第一次写" Hello World"它写了那11个字符的长度。当"测试"写完了,它只写了"测试"进入共享内存。这就是为什么字符串的其余部分仍然附加。一个可能的解决方案是采用这样的长度:

$ shm_bytes_written = shmop_write($ shmid,$ string,0);

并将下一个字符串填充到该长度。或者我猜你可以写出共享块的整个大小,但这可能不是你想要的。

编辑:

代码应该是这样的(未经过测试或编译)。这是针对ASCII的。如果您使用的是UTF-8,那么您需要处理字符串长度有点不同。希望你能得到这个想法

$shmid = shmop_open($key, $mode, $permission, 1024);

$string = "Hello World !!!";

$s1bytes = strlen( $string );

$shm_bytes_written = shmop_write($shmid, $string, 0);

$string2 = "Test";

$padLen = strlen( $string ) - strlen( $string2 );

$s2Pad = str_pad( "Test", $padLen );

$shm_bytes_written = shmop_write($shmid, $s2Pad, 0);

$size = shmop_size($shmid);
echo shmop_read($shmid, 0, $size);

shmop_delete($shmid);
shmop_close($shmid);

答案 1 :(得分:0)

我从php.net shmop_read's comment by Craig Manley

获得了一个解决方案

演示代码,'hello'覆盖'helloworld':

$shmid = shmop_open(10014, "c", 0755, 2048);
$size = shmop_size($shmid);
$write = "helloworld";
$writeStr = str_to_nts($write);
shmop_write($shmid,$writeStr, 0);
$str = shmop_read($shmid, 0, $size);
$rawStr =  str_from_mem($str);
$oldLengh = mb_strlen($rawStr, '8bit');
echo $rawStr . "\n";
echo $oldLengh . "\n";

$writeStr = "hello";
shmop_write($shmid, str_to_nts($writeStr), 0);
$str = shmop_read($shmid, 0, $size);
$rawStr =  str_from_mem($str);
$newLengh = mb_strlen($rawStr, '8bit');
echo $rawStr . "\n";
echo $newLengh . "\n";
shmop_delete($shmid);
shmop_close($shmid);

定义:

function str_from_mem(&$value) {
    $i = strpos($value, "\0");
    if ($i === false) {
        return $value;
    }
    $result =  substr($value, 0, $i);
    return $result;
}
function str_to_nts($value) {
    return "$value\0";
}

正如Craig Manley的评论:shmop_read()读取并返回整个内存段的数据。如果您只是使用字符串,这没用。