繁体   English   中英

如何优化 SQL 查询?

[英]How to optimize SQL query?

我有 2 个表(“keys”由大约 6 个字段组成,“stats”由大约 65 个字段组成)。

我想在两个表中插入行而不复制短语文本。 我使用这样的东西:

UPDATE Keys SET CommandType = 'ADDED', CommandCode = @CommandCode WHERE 
KeyText = @KeyText AND Tab_ID = @TabID AND CommandType = 'DELETED';

INSERT INTO Keys (IsChecked, KeyText, AddDateTime, Tab_ID, KeySource_ID, CommandCode, CommandType)
SELECT 0, @KeyText, datetime(), @TabID, @KeySourceID, @CommandCode, 'ADDED'
WHERE NOT EXISTS (SELECT 1 FROM Keys WHERE Tab_ID = @TabID AND KeyText = @KeyText);

INSERT INTO Statistics (Key_ID)
SELECT ID FROM Keys WHERE KeyText = @KeyText AND Tab_ID = @TabID AND (CommandType IS NULL OR CommandType <> 'DELETED') AND 
NOT EXISTS (SELECT 1 FROM Statistics WHERE Key_ID = (SELECT ID FROM Keys WHERE KeyText = @KeyText AND Tab_ID = @TabID AND (CommandType IS NULL OR CommandType <> 'DELETED') LIMIT 1));

我该如何优化它? 我为此查询字段中使用的所有内容创建索引。 也许您可以向我推荐一些解决方案?

感谢您的帮助,并为我的英语不好感到抱歉。

您可以使用 MERGE 语句将插入/更新语句组合成单个语句。 如果要将键的修改复制到统计信息中,可以使用 OUTPUT 语句。

您必须将索引添加到问题中才能评论它们的有效性,但基本上您希望每个表上都有一个索引,其中包含 where 子句中的所有列。 您想将包含列用于 select 中不在 where 子句中的任何内容。

优化的最佳方法是获取估计/实际的查询计划,并查看查询的哪些部分较慢。 在 SQL 服务器中,这是从“查询”菜单完成的。 基本上,请注意任何说“扫描”的内容,这意味着您缺少索引。 “寻求”是好的。

但是,查询计划最有助于微调。 在这种情况下,使用不同的算法(如合并/输出)将产生更大的差异。

在 SQL 服务器中,结果看起来有点像这样:

INSERT INTO [Statistics] (ID)
SELECT ID FROM
(
    MERGE [Keys] AS TARGET
    USING (
        SELECT @KeyText AS KeyText, @TabID AS TabId, @CommandCode AS CommandCode, @KeySourceID AS KeySourceID, 'Added' AS CommandType
    ) AS SOURCE
    ON (target.KeyText = source.KeyText AND target.Tab_Id = @TabID)
    WHEN MATCHED AND CommandType = 'DELETED' THEN
        UPDATE SET Target.CommandType = Source.CommandType, Target.CommandCode = Source.CommandCode
    WHEN NOT MATCHED BY TARGET THEN
        INSERT (IsChecked, KeyText, AddDateTime, Tab_Id, KeySource_ID, CommandCode, CommandType) VALUES (0, KeyText, getdate(), TabId, KeySourceId, CommandCode, CommandType)
    OUTPUT $Action, INSERTED.ID
) AS Changes (Action, ID)
WHERE Changes.Action = 'INSERT'
AND NOT EXISTS (SELECT 1 FROM Statistics b WHERE b.ID = Changes.ID)

创建索引会减慢插入和更新查询的速度,因为索引必须与数据一起更新。 要优化您的特定插入语句,请去掉典型 select 语句不需要的任何索引。 然后努力简化那些“不存在”的条款。 这些是您将获得的任何性能提升的唯一来源。 简化后,尝试创建索引以加快该子查询的速度。

问题在于我的表的索引错误。 我重建它并用 static 内容替换了一些查询参数,效果很好!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM