为什么SELECT *
不好做法?如果添加了您想要的新列,是不是意味着要更改的代码更少?
我知道这SELECT COUNT(*)
是一些DB上的性能问题,但是如果你真的想要每一列呢?
Dav*_*kle 297
实际上有三个主要原因:
将数据移动到消费者的效率低下. 当您选择SELECT*时,您经常从数据库中检索比您的应用程序真正需要的功能更多的列.这会导致更多数据从数据库服务器移动到客户端,从而减慢访问速度并增加计算机负载,并且需要更多时间在网络上传输.当有人向基础表添加新列时,尤其如此,当原始使用者对其数据访问进行编码时,这些列不存在且不需要.
索引问题. 考虑一种情况,您希望将查询调整到高级别的性能.如果您要使用*,并且它返回的列数超过您实际需要的数量,那么服务器通常必须执行更昂贵的方法来检索您的数据.例如,你将无法创建一个只覆盖SELECT列表中的列的索引,即使你做了(包括所有列[ shudder ]),下一个人来到底层并向底层添加了一列table会导致优化器忽略您的优化覆盖索引,并且您可能会发现查询的性能会因为没有明显原因而大幅下降.
约束问题.SELECT*时,可以从两个不同的表中检索两个同名的列.这通常会使您的数据使用者崩溃.想象一下连接两个表的查询,这两个表都包含一个名为"ID"的列.消费者如何知道哪个是哪个?当底层表结构发生更改时,SELECT*还会混淆视图(至少在某些版本的SQL Server中) - 视图不会重建,而返回的数据可能是无意义的.而最糟糕的部分是,您可以随心所欲地为您的列命名,但是下一个出现的人可能无法知道他必须担心添加会与您已开发的列发生冲突的列名.
但对SELECT*来说并不是一件坏事.我在这些用例中大量使用它:
临时查询. 在尝试调试某些东西时,特别是在我可能不熟悉的狭窄桌子上,SELECT*通常是我最好的朋友.它帮助我看到正在发生的事情,而无需对底层列名称进行大量研究.列名称越长,这就越大"加".
当*表示"一行"时. 在下面的使用案例中,SELECT*就好了,并且传言它是性能杀手只是城市传说,这可能在很多年前有一定的效力,但现在还没有:
SELECT COUNT(*) FROM table;
Run Code Online (Sandbox Code Playgroud)
在这种情况下,*表示"计算行数".如果要使用列名而不是*,则会计算该列的值不为空的行.对我来说,COUNT(*)确实驱动了你计算行的概念,并且避免了由于从聚合中消除NULL而导致的奇怪边缘情况.
这种类型的查询也是如此:
SELECT a.ID FROM TableA a
WHERE EXISTS (
SELECT *
FROM TableB b
WHERE b.ID = a.B_ID);
Run Code Online (Sandbox Code Playgroud)
在任何值得盐的数据库中,*只是意味着"一排".你在子查询中放入什么并不重要.有些人在SELECT列表中使用b的ID,或者他们将使用数字1,但IMO这些约定几乎是荒谬的.你的意思是"计算行",这就是*表示的意思.大多数查询优化器都足够聪明,可以知道这一点.(虽然说实话,我只知道 SQL Server和Oracle都是如此.)
OMG*_*ies 88
SELECT语句中的星号字符"*"是查询中涉及的表中所有列的简写.
该*
速记速度可能很慢,因为:
SELECT *
的内容可能会导致全表扫描使用时SELECT *
:
SELECT *
则会在表更改了列顺序时隐藏等待发生的错误.SELECT *
是一种反模式:
SELECT *
当显式需要所涉及的表中的每一列时,使用它是可以接受的,而不是在编写查询时存在的每一列.数据库将在内部将*扩展为完整的列列表 - 没有性能差异.
否则,显式列出要在查询中使用的每一列 - 最好是在使用表别名时.
Mar*_*ers 18
即使您现在想要选择每一列,也可能不希望在某人添加一个或多个新列后选择每一列.如果你写与查询SELECT *
你正在服用的,在某些时候有人可能会增加一列文本,让您的查询的运行速度比较慢,即使你实际上并不需要该列中的风险.
如果添加了您想要的新列,是不是意味着要更改的代码更少?
如果您确实想要使用新列,则无论如何您都必须对代码进行大量其他更改.你只是保存, new_column
- 只有几个字符的输入.
归档时间: |
|
查看次数: |
71351 次 |
最近记录: |