当前位置: 首页> 技术教程> 正文

PHP Memcached教程

宁旺春土特产品

在现代Web应用开发中,高并发场景下的性能优化始终是开发者无法回避的核心问题,而缓存技术作为缓解数据库压力、提升接口响应速度的关键手段,早已成为项目架构中不可或缺的组成部分,PHP作为主流的服务端开发语言,搭配Memcached内存缓存系统更是中小型项目的常见技术组合。

PHP Memcached教程

要在PHP中使用Memcached,首先需要完成基础环境的搭建与扩展安装。Memcached本身是一个独立的分布式内存对象缓存系统,采用键值对的形式存储任意类型的数据,开发者需要先在服务器上安装Memcached服务端程序,Linux系统下可以通过包管理器直接安装,比如Ubuntu系统使用`apt install memcached`命令,CentOS系统使用`yum install memcached`命令,安装完成后可以通过`service memcached start`命令启动服务,默认监听11211端口。服务端准备就绪后,还需要为PHP安装对应的客户端扩展,PHP的Memcached扩展有两个常用版本,分别是memcache扩展和memcached扩展,后者功能更完善,支持更多的特性如二进制协议、SASL认证等,推荐使用memcached扩展。安装扩展可以通过PECL工具,执行`pecl install memcached`命令即可,安装完成后需要在php.ini配置文件中添加`extension=memcached.so`,重启PHP-FPM或Web服务器后,就可以通过phpinfo()函数查看扩展是否成功加载。

PHP中操作Memcached的核心是Memcached类,所有的缓存操作都需要先实例化该类,然后添加Memcached服务器节点。实例化时可以传入一个持久化ID,用于创建持久连接,减少频繁建立连接的开销,比如`$memcached = new Memcached('persistent_id');`。添加服务器可以使用addServer方法添加单个服务器,也可以使用addServers方法批量添加多个服务器,实现分布式缓存,比如`$memcached->addServer('127.0.0.1', 11211);`,如果有多个服务器节点,addServers方法接收一个二维数组,每个子数组包含服务器地址和端口号。需要注意的是,Memcached的分布式是由客户端实现的,扩展会根据键名的哈希值将数据分配到不同的服务器节点上,因此添加服务器的顺序和数量一旦确定,不要轻易修改,否则会导致大量缓存失效。

Memcached最基础的操作包括数据的设置、获取、删除和过期时间设置。设置缓存使用set方法,该方法接收三个参数,分别是键名、值和过期时间,比如`$memcached->set('user_info', ['id' => 1, 'name' => 'test'], 3600);`,这条语句会将用户信息数组存储在键名为user_info的缓存中,过期时间为3600秒也就是1小时。如果需要设置的缓存键已经存在,set方法会覆盖原来的值,如果不想覆盖,可以使用add方法,只有当键不存在时才会设置成功,常用于防止缓存并发写入的场景。获取缓存使用get方法,传入键名即可返回对应的值,如果键不存在或已过期则返回false,比如`$userInfo = $memcached->get('user_info');`。删除缓存使用delete方法,传入键名即可立即删除对应的缓存,比如`$memcached->delete('user_info');`,也可以传入第二个参数指定延迟删除的时间,单位为秒。除了这些基础操作,Memcached还支持批量操作,比如getMulti方法可以一次性获取多个键的缓存值,setMulti方法可以一次性设置多个键值对,批量操作能够减少网络IO次数,在需要操作多个缓存项时能显著提升性能。

在实际项目开发中,Memcached的应用场景非常广泛,最常见的就是数据库查询结果的缓存。对于一些查询频率高但数据更新不频繁的接口,比如商品详情页、文章详情页、用户中心基础信息等,可以将数据库查询的结果缓存到Memcached中,当用户再次请求时,先从缓存中读取数据,如果缓存命中就直接返回,不再查询数据库,这样可以大大降低数据库的查询压力。比如实现一个查询用户信息的函数,先检查缓存中是否存在,存在则返回缓存数据,不存在则查询数据库,然后将结果写入缓存再返回,这就是典型的缓存旁路模式。除了数据库缓存,Memcached还可以用于存储Session会话数据,PHP默认的Session是存储在文件中的,在分布式部署的场景下,文件Session无法跨服务器共享,将Session存储到Memcached中就可以解决这个问题,只需要修改php.ini中的session.save_handler为memcached,session.save_path设置为Memcached服务器的地址即可。Memcached还可以用于计数器、分布式锁、接口限流等场景,比如使用increment和decrement方法实现文章浏览量、点赞数的计数,避免每次都更新数据库。

使用Memcached的过程中也有很多需要注意的问题,首先是缓存穿透的问题,也就是查询一个数据库中一定不存在的数据,由于缓存中也没有,每次请求都会穿透到数据库,导致数据库压力过大,解决方法是将不存在的数据也缓存一个空值,设置较短的过期时间,或者使用布隆过滤器过滤掉不存在的键。其次是缓存击穿的问题,对于一个热点Key,在缓存过期的瞬间,大量并发请求同时过来,都会穿透到数据库,解决方法是使用互斥锁,当缓存失效时,只允许一个请求去查询数据库并更新缓存,其他请求等待缓存更新完成后再读取。还有缓存雪崩的问题,也就是大量缓存同时过期,或者Memcached服务宕机,导致所有请求都打到数据库上,解决方法是给缓存的过期时间加上随机值,避免大量缓存同时过期,同时搭建Memcached集群,提高服务的可用性。Memcached是内存存储,数据断电后会丢失,因此不能将其作为持久化存储使用,只能作为缓存层,数据的最终来源还是数据库,当缓存更新时要注意数据库和缓存的一致性问题,通常采用

PC右下角
wap底部