我正在Behold WordPress, Destroyer of CPUs阅读Jeff Atwood的博客,看到很多人认为每页加载20个SQL查询很多。现在,对于具有自动建议,自动刷新数据,自定义页面和厨房水槽的高动态页面,每页的平均查询量是多少?
举一个简单的例子,Amazon.com几乎可以根据他们认为我会购买的东西来定制我的主页。对我来说,这看起来并不只是对首页使用5个或更少的查询。
我仍然是数据库的新手,所以请告诉我,我是否遗漏了一些明显的东西。
答案 0 :(得分:26)
您通常可以将所有数据放在两个或三个大查询中,而不是二十个小查询中。最小化查询量与编写最佳查询以最大化性能一样重要,如果不是最重要的话。
当然,您应该始终分析查询计划,并针对最佳查询,无论是小型还是大型。
问题在于,设计糟糕的网页会执行许多查询,每个小任务一个查询,可以轻松地在一个查询中进行分组。
例如,设计糟糕的stackoverflow可以执行查询以获取它将在主页面上显示的所有问题ID,然后针对每个问题执行一个查询以获取摘要和投票。然后你有20个无用的查询。设计良好的将执行单个查询,获取有关它将显示的所有问题的所有信息。
当然,通过良好的缓存来减少这一切的影响,这是所有大型网站所做的,这样你实际上可以做很多查询并且仍然可以获得不错的性能。
答案 1 :(得分:12)
更多是关于缓存。
如果您获得了大量的并发页面视图,并且每个页面视图都会执行大量查询,那么每次点击数据库都没有多大意义。单。时间。特别是当很多数据返回时,半动态参考数据只会偶尔发生变化(而不是会话或实时数据总是在变化)。
您也可以使用memcached或类似的方法缓存这些数据库结果。您不一定需要缓存整个页面(尽管这是大多数Wordpress缓存插件所做的),因为这会杀死交互性,但您可以逐个数据地缓存。
还有优化查询的问题。特别是避免了对父记录执行一次查询的可怕N + 1情况,然后对其子项的每个进行额外查询。单独来回往返数据库的延迟将会破坏您的页面呈现性能,更不用说引起数据库本身的悲痛。
答案 2 :(得分:6)
我在派对上总是迟到,这有点迟了5年......
但对于这个问题的最重要的答案是,查询的数量至少比查询时间要长。
如果具有多个连接和子查询的大型查询需要20秒才能执行,那么(我认为)20个小查询总共需要0.2秒才会更好。
我发现管理较小的查询更容易,主要是因为我缓存了每个查询,我可以一次又一次地重复使用来自该查询的数据......
答案 3 :(得分:5)
答案实际上取决于几个关键因素: - 您网站的流量 - 支持的IT预算 - 网站的复杂性和优化所需的资源
如果您的网站每天点击几次,那么谁会关心20个查询。 另一方面,如果您是亚马逊,那么您将以较大的基础设施成本提供所需的内容。
世界上其他所有人都处于这两个极端之间,必须根据自己的资源进行平衡。
我要说的另一件事就是缓存是你的朋友。
答案 4 :(得分:1)
如果你必须做20个查询,那么就这样吧,但如果它是一个头版,它会让我有点紧张。
在可能的情况下组合查询可能会有所帮助,但考虑缓存是最重要的部分。
我目前正在升级一个网站,每年有5到6次更改的数据每天被查询数千次,使用一些非常讨厌的SQL将其变成树,但可以保存为大约200k的树结构RAM。 (头版也是700k的观点状态,但那是另一个故事......)这些都是那些使网站瘫痪的事情。
所以,关于你应该或不应该做多少查询,没有神奇的数字,但想想它们中的每一个,即使你只缓存其中一些只有5分钟,这将产生巨大的差异,如果有的话你点击了digg的头版。
只有1个查询的5分钟缓存可以在您的网站受到压力时删除数千个数据库命中。
答案 5 :(得分:1)
鉴于没有使用Ajax,每个页面都是原子的,我没有发现在3个或更少的查询中生成相当复杂的页面很困难。从概念上讲,典型的页面集包括:
需要提前规划;但另一方面,在大多数情况下,这是一个简单的重构练习。
答案 6 :(得分:1)
这取决于您正在构建的应用程序类型,查询的复杂性以及数据库引擎和服务器允许您执行的操作。
如果您的数据库服务只允许您进行简单的SQL查询,那么对于一个小的,通用的网页来说,只有不到20个查询就可以了,但如果它是您大学的网页或决定采用支持应用程序,那么60可能不够
如果您具有权限并且您的DBMS能够(例如,与旧版本的MySql相比,Oracle等),则超过20个查询会要求您开始为繁重的任务创建存储过程,函数和触发器。在许多情况下你不能,所以查询的数量自然增长,你开始使用缓存来缓解服务器的压力。
例如,使用子查询可以在较少的查询中实现一些繁重的任务,但它们在数据库引擎上非常繁重。在某些情况下,它们并不是真正建议的,如果它们涉及数千条记录,则应谨慎使用。
来自Vinko的例子可能适用于小型的1周开发“项目”,但如果你问亚马逊,他们就不会使用你常用的PHP / MySQL开发包;前门背后是一个复杂的分布式计算系统和数据挖掘算法。如果你是新手,你不应该把这样的大兄弟作为参考......
答案 7 :(得分:0)
我的经验法则是尽可能将首页保持在5-7以下,具体取决于网站的类型。
内页,取决于他们需要的东西可能有更多,但我会尽我所能将其保持在20以下。
然而,与此同时,根据您正在尝试做什么以及您使用该信息进行的缓存类型20如果其中15个被高度缓存可能并不错...
答案 8 :(得分:0)
查询的数量并不是那么重要。这真的是你如何处理连接。如果你有连接池,那么它确实无关紧要,服务器的物理位置很重要。如果您的服务器在数据中心中彼此相邻,那么设置连接可能非常快。大多数情况下,如果数据库驱动的站点是等待连接打开和获取数据,那么您的网站会花费加载。图打开连接需要100 - 300ms。因此,如果您必须为每个数据库访问打开20个连接,那么打开和关闭连接只需4-6秒。
由于Jeff Atwood正在使用LINQ,我假设他只打开一个连接,执行他的20个查询然后关闭连接。这一切都可能很快发生。
此外,Jeff的数据库在同一台物理计算机上运行,并使用内部计算机通信与数据库而不是网络进行通信,因此确实没有任何与TCP类型连接打开关联的延迟。 (他几周前在Hanselminutes播客上谈过这个。)
我的一个站点使用LINQ和数据库在同一个盒子上有类似的配置。当我在本地计算机上运行该站点时,在另一个状态下访问服务器上的数据库时,最多需要6秒钟才能加载一些数据量很大的页面。当我在服务器上运行该站点时,页面加载的时间不到一秒,因为一切都是服务器本地的。