测试设置的一些特征:
- AMD Ryzen 3600 CPU 设置为性能模式。我的测试脚本本质上是同步的,即基本上使用单个 CPU 内核,所以速度可能很重要。
- Ubuntu 20.04 桌面作为操作系统,禁用交换。
- PostgreSQL v13.3,即最新的。
- 默认 PostgreSQL 配置:“shared_buffers=512MB”、“track_io_timing=on”、“shared_preload_libraries='pg_stat_statements'”。
- 用于系统和数据库的单个 NVMe SSD。
- 使用准备好的语句读取/写入 Postgres 以获得最佳查询性能,避免解析后续调用。
- 完全适合 PostgreSQL 管理缓存(共享缓冲区)的数据集大小。
- 异步模式用于写入数据,这意味着在服务器崩溃/重启的情况下,最近的数据可能会略有丢失,作为更多写入(尤其是在小事务中)性能的权衡。但这与 Redis 和 Memcached 默认处理写入的方式一致。不过,使用 Redis,还可以启用 AOF 持久性以获得 PostgreSQL 默认行为。
- 两个读/写测试都从 1 到$rows一一遍历所有插入的随机生成的浮点数据键。
- 键值表在读取测试之前被提取到 Postgres 缓存中,因此不会像 Redis/Memcached 那样有冷缓存效应。
- 我没有测量 Postgres 的内存使用情况,因为在插入和缓存所有数据之后,对于这个用例,这预计会非常稳定。
- 执行时间记录在应用程序端,并调用系统时钟以匹配原始测试。请注意,我决定从服务器端测量执行时间也是为了更好地了解“浪费”的数量,因为毕竟 Python 并不是性能测试的最佳选择,原因有很多,我不想在这里深入研究. 再往前走一点——结果确实非常可怕,人们不应该使用 Python 来对数据库进行基准测试——很多 CPU 时间就在某处消失了!
- 完整的测试脚本可在此处获得。运行大约需要 10-15 分钟。基本上是这样的:
CREATE UNLOGGED TABLE kv_test(key text, value int); |
PostgreSQL vs Redis vs Memcached:写操作
写入键值对的计算时间以毫秒为单位。
数据库 1,000行 10,000行 100,000行 1,000,000行 |
PostgreSQL vs Redis vs Memcached:读操作
计算的读取键值对的时间(毫秒)。
数据库 1,000 10,000 100,000 1,000,000 |
Postgres 的读测试结果领先,看起来非常好!与 Postgres 相比,Redis/Memcached 的平均键读取时间似乎太慢了。我怀疑他们仍然使用远程机器作为缓存。
写入操作方面,Postgres 对于 100k 和 1M 行记录写入,仅比 Redis 慢 2 倍。
缓存的主要思想是,与无论如何写入/更新相比,只有当我们从它们中读取更多内容时,它们才有用!
很高兴看到 Postgres 对不断增长的数据集的响应的相对稳定性非常非常好!甚至击败了在 100 万行读取慢2 倍的 Memcached!
这一切都可能表明,为 PostgreSQL 选择的算法在数学上是合理的,并且实现得很好!
banq注:不能忽视Redis/Memcached分布式伸缩扩展能力。