21年11月第4题

常见的反规划化设计方法

  • (1)增加冗余列:#card

    • 增加冗余列是指在多个表中具有相同的列,它常用来在查询时避免连接操作。
  • (2)增加派生列:#card

    • 增加派生列指增加的列可以通过表中其他数据计算生成。它的作用是在查询时减少计算量,从而加快查询速度。
  • (3)重新组表:#card

    • 重新组表指如果许多用户需要查看两个表连接出来的结果数据,则把这两个表重新组成一个表来减少连接而提高性能。
  • (4)分割表:#card

    • 有时对表做分割可以提高性能。

反规范化解决数据不一致问题的方法

  • 定期同步更新:#card

    • 通过定时任务批量更新冗余字段,适合实时性要求不高的场景。
  • 触发器同步:#card

    • 在数据库中设置触发器,当源表更新时自动同步冗余字段,实时性高。
  • 应用程序级同步:#card

    • 在业务逻辑中,更新源表数据的同时也更新冗余数据,通常借助事务保持一致性。

该医药销售系统,药品数据更新频繁,采用触发器法和应用程序校验较合适。#card

  • 因为它能在数据更新瞬间自动维护一致性,无需应用程序过多干预,也避免了定时任务的延迟性,可实时保证数据一致性 ,不影响系统对药品信息的实时展示和业务操作。

其中 ZSet(有序集合) 最适合实现热销药品排名 #card

  • 因为它可以通过 score 存储销量,并且支持自动排序、区间查询,非常契合排行榜场景。

  • 例如:ZINCRBY sales 1 drugID 可以为某药品销量加 1,然后通过 ZREVRANGE 获取销量前 N 的药品。

解决 Redis 和 MySQL 数据实时同步问题的方案 缓存与数据库的数据一致性

  • 基于 Binlog 异步同步 。#card

    • 用 Canal 等工具监听 MySQL 的 Binlog 日志,解析数据变更事件并推送到 Redis。

    • 对应用透明,能捕获多种操作,可靠性高,但有延迟,部署复杂。

    • 适用于高频写且要求最终一致场景。

  • 应用层双写。#card

    • 业务代码中同步写 MySQL 和 Redis,靠事务保证原子性。强一致、低延迟,但双写增加耗时,事务处理复杂。

    • 适用于低频写、强一致场景 。

  • 消息队列解耦。 #card

    • 写 MySQL 后发消息到队列,消费者异步更新 Redis。

    • 可解耦、削峰填谷,但有秒级延迟和消息堆积风险。

    • 适用于高并发写、允许短暂不一致场景。

  • 延迟双删。#card

    • 更新 MySQL 前后各删一次 Redis 缓存。

    • 简单有效,能减少不一致窗口,但极端并发下仍可能有脏数据。适用于读多写少、对一致性要求不苛刻场景。

  • 结合数据库触发器。#card

    • 在 MySQL 设触发器,监听数据变更并调外部程序更新 Redis。会增加数据库负载,维护困难。适用于遗留系统改造。
作者

Ryen Xiang

发布于

2026-01-31

更新于

2025-10-22

许可协议


网络回响

评论