MySQL入门(三)
写了两篇《MySQL入门》以后我发现,写书的人还是都挺有本事的,起码人家知道怎么编排自己想讲的知识点,我实在是不知道该先说那里后说哪里,那我就想到什么讲什么吧。
一 写SQL
其实我是不想写有关SQL的部分的,因为这个部分其实很简单,基本上大学只要好好听听数据库概论这门课基本上都能写满足功能的SQL,但是后来想想,SQL其实是人和数据库交互的一种接口,不会SQL确实是不可以的,写的不好感觉不出数据库有多么的强大,甚至有可能会让人产生出数据库慢的坏印象。
MySQL作为most popular的开源数据库,其实在SQL支持这里做的不是那么完美,比如5.6为止还是不支持全外连接(5.7没试过是不是支持)。如果有人说全外连接这东西不支持就不支持了,没什么,但是我想说的是既然RDBMS是基于Codd的理论,那么全外连接作为关系代数的一部分,不实现是有点说不过去的。相反,Berkeley出身的PostgreSQL就做的很好了,毕竟人家是most advanced开源数据库。
闲话少叙。其实平时很多程序员写的最多的SQL是这样子的:
select t1.a, t1.b, t2.c, t2.d from table1 t1, table2 t2 where t1.m = t2.m and t1.k = ?;
这个写法一点问题都没有,特别的自然,翻译成汉语是这样的:
我需要从table1和table2中取一些数据出来,这两张表通过m列关联起来取交集,其中table1要卡k条件。
这个SQL按下不表,继续说些技术性的东西。
基础语法的东西就不说了,说一下连接。使用频率最高的就是内连接和外连接两种了。连接在我看来就是一种集合运算,比如内连接就是很自然的取交集运算,以两张表的内连接说,就是A和B两个集合做了A∩B运算。
内连接,翻译成英文就是inner join;外连接,翻译成英文就是outer join。所以说SQL是很好理解的,甚至接近了自然的语言。
写一个内连接:
select t1.a, t1.b, t2.c, t2.d from table1 t1 inner join table2 t2 on t1.m = t2.m where t1.k = ?;
这个SQL就是上面那个SQL的等价形式,只不过这是ANSI SQL92写法,上面那种是ANSI SQL89写法,SQL是一种语言,更是一种标准,新的标准更好理解,显然的让我们知道了这个SQL采用了内连接的形式。
至于连接具体怎么写,我很早以前写了一篇笔记:《Oracle的连接》。我就不重复发明轮子了,虽然当时采用的是Oracle,但是我说过了,SQL是一种标准,因此放到任何一个RDBMS里,这些都是通用的。
我本来就没有打算把这个写成什么正式的东西,我没有写书的梦想,所以基本上都是扯淡,扯淡的中途讲点知识。
二 数据类型
SQL也是一种编程语言!SQL也是一种编程语言!SQL也是一种编程语言!
我要把这个强调三遍,因为很多很多,多入牛毛的同行都会觉得写SQL是个很简单的事情,SQL就是增删改查数据,学一个小时就会的东西,是个很low的东西。我见过的很多人都问我SQL到底有什么写的,不就些破命令么?我真的不知道怎么回答他们。
SQL真的可以做很多事情,而写好SQL并不太容易,当然,更不难。
MySQL支持的数据类型大致分为:数字类型,时间日期类型,字符型。
以前玩儿Oracle的时候,数字类型通通是number型,好用到没朋友。但是MySQL不是这样搞的,MySQL的数字类型分为tinyint, smallint, mediumint, int, bigint。每种类型都会有“有符号”和“无符号”的属性,他们的范围如下表:
| 类型 | 占用空间(字节) | 最小值 | 最大值 |
| tinyint | 1 | -128 | 127 |
| tinyint(unsigned) | 1 | 0 | 255 |
| smallint | 2 | -32768 | 32767 |
| smallint(unsigned) | 2 | 0 | 65535 |
| mediumint | 3 | -8388608 | 8388607 |
| mediumint(unsigned) | 3 | 0 | 16777215 |
| int | 4 | -2147483648 | 2147483647 |
| int(unsigned) | 4 | 0 | 4294967295 |
| bigint | 8 | -9223372036854775808 | 9223372036854775807 |
| bigint(unsigned) | 8 | 0 | 18446744073709551615 |
很难记,但是其实不是很难,占用空间这里呢,我们都知道1Byte等于8bit,那么tinyint的取值范围就应该是[-2^(8-1), 2^(8-1)-1]。如果是无符号类型的取值范围就能推导出来了,有基本数学知识都能理解。
我第一次玩儿MySQL的时候,发现列类型经常是int(4)这样的,这个4是什么呢?从上面的表中明显可以看出数字型占用的空间总是一定的,那这里的4就不是char(4)里面那种意思了,这其实是填充格式用的,要和ZEROFILL属性一起用的,这样就能让字段被填充满,不过不影响取值,感觉像是语法糖之类的东西。
后来我觉得MySQL的varchar型有意思,有意思就在于varchar括号内的长度不是字节数,而是字符数,与汉字英文无关,就是字符数,这个感觉又是一个语法糖之类的东西,我在设计表的时候就不需要考虑什么字符集了,直接告诉程序员我给你了一个列,这个列最多存100个字符,你们自己控制。
但是这里还是有个陷阱。很多书上和网上的资料都会说,InnoDB表的所有varchar字段长度的总和不得超过65535,就说到了这里就不说了。实际上不能忽略一个前提,就是字符集应该选择latin1,而且绝对不是65535,是65532,还有些别的开销。如果换成UTF8字符集呢?这个理论总和限制就会变成21845,这个数字其实就是65535/3,实际上的限制是21844。所以我说这个是个语法糖,其实还是字符集相关的,只是不再让上层的程序员去考虑了,而是由DB自己保证。
时间和日期类型MySQL也是很丰富的,而且特别简单,'2015-12-12 12:31:20'这样就可以,Oracle的话还得写个什么函数去把字符串转成date型。当然时间和日期类型也是有空间占用的,很多资料上都会说用TIMESTAMP类型取代DATETIME类型,这样节省空间,确实没有问题,TIMESTAMP占用的空间仅有DATETIME的一半,但是要注意,TIMESTAMP的范围不大,1970年到2038年,节省空间是对的,但是要注意应用场景。
当然还有很讨厌的BLOB和TEXT这样的大数据类型(huge size data type),这可不是现在特别火的big data。这部分数据嘛,我觉得能不用就别用了,他们的存储都是在单独的地方,效率上我个人觉得堪忧。不过还是那句话,设计的时候要注意应用场景,给恰当的数据类型。
今天就扯到这里吧。
MySQL入门(三)的更多相关文章
- MYSQL入门(三)
索引简介 索引是对数据库表中一个或多个列(例如,employee 表的姓名 (name) 列)的值进行排序的结构.如果想按特定职员的姓来查找他或她,则与在表中搜索所有的行相比,索引有助于更快地获取信息 ...
- <MySQL>入门三 数据定义语言 DDL
-- DDL 数据定义语言 /* 库和表的管理 一.库的管理:创建.修改.删除 二.表的管理:创建.修改.删除 创建:create 修改:alter 删除:drop */ 1.库的管理 -- 库的管理 ...
- MySQL概述及入门(三)
MySql概述及入门(三) MySQL性能优化 主要优化安全和性能方面 安全方面 : 数据可持续性 性能方面 : 数据的高性能访问 性能优化——慢查询 在MySQL数据库中有一个慢查询日志功能,去获取 ...
- 【数据库】3.0 MySQL入门学习(三)——Windows系统环境下MySQL安装
1.0 我的操作系统是window10 专业版 64位.,不过至少windows7以上系统都是一样的. 关于MySQL如何下载,请参考博文: [数据库]2.0 如何获得MySQL以及MySQL安装 h ...
- Mysql快速入门(三)
MySQL性能优化之查看执行计划explain 介绍: (1).MySQL 提供了一个 EXPLAIN 命令, 它可以对 SELECT 语句进行分析, 并输出 SELECT 执行的详细信息, 以供开发 ...
- 21分钟 MySQL 入门教程(转载!!!)
21分钟 MySQL 入门教程 目录 一.MySQL的相关概念介绍 二.Windows下MySQL的配置 配置步骤 MySQL服务的启动.停止与卸载 三.MySQL脚本的基本组成 四.MySQL中的数 ...
- MYSQL入门全套(第三部)
MYSQL入门全套(第一部) MYSQL入门全套(第二部) 索引简介 索引是对数据库表中一个或多个列(例如,employee 表的姓名 (name) 列)的值进行排序的结构.如果想按特定职员的姓来查找 ...
- MySQL入门笔记
MySQL入门笔记 版本选择: 5.x.20 以上版本比较稳定 一.MySQL的三种安装方式: 安装MySQL的方式常见的有三种: · rpm包形式 · 通用二进制 ...
- MySQL入门转载
21分钟 MySQL 入门教程 http://www.cnblogs.com/mr-wid/archive/2013/05/09/3068229.html 目录 一.MySQL的相关概念介绍 二.Wi ...
随机推荐
- 自行实现PHP代码注解特性
PHP 注解 到目前为止,PHP的反射特性中是不支持注解Annotation的,但是可以支持基本的文档注释内容的获取 ReflectionMethod::getDocComment() - 从5.1. ...
- 泛函编程(36)-泛函Stream IO:IO数据源-IO Source & Sink
上期我们讨论了IO处理过程:Process[I,O].我们说Process就像电视信号盒子一样有输入端和输出端两头.Process之间可以用一个Process的输出端与另一个Process的输入端连接 ...
- php中的字符串常用函数(五) explode 妙用
// 示例 2 $data = "foo:*:1023:1000::/home/foo:/bin/sh" ; list( $user , $pass , $uid , $gid , ...
- python 函数小实例
1.判断一个数字是否为素数: import math # -----------------判断一个数是否是素数------------------ def sushu(a): i=1 for i i ...
- Yii2.0学习笔记:第一个页面Saying Hello
Controller目录下创建TestController.php 复制下面代码,yii跟tp一样,全程命名空间 <?php namespace app\controllers; use yii ...
- linux基础知识总结
使用linux将近一年了,一直都没有时间来总结一下,借着最近在整理知识框架的机会总结一下linux的应用知识. 1.linux有两个目录很特殊,一个是~,另一个是/.两个目录的含义不一样,/是系统 ...
- Mybatis分页插件 - PageHelper
1.说明 如果你也在用Mybatis,建议尝试该分页插件,这个一定是最方便使用的分页插件. 该插件目前支持Oracle,Mysql,MariaDB,SQLite,Hsqldb,PostgreSQL六种 ...
- 实例之HTML标签属性
鼠标放在图片上会显示说明文字的代码 <img src="图片地址" width=620 height=138 border=0 title="说明文字" ...
- go语言 类型:数组切片
初看起来,数组切片就像一个指向数组的指针,实际上它拥有自己的数据结构,而不仅仅是个指针.数组切片的数据结构可以抽象为以下3个变量: 1.一个指向原生数组的指针: 2.数组切片中的元素个数: 3.数组切 ...
- [javascript svg fill stroke stroke-width circle 属性讲解] svg fill stroke stroke-width circle 属性 绘制圆形及引入方式讲解
<!DOCTYPE html> <html lang='zh-cn'> <head> <title>Insert you title</title ...