mysql中整数类型后⾯的数字,⽐如int(11),11代表11个字节
吗?
原先对mysql不太理解,但也没有报错。但理解的不够深⼊。这次补上。
原来以为int(11)是指11个字节,int(10)就是10个字节。我错了。
mysql的基本数据类型⾥⼏个int如下:
类型⼤⼩范围(有符号)范围(⽆符号)⽤途
TINYINT 1字节 (-128,127) (0,255) ⼩整数值
SMALLINT 2 字节 ( -2^15 :-32 768,2^15 - 1:32 767) (0,65 535) ⼤整数值
MEDIUMINT 3 字节 (-8 388 608,8 388 607) (0,16 777 215) ⼤整数值
INT或INTEGER(int 的 SQL-92 同义字为 integer) 4 字节 (-2^31:-2 147 483 648, 2^31 - 1:2 147 483 647) (0,4 294 967 295) ⼤整数值
BIGINT 8 字节 (-2^63:-9 233 372 036 854 775 808,2^63-1:9 223 372 036 854 775 807) (0,18 446 744 073 709 551 615) 极⼤整数值
这些类型,是定长的,其容量是不会随着后⾯的数字⽽变化的,⽐如int(11)和int(8),都是⼀样的占4字节。tinyint(1)和tinyint(10)也都占⽤⼀个字节。
那么后⾯的11和8,有啥⽤呢。
mysql数据库中以:数据类型(m)  来约束数据,其中数字m在不同的数据类型中表⽰含义是不同的。咱们这⾥只讲整数。
整型数系统已经限制了取值范围,tinyint占1个字节、int占4个字节。所以整型数后⾯的m不是表⽰的数据长度,⽽是表⽰数据在显⽰时显⽰的最⼩长度。
tinyint(1) 这⾥的1表⽰的是最短显⽰⼀个字符。tinyint(2) 这⾥的2表⽰的是最短显⽰两个字符。
当字符长度超过(m)时,相当于啥都没发⽣;
当字符长度⼩于(m)时,就需要指定拿某个字符来填充,⽐如zerofill(表⽰⽤0填充),
设置tinyint(2) zerofill 你插⼊1时他会显⽰01;设置tinyint(4) zerofill 你插⼊1时他会显⽰0001。
所以,没有zerofill,(m)就是⽆⽤的。
综上整型的数据类型括号内的数字不管是多少,所占的存储空间都固定的。
mysql 中int(1)和tinyint(1)中的1只是指定显⽰长度,并不表⽰存储长度,只有字段指定zerofill时有⽤。
位数限制基本没有意义。
在mysql中我做过实验,对于⼀个tinyint类型的字段,不管它是tinyint(1)还是tinyint(2)还是tinyint(3),
当你插⼊⼤于127的数,都会存⼊127。跟上⽂中的结论是⼀样的。
总结:int(11),tinyint(1),bigint(20),后⾯的数字,不代表占⽤空间容量。⽽代表最⼩显⽰位数。这个东西基本没有意义,除⾮你对字段指定zerofill。
所以我们在设计mysql数据库时,
建表时,mysql会⾃动分配长度:int(11)、tinyint(4)、smallint(6)、mediumint(9)、bigint(20)。
所以,就⽤这些默认的显⽰长度就可以了。不⽤再去⾃⼰填长度,⽐如搞个int(10)、tinyint(1)之类的,基本没⽤。⽽且导致表的字段类型多样化。
该⽂很好地总结了mysql所有的数据类型。
我在建⼀个float类型的字段时,故意建成float(2,3)型,是错误的。报错如下。
第⼀个数字M,代表总长度限制(总长度包括⼩数位和整数位),2代表总长度不能超过2个字符,⽐如2.34,就超过了2位总长度;
第⼆个数字D,代表⼩数位的长度限制。0.2表⽰占⽤了1个⼩数位。
这样看,当然M必需⼤于等于D。
⽐如设置为float(2,2),那么写⼊12.3这个数字时,实际插⼊的是0.99。
⽐如设置为float(2,1),那么写⼊12.3这个数字时,实际插⼊的是9.9。
mysql会⾃动截取该字段能接受的最⼤值存⼊。
那么设置为float(0,0),则相当于不受限制,或者说受float本⾝的精度限制。
再来看看mysql的整型、浮点型,怎么跟oracle的数据类型NUMBER对应的。
先来看看oracle的NUMBER类型的特点:
Number(p, s) 声明⼀个定点数 p(precision)为精度,s(scale)表⽰⼩数点右边的数字个数,精度最⼤值为38,scale的取值范围为-84到127 Number(p) 声明⼀个整数相当于Number(p, 0)
Number 声明⼀个浮点数其精度为38,要注意的是scale的值没有应⽤,也就是说scale的值不能简单的理解为0,或者其他的数。
定点数的精度(p)和刻度(s)遵循以下规则:
当⼀个数的整数部分的长度 > p-s 时,Oracle就会报错。(可见s个位置是留给⼩数的;p-s个位置是留给整数部分的,这样很清晰啊。p代表整数位和⼩数位全部的长度限制,这⼀点跟mysql很像)
当⼀个数的⼩数部分的长度 > s 时,Oracle就会舍⼊。(同上,实际上不会报错,oracle会四舍五⼊,⽐如NUMBER(4,2),插⼊99.248,保存为99.25;插⼊99.242,保存为99.24;插⼊99.2448,保存为99.24⽽不是99.25,注意他四舍五⼊的位置是s位。)
当s(scale)为负数时,Oracle就对⼩数点左边的s个数字进⾏舍⼊。(暂时不管它)
当s > p 时, p表⽰⼩数点后第s位向左最多可以有多少位数字,如果⼤于p则Oracle报错,⼩数点后s位向右的数字被舍⼊。(暂时不管它)经实验,⽐如定义⼀个字段为Number(3),那么写⼊该字段,最多不能超过3个数字。⽐如,你可以插⼊999(或-999),但是不能插⼊1000(或-1000)。以此类推。
⽐如定义⼀个字段为Number(3,2),那么写⼊该字段,最多不能超过3位的整数,最多2位的⼩数。
综上,我们可以看出mysql和oracle的对应关系:
mysql oracle理由
tinyint(1字节)
以及tinyint unsigned NUMBER(3)
范围(-128,127) (0,255),所以⾄少NUMBER(3)对应。
但是不能NUBER(1),这样只能最⼤存9。
smallint(2字节)
以及smallint unsigned
NUMBER(5)范围(-32 768,32 767) (0,65 535) ,所以⾄少NUMBER(5)对应。
MEDIUMINT(3字节)以及
MEDIUMINT unsigned NUMBER(7)
以及
NUMBER(8)
范围(-8 388 608,8 388 607) (0,16 777 215),所以
⾮unsigned⽤NUMBER(7)对应;
unsigned⽤NUMBER(8)对应。
int(4字节)
以及NUMBER(10)
范围(-2 147 483 648, 2 147 483 647) (0,4 294 967 295),
所以⾄少NUMBER(10)对应。
int unsigned bigint(5字节)
以及bigint unsigned NUMBER(19)
以及
NUMBER(20)
范围(-9 233 372 036 854 775 808,9 223 372 036 854 775 807)
(0,18 446 744 073 709 551 615),
所以⾮unsigned⽤NUMBER(19)对应;
unsigned⽤NUMBER(20)对应。
float(m,d)
以及unsigned NUMBER(m,d)
因为NUMBER(m,d)是定点数,精度超过浮点数。
所以只需保持位数⼀致即可,精度也会更强。
double(m,d)
以及
unsigned
NUMBER(m,d)同上。decimal(m,d)
以及unsigned NUMBER(m,d)
Decimal(n,m)表⽰数值中共有n位数,其中整数n-m位,⼩数m位。
例:decimal(10,6),数值中共有10位数,其中整数占4位,⼩数占6位。
p (有效位数)必需是1~38之间的数。
float几个字节多少位ORACLE中有SMALLINT,INT,INTEGER类型,不过这是NUMBER(38,0)的同义词。