只是想知道你们中是否有人使用Count(1)而不是Count(*),是否在性能上有明显的差异,或者这只是过去几天养成的传统习惯?

特定的数据库是SQL Server 2005。


当前回答

显然,COUNT(*)和COUNT(1)将始终返回相同的结果。因此,如果一个比另一个慢,这实际上是由于优化器错误。由于这两种形式在查询中都使用得非常频繁,所以DBMS不允许这样的错误保持不变是没有意义的。因此,您将发现两种形式的性能(可能)在所有主要的SQL DBMS中都是相同的。

其他回答

在SQL Server中,这些语句产生相同的计划。

与流行的观点相反,在甲骨文公司,他们也是如此。

Oracle中的SYS_GUID()是一个计算密集型函数。

在我的测试数据库中,t_even是一个包含1000000行的表

此查询:

SELECT  COUNT(SYS_GUID())
FROM    t_even

运行48秒,因为函数需要计算返回的每个SYS_GUID(),以确保它不是NULL。

但是,此查询:

SELECT  COUNT(*)
FROM    (
        SELECT  SYS_GUID()
        FROM    t_even
        )

运行仅2秒,因为它甚至不尝试计算SYS_GUID()(尽管*是COUNT(*)的参数)

COUNT(*)和COUNT(1)在结果和性能方面是相同的。

我希望优化器能够确保在奇怪的边缘情况之外没有真正的差异。

与任何事情一样,唯一真正的方法就是衡量你的具体情况。

也就是说,我一直使用COUNT(*)。

在所有RDBMS中,这两种计数方式在产生什么结果方面是等价的。关于性能,我没有在SQL Server中观察到任何性能差异,但值得指出的是,一些RDBMS,例如PostgreSQL 11,在检查参数表达式的可空性时,COUNT(1)的实现不太理想,如本文所示。

我发现运行以下命令时,1M行的性能差异为10%:

-- Faster
SELECT COUNT(*) FROM t;

-- 10% slower
SELECT COUNT(1) FROM t;

COUNT(1)与COUNT。关于计数空列的问题,这可以直接演示COUNT(*)和COUNT之间的差异(<somecol>)--

USE tempdb;
GO

IF OBJECT_ID( N'dbo.Blitzen', N'U') IS NOT NULL DROP TABLE dbo.Blitzen;
GO

CREATE TABLE dbo.Blitzen (ID INT NULL, Somelala CHAR(1) NULL);

INSERT dbo.Blitzen SELECT 1, 'A';
INSERT dbo.Blitzen SELECT NULL, NULL;
INSERT dbo.Blitzen SELECT NULL, 'A';
INSERT dbo.Blitzen SELECT 1, NULL;

SELECT COUNT(*), COUNT(1), COUNT(ID), COUNT(Somelala) FROM dbo.Blitzen;
GO

DROP TABLE dbo.Blitzen;
GO