2014-10-20 66 views
0

我有两个表A和B. A有浮点变量X1,X2,X3,...,X9,游标和14,000行。 B具有浮动变量X1,X2,X3,...,X9,这是一个文本变量'Model',其值为'Model 1','Model 2'等等,以及50行。
我试图加入和使用以下代码执行SUMPRODUCT操作:如何加快SQL Server 2008中的加入和求和产品查询?

Update A set a.sumprod = a.X1*b.X1 + a.X2*b.X2 + ... + a.X9*b.X9 
from a left join b 
on b.Model = 'Model 2'; 

我有多个这样的查询与不同的表为A,并且在表B中的模型变量I具有对应不同的连接条件将这些查询标识为在我的存储过程中花费的时间最长,并且正在寻找一种使其更快的方法。

我试图此查询像下面的变体而不会在运行时的任何重大变化:

变型1:

Update A 
set a.sumprod = a.X1*b.X1 + a.X2*b.X2 + ... + a.X9*b.X9 
from a left join b 
on 1 = 1 
where b.Model = 'Model 2'; 

变体2:

merge A 
using (select X1, X2, ..., X9 from B where Model = 'Model 2') C 
on 1 = 1 
when matched then update 
set sumprod = a.X1*c.X1 + a.X2*c.X2 + ... + a.X9*c.X9; 

编辑为了更清楚:

有多个表A's:A1,A2,A3,...每个表A#都包含exp模型的对角变量(X1,X2等)(对应于表B中的型号)。

所以表A1可能是:

X1 | X2 | X3 | X4 | Sumprod

6 | 7 | 3 | 5 |

5 | 3 | 4 | 4 |

...

表A2将有不同数量的解释变量,并解释变量本身会有所不同。而且,行数将与A1不同。

表B具有每个模型的模型系数,如下所示:

模型| X1 | X2 | X3 | X4 | X5 | X6 | X7 | X8 | X9

模型1 | 3 | 2 | 5 | 9 | 0 | 0 | 0 | 0 | 0

模型2 | 4 | 7 | 8 | 3 | 5 | 8 | 0 | 0 | 0

...

模型1具有四个解释变量,所以模型1行表B中具有用于列X5起零个系数。

我想在每个表A的sumprod列中做的事情是从表B的正确的行取解释变量和系数的和。在表A和系数之间没有公共行标识符表B.我将A1中每行的总和乘以B中的单行。

的加入后,我想表A1的sumprod列填充如下:

X1 | X2 | X3 | X4 | Sumprod

1 | 7 | 3 | 5 | 6 * 3 + 7 * 2 + 3 * 5 + 5 * 9 = 92

5 | 3 | 4 | 4 | 5 * 3 + 3 * 2 + 4 * 5 + 4×9 = 77

...

值的解释变量是固定的但对模型系数的值是用户输入的,并预期相当改变经常。

从最初的评论看来,这不是我想要做的一个好的数据库结构。有关如何让这个速度更快的建议?

+0

您实际上并未执行连接; '从1 = 1的左连接b'连接'a'的每一行到'b'的每一行。例如,如果'a'和'b'每行都有10000行,那么您将创建100000000行的笛卡尔连接。 '更新A'将更新'A'的每一行的次数,因为有'B'行。这似乎效率很低。 – 2014-10-20 19:13:59

回答

0

FROM a LEFT JOIN b ON b.Model = 'Model 2'?我不知道你希望从这个连接中得到什么样的行为,我怀疑查询引擎同样困惑。你真的想要一个CROSS JOIN?那么你应该说CROSS JOIN

这里是我会做:

UPDATE a 
SET a.sumprod = a.X1 * b1.X1 + a.X2 * b1.X2 +...+ a.X9 * b1.X9 
FROM a 
CROSS JOIN (
    SELECT Model, X1, X2, ..., X9 FROM b where Model = 'Model 2' 
    ) b1 
WHERE a.sumprod <> a.X1 * b1.X1 + a.X2 * b1.X2 +...+ a.X9 * b1.X9 
    OR a.sumprod is NULL; 

有,你必须CROSS JOIN理由吗? ab之间是否真的没有关系?这似乎是一个设计问题。你想让的所有内容a.sumprodb的一行中的内容的函数?你打算反复改变它吗?你已经抽象得太过分,无法告诉你想要完成什么。

就个人而言,我会创建一个VIEW返回的必要的乘积,而不是a更新字段存储的聚集是一个普遍较差的想法,但如果你已经有性能问题,可能并不明智。