当前位置:文档之家› MySQL常用数据类型和建库策略

MySQL常用数据类型和建库策略

1. MYSQL 5数据类型,长度范围1.1数值类型MySQL支持所有标准SQL数值数据类型.这些类型包括严格数值数据类型(INTEGER,SMALLINT,DECIMAL和NUMERIC),以及近似数值数据类型 (FLOAT,REAL 和DOUBLE PRECISION).关键字INT是INTEGER的同义词,关键字DEC是DECIMAL 的同义词.BIT 数据类型保存位字段值,并且支持MyISAM,MEMORY,InnoDB和BDB表.作为SQL标准的扩展,MySQL也支持整数类型 TINYINT,MEDIUMINT和BIGINT.下面的表显示了需要的每个整数类型的存储和范围.MySQL还支持选择在该类型关键字后面的括号内指定整数值的显示宽度(例如,INT(4)).该可选显示宽度规定用于显示宽度小于指定的列宽度的值时从左侧填满宽度.显示宽度并不限制可以在列内保存的值的范围,也不限制超过列的指定宽度的值的显示.当结合可选扩展属性ZEROFILL使用时, 默认补充的空格用零代替.例如,对于声明为INT(5) ZEROFILL的列,值4检索为00004.请注意如果在整数列保存超过显示宽度的一个值,当MySQL为复杂联接生成临时表时会遇到问题,因为在这些情况下MySQL相信数据适合原列宽度.所有整数类型可以有一个可选(非标准)属性UNSIGNED.当你想要在列内只允许非负数和该列需要较大的上限数值范围时可以使用无符号值.浮点和定点类型也可以为UNSIGNED.同数类型,该属性防止负值保存到列中.然而,与整数类型不同的是,列值的上范围保持不变.如果为一个数值列指定ZEROFILL,MySQL自动为该列添加UNSIGNED属性.对于浮点列类型,在MySQL中单精度值使用4个字节,双精度值使用8个字节.FLOAT类型用于表示近似数值数据类型.SQL标准允许在关键字FLOAT后面的括号内选择用位指定精度(但不能为指数范围).MySQL还支持可选的只用于确定存储大小的精度规定.0到23的精度对应FLOAT 列的4字节单精度.24到53的精度对应DOUBLE列的8字节双精度.MySQL允许使用非标准语法:FLOAT(M,D)或 REAL(M,D)或DOUBLE PRECISION(M,D).这里,"(M,D)"表示该值一共显示M位整数,其中D位位于小数点后面.例如,定义为FLOAT(7,4)的一个列可以显示为-999.9999.MySQL保存值时进行四舍五入,因此如果在FLOAT(7,4)列内插入999.00009,近似结果是999.0001.MySQL 将DOUBLE视为DOUBLE PRECISION(非标准扩展)的同义词.MySQL还将REAL 视为DOUBLE PRECISION(非标准扩展)的同义词,除非SQL服务器模式包括REAL_AS_FLOAT选项.为了保证最大可能的可移植性,需要使用近似数值数据值存储的代码应使用FLOAT或DOUBLE PRECISION,不规定精度或位数.DECIMAL和NUMERIC类型在MySQL中视为相同的类型.它们用于保存必须为确切精度的值,例如货币数据.当声明该类型的列时,可以(并且通常要)指定精度和标度;例如:salary DECIMAL(5,2)在该例子中,5是精度,2是标度.精度表示保存值的主要位数,标度表示小数点后面可以保存的位数.在MySQL 5.1中以二进制格式保存DECIMAL和NUMERIC值.标准SQL要求salary列能够用5位整数位和两位小数保存任何值.因此,在这种情况下可以保存在salary列的值的范围是从-999.99到999.99.在标准SQL中,语法DECIMAL(M)等价于 DECIMAL(M,0).同样,语法DECIMAL等价于DECIMAL(M,0),可以通过计算确定M的值.在MySQL 5.1中支持DECIMAL和NUMERIC数据类型的变量形式.M默认值是10.DECIMAL或NUMERIC的最大位数是65,但具体的DECIMAL或NUMERIC列的实际范围受具体列的精度或标度约束.如果此类列分配的值小数点后面的位数超过指定的标度允许的范围,值被转换为该标度.(具体操作与操作系统有关,但一般结果均被截取到允许的位数).BIT数据类型可用来保存位字段值.BIT(M)类型允许存储M位值.M范围为1到64.要指定位值,可以使用b'value'符.value是一个用0和1编写的二进制值.例如,b'111'和 b'100000000'分别表示7和128.参见9.1.5节,"位字段值".如果为BIT(M)列分配的值的长度小于M位,在值的左边用0填充.例如,为BIT(6)列分配一个值b'101',其效果与分配b'000101'相同.当要在一个数值列内保存一个超出该列允许范围的值时,MySQL的操作取决于此时有效的SQL模式.如果模式未设置,MySQL将值裁剪到范围的相应端点,并保存裁减好的值.但是,如果模式设置为traditional("严格模式"),超出范围的值将被拒绝并提示错误,并且根据SQL标准插入会失败.参见5.3.2节,"SQL服务器模式".如果INT列是UNSIGNED,列范围的大小相同,但其端点会变为到0和4294967295.如果你试图保存-9999999999和 9999999999,以非严格模式保存到列中的值是0和4294967296.如果在浮点或定点列中分配的值超过指定(或默认)精度和标度规定的范围,MySQL以非严格模式保存表示范围相应端点的值.当MySQL没有工作在严格模式时,对于ALTER TABLE,LOAD DATA INFILE,UPDATE 和多行INSERT语句,由于裁剪发生的转换将报告为警告.当MySQL工作在严格模式时,这些语句将失败,并且部分或全部值不会插入或更改,取决于是否表为事务表和其它因素.这里将数字类型按照分类方法分为三类:整数类,小数类和数字类.我所谓的"数字类",就是指 DECIMAL 和 NUMERIC,它们是同一种类型.它严格的说不是一种数字类型,因为他们实际上是将数字以字符串形式保存的;他的值的每一位 (包括小数点) 占一个字节的存储空间,因此这种类型耗费空间比较大.但是它的一个突出的优点是小数的位数固定,在运算中不会"失真",所以比较适合用于"价格","金额"这样对精度要求不高但准确度要求非常高的字段.小数类,即浮点数类型,根据精度的不同,有 FLOAT 和 DOUBLE 两种.它们的优势是精确度,FLOAT 可以表示绝对值非常小,小到约 1.17E-38 (0.000...0117,小数点后面有 37 个零) 的小数,而 DOUBLE 更是可以表示绝对值小到约2.22E-308 (0.000...0222,小数点后面有 307 个零) 的小数.FLOAT 类型和DOUBLE 类型占用存储空间分别是 4 字节和 8 字节.如果需要用到小数的字段,精度要求不高的,当然用 FLOAT 了.可是说句实在话,我们"民用"的数据,哪有要求精度那么高的呢?这两种类型至今我没有用过――我还没有遇到适合于使用它们的事例.用的最多的,最值得精打细算的,是整数类型.从只占一个字节存储空间的TINYINT 到占 8 个字节的 BIGINT,挑选一个"够用"并且占用存储空间最小的类型是设计数据库时应该考虑的.TINYINT,SMALLINT,MEDIUMINT,INT 和 BIGINT 占用存储空间分别为 1 字节,2 字节,3 字节,4 字节和 8 字节,就无符号的整数而言,这些类型能表示的最大整数分别为 255,65535,16777215,4294967295 和 18446744073709551615.如果用来保存用户的年龄 (举例来说,数据库中保存年龄是不可取的),用 TINYINT 就够了;九城的《纵横》里,各项技能值,用SMALLINT 也够了;如果要用作一个肯定不会超过 16000000 行的表的AUTO_INCREMENT 的 IDENTIFY 字段,当然用 MEDIUMINT 不用 INT,试想,每行节约一个字节,16000000 行可以节约 10 兆多.1.2日期和时间类型表示时间值的DATE和时间类型为DATETIME,DATE,TIMESTAMP,TIME和YEAR.每个时间类型有一个有效值范围和一个"零"值,当指定不合法的MySQL不能表示的值时使用"零"值.TIMESTAMP类型有专有的自动更新特性,将在后面描述.如果试图插入一个不合法的日期,MySQL将给出警告或错误.可以使用ALLOW_INVALID_DATES SQL模式让MySQL接受某些日期,例如'1999-11-31'.当你想要保存一个"可能错误的"用户已经在数据库中指定(例如,以web形式)用于将来处理的值时很有用.在这种模式下,MySQL只验证月范围为从0到12,日范围为从0到31.这些范围可以包括零,因为MySQL允许在DATE或 DATETIME列保存日/月和日是零的日期.这在应用程序需要保存一个你不知道确切日期的生日时非常有用.在这种情况下,只需要将日期保存为 '1999-00-00'或'1999-01-00'.如果保存此类日期,DATE_SUB()或DATE_ADD等需要完整日期的函数不会得到正确的结果.(如果你不想在日期中出现零,可以使用NO_ZERO_IN_DATE SQL模式).MySQL还允许将'0000-00-00'保存为"伪日期"(如果不使用NO_ZERO_DATE SQL 模式).这在某些情况下比使用NULL值更方便(并且数据和索引占用的空间更小).将 sql_mode系统变量设置为相应模式值,可以更确切你想让MySQL支持哪种日期.参见5.3.2节,"SQL服务器模式".当使用日期和时间类型时应记住以下几点:· MySQL以标准输出格式检索给定日期或时间类型的值,但它尽力解释你指定的各种输入值格式(例如,当你指定一个分配给或与日期或时间类型进行比较的值时).只支持下面章节中描述的格式.期望你能提供有效值.如果你使用其它格式的值会发生意想不到的结果.· 包含两位年值的日期会令人模糊,因为世纪不知道.MySQL使用以下规则解释两位年值:o 70-99范围的年值转换为1970-1999.o 00-69范围的年值转换为2000-2069.· 尽管MySQL尝试解释几种格式的值,日期总是以年-月-日顺序(例如,'98-09-04'),而不是其它地方常用的月-日-年或日-月-年顺序(例如,'09-04-98','04-09-98').· 如果值用于数值上下文中,MySQL自动将日期或时间类型的值转换为数字,反之亦然.· 当 MySQL遇到一个日期或时间类型的超出范围或对于该类型不合法的值时(如本节开始所描述),它将该值转换为该类的"零"值.一个例外是超出范围的TIME值被裁剪到TIME范围的相应端点.下面的表显示了各类"零"值的格式.请注意如果启用NO_ZERO_DATE SQL模式,使用这些值会产生警告.1.3 String类型字符串类型指CHAR,VARCHAR,BINARY,VARBINARY,BLOB,TEXT,ENUM和 SET.该节描述了这些类型如何工作以及如何在查询中使用这些类型.CHAR和VARCHAR类型类似,但它们保存和检索的方式不同.它们的最大长度和是否尾部空格被保留等方面也不同.在存储或检索过程中不进行大小写转换.CHAR和VARCHAR类型声明的长度表示你想要保存的最大字符数.例如,CHAR(30)可以占用30个字符.CHAR列的长度固定为创建表时声明的长度.长度可以为从0 到255的任何值.当保存CHAR值时,在它们的右边填充空格以达到指定的长度.当检索到CHAR值时,尾部的空格被删除掉.在存储或检索过程中不进行大小写转换.VARCHAR列中的值为可变长字符串.长度可以指定为0到65,535之间的值.(VARCHAR的最大有效长度由最大行大小和使用的字符集确定.整体最大长度是65,532字节).同CHAR对比,VARCHAR值保存时只保存需要的字符数,另加一个字节来记录长度(如果列声明的长度超过255,则使用两个字节).VARCHAR值保存时不进行填充.当值保存和检索时尾部的空格仍保留,符合标准SQL.如果分配给CHAR或VARCHAR列的值超过列的最大长度,则对值进行裁剪以使其适合.如果被裁掉的字符不是空格,则会产生一条警告.如果裁剪非空格字符,则会造成错误(而不是警告)并通过使用严格SQL模式禁用值的插入.下面的表显示了将各种字符串值保存到 CHAR(4)和VARCHAR(4)列后的结果,说明了CHAR和VARCHAR之间的差别:请注意上表中最后一行的值只适用不使用严格模式时;如果MySQL运行在严格模式,超过列长度不的值不保存,并且会出现错误.从CHAR(4)和VARCHAR(4)列检索的值并不总是相同,因为检索时从CHAR列删除了尾部的空格.通过下面的例子说明该差别:mysql> CREATE TABLE vc (v VARCHAR(4), c CHAR(4));Query OK, 0 rows affected (0.02 sec)mysql> INSERT INTO vc VALUES ('ab ', 'ab ');Query OK, 1 row affected (0.00 sec)mysql> SELECT CONCAT(v, '+'), CONCAT(c, '+') FROM vc;BINARY和VARBINARY类类似于CHAR和VARCHAR,不同的是它们包含二进制字符串而不要非二进制字符串.也就是说,它们包含字节字符串而不是字符字符串.这说明它们没有字符集,并且排序和比较基于列值字节的数值值.BINARY和 VARBINARY允许的最大长度一样,如同CHAR和VARCHAR,不同的是BINARY和VARBINARY的长度是字节长度而不是字符长度.BINARY 和VARBINARY数据类型不同于CHAR BINARY和VARCHAR BINARY数据类型.对于后一种类型,BINARY属性不会将列视为二进制字符串列.相反,它致使使用列字符集的二元校对规则,并且列自身包含非二进制字符字符串而不是二进制字节字符串.例如CHAR(5) BINARY被视为CHAR(5) CHARACTER SET latin1 COLLATE latin1_bin,假定默认字符集是latin1.这不同于BINARY(5),它保存5字节二进制字符串,没有字符集或校对规则.当保存BINARY值时,在它们右边填充值以达到指定长度.填充值是0x00(零字节).插入值时在右侧添加0x00 on,并且选择时不删除尾部的字节.比较时所有字节很重要,包括ORDER BY和DISTINCT操作.比较时0x00字节和空格是不同的,0x00<空格.例如:对于一个BINARY(3)列,当插入时 'a' 变为 'a �'.'a�'插入时变为'a��'.当选择时两个插入的值均不更改.对于VARBINARY,插入时不填充字符,选择时不裁剪字节.比较时所有字节很重要,包括ORDER BY和DISTINCT操作.比较时0x00字节和空格是不同的,0x00<空格.对于尾部填充字符被裁剪掉或比较时将它们忽视掉的情形,如果列的索引需要唯一的值,在列内插入一个只是填充字符数不同的值将会造成复制键值错误.如果你计划使用这些数据类型来保存二进制数据并且需要检索的值与保存的值完全相同,应考虑前面所述的填充和裁剪特征.下面的例子说明了用0x00填充的BINARY值如何影响列值比较:mysql> CREATE TABLE t (c BINARY(3));Query OK, 0 rows affected (0.01 sec)mysql> INSERT INTO t SET c = 'a';Query OK, 1 row affected (0.01 sec)mysql> SELECT HEX(c), c = 'a', c = 'a��' from t;+--------+---------+-------------+| HEX(c) | c = 'a' | c = 'a��' |+--------+---------+-------------+| 610000 | 0 | 1 |+--------+---------+-------------+1 row in set (0.09 sec)如果检索的值必须与指定进行存储而没有填充的值相同,最好使用BLOB数据类型.BLOB是一个二进制大对象,可以容纳可变数量的数据.有4种BLOB类型:TINYBLOB,BLOB,MEDIUMBLOB和LONGBLOB.它们只是可容纳值的最大长度不同.有4种TEXT类型:TINYTEXT,TEXT,MEDIUMTEXT和LONGTEXT.这些对应4种BLOB 类型, 有相同的最大长度和存储需求.BLOB 列被视为二进制字符串(字节字符串).TEXT列被视为非二进制字符串(字符字符串).BLOB列没有字符集,并且排序和比较基于列值字节的数值值.TEXT 列有一个字符集,并且根据字符集的校对规则对值进行排序和比较.在TEXT或BLOB列的存储或检索过程中,不存在大小写转换.当未运行在严格模式时,如果你为BLOB或TEXT列分配一个超过该列类型的最大长度的值值,值被截取以保证适合.如果截掉的字符不是空格,将会产生一条警告.使用严格SQL模式,会产生错误,并且值将被拒绝而不是截取并给出警告.在大多数方面,可以将BLOB列视为能够足够大的VARBINARY列.同样,可以将TEXT列视为VARCHAR列.BLOB和TEXT在以下几个方面不同于VARBINARY和VARCHAR:· 当保存或检索BLOB和TEXT列的值时不删除尾部空格.(这与VARBINARY和VARCHAR列相同).请注意比较时将用空格对TEXT进行扩充以适合比较的对象,正如CHAR和VARCHAR.· 对于BLOB和TEXT列的索引,必须指定索引前缀的长度.对于CHAR和VARCHAR,前缀长度是可选的.· BLOB和TEXT列不能有默认值.LONG和LONG VARCHAR对应MEDIUMTEXT数据类型.这是为了保证兼容性.如果TEXT 列类型使用BINARY属性,将为列分配列字符集的二元校对规则.MySQL 连接程序/ODBC将BLOB值定义为LONGVARBINARY,将TEXT值定义为LONGVARCHAR.由于BLOB和TEXT值可能会非常长,使用它们时可能遇到一些约束:· 当排序时只使用该列的前max_sort_length个字节.max_sort_length的默认值是1024;该值可以在启动mysqld服务器时使用--max_sort_length选项进行更改.运行时增加 max_sort_length的值可以在排序或组合时使更多的字节有意义.任何客户端可以更改其会话max_sort_length变量的值:mysql> SET max_sort_length = 2000;mysql> SELECT id, comment FROM tbl_name-> ORDER BY comment;当你想要使超过max_sort_length的字节有意义,对含长值的BLOB或TEXT列使用GROUP BY或ORDER BY的另一种方式是将列值转换为固定长度的对象.标准方法是使用SUBSTRING函数.例如,下面的语句对comment列的2000个字节进行排序:mysql> SELECT id, SUBSTRING(comment,1,2000) FROM tbl_name-> ORDER BY SUBSTRING(comment,1,2000);· BLOB或TEXT对象的最大大小由其类型确定,但在客户端和服务器之间实际可以传递的最大值由可用内存数量和通信缓存区大小确定.你可以通过更改max_allowed_packet变量的值更改消息缓存区的大小,但必须同时修改服务器和客户端程序.例如,可以使用 mysql和mysqldump来更改客户端的max_allowed_packet值.参见7.5.2节,"调节服务器参数",8.3 节,"mysql:MySQL命令行工具"和8.8节,"mysqldump:数据库备份程序".每个BLOB或TEXT值分别由内部分配的对象表示.这与其它列类型形成对比,后者是当打开表时为每1列分配存储引擎.不要以为字符类型就是 CHAR,CHAR 和 VARCHAR 的区别在于 CHAR 是固定长度,只要你定义一个字段是 CHAR(10),那么不论你存储的数据是否达到了 10 个字节,它都要占去 10 个字节的空间;而 VARCHAR 则是可变长度的,如果一个字段可能的值是不固定长度的,我们只知道它不可能超过 10 个字符,把它定义为VARCHAR(10) 是最合算的,VARCHAR 类型的占用空间是它的值的实际长度 +1.为什么要 +1 呢?这一个字节用于保存实际使用了多大的长度.从这个 +1 中也应该看到,如果一个字段,它的可能值最长是 10 个字符,而多数情况下也就是用到了 10 个字符时,用 VARCHAR 就不合算了:因为在多数情况下,实际占用空间是11 个字节,比用 CHAR(10) 还多占用一个字节.举个例子,就是一个存储股票名称和代码的表,股票名称绝大部分是四个字的,即 8 个字节;股票代码,上海的是六位数字,深圳的是四位数字.这些都是固定长度的,股票名称当然要用 CHAR(8);股票代码虽然是不固定长度,但如果使用VARCHAR(6),一个深圳的股票代码实际占用空间是 5 个字节,而一个上海的股票代码要占用 7 个字节!考虑到上海的股票数目比深圳的多,那么用 VARCHAR(6) 就不如 CHAR(6) 合算了.虽然一个 CHAR 或 VARCHAR 的最大长度可以到 255,我认为大于 20 的 CHAR 是几乎用不到的――很少有大于 20 个字节长度的固定长度的东东吧?不是固定长度的就用 VARCHAR.大于 100 的 VARCHAR 也是几乎用不到的――比这更大的用 TEXT 就好了.TINYTEXT,最大长度为 255,占用空间也是实际长度 +1;TEXT,最大长度 65535,占用空间是实际长度 +2;MEDIUMTEXT,最大长度 16777215,占用空间是实际长度 +3;LONGTEXT,最大长度 4294967295,占用空间是实际长度+4.为什么 +1,+2,+3,+4?你要是还不知道就该打 PP 了.这些可以用在论坛啊,新闻啊,什么的,用来保存文章的正文.根据实际情况的不同,选择从小到大的不同类型.ENUM是一个字符串对象,其值来自表创建时在列规定中显式枚举的一列值.在某些情况下,ENUM值也可以为空字符串('')或NULL:· 如果你将一个非法值插入ENUM(也就是说,允许的值列之外的字符串),将插入空字符串以作为特殊错误值.该字符串与"普通"空字符串不同,该字符串有数值值0.后面有详细讨论.· 如果将ENUM列声明为允许NULL,NULL值则为该列的一个有效值,并且默认值为NULL.如果ENUM列被声明为NOT NULL,其默认值为允许的值列的第1个元素.每个枚举值有一个索引:· 来自列规定的允许的值列中的值从1开始编号.· 空字符串错误值的索引值是0.这说明你可以使用下面的SELECT语句来找出分配了非法ENUM值的行:· mysql> SELECT * FROM tbl_name WHERE enum_col=0;· NULL值的索引是NULL.例如,定义为ENUM的列('one','two','three')可以有下面所示任何值.还显示了每个值的索引:枚举最多可以有65,535个元素.当创建表时,ENUM成员值的尾部空格将自动被删除.当检索时,保存在ENUM列的值使用列定义中所使用的大小写来显示.请注意可以为 ENUM列分配字符集和校对规则.对于二进制或大小写敏感的校对规则,当为列分配值时应考虑大小写.如果在数值上下文中检索一个ENUM 值,将返回列值的索引.例如,你可以这样从ENUM列搜索数值值:mysql> SELECT enum_col+0 FROM tbl_name;如果将一个数字保存到ENUM列,数字被视为索引,并且保存的值是该索引对应的枚举成员.(但是,这不适合LOAD DATA,它将所有输入视为字符串).不建议使用类似数字的枚举值来定义一个ENUM列,因为这很容易引起混淆.例如,下面的列含有字符串值 '0','1'和'2'的枚举成员,但数值索引值为1,2和3:numbers ENUM('0','1','2')根据枚举成员在列定义中列出的顺序对ENUM值进行排序.(换句话说,ENUM值根据索引编号进行排序).例如,对于ENUM('a','b'),'a'排在'b'前面,但对于ENUM('b','a'),'b'排在'a'前面.空字符串排在非空字符串前面,并且NULL值排在所有其它枚举值前面.要想防止意想不到的结果,按字母顺序规定ENUM列.还可以使用GROUP BY CAST(col AS CHAR)或GROUP BY CONCAT(col)来确保按照词汇对列进行排序而不是用索引数字.如果你想要确定一个ENUM列的所有可能的值,使用SHOW COLUMNS FROM tbl_name LIKE enum_col,并解析输出中第2列的ENUM定义.2.字段列类型存储条件说明根据类别列出了MySQL支持的每个列类型的存储需求.MyISAM表中行的最大大小为65,534字节. 每个BLOB和TEXT列账户只占其中的5至9个字节.如果MyISAM表包括变长列类型,记录格式也是可变长度.当创建表时,在某些条件下,MySQL可以将一个列从变长类型改为固定长度的类型或反之亦然.数值类型存储规则DECIMAL(和NUMERIC)的存储需求与具体版本有关:使用二进制格式将9个十进制(基于10)数压缩为4个字节来表示DECIMAL列值.每个值的整数和分数部分的存储分别确定.每个9位数的倍数需要4个字节,并且"剩余的"位需要4个字节的一部分.下表给出了超出位数的存储需求:日期和时间类型的存储需求The storage requirements shown in the table arise from the way that MySQL represents temporal values:DATE: A three-byte integer packed as DD + MM×32 + YYYY×16×32TIME: A three-byte integer packed as DD×24×3600 + HH×3600 + MM×60 + SSDATETIME: Eight bytes:A four-byte integer packed as YYYY×10000 + MM×100 + DDA four-byte integer packed as HH×10000 + MM×100 + SSTIMESTAMP: A four-byte integer representing seconds UTC since the epoch ('1970-01-01 00:00:00' UTC)YEAR: A one-byte integer字符串类型的存储需求VARCHAR,BLOB 和TEXT类是变长类型.每个类型的存储需求取决于列值的实际长度(用前面的表中的L表示),而不是该类型的最大可能的大小.例如,VARCHAR(10)列可以容纳最大长度为10的字符串.实际存储需求是字符串(L)的长度,加上一个记录字符串长度的字节.对于字符串 'abcd',L是4,存储需要5个字节.对于CHAR,VARCHAR和TEXT类型,前面的表中的值L和M应解释为字符数目,并且列定义中的这些类型的长度表示字符数目.例如,要想保存一个TINYTEXT值需要L字符+ 1个字节.要想计算用于保存具体 CHAR,VARCHAR或者TEXT列值的字节数,需要考虑该列使用的字符集.在具体情况中,当使用Unicode时,必须记住所有Unicode字符使用相同的字节数.为了细分用于不同类Unicode字符使用的存储,注释:VARCHAR列的有效最大长度为65,532字符NDBCLUSTER 引擎只支持固定宽度的列.这说明MySQL簇中的表中的VARCHAR列的行为如同类型CHAR(不同的是每个记录仍然有一个额外字节空间).例如,在Cluster表中,声明为VARCHAR(100)的列中的每个记录存储时将占用101个字节,无论实际存储的记录中的字符串的长度为多少.BLOB 和TEXT类需要 1,2,3或者4个字节来记录列值的长度,取决于该类的最大可能的长度.在NDB Cluster存储引擎中,TEXT和BLOB列的实施是不同的,其中TEXT列中的每个记录由两个单独部分组成.一个是固定大小(256字节),并且实际上保存在原表中.另一个包括超出256字节的任何数据,保存在隐含的表中.第2个表中的记录总是2,000字节长.这说明如果size<= 256,TEXT列的大小为256(其中size 表示记录的大小);否则,大小是256 +size+(2000–(size–256)%2000).ENUM 对象的大小由不同的枚举值的数目确定.枚举用一个字节,可以有255个可能的值.当枚举的值位于256和65,535之间时,用两个字节.参见 11.4.4节,"ENUM类型".SET对象的大小由不同的set成员的数量确定.如果set大小是N,对象占(N+7)/8个字节,四舍五入到1,2,3,4或者8个字节.SET最多可以有64个成员.3.选择正确的列类型为了优化存储,在任何情况下均应使用最精确的类型.例如,如果列的值的范围为从1到99999,若使用整数,则MEDIUMINT UNSIGNED是好的类型.在所有可以表示该列值的类型中,该类型使用的存储最少.用精度为65位十进制数(基于10)对DECIMAL 列进行所有基本计算(+,-,*,/).使用双精度操作对DECIMAL值进行计算.如果准确度不是太重要或如果速度为最高优先级,DOUBLE类型即足够了.为了达到高精度,可以转换到保存在BIGINT中的定点类型.这样可以用64位整数进行所有计算,根据需要将结果转换回浮点值.4.使用来自其他数据库引擎的列类型为了使用由其它卖方编写的SQL执行代码,MySQL按照下表所示对列类型进行映射.通过这些映射,可以很容易地从其它数据库引擎将表定义导入到MySQL中:。

相关主题