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 / 问题 / 233445
Accepted
Erik Darling
Erik Darling
Asked: 2019-03-29 15:15:23 +0800 CST2019-03-29 15:15:23 +0800 CST 2019-03-29 15:15:23 +0800 CST

在 SQL Server 中,并行性如何更改内存授予?

  • 772

我听说过有关并行选择查询的内存授予的相互矛盾的事情:

  • 内存授予乘以 DOP
  • 内存授予除以 DOP

它是哪一个?

sql-server parallelism
  • 1 1 个回答
  • 451 Views

1 个回答

  • Voted
  1. Best Answer
    Erik Darling
    2019-03-29T15:15:23+08:002019-03-29T15:15:23+08:00

    苏?

    对于需要额外内存的 SQL Server 查询,授权是为串行计划派生的。如果探索和选择并行计划,内存将在线程之间平均分配。

    内存授予估计基于:

    • 行数(基数)
    • 行大小(数据大小)
    • 并发内存消耗运算符的数量

    如果选择了并行计划,则处理并行交换(分发、重新分发和收集流)会产生一些内存开销,但是它们的内存需求仍然不会以相同的方式计算。

    消耗内存的运算符

    最常见的请求内存的运算符是

    • 排序
    • 哈希(连接、聚合)
    • 优化的嵌套循环

    需要内存的不太常见的运算符是插入列存储索引。它们的不同之处还在于,内存授权当前乘以 DOP。

    排序的内存需求通常远高于散列。排序将要求至少估计内存授予的数据大小,因为它们需要按排序元素对所有结果列进行排序。哈希需要内存来构建哈希表,它不包括所有选定的列。

    例子

    如果我运行这个查询,故意提示 DOP 1,它将要求 166 MB 的内存。

    SELECT *
    FROM 
         (  
            SELECT TOP (1000) 
                   u.Id 
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u
    OPTION(MAXDOP 1);
    

    坚果

    如果我运行这个查询(再次,DOP 1),计划会改变,内存授权会稍微增加。

    SELECT *
    FROM (  
            SELECT TOP (1000) 
                   u.Id
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u
    JOIN (
            SELECT TOP (1000) 
                   u.Id
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u2
    ON u.Id = u2.Id
    OPTION(MAXDOP 1);
    

    坚果

    有两种排序,现在是哈希连接。内存授权稍微增加以适应哈希构建,但它不会加倍,因为排序运算符不能同时运行。

    如果我更改查询以强制嵌套循环连接,则授权将加倍以处理并发排序。

    SELECT *
    FROM (  
            SELECT TOP (1000) 
                   u.Id
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u
    INNER LOOP JOIN ( --Force the loop join
            SELECT TOP (1000) 
                   u.Id
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u2
    ON u.Id = u2.Id
    OPTION(MAXDOP 1);
    

    坚果

    内存授权加倍,因为 Nested Loop 不是阻塞运算符,而 Hash Join 是。

    数据大小很重要

    该查询选择不同组合的字符串数据。根据我选择的列,内存授予的大小会增加。

    为可变字符串数据计算数据大小的方式是行 * 列声明长度的 50%。这对于 VARCHAR 和 NVARCHAR 是正确的,尽管 NVARCHAR 列是双倍的,因为它们存储双字节字符。在某些情况下,新的 CE 确实改变了这一点,但没有记录详细信息。

    数据大小对于散列操作也很重要,但程度不如排序。

    SELECT *
    FROM 
         (  
            SELECT TOP (1000) 
                     u.Id          -- 166MB (INT)
                   , u.DisplayName -- 300MB (NVARCHAR 40)
                   , u.WebsiteUrl  -- 900MB (NVARCHAR 200)
                   , u.Location    -- 1.2GB (NVARCHAR 100)
                   , u.AboutMe     -- 9GB   (NVARCHAR MAX)
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u
    OPTION(MAXDOP 1);
    

    但是并行性呢?

    如果我在不同的 DOP 上运行此查询,则内存授予不会乘以 DOP。

    SELECT *
    FROM (  
            SELECT TOP (1000) 
                   u.Id
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u
    INNER HASH JOIN (
            SELECT TOP (1000) 
                   u.Id
            FROM dbo.Users AS u
            ORDER BY u.Reputation
         ) AS u2
    ON u.Id = u2.Id
    ORDER BY u.Id, u2.Id -- Add an ORDER BY
    OPTION(MAXDOP ?);
    

    坚果

    每个交换运算符处理更多的并行缓冲区略有增加,也许有内部原因,排序和哈希构建需要额外的内存来处理更高的 DOP,但这显然不是一个乘数。

    • 12

相关问题

  • SQL Server - 使用聚集索引时如何存储数据页

  • 我需要为每种类型的查询使用单独的索引,还是一个多列索引可以工作?

  • 什么时候应该使用唯一约束而不是唯一索引?

  • 死锁的主要原因是什么,可以预防吗?

  • 如何确定是否需要或需要索引

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