首頁 类库下载 PHP类库 php的memcache擴充和memcached擴充讀寫陣列不相容原因探究

php的memcache擴充和memcached擴充讀寫陣列不相容原因探究

Oct 15, 2016 pm 04:19 PM

背景

最近公司許多團隊進行升級php7,目前支援php7讀取mc的擴充只有memcached。但是公司許多專案都會共用一個mc集群來訪問用戶session數據,存的時候是登陸時用memcache擴展以array的形式寫進去,讀的時候自然是用memcache擴展以array的形式讀出來。 但現在只能使用memcached進行讀取。但據我所知兩者讀取array形式的資料是互不相容的,因此想探究一下究竟是為什麼。

驗證

驗證memcache擴展和memcached擴展讀寫數組資料是否不相容測試腳本:

<?php 
echo "========== test string ============\n"; 
$mc = new memcache; 
$mc->addServer(&#39;10.199.189.129&#39;, 11511); 
$key = &#39;testString&#39;; 
$mc->set($key, &#39;test success&#39;); 
var_dump($mc->get($key)); 
$mc2 = new memcached; 
$mc2->addServer(&#39;10.199.189.129&#39;, 11511); 
var_dump($mc2->get($key)); 
echo "========== test array ============\n"; 
$key2 = &#39;testArray&#39;; 
$mc->set($key2, [1,2,3]); 
var_dump($mc->get($key2)); 
var_dump($mc2->get($key2));
登入後複製

執行結果:

➜ ~ php /apps/dat/test.php 
========== test string ============ 
string(12) "test success" 
string(12) "test success" 
========== test array ============ 
array(3) { [0]=> int(1) [1]=> int(2) [2]=> int(3) } 
int(0)
登入後複製

從結果來看,印證了我們之前的說法。

猜測原因

由於string沒有問題,出問題是在array格式裡面。所以懷疑是array存進mc時的序列化方法不同。於是乎進行進一步的測試:編寫測試腳本

<?php 
echo "========== test array ============\n"; 
$mc = new memcache; 
$mc->addServer(&#39;10.199.189.129&#39;, 11511); 
$mc2 = new memcached; 
$mc2->addServer(&#39;10.199.189.129&#39;, 11511); 
$key2 = &#39;testArray1&#39;; 
$key3 = &#39;testArray2&#39;; 
$mc->set($key2, [1,2,3]); 
$mc2->set($key3, [1,2,3]); 
var_dump($mc->get($key2)); 
var_dump($mc2->get($key3));
登入後複製

執行結果:

➜ ~ php /apps/dat/test.php 
========== test array ============ 
array(3) { [0]=> int(1) [1]=> int(2) [2]=> int(3) } 
array(3) { [0]=> int(1) [1]=> int(2) [2]=> int(3) }
登入後複製

接下來直接連接mc進行查看

➜ ~ telnet 10.199.189.129 11511 
Trying 10.199.189.129... 
Connected to 10.199.189.129
Escape character is &#39;^]&#39;. 
get testArray1 
VALUE testArray1 1 30 
a:3:{i:0;i:1;i:1;i:2;i:2;i:3;} 
END 
get testArray2 
VALUE testArray2 4 30 
a:3:{i:0;i:1;i:1;i:2;i:2;i:3;} 
END
登入後複製

從結果來看,我們可以發現,memcache和memcached寫到mc裡面的結果是一樣的,也就是說我們的猜測是錯的。兩個值的序列化處理一模一樣,差異在於值的flag不同。 memcache儲存array資料的時候,falg為1,而memcached為4. 我們知道,mc中值的flag是提供給用戶自訂,方便再讀取的時候做不同的處理。但為什麼兩者的flag定義會不相同呢。 抱著這個疑問,試著透過閱讀兩個擴充的原始碼來找出原因。

閱讀兩個擴充的原始碼

memcache

php_memcache.h:

#define MMC_SERIALIZED 1 
#define MMC_COMPRESSED 2
登入後複製

memcached

php_memcached.cache

reee

reee

碼,發現數字php存進mc中的值進行詳細的型別區分,將資料型別定義了string,long,double等等的資料型別。也就是說,當你使用memcache的時候,運行

#define MEMC_VAL_IS_STRING 0 
#define MEMC_VAL_IS_LONG 1 
#define MEMC_VAL_IS_DOUBLE 2 
#define MEMC_VAL_IS_BOOL 3 
#define MEMC_VAL_IS_SERIALIZED 4 
#define MEMC_VAL_IS_IGBINARY 5 
#define MEMC_VAL_IS_JSON 6 
#define MEMC_VAL_IS_MSGPACK 7
登入後複製

執行結果是:

<?php
$mc = new memcache; 
$mc->addServer(&#39;10.199.189.129&#39;, 11511); 
$mc->set(&#39;123&#39;,1); 
var_dump($mc->get(&#39;123&#39;));
登入後複製

你明明存了一個值為數字1的key,但是讀取的時候卻為字符串。 而當你使用memcached的時候,運行

string(1) "1"
登入後複製

執行結果是:

<?php$mc = new memcached; 
$mc->addServer(&#39;10.199.189.129&#39;, 11511); 
$mc->set(&#39;123&#39;,1); 
var_dump($mc->get(&#39;123&#39;));
登入後複製
結論🎜

memcache擴展和memcached擴展讀寫數組資料不相容的原因是,memcached為了詳細地區分資料類型,定義了各種資料類型的標識,而其中數組的標識與memcache定義的數組標識不一致導致。
為了確保memcache擴充和memcached擴充直接寫的資料可以互相讀取,只能用string的格式寫入mc。
經過這次探究,也讓我認識到許多memcached比memcache更優秀的地方,相信隨著php7的普及,memcache會加速地被歷史所淘汰。


本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn

熱AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Clothoff.io

Clothoff.io

AI脫衣器

Video Face Swap

Video Face Swap

使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

<🎜>:泡泡膠模擬器無窮大 - 如何獲取和使用皇家鑰匙
4 週前 By 尊渡假赌尊渡假赌尊渡假赌
北端:融合系統,解釋
4 週前 By 尊渡假赌尊渡假赌尊渡假赌
Mandragora:巫婆樹的耳語 - 如何解鎖抓鉤
3 週前 By 尊渡假赌尊渡假赌尊渡假赌

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的程式碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

強大的PHP整合開發環境

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發工具

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

熱門話題

Java教學
1672
14
CakePHP 教程
1428
52
Laravel 教程
1332
25
PHP教程
1277
29
C# 教程
1257
24