1

在我的应用程序中,我尝试在尽可能少的查询中获取我需要的所有数据。这通常会导致具有许多连接的大型查询。这限制了您可以使用 Memcache 或 Redis 等软件缓存的内容(据我所知)。对于大型查询,您不知道哪些部分可能已被缓存。似乎您必须以较小的部分查询所有内容,以便可以单独缓存这些小部分。这个想法是,您只需执行几十个小查询即可填充缓存,并且大多数情况下您将访问缓存而不是查询。这就是高流量 PHP/MySQL 网站的处理方式吗?即使您有具有许多连接的大型查询,是否有一种有效缓存的好方法?

例子:

SELECT user.name, user.birthday 
FROM follower
    INNER JOIN user ON (user.id = follower.user)
WHERE follower.following = '1'

此查询的结果包括关注用户 1 的任何用户的姓名和生日。此查询的结果可以被缓存,但这仅在获取用户 1 的关注者时才有用。

替代方案:

SELECT follower.user
FROM follower
WHERE follower.following = '1'

对于每个结果?由上一个查询中的 follower.user 填充:

SELECT name, birthday FROM user where user.id = ?

在这种情况下,我们可以在从 MySQL 查询之前检查用户 ? 的姓名和生日是否被缓存。如果它们没有被缓存,或者有些被缓存而有些没有,那么抓取丢失的并缓存它们。您还可以缓存关注者 ID 列表,然后下次不需要运行任何查询。不同之处在于,用户的姓名和生日将对任何其他最终需要在任何其他上下文中了解这些关注者的信息的用户有用。

我在缓存更大的查询时遗漏了一些东西吗?还是第二种方式是正确的方式?

4

2 回答 2

2

正确答案是:视情况而定。

缓存是一种优化公认的使用模式的方法,它通过重复使用先前运行的数据来缩短重复产生昂贵数据的速度。

因此,您应该回答的第一个问题是:是否存在观察到的重复使用模式,该模式具有显着的“昂贵”数据生成步骤?如果不是:不要使用你仍然不需要的缓存,等到你可以观察到一些东西。

您应该能够回答的第二个问题是:您能否测量使用和不使用缓存需要多长时间,并且差异是否明显?

第三个要回答的重要问题是:如果原始数据发生更改,您如何清除缓存中的过时信息,并且您希望立即显示新数据?

因此,在您的情况下,您询问是否将缓存用于大量小型但看似更通用的查询然后组合起来比缓存一个大查询更有益。没有理论上的答案,因为它取决于一个大结果的缓存命中与组合结果的多个缓存命中相比有多快。向缓存发出多个请求可能比从原始源获取数据要慢得多,并且将数据组合成所需的复杂结果也可能比直接从缓存中获取一个复杂结果要慢。

此外,如果对组合结果使用多个缓存条目,您现在必须处理很多情况,其中只有部分信息已过时,而其他信息未过时。所以结果变得更加不可靠——你不能确定结果的每个部分是否都是最新的,或者它有多旧。

于 2013-08-20T20:58:32.667 回答
0

@Sven 你说得对!我添加了更多原始建议。

@Barakat 大查询通常对 MySql 来说没什么大不了的,精心设计的数据库、索引和调整引擎参数通常会带来高性能。

做很多小查询会导致很多开销(缓存或不缓存),我通常会避免这种情况。

如果您的大查询给出了大的结果(成百上千行),您可能可以避免它对结果进行分页或将答案限制为最佳分数。

MysqlTuner.pl是一个非常简单且有效的调整 mysql 服务器的工具,因为您可以使用 MySql内部缓存而无需担心一致性!

于 2013-08-20T21:18:33.723 回答