探究php的memcache和memcached扩展读写数组数据不相兼容原因
admin
2023-06-20 15:41:23
0

最近公司许多团队进行升级php7,目前支持php7读取mc的扩展只有memcached。

但是公司许多项目都会共用一个mc集群来存取用户session数据,存的时候是登陆时用memcache扩展以array的形式写进去,读的时候自然是用memcache扩展以array的形式读出来。 但是现在只能使用memcached进行读取。但是据我所知两者读取array形式的数据是互不兼容的,因此想探究一下究竟是为什么。

验证memcache扩展和memcached扩展读写数组数据是否不相兼容

测试脚本:

addServer('10.199.189.129', 10002);$key = 'testString';$mc->set($key, 'test success');var_dump($mc->get($key));$mc2 = new memcached;$mc2->addServer('10.199.189.129', 11511);var_dump($mc2->get($key));echo "========== test  array  ============\n";$key2 = 'testArray';$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时的序列化方法不同。于是乎进行进一步的测试:

编写测试脚本

addServer('10.199.189.129', 11511);$mc2 = new memcached;$mc2->addServer('10.199.189.129', 11511);$key2 = 'testArray1';$key3 = 'testArray2';$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 msession.vip.vip.co.
Escape character is '^]'.

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.c

#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

经阅读源码,发现memcache将array的数组格式的flag定义为1,而memcached为了将php存进mc中的值进行详细的类型区分,将数据类型定义了string,long,double等等的数据类型。

也就是说,当你使用memcache的时候,运行

$mc = new memcache;$mc->addServer('10.199.189.129', 11511);$mc->set('123',1);var_dump($mc->get('123'));

执行结果是:

string(1) "1"

你明明存了一个值为数字1的key,但是读取的时候却为字符串。 而当你使用memcached的时候,运行

$mc = new memcached;$mc->addServer('10.199.189.129', 11511);$mc->set('123',1);var_dump($mc->get('123'));

执行结果是:

int(1)

结论

memcache扩展和memcached扩展读写数组数据不相兼容的原因是,memcached为了详细地区分数据类型,定义了各种数据类型的标示,而导致其中数组的标识与memcache定义的数组标识不一致导致。 经过这次探究,也让我认识到许多memcached比memcache更优秀的地方,相信随着php7的普及,memcache会加速地被历史所淘汰。

  • 作者: Akay 探究php的memcache和memcached扩展读写数组数据不相兼容原因

  • 本文地址: http://www.akayzhang.com/article/6

  • 转载请注明出处


相关内容

热门资讯

新一代网络与存储模组发布,释放... 来源:市场资讯 (来源:华为计算) 【中国,北京,2026年5月23日】鲲鹏昇腾开发者大会2026(...
网络安全人的2026:AI攻击... HSBC CEO在最近一次采访中说了一句话:"不要和AI对抗——银行正在因为AI裁员,也正在被AI攻...
7名科学家获2026年度邵逸夫... 中新社香港5月27日电 (记者 赵静怡)邵逸夫奖基金会27日在香港公布2026年度邵逸夫奖获奖名单,...
跨越式升级!解析Harmony... 2026年4月20日,华为正式发布了HUAWEI Pura X Max、HUAWEI MateBoo...
甘肃天水5G+智慧物流园开启快... 今年,天水5G+智慧物流园项目投入试运行以来,5G智慧分拣配送中心无人分拣设备运行稳定,日均分拣包裹...
禾电迅取得小型化北斗多频卫星天... 国家知识产权局信息显示,深圳市禾电迅科技有限公司取得一项名为“一种小型化北斗多频卫星天线”的专利,授...
特朗普警告盟友阿曼:不守规矩会... 新华社华盛顿5月27日电(记者黄强 徐剑梅)美国总统特朗普27日在白宫举行的内阁会议上说,霍尔木兹海...
4G DTU模块厂家梳理 工业... 导语:在工业物联网场景中,4G DTU模块作为数据传输的核心设备,其稳定性、兼容性及服务响应能力直接...
原创 美... 5月25日,华为在上海丢出了一颗深水炸弹。 半导体业务部总裁何庭波在IEEE国际电路与系统研讨会上,...
真正该按下暂停键的,不是AI的... 事情发生在一个寻常不过的深夜。 我正坐在电脑前,赶着明天要交的企划案,窗外是连绵不断的春雨。工作堆得...