5

我在 excel 中有以下一组计算,我希望能够在存储过程中使用它们。

Excel

CellA: 45/448.2 = 0.100401606425703
CellB: 1-CellA = 0.899598393574297
CellC: 1-CellB = 0.100401606425703
CellD: CellC * 448.2 = 45.000000000000000

在 SQL 中,我正在执行以下操作:

declare @a decimal(18,15) = 45/448.2  
declare @b decimal(18,15) = 1-@a
declare @c decimal(18,15) = 1-@b
declare @d decimal(18,15) = @c * 448.2

我也尝试过在一行中运行计算

declare @e decimal(18,15) = (1-(1-(45/448.2)))*448.2

当我返回值时,SQL 给了我以下信息:

@a: 0.100401000000000
@b: 0.899599000000000
@c: 0.100401000000000
@d: 44.999728200000000

@e: 44.999728200000000

我已经尝试在 SQL 中调整小数的精度,但没有任何区别,它只返回小数的前 6 位。

Excel 在运行公式时是否进行任何优化?

有任何想法吗?

4

1 回答 1

7

即使只是您的第一行也足以说明问题:

declare @a decimal(18,15) = 45/448.2  
print @a

---------------------------------------
0.100401000000000

这是因为数据类型。当你说

448.2

它(根据文档)被解释为类型的常量decimal,并且也根据文档

在 Transact-SQL 语句中,带小数点的常量会自动转换为数字数据值,使用所需的最小精度和小数位数。例如,常数 12.345 被转换为精度为 5、小数位数为 3 的数值。

448.2也是如此decimal(4,3)45is integer,当与 a 结合时,它decimal 被视为具有 10 的精度和 0 的比例。当我们分开时,规则

Operation     Result precision                        Result scale
e1 / e2       p1 - s1 + s2 + max(6, s1 + p2 + 1)      max(6, s1 + p2 + 1)

在这种情况下,它给出了 的结果精度10 - 3 + 0 + max(6, 0 + 3 + 1)和比例max(6, 0 + 3 + 1),得出136

这个结果比例6就是为什么结果只有这六个小数位。

修复它的方法是在对它们进行操作之前将您的操作数转换为适当的类型;例如,这里有两种方法:

强制将数字视为浮点数:

declare @a decimal(18,15) = 45/448.2e0  
select @a

---------------------------------------
0.100401606425703

显式提供小数刻度:

declare @a decimal(18,15) = 45/cast(448.2 as decimal(18,10))
select @a

---------------------------------------
0.100401606425703
于 2013-04-08T16:09:55.343 回答