SELECT SUM(单价) AS 金额 --这里用了聚合函数,所以字段金额会用默认的精度 INTO 表2 FROM 表1
--下面是例子:--测试表 create table tb(a decimal(18,9))--生成tb1,用聚合函数,精度&长度就是默认值 select aa=sum(a) into tb1 from tb--生成tb2,不用聚合函数,精度&长度就不会变 select aa=a into tb2 from tb--显示表结构 SELECT 表名=case when a.colorder=1 then d.name else '' end, 字段名=a.name,类型=b.name,占用字节数=a.length, 长度=COLUMNPROPERTY(a.id,a.name,'PRECISION'), 小数位数=isnull(COLUMNPROPERTY(a.id,a.name,'Scale'),0) FROM syscolumns a left join systypes b on a.xtype=b.xusertype inner join sysobjects d on a.id=d.id and d.xtype='U' and d.name<>'dtproperties' where d.name in('tb','tb1','tb2') order by a.id,a.colordergo --删除测试 drop table tb,tb1,tb2/*--测试结果 表名 字段名 类型 占用字节数 长度 小数位数 ------- ------- -------------------- ---- ------- tb a decimal 9 18 9 tb1 aa decimal 17 38 9 tb2 aa decimal 9 18 9(所影响的行数为 3 行) --*/
指定精度或对象能够控制的数字个数。s
指定可放到小数点右边的小数位数或数字个数。p 和 s 必须遵守以下规则:0 <= s <= p <= 38。
带定点精度和小数位数的 numeric 数据类型。decimal[(p[, s])] 和 numeric[(p[, s])]定点精度和小数位数。使用最大精度时,有效值从 - 10^38 +1 到 10^38 - 1。decimal 的 SQL-92 同义词是 dec 和 dec(p, s)。p(精度)指定小数点左边和右边可以存储的十进制数字的最大个数。精度必须是从 1 到最大精度之间的值。最大精度为 38。s(小数位数)指定小数点右边可以存储的十进制数字的最大个数。小数位数必须是从 0 到 p 之间的值。默认小数位数是 0,因而 0 <= s <= p。最大存储大小基于精度而变化。精度 存储字节数
1 - 9 5
10-19 9
20-28 13
29-38 17
但我现在最关心的不是decimal的精度到底最大是多少,我最关心的是:我的原表:表1中“单价”字段的类型是decimal,长度是9,精度是18,为什么通过上面的操作产生的表2中,金额字段长度变成了17,精度38呢?
INTO 表2
FROM 表1
create table tb(a decimal(18,9))--生成tb1,用聚合函数,精度&长度就是默认值
select aa=sum(a) into tb1 from tb--生成tb2,不用聚合函数,精度&长度就不会变
select aa=a into tb2 from tb--显示表结构
SELECT
表名=case when a.colorder=1 then d.name else '' end,
字段名=a.name,类型=b.name,占用字节数=a.length,
长度=COLUMNPROPERTY(a.id,a.name,'PRECISION'),
小数位数=isnull(COLUMNPROPERTY(a.id,a.name,'Scale'),0)
FROM syscolumns a
left join systypes b on a.xtype=b.xusertype
inner join sysobjects d on a.id=d.id and d.xtype='U' and d.name<>'dtproperties'
where d.name in('tb','tb1','tb2')
order by a.id,a.colordergo
--删除测试
drop table tb,tb1,tb2/*--测试结果
表名 字段名 类型 占用字节数 长度 小数位数
------- ------- -------------------- ---- -------
tb a decimal 9 18 9
tb1 aa decimal 17 38 9
tb2 aa decimal 9 18 9(所影响的行数为 3 行)
--*/
精度是数中的数字个数。小数位数是数中小数点右边的数字个数。例如,数 123.45 的精度是 5,小数位数是2。numeric 和 decimal 数据类型默认的最大精度是 38。在 SQL Server 早期版本中,默认的最大值是 28。数字数据类型的长度是存储此数所占用的字节数。字符串或 Unicode 数据类型的长度是字符个数。binary、varbinary、和 image 数据类型的长度是字节数。例如,int 数据类型可以有 10 位数,用 4 个字节存储,不接受小数点。int 数据类型的精度是 10,长度是 4,小数位数是 0。当两个 char、varchar、binary 或 varbinary 表达式串联时,结果表达式的长度是这两个源表达式长度之和,或是 8,000 字符,以二者中少者计。当两个 nchar 或 nvarchar 表达式串联时,结果表达式的长度是两个源表达式长度之和,或是 4,000 字符,以二者中少者计。除了 decimal 类型之外,数字数据类型的精度和小数位数是固定的。如果算术运算符有两个相同类型的表达式,结果就为该数据类型,并且有对此类型定义的精度和小数位数。如果运算符有两个不同数字数据类型的表达式,数据类型优先规则决定结果的数据类型。结果为该数据类型定义的精度和小数位数。下表定义了当运算的结果是 decimal 类型时,结果的精度和小数位数是如何计算的。当以下情况时,结果是 decimal 类型: 两个表达式是 decimal 类型。
一个表达式是 decimal 类型,而另一个是比 decimal 优先顺序低的数据类型。
操作数表达式由表达式 e1(精度为 p1,小数位数为 s1)和表达式 e2(精度为 p2,小数位数为 s2)来表示。非 decimal 类型的表达式的精度和小数位数,是对此表达式数据类型定义的精度和小数位数。
两个表达式是 decimal 类型。
一个表达式是 decimal 类型,而另一个是比 decimal 优先顺序低的数据类型。
操作数表达式由表达式 e1(精度为 p1,小数位数为 s1)和表达式 e2(精度为 p2,小数位数为 s2)来表示。非 decimal 类型的表达式的精度和小数位数,是对此表达式数据类型定义的精度和小数位数。
操作 结果精度 结果小数位数 *
e1 + e2 max(s1, s2) + max(p1-s1, p2-s2) + 1 max(s1, s2)
e1 - e2 max(s1, s2) + max(p1-s1, p2-s2) max(s1, s2)
e1 * e2 p1 + p2 + 1 s1 + s2
e1 / e2 p1 - s1 + s2 + max(6, s1 + p2 + 1) max(6, s1 + p2 + 1)
* 结果精度和小数位数有绝对最大值 38。当结果精度大于 38 时,相应的小数位数会减少,以避免结果的整数部分被截断。