首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >运行速度(低效查询)

运行速度(低效查询)
EN

Stack Overflow用户
提问于 2014-04-10 12:51:29
回答 7查看 77关注 0票数 0

我有下面的查询,这个查询效率不高,而且很多时候会带来内存不足的消息,有人能给出一些建议来帮助加快速度吗?谢谢吉姆

代码语言:javascript
复制
DECLARE @period_from INT
SET @period_from = 201400

DECLARE @period_to INT
SET @period_to = 201414

Declare @length INT
Set @length = '12'

DECLARE @query VARCHAR(MAX)
SET @query = '%[^-a-zA-Z0-9() ]%'

SELECT 'dim_2' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_2 LIKE @query
UNION
SELECT 'dim_3' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_3 LIKE @query
UNION
SELECT 'dim_4' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_4 LIKE @query
UNION
SELECT 'dim_5' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_5 LIKE @query
UNION
SELECT 'dim_6' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_6 LIKE @query
UNION
SELECT 'dim_7' AS field, NULL AS Length,* FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_7 LIKE @query
UNION
SELECT 'ext_inv_ref' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND ext_inv_ref LIKE @query
UNION
SELECT 'ext_ref' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND ext_ref LIKE @query
UNION
SELECT 'description' AS field, NULL AS Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND description LIKE @query
UNION
SELECT 'Length dim_2' AS field,LEN(dim_2) as Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_2 is not null and len(dim_2) >@length
UNION
SELECT 'Length dim_3' AS field, LEN(dim_3) as Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_3 is not null and len(dim_3) >@length
UNION
SELECT 'Length dim_4' AS field, LEN(dim_4) as Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_4 is not null and len(dim_4) >@length
UNION
SELECT 'Length dim_5' AS field, LEN(dim_5) as Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_5 is not null and len(dim_5) >@length
UNION
SELECT 'Length dim_6' AS field, LEN(dim_6) as Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_6 is not null and len(dim_6) >@length
UNION
SELECT 'Length dim_7' AS field, LEN(dim_7) as Length, * FROM table1 WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to AND dim_7 is not null and len(dim_7) >@length
EN

回答 7

Stack Overflow用户

回答已采纳

发布于 2014-04-10 13:13:32

您可以显着地减少工会的数量,但是工作会进入WHERE子句。SQL查询优化器应该知道,对于每个union语句,您只需要遍历表中的行一次,所以它应该会更快。像这样试试,看看!

代码语言:javascript
复制
SELECT 
CASE 
 WHEN dim_2 like @query Then 'dim_2' 
 WHEN dim_3 like @query Then 'dim_3' 
 WHEN dim_4 like @query Then 'dim_4' 
 WHEN dim_5 like @query Then 'dim_5' 
 WHEN dim_6 like @query Then 'dim_6' 
 WHEN dim_7 like @query Then 'dim_7' 
 WHEN ext_inv_ref LIKE @query Then 'ext_inv_ref'
 WHEN ext_ref LIKE @query Then 'ext_ref'
END AS field, 
NULL AS Length, 
* 
FROM table1 
WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to 
AND (dim_2 LIKE @query 
     OR dim_3 LIKE @query 
     OR dim_4 LIKE @query 
     OR dim_5 LIKE @query 
     OR dim_6 LIKE @query 
     OR dim_7 LIKE @query
     OR ext_inv_ref LIKE @query
     OR ext_ref LIKE @query)

友联市

代码语言:javascript
复制
SELECT 
CASE 
 WHEN dim_2 is not null and len(dim_2) >@length Then 'Length dim_2' 
 WHEN dim_3 is not null and len(dim_3) >@length Then 'Length dim_3' 

 ....     

END AS field, 
LEN(dim_2) as Length,
* 
FROM table1 
WHERE client = 'CL'AND period >= @period_from AND @period_to <= @period_to 
AND ((dim_2 is not null and len(dim_2) >@length)
     OR
     (dim_3 is not null and len(dim_3) >@length)
     OR ....
     )
票数 1
EN

Stack Overflow用户

发布于 2014-04-10 13:09:30

我不认为你能优化这么多。数据库将dim1到dim7作为一个表的列。现在你想把他们当作独立的专栏对待。因此,数据库设计不能满足您的要求。如果这只是一个例外,你将不得不忍受它。但是,如果这种使用成为典型的访问方式,那么应该考虑更改数据库设计,并为维度设置一个额外的表。

您不必要地做的一件事是使用UNION,它允许dbms查找副本。当您的记录以不同的常量开始时,每个工会组都不会有。改用UNION ALL

票数 2
EN

Stack Overflow用户

发布于 2014-04-10 13:05:40

这里有很多事情要做,但是您可以这样做:

代码语言:javascript
复制
CREATE TEMPORARY TABLE temp_table1 
SELECT * FROM table WHERE client = 'CL' 
AND period >= @period_from AND @period_to <= @period_to; 

然后使用此表作为其他工会的基础,然后删除它。如果经常这样选择,在创建临时表时,在periodclient字段中引入复合索引可能也会有所帮助:

代码语言:javascript
复制
ALTER TABLE table1 ADD KEY period_client (client, period);
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/22988621

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档