SELECT SQL查询执行时间过长,如何优化加速该语句?
SQL查询优化建议
- 创建匹配查询逻辑的联合索引
你的查询逻辑为等值匹配IsBuy = 0后按Price升序取符合@price >= Price的第一条记录,按「等值条件在前、排序/范围条件在后」的原则创建联合索引,即可让数据库直接利用索引的有序性定位目标行,避免全表扫描和额外排序操作:CREATE NONCLUSTERED INDEX IX_BTC_USDT_OpenOrders_IsBuy_Price ON [Exchange].[Dbo].[BTC_USDT_OpenOrders] (IsBuy, Price ASC) - 使用覆盖索引减少回表开销
尽量不要用SELECT *,仅查询你实际需要的字段,再把这些字段加到索引的INCLUDE子句中,做成覆盖索引,完全跳过回表取数的步骤,进一步提升性能。示例如下(把需要的字段替换到INCLUDE中即可):CREATE NONCLUSTERED INDEX IX_BTC_USDT_OpenOrders_IsBuy_Price_Cover ON [Exchange].[Dbo].[BTC_USDT_OpenOrders] (IsBuy, Price ASC) INCLUDE (Id, Amount, CreateTime, [其他你需要的字段]) - 针对场景使用过滤索引(可选)
如果你固定只查询IsBuy = 0的卖单,可以创建过滤索引,仅存储符合条件的记录,索引体积更小、查询速度更快:CREATE NONCLUSTERED INDEX IX_BTC_USDT_OpenOrders_SellOrder_Price ON [Exchange].[Dbo].[BTC_USDT_OpenOrders] (Price ASC) INCLUDE (你需要的字段) WHERE IsBuy = 0 - 规避隐式类型转换
确认变量@price的数据类型和表中Price字段的数据类型完全一致,避免隐式类型转换导致索引失效。 - 简化数据存储逻辑(可选)
如果后续业务仅需要用到这条订单的个别字段,无需用到整条记录的所有内容,可以直接用变量存储查询结果,省去创建临时表的开销:DECLARE @OrderId BIGINT, @OrderPrice DECIMAL(18,8) -- 按需定义变量类型 SELECT TOP 1 @OrderId = Id, @OrderPrice = Price FROM [Exchange].[Dbo].[BTC_USDT_OpenOrders] WHERE IsBuy = 0 AND @price >= Price ORDER BY Price
内容的提问来源于stack exchange,提问作者AlexPIgalyov
相关产品推荐
相关产品推荐

