- r - 以节省内存的方式增长 data.frame
- ruby-on-rails - ruby/ruby on rails 内存泄漏检测
- android - 无法解析导入android.support.v7.app
- UNIX 域套接字与共享内存(映射文件)
我正在尝试在 redis 中存储一个单词表。表演很棒。
我的方法是创建一个名为“words”的集合并通过“sadd”添加每个新单词。
当添加一个 15.9 MB 且包含大约一百万字的文件时,redis-server 进程会消耗 160 MB 的内存。为什么我使用了 10 倍的内存,有没有更好的方法来解决这个问题?
最佳答案
这是任何高效的数据存储所期望的:单词必须在内存中以由指针链接的单元格的动态数据结构进行索引。结构元数据、指针和内存分配器内部碎片的大小是数据比相应平面文件占用更多内存的原因。
Redis 集以哈希表的形式实现。这包括:
以上所有大小都是针对 64 位实现给出的。考虑到内存分配器开销,对于使用 jemalloc 分配器 (>= 2.4) 的最新版本的 Redis,Redis 每个集合项(在数据之上)至少占用 64 个字节
Redis 提供 memory optimizations对于某些数据类型,但它们不涵盖字符串集。如果你真的需要优化集合的内存消耗,你可以使用一些技巧。我不会只为 160 MB 的 RAM 执行此操作,但如果您有更大的数据,您可以这样做。
如果您不需要集合的并集、交集、差集功能,那么您可以将单词存储在哈希对象中。好处是如果哈希对象足够小,Redis 可以使用 zipmap 自动优化哈希对象。 zipmap 机制在 Redis >= 2.6 中已被 ziplist 取代,但想法是一样的:使用可放入 CPU 缓存中的序列化数据结构,以获得性能和紧凑的内存占用。
为了保证散列对象足够小,数据可以按照某种散列机制进行分布。假设你需要存储1M个项目,添加一个词可以通过以下方式实现:
而不是存储:
words => set{ hi, hello, greetings, howdy, bonjour, salut, ... }
你可以存储:
words:H1 => map{ hi:1, greetings:1, bonjour:1, ... }
words:H2 => map{ hello:1, howdy:1, salut:1, ... }
...
要检索或检查单词的存在,它是相同的(散列并使用 HGET 或 HEXISTS)。
使用此策略,如果哈希的模数为根据 zipmap 配置(或 Redis >= 2.6 的 ziplist)选择:
# Hashes are encoded in a special way (much more memory efficient) when they
# have at max a given number of elements, and the biggest element does not
# exceed a given threshold. You can configure this limits with the following
# configuration directives.
hash-max-zipmap-entries 512
hash-max-zipmap-value 64
注意:这些参数的名称已随着 Redis >= 2.6 更改。
这里,1M 项的模 10000 意味着每个哈希对象有 100 个项,这将保证所有这些项都存储为 zipmaps/ziplists。
关于performance - Redis 内存使用量比数据多 10 倍,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10004565/
我有一个关于 Redis Pubsub 的练习,如下所示: 如果发布者发布消息但订阅者没有收到服务器崩溃。订阅者如何在重启服务器时收到该消息? 请帮帮我,谢谢! 最佳答案 在这种情况下,消息将永远消失
我们正在使用 Service Stack 的 RedisClient 的 BlockingDequeue 来保存一些数据,直到它可以被处理。调用代码看起来像 using (var client =
我有一个 Redis 服务器和多个 Redis 客户端。每个 Redis 客户端都是一个 WebSocket+HTTP 服务器,其中包括管理 WebSocket 连接。这些 WebSocket+HTT
我有多个 Redis 实例。我使用不同的端口创建了一个集群。现在我想将数据从预先存在的 redis 实例传输到集群。我知道如何将数据从一个实例传输到集群,但是当实例多于一个时,我无法做到这一点。 最佳
配置:三个redis集群分区,跨三组一主一从。当 Master 宕机时,Lettuce 会立即检测到中断并开始重试。但是,Lettuce 没有检测到关联的 slave 已经将自己提升为 master
我想根据从指定集合中检索这些键来删除 Redis 键(及其数据集),例如: HMSET id:1 password 123 category milk HMSET id:2 password 456
我正在编写一个机器人(其中包含要禁用的命令列表),用于监视 Redis。它通过执行禁用命令,例如 (rename-command ZADD "")当我重新启动我的机器人时,如果要禁用的命令列表发生变化
我的任务是为大量听众使用发布/订阅。这是来自 docs 的订阅的简化示例: r = redis.StrictRedis(...) p = r.pubsub() p.subscribe('my-firs
我一直在阅读有关使用 Redis 哨兵进行故障转移的内容。我打算有1个master+1个slave,如果master宕机超过1分钟,就把slave变成master。我知道这在 Sentinel 中是
与仅使用常规 Redis 和创建分片相比,使用 Redis 集群有哪些优势? 在我看来,Redis Cluster 更注重数据安全(让主从架构解决故障)。 最佳答案 我认为当您需要在不丢失任何数据的情
由于 Redis 以被动和主动方式使 key 过期, 有没有办法得到一个 key ,即使它的过期时间已过 (但 在 Redis 中仍然存在 )? 最佳答案 DEBUG OBJECT myKey 将返回
我想用redis lua来实现monitor命令,而不是redis-cli monitor。但我不知道怎么办。 redis.call('monitor') 不起作用。 最佳答案 您不能从 Redis
我读过 https://github.com/redisson/redisson 我发现有几个 Redis 复制设置(包括对 AWS ElastiCache 和 Azure Redis 缓存的支持)
Microsoft.AspNet.SignalR.Redis 和 StackExchange.Redis.Extensions.Core 在同一个项目中使用。前者需要StackExchange.Red
1. 认识 Redis Redis(Remote Dictionary Server)远程词典服务器,是一个基于内存的键值对型 NoSQL 数据库。 特征: 键值(key-value)型,value
1. Redis 数据结构介绍 Redis 是一个 key-value 的数据库,key 一般是 String 类型,但 value 类型多种多样,下面就举了几个例子: value 类型 示例 Str
1. 什么是缓存 缓存(Cache) 就是数据交换的缓冲区,是存贮数据的临时地方,一般读写性能较高。 缓存的作用: 降低后端负载 提高读写效率,降低响应时间 缓存的成本: 数据一致性成本 代码维护成本
我有一份记录 list 。对于我的每条记录,我都需要进行一些繁重的计算,因为我要在Redis中创建反向索引。为了达到到达记录,需要在管道中执行多个redis命令(sadd为100 s + set为1
我有一个三节点Redis和3节点哨兵,一切正常,所有主服务器和从属服务器都经过验证,并且哨兵配置文件已与所有Redis和哨兵节点一起更新,但是问题是当Redis主服务器关闭并且哨兵希望选举失败者时再次
我正在尝试计算Redis中存储的消息之间的响应时间。但是我不知道该怎么做。 首先,我必须像这样存储chat_messages的时间流 ZADD conversation:CONVERSATION_ID
我是一名优秀的程序员,十分优秀!