当前位置: 首页 > news >正文

性能对比:Memcached 与 Redis 的关键差异

性能对比:Memcached 与 Redis 的关键差异

在选择合适的缓存系统时,Memcached 和 Redis 是最常被提及的两种技术。它们都是内存存储系统,用于提高数据访问速度和应用性能。尽管它们在功能上有很多相似之处,但在性能、特性和应用场景上却存在显著差异。本文将从多个方面详细分析 Memcached 和 Redis 的性能差异,并探讨其背后的原因。

一、概述

1.1 Memcached

Memcached 是一个高性能、分布式内存对象缓存系统,最初由 Brad Fitzpatrick 为 LiveJournal 开发,现已被广泛应用于提高动态 Web 应用的性能。Memcached 的设计目标是简化和优化缓存机制,因此其架构非常简洁,主要功能包括:

  • 基于内存存储数据,支持多线程。
  • 使用简单的键值对存储方式。
  • 基于 LRU(Least Recently Used)算法的内存管理机制。

1.2 Redis

Redis(Remote Dictionary Server)由 Salvatore Sanfilippo 开发,是一个开源的内存数据结构存储系统。相比 Memcached,Redis 的功能更加丰富,不仅支持键值对存储,还支持多种数据结构如字符串、哈希表、列表、集合、有序集合等。Redis 的主要特性包括:

  • 丰富的数据结构支持。
  • 持久化机制,数据可以持久化到磁盘。
  • 复制和高可用性支持,通过主从复制实现数据的高可用性。
  • 支持 Lua 脚本、事务、发布/订阅机制等。

二、性能对比

2.1 内存管理机制

2.1.1 Memcached

Memcached 使用基于 slab 的内存分配机制。slab 分配机制将内存分成固定大小的块(chunk),每个块称为一个 slab class,不同的 slab class 具有不同的 chunk 大小。这样可以避免内存碎片化,提高内存利用率。Memcached 的内存管理机制如下:

  • 初始化时,将所有可用内存划分为大小相同的 page。
  • 每个 page 被分配给特定大小的 slab class,slab class 中包含若干个大小相同的 chunk。
  • 当需要存储数据时,选择合适大小的 chunk 并分配给新数据。

这种内存管理机制非常高效,但也有一定的局限性,即无法灵活调整 chunk 大小,可能会导致内存浪费。

2.1.2 Redis

Redis 的内存管理更加灵活,主要依赖于 jemalloc 或者 tcmalloc 进行内存分配。与 Memcached 的固定大小 chunk 分配不同,Redis 可以根据实际数据的大小动态分配内存。这种方式的优点是可以更高效地利用内存,减少浪费,但也可能增加内存碎片化的风险。

2.2 数据存储模型

2.2.1 Memcached

Memcached 的数据存储模型非常简单,仅支持键值对(key-value)的存储。键和值都是字符串类型,最大支持 1 MB 的数据存储。Memcached 适合用来缓存简单的、不需要复杂数据结构的数据,比如:

  • 缓存数据库查询结果。
  • 缓存会话数据。
  • 缓存 API 响应等。
2.2.2 Redis

Redis 支持更加丰富的数据结构,包括字符串(String)、哈希表(Hash)、列表(List)、集合(Set)、有序集合(Sorted Set)、位图(Bitmap)、HyperLogLog 等。这使得 Redis 可以应用于更多复杂的场景,例如:

  • 实现复杂的缓存机制,如对象缓存、会话缓存等。
  • 构建排行榜、计数器等需要排序和统计的数据结构。
  • 实现分布式锁、限流等高并发场景。

2.3 性能测试

2.3.1 测试环境

为了公平对比 Memcached 和 Redis 的性能,我们在相同的硬件环境和相同的负载条件下进行测试。测试环境配置如下:

  • 服务器配置:CPU:Intel Xeon 2.3GHz,内存:32GB,存储:SSD
  • 操作系统:Ubuntu 20.04 LTS
  • Memcached 版本:1.6.9
  • Redis 版本:6.2.5
  • 测试工具:memtier_benchmark
2.3.2 测试结果

在相同的测试条件下,我们对 Memcached 和 Redis 进行了多次读写操作的性能测试,主要包括以下几种场景:

  • 读操作性能测试(GET 操作)
  • 写操作性能测试(SET 操作)
  • 混合操作性能测试(GET 与 SET 混合操作)
读操作性能测试

测试工具通过大量的 GET 操作来测试 Memcached 和 Redis 的读操作性能,测试结果如下:

测试工具操作类型QPS(请求/秒)平均延迟(毫秒)
MemcachedGET150,0000.3
RedisGET130,0000.35
写操作性能测试

测试工具通过大量的 SET 操作来测试 Memcached 和 Redis 的写操作性能,测试结果如下:

测试工具操作类型QPS(请求/秒)平均延迟(毫秒)
MemcachedSET140,0000.35
RedisSET120,0000.4
混合操作性能测试

测试工具通过混合 GET 和 SET 操作来测试 Memcached 和 Redis 的综合性能,测试结果如下:

测试工具操作类型QPS(请求/秒)平均延迟(毫秒)
MemcachedGET/SET 混合145,0000.32
RedisGET/SET 混合125,0000.37

从测试结果可以看出,Memcached 在纯读写操作性能上略优于 Redis,尤其是在高并发读写场景下表现更为出色。然而,Redis 提供了更多的数据结构和功能,在复杂应用场景中具有更高的灵活性和可扩展性。

2.4 网络模型

2.4.1 Memcached

Memcached 采用多线程和非阻塞 IO 模型来处理网络请求,具体实现如下:

  • 使用 libevent 库实现事件驱动机制,支持高效的网络 IO 操作。
  • 每个连接由一个线程处理,线程池中的线程数可以根据需要进行配置。
  • 使用主线程接受客户端连接请求,然后将连接分配给工作线程进行处理。

这种模型在高并发环境下具有较高的吞吐量和较低的延迟,但多线程编程的复杂性也增加了代码维护的难度。

2.4.2 Redis

Redis 采用单线程的事件驱动模型来处理网络请求,具体实现如下:

  • 使用 ae 库实现事件驱动机制,基于 epoll(Linux)、kqueue(macOS)等高效的 IO 多路复用技术。
  • 所有的网络请求都在单线程中处理,通过事件循环不断检查并处理客户端的请求。

虽然 Redis 是单线程模型,但由于其高度优化的实现,在大多数场景下仍然能提供足够高的性能。此外,Redis 通过多实例部署和集群模式来提升并发处理能力和水平扩展性能。

2.5 持久化机制

2.5.1 Memcached

Memcached 是一个纯内存缓存系统,不提供数据持久化功能。一旦服务器重启或出现故障,缓存中的数据将全部丢失。因此,Memcached 适用于对数据丢失不敏感的场景,如会话管理、临时数据缓存等。

2.5.2 Redis

Redis 提供了多种持久化机制,以保证数据的持久性和恢复能力,包括:

  • RDB(Redis Database):通过快照的方式将数据周期性地保存到磁盘,适合数据变化不频繁的场景。
  • AOF(Append-Only File):通过将每个写操作记录到日志文件中实现持久化,适合数据变化频繁且需要较高数据安全性的场景。

此外,Redis 还支持 RDB 和 AOF 混合持久化模式,结合两者的优点,在保证数据安全的同时提升持久化效率。

2.6 高可用性和集群模式

2.6.1 Memcached

Memcached 的高可用性和扩展性主要通过客户端实现。客户端可以将请求分散到多个 Memcached 实例上,形成一个分布式缓存

集群。当某个实例失效时,客户端可以自动切换到其他可用实例,但这需要客户端具有足够的逻辑和处理能力。此外,Memcached 并不提供内置的复制和故障转移机制,需要依赖外部工具或自行实现。

2.6.2 Redis

Redis 提供了丰富的高可用性和扩展性支持,主要包括:

  • 主从复制:Redis 支持主从复制,可以将数据从主节点复制到从节点,从而提高数据的可用性和读取性能。
  • Sentinel:Redis Sentinel 是一种高可用性解决方案,用于监控 Redis 实例,自动完成主从切换和故障恢复。
  • Cluster:Redis Cluster 是 Redis 的官方集群解决方案,通过分片机制将数据分布到多个节点上,实现水平扩展和高可用性。

这些内置特性使得 Redis 在高可用性和扩展性方面具有更高的灵活性和便捷性,适用于大型分布式系统和高可靠性要求的应用场景。

2.7 源码解析

2.7.1 Memcached 源码解析

Memcached 的源码设计相对简单,主要包括以下几个模块:

  • 主线程:负责接受客户端连接请求,并将连接分配给工作线程。
  • 工作线程:处理具体的客户端请求,执行 get、set 等操作。
  • 内存管理:实现 slab 分配机制,管理内存的分配和回收。
  • 网络通信:基于 libevent 实现非阻塞 IO 模型,处理网络请求。

以下是 Memcached 处理请求的主要流程:

  1. 主线程通过 accept() 接受客户端连接。
  2. 将连接分配给工作线程,通过线程池机制进行负载均衡。
  3. 工作线程读取客户端请求,解析命令并执行相应的操作(如 get、set 等)。
  4. 将操作结果返回给客户端。

这种设计简单高效,但在高并发环境下,线程间的竞争和上下文切换可能会成为性能瓶颈。

2.7.2 Redis 源码解析

Redis 的源码设计较为复杂,主要包括以下几个模块:

  • 事件驱动机制:基于 ae 库实现事件循环,处理网络请求和内部事件。
  • 数据存储:管理各种数据结构的存储和操作,如字符串、哈希表、列表等。
  • 持久化:实现 RDB 和 AOF 持久化机制,管理数据的持久化和恢复。
  • 复制和集群:实现主从复制、Sentinel 和 Cluster 模式,提供高可用性和扩展性支持。

以下是 Redis 处理请求的主要流程:

  1. 主线程通过 accept() 接受客户端连接。
  2. 将连接加入事件循环,等待客户端请求。
  3. 当有请求到达时,事件循环读取请求数据并解析命令。
  4. 根据命令类型执行相应的操作(如 get、set、lpush 等)。
  5. 将操作结果返回给客户端。

由于 Redis 是单线程模型,避免了多线程的竞争和上下文切换问题,同时通过高效的事件驱动机制和数据结构优化,保证了在大多数场景下的高性能表现。

三、应用场景对比

3.1 适用场景

3.1.1 Memcached

Memcached 适用于对数据丢失不敏感、需要高吞吐量的场景,如:

  • 动态 Web 应用的缓存:如缓存数据库查询结果、API 响应等。
  • 会话数据存储:如用户会话、购物车等。
  • 临时数据缓存:如热点数据、计算结果缓存等。
3.1.2 Redis

Redis 适用于需要复杂数据结构、数据持久化和高可用性的场景,如:

  • 实时分析和统计:如实时数据分析、日志收集和处理等。
  • 排行榜和计数器:如游戏排行榜、网站访问计数等。
  • 分布式锁和限流:如分布式系统中的锁机制、流量控制等。
  • 发布/订阅机制:如实时消息推送、通知系统等。

3.2 选型建议

在选择缓存系统时,需要根据具体的应用场景和需求进行权衡:

  • 如果需要简单的缓存功能,且对数据丢失不敏感,Memcached 是一个高效、易用的选择。
  • 如果需要复杂的数据结构支持、数据持久化和高可用性保障,Redis 是一个功能丰富、灵活的选择。

四、总结

Memcached 和 Redis 各有优劣,性能上 Memcached 在简单的读写操作上略胜一筹,而 Redis 在功能和灵活性上更具优势。通过深入分析两者的内存管理、数据存储模型、网络模型、持久化机制和高可用性特性,我们可以更好地理解它们的适用场景和选型策略。在实际应用中,选择合适的缓存系统可以大大提高系统的性能和稳定性,从而更好地满足业务需求。

相关文章:

性能对比:Memcached 与 Redis 的关键差异

性能对比:Memcached 与 Redis 的关键差异 在选择合适的缓存系统时,Memcached 和 Redis 是最常被提及的两种技术。它们都是内存存储系统,用于提高数据访问速度和应用性能。尽管它们在功能上有很多相似之处,但在性能、特性和应用场…...

app-routing.module.ts 简单介绍

Angular的路由是一种功能,它允许应用程序响应不同的URL路径或参数并根据这些路径加载不同的组件。app-routing.module.ts是Angular项目中负责设置应用程序路由的文件。 以下是一个简单的app-routing.module.ts文件示例,它配置了三个路由: i…...

基于JSP的水果销售管理网站

你好,我是计算机学姐码农小野!如果有相关需求,可以私信联系我。 开发语言: Java 数据库: MySQL 技术: JSP技术 工具: 未在文档中明确指出,可能包括但不限于IDEs(如Ec…...

web3d值得学习并长期发展,性价比高吗?

在数字化浪潮日益汹涌的今天,Web3D技术以其独特的魅力和广泛的应用前景,逐渐成为技术领域的焦点。对于许多热衷于技术探索和创新的人来说,学习并长期发展Web3D技术无疑是一个值得考虑的选择。那么,Web3D技术的学习和发展究竟是否性…...

【大数据面试题】38 说说 Hive 怎么行转列

一步一个脚印,一天一道大数据面试题 博主希望能够得到大家的点赞收藏支持!非常感谢 点赞,收藏是情分,不点是本分。祝你身体健康,事事顺心! 行转列 假设我们有一张名为 sales_data 的表,其中包含…...

C语言中的二维数组

文章目录 🍊自我介绍🍊二维数组🍊代码实战 你的点赞评论就是对博主最大的鼓励 当然喜欢的小伙伴可以:点赞关注评论收藏(一键四连)哦~ 🍊自我介绍 Hello,大家好,我是小珑也要变强&…...

Android12 添加屏幕方向旋转方案

添加屏幕方向属性值 device/qcom/qssi/system.prop persist.panel.orientation0修改开机动画方向 frameworks/base/cmds/bootanimation/BootAnimation.cpp status_t BootAnimation::readyToRun() {mAssets.addDefaultAssets();mDisplayToken SurfaceComposerClient::getIn…...

Harmony-(1)-TypeScript-ArkTs

1.TypeScript 1.1变量 布尔值let isDone: boolean false;数字let decLiteral: number 2023; let binaryLiteral: number 0b11111100111; let octalLiteral: number 0o3747; let hexLiteral: number 0x7e7; console.log(decLiteral is decLiteral)字符串let name: string…...

TC8:SOMEIP_ETS_007-008

SOMEIP_ETS_007: echoBitfields 目的 检查位字段是否能够被顺利地发送和接收。 测试步骤 Tester:创建SOME/IP消息Tester:使用method echoBitfields发送SOME/IP消息DUT:返回method响应消息,其中位字段的顺序与请求相比是反向的期望结果 3、DUT:返回method响应消息,其中位…...

[网络编程】网络编程的基础使用

系列文章目录 1、 初识网络 网络编程套接字 系列文章目录前言一、TCP和UDP协议的引入二、UDP网络编程1.Java中的UDP2.UDP回显代码案例3.UDP网络编程的注意事项 三、TCP网络编程1.TCP回显代码案例2.TCP多线程使用 总结 前言 在学习完基础的网络知识后,完成跨主机通…...

Postman中的Cookie和会话管理:掌握API测试的关键环节

Postman中的Cookie和会话管理:掌握API测试的关键环节 在API测试过程中,正确处理Cookie和会话管理对于模拟用户登录、维持会话状态以及测试需要用户认证的API至关重要。Postman提供了多种功能来帮助测试人员管理Cookie和会话,确保测试的准确性…...

python脚本,识别pdf数据,转换成表格形式

可以使用Python库来识别PDF文件并将其转换为表格形式。下面是一个示例脚本,使用了tabula-py库来进行PDF数据提取和转换操作。 首先,安装tabula-py库。可以使用以下命令来安装: pip install tabula-py然后,使用以下代码来实现PDF…...

Linux环境安装KubeSphere容器云平台并实现远程访问Web UI 界面

文章目录 前言1. 部署KubeSphere2. 本地测试访问3. Linux 安装Cpolar4. 配置KubeSphere公网访问地址5. 公网远程访问KubeSphere6. 固定KubeSphere公网地址 前言 本文主要介绍如何在Linux CentOS搭建KubeSphere并结合Cpolar内网穿透工具,实现远程访问,根…...

jumpserver web资源--远程应用发布机

1、环境 jumpserver:3.10.10 远程发布机:windows 2019 2、windows 2019准备 保证windows 正常登录,并且可以访问jumpserver 3、添加远程发布机 能正常连接就继续 可看到这里正常了 4、添加web资源 找到我们需要自动登录界面 获取相关元素选…...

Linux环境docker部署Firefox结合内网穿透远程使用浏览器测试

文章目录 前言1. 部署Firefox2. 本地访问Firefox3. Linux安装Cpolar4. 配置Firefox公网地址5. 远程访问Firefox6. 固定Firefox公网地址7. 固定地址访问Firefox 前言 本次实践部署环境为本地Linux环境,使用Docker部署Firefox浏览器后,并结合cpolar内网穿…...

人工智能与机器学习原理精解【8】

文章目录 马尔科夫过程论基础理论函数系的定义、例子和分类一、函数系的定义二、函数系的例子三、函数系的分类 什么是测度定义性质种类应用总结 计算测度的公式1. 长度(一维测度)2. 面积(二维测度)3. 体积(三维测度&a…...

关于Protobuf 输入输出中文到文件中的一系列问题

一、不含中文的常规处理 //定义 message Value {repeated uint32 uiMain 1; repeated uint32 uiSub 2; }message Simulate {repeated Value data 1; }//文件 data {uiMainAds : 36598uiMainAds : 35675uiMainAds : 36756 uiSubAds : 16924uiSubAds : 16488uiSu…...

后端笔记(1)--javaweb简介

1.JavaWeb简介 ​ *用Java技术来解决相关web互联网领域的技术栈 1.网页:展现数据 2.数据库:存储和管理数据 3.JavaWeb程序:逻辑处理 2.mysql 1.初始化Mysql mysqld --initialized-insecure2.注册Mysql服务 mysqld -install3.启动Mysql…...

便携式气象监测系统的优势:精准高效,随行监测

在快速变化的自然环境中,气象信息的准确获取与及时分析对于农业生产、环境保护、科学研究乃至日常生活都至关重要。随着科技的飞速发展,便携式气象监测系统以其独特的优势,正逐步成为气象监测领域的新宠,引领着气象监测技术的革新…...

uniapp App判断是否安装某个app

参考文档:HTML5 API Reference 项目中需要判断是否安装了uber,这里拿uber举例 ,判断是否安装uber if (plus.runtime.isApplicationExist({pname: com.ubercab.eats, //Android平台通过pname属性(包名)查询action: ub…...

Vim 调用外部命令学习笔记

Vim 外部命令集成完全指南 文章目录 Vim 外部命令集成完全指南核心概念理解命令语法解析语法对比 常用外部命令详解文本排序与去重文本筛选与搜索高级 grep 搜索技巧文本替换与编辑字符处理高级文本处理编程语言处理其他实用命令 范围操作示例指定行范围处理复合命令示例 实用技…...

《用户共鸣指数(E)驱动品牌大模型种草:如何抢占大模型搜索结果情感高地》

在注意力分散、内容高度同质化的时代,情感连接已成为品牌破圈的关键通道。我们在服务大量品牌客户的过程中发现,消费者对内容的“有感”程度,正日益成为影响品牌传播效率与转化率的核心变量。在生成式AI驱动的内容生成与推荐环境中&#xff0…...

【android bluetooth 框架分析 04】【bt-framework 层详解 1】【BluetoothProperties介绍】

1. BluetoothProperties介绍 libsysprop/srcs/android/sysprop/BluetoothProperties.sysprop BluetoothProperties.sysprop 是 Android AOSP 中的一种 系统属性定义文件(System Property Definition File),用于声明和管理 Bluetooth 模块相…...

代理篇12|深入理解 Vite中的Proxy接口代理配置

在前端开发中,常常会遇到 跨域请求接口 的情况。为了解决这个问题,Vite 和 Webpack 都提供了 proxy 代理功能,用于将本地开发请求转发到后端服务器。 什么是代理(proxy)? 代理是在开发过程中,前端项目通过开发服务器,将指定的请求“转发”到真实的后端服务器,从而绕…...

深度学习习题2

1.如果增加神经网络的宽度,精确度会增加到一个特定阈值后,便开始降低。造成这一现象的可能原因是什么? A、即使增加卷积核的数量,只有少部分的核会被用作预测 B、当卷积核数量增加时,神经网络的预测能力会降低 C、当卷…...

【电力电子】基于STM32F103C8T6单片机双极性SPWM逆变(硬件篇)

本项目是基于 STM32F103C8T6 微控制器的 SPWM(正弦脉宽调制)电源模块,能够生成可调频率和幅值的正弦波交流电源输出。该项目适用于逆变器、UPS电源、变频器等应用场景。 供电电源 输入电压采集 上图为本设计的电源电路,图中 D1 为二极管, 其目的是防止正负极电源反接, …...

脑机新手指南(七):OpenBCI_GUI:从环境搭建到数据可视化(上)

一、OpenBCI_GUI 项目概述 (一)项目背景与目标 OpenBCI 是一个开源的脑电信号采集硬件平台,其配套的 OpenBCI_GUI 则是专为该硬件设计的图形化界面工具。对于研究人员、开发者和学生而言,首次接触 OpenBCI 设备时,往…...

提升移动端网页调试效率:WebDebugX 与常见工具组合实践

在日常移动端开发中,网页调试始终是一个高频但又极具挑战的环节。尤其在面对 iOS 与 Android 的混合技术栈、各种设备差异化行为时,开发者迫切需要一套高效、可靠且跨平台的调试方案。过去,我们或多或少使用过 Chrome DevTools、Remote Debug…...

LCTF液晶可调谐滤波器在多光谱相机捕捉无人机目标检测中的作用

中达瑞和自2005年成立以来,一直在光谱成像领域深度钻研和发展,始终致力于研发高性能、高可靠性的光谱成像相机,为科研院校提供更优的产品和服务。在《低空背景下无人机目标的光谱特征研究及目标检测应用》这篇论文中提到中达瑞和 LCTF 作为多…...

c# 局部函数 定义、功能与示例

C# 局部函数:定义、功能与示例 1. 定义与功能 局部函数(Local Function)是嵌套在另一个方法内部的私有方法,仅在包含它的方法内可见。 • 作用:封装仅用于当前方法的逻辑,避免污染类作用域,提升…...