AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / dba / 问题 / 312816
Accepted
SEarle1986
SEarle1986
Asked: 2022-06-02 05:39:40 +0800 CST2022-06-02 05:39:40 +0800 CST 2022-06-02 05:39:40 +0800 CST

SQL如何估计小于<谓词中的行数

  • 772

我一直在做一些测试,试图更好地理解 SQL Server 如何使用直方图来估计将匹配相等谓词以及 < 或 > 谓词的行数

鉴于我正在使用AdventureWorks2016 OLTP 数据库

如果能理解 SQL Server 对 = 和 > 谓词的估计过程:

/* update stats with fullscan first */    
UPDATE STATISTICS Production.TransactionHistory WITH FULLSCAN

然后我可以看到该列的直方图TransactionHistory.Quantity

DBCC SHOW_STATISTICS (
    'Production.TransactionHistory', 
    'Quantity')

下面的屏幕截图是我运行测试的直方图的顶端:

在此处输入图像描述

以下查询将估计 6 行,因为谓词中的值是 RANGE_HI_KEY,因此对该存储桶使用 EQ_ROWS:

SELECT  * 
FROM    Production.TransactionHistory
WHERE   Quantity = 2863

以下将估计 1.36 行,因为它不是 RANGE_HI_KEY,因此将 AVG_RANGE_ROWS 用于它所在的存储桶:

SELECT  * 
FROM    Production.TransactionHistory
WHERE   Quantity = 2862

以下“大于”查询将估计 130 行,这似乎是所有 RANGE_HI_KEY > 2863 的桶的 RANGE_ROWS 和 EQ_ROWS 的总和

SELECT  * 
FROM    Production.TransactionHistory
WHERE   Quantity > 2863

下面的类似查询,但该值不是直方图中的 RANGE_HI_KEY。SQL Server 再次估计为 130 并且似乎使用与上述相同的方法

SELECT  * 
FROM    Production.TransactionHistory
WHERE   Quantity > 2870 

到目前为止,这一切都很有意义,所以我的测试转移到了“小于”查询

SELECT  * 
FROM    Production.TransactionHistory
WHERE   Quantity < 490 

对于这个查询,SQL Server 估计有 109,579 行,但我不知道它是从哪里得到的:

所有存储桶的 RANGE_HI_KEY + RANGE_ROWS 直到 RANGE_HI_KEY 470 = 109,566 = 109,566 所以我们在某个地方还差 11 个。

SQL Server 如何使用直方图估计“小于”谓词将返回的行数

sql-server-2016 statistics
  • 1 1 个回答
  • 142 Views

1 个回答

  • Voted
  1. Best Answer
    Paul White
    2022-06-07T04:39:23+08:002022-06-07T04:39:23+08:00

    对于这个查询,SQL Server 估计有109,579 行,但我不知道它是从哪里得到的:

    所有存储桶的 RANGE_HI_KEY + RANGE_ROWS 直到 RANGE_HI_KEY 470 = 109,566 = 109,566所以我们在某个地方还差 11 个。

    你矮 13 岁,而不是 11 岁:109,579 - 109,566 = 13。

    如我的相关答案所示,一般的想法是在部分步骤中使用线性插值,假设均匀。

    在你的情况下:

    直方图片段

    所以问题是当假设它们在直方图步骤中以500均匀分布时RANGE_ROWS,我们期望有多少这 23 个与谓词匹配:< 490RANGE_HI_KEY

    DECLARE
        @ARR float = 23e0 / 6e0, -- AVG_RANGE_ROWS
        @DRR float = 6e0,        -- DISTINCT_RANGE_ROWS
        @PR float = 490 - 470,   -- predicate range
        @SR float = 499 - 470    -- whole step range (excluding high key)
    
    SELECT (@DRR - 1) * ((@PR - 1) / @SR) / ((@SR - 1) / @SR) * @ARR;
    

    该计算得出13.00595。

    假设使用排除一行的-1因素。使用时,假定该行与谓词匹配。<DISTINCT_RANGE_ROW<=

    整个事情是应用您要求的范围的分数与直方图步骤覆盖的范围的修改。在不排除不匹配的值的情况下,它只是@PR/@SR.

    • 6

相关问题

  • 在 Oracle 中获取表的统计信息

  • 计算百分位数的快速通用方法

  • 中位数、众数、百分位数和 OLAP

  • 估计mysql中行访问的分布

  • 什么是数据库统计信息,我如何从中受益?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目

    • 12 个回答
  • Marko Smith

    如何让sqlplus的输出出现在一行中?

    • 3 个回答
  • Marko Smith

    选择具有最大日期或最晚日期的日期

    • 3 个回答
  • Marko Smith

    如何列出 PostgreSQL 中的所有模式?

    • 4 个回答
  • Marko Smith

    列出指定表的所有列

    • 5 个回答
  • Marko Smith

    如何在不修改我自己的 tnsnames.ora 的情况下使用 sqlplus 连接到位于另一台主机上的 Oracle 数据库

    • 4 个回答
  • Marko Smith

    你如何mysqldump特定的表?

    • 4 个回答
  • Marko Smith

    使用 psql 列出数据库权限

    • 10 个回答
  • Marko Smith

    如何从 PostgreSQL 中的选择查询中将值插入表中?

    • 4 个回答
  • Marko Smith

    如何使用 psql 列出所有数据库和表?

    • 7 个回答
  • Martin Hope
    Jin 连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane 如何列出 PostgreSQL 中的所有模式? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh 为什么事务日志不断增长或空间不足? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland 列出指定表的所有列 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney MySQL 能否合理地对数十亿行执行查询? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx 如何监控大型 .sql 文件的导入进度? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison 你如何mysqldump特定的表? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 对 SQL 查询进行计时? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas 如何从 PostgreSQL 中的选择查询中将值插入表中? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 列出所有数据库和表? 2011-02-18 00:45:49 +0800 CST

热门标签

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve