zoukankan      html  css  js  c++  java
  • MySQL基础原创笔记(一)

    对表的增删改操作:

    创建表:

    create table student (

             id  int  primary key  auto_increment,

             name  varchar(10)  character set utf8  not null,

             sex    char(2)  default ‘M’,

             constraint  fk_student_score  foreign key(id)  references score(id)

    )  engine=InnoDB;

    primary key :指定表的主键;

    如果是指定单个主键,可直接在该字段后声明;

    如果是指定多个主键,只能采用primary key (X,Y)的形式;

    定义外键

    constraint fk_T2_T1 foreign key(t2_id) references T1(t1_id); //将T1表中的t1_id字段设置成为T2表的外键;

    增加外键

    alter table T2 orderitemds add constraint fk_T2_T1 foreign key(id) references T1(id); //将T1表中的t1_id字段设置成为T2表的外键;

    auto_increment :让Mysql自动对该列增量;每个表只允许有一个auto_increment列,且必须被索引(以最大的数去递增),从而可将该列当作主键;

    注:select last_insert_id():该语句可获得最后一个auto_increment的值;

    default:为字段设置默认值;

    character set …:指定编码格式,通常是为了让其能识别中文;

    engine = :指定mysql引擎;

    常用的引擎类型:

    InnoDB:可靠地事物处理引擎,但不支持全文检索;

    MyISAM:性能极高的引擎,支持全文检索,但不支持事务处理;

    MEMORY:功能同于MyISAM,但由于数据库在内存里,速度很快;适用于临时表;

    注:新版Mysql默认引擎是InnoDB

    更新表:使用alter table语句

    增加列:

    alter table T add Tname varchar(20); //为T表增加一个名为Tname的列

    删除列:一次只能删除一列;

    alter table T drop column Tname; ///删除T表中名为Tname的列

    删除表:使用Drop table语句

    例:drop table T;

    重命名表:使用rename table语句

    例:rename table T1 to t1, T2 to t2, T3 to t3;

    对表中数据的查询操作

    SQL语句格式:

    select

    from

    where

    group by

    having

    order by

    limit

     

    去重:distinct

    例:select distinct * from T

    数据分组: group by , having , rollup

    group by  :进行分组; 如果分组中具有null值,则null将作为一个分组返回;

    having   :过滤分组; 它支持所有where中的操作符;

    注:可以使用rollup关键字来显示出分组前所有的数据;例:group by prod_id with rollup;

    除聚集计算语句外,select语句中使用的每个选择列或表达式列,都必须在group by子句中给出;

    排序:order by

    select * from XXX order byXXX (desc(降序)/asc(升序))

    限制检索行数:limit limit offset

    例:    select * from XXX limit 0,2 (从第0行开始,取2行)

    等价于  select * from xxx limit 1 offset 2(从第2行开始取1行)

    起别名:

    可以为表或列起别名;

    有两种形式:

    (1)table1 t1

    (2)table1 as t1

    where语句中注意的问题:

    注:and比or的优先级高

        ‘<>’ 等价于 ‘!=’f

        between A and B:包括边界

         is null

         in :指定条件范围 取值时用","分隔,相当于or的作用,但比or操作符执行的更快;并且可以包含select语句;

         not

         like: %:任意字符(null除外)   _:单个字符

        注:用通配符过滤:花费时间较长,避免过度使用;可以考虑用正则表达式;

    mysql支持部分正则表达式,可以匹配基本的字符和字符串;

    形如: select * from products where prod_name regexp ‘XXXX’

    例:检索到prod_name包含文本1000的所有行;

    select *   from products   where prod_name regexp ‘1000’

    mysql的预定义字符集:

    [:digit:]---任意的数字(同[0-9])

    [:lower:]---任意小写字母(同[a-z])

    [:upper:]---任意大写字母(同[A-Z])

    [:alpha:]---任意字符(同[a-zA-Z])

    [:alnum:]---任意数字和字母(同[a-zA-Z0-9])

    [:blank:]---空格和制表符(同[\t])

    [:space:]---任意的空白字符,包括空格;(同[\f\n\r\t\v])

    例:-- 表示检索出现连在一起的任意4位数字和小写字母的所有行

    select prod_name

    from products

    where prod_name regexp ‘[[:digit:][:lower:]]{4}’  

    like 和 regexp的区别:

    like是匹配这个列,如果被匹配的文本仅在列值中出现,like并不会找到它,相应的行将不会返回(使用通配符除外)。

    regexp是匹配列值,如果被匹配的文本在列值中出现,regexp会找到它,相应的行将会返回(可以用定位符号^和$,让regexp匹配这个列,而非列值)。

    当一些操作,不需要从表上选择数据时,mysql中提供了一个内置的特殊的表dual(空表),来方便操作;

    mysql中提供的一些常用函数:

    聚集函数(汇总函数):

    max(),   min(),   sum(),  avg(),  count();

    注:它们都忽略列值为null的行;

    它们都可以和distinct关键字联合使用;例如:count(distinct prod_price)

    文本处理函数:

    concat( , ) :用来拼接字段

    例:

    select concat(vend_name, vend_country)

    from vendors

    trim( , ):去掉字段中值中的所有空格

    rtrim( , ):去掉字段中值右边的所有空格

    ltrim( , ):去掉字段中值左边的所有空格

    soundex( ):能对串进行发音比较;可将任何文本串转化为描述其语音表示的字母数字;

    例如:soundex(cust_contact) = soundex(‘Y.Lie’) //可找到表中cust_contact=Y Lee的这条记录;

    日期和时间处理函数:

    Now() :返回当前日期和时间

    CurData():返回当前日期

    Curtime():返回当前时间

    Year(D):返回回一个日期D中的年份部分 类似有:Month(D)……

    DateOfWeek(D):返回对于一个日期D,返回对应的星期几

    DateDiff(D1,D2):计算D1到D2两个日期之差

    Date_Format(D,F):按照表示式F的要求显示日期D;

    AddDate(D,n):计算起始日期D加上n天的日期;

    SubDate(D,n): 计算起始日期D减去n天的日期;

    子查询:嵌套在其他查询中的查询

    使用子查询的两种方式:

    1.一般与in操作符结合使用,但也可以用于测试等不等于;

    2.用子查询去创建计算字段;将子查询整体作为一个计算字段使用;

    注:一切的问题都可以采用子查询写出;

    连接:两个表之间字段取交集

    等值连接:where …=…

    例: from T1,T2   where T1.p_id=T2.p_id;

    内部连接:inner join…on…

    例:from T1 inner join T2 on T1.p_id =T2.p_id;

    注:推荐用inner join on子句,它的性能好于where.

    外连接:left outer join … on… 、right outer join …on…

    左外连接:得到的内容为 两者的公共交集+ 左边的表中非关联部分

    右外连接:得到的内容为 两者的公共交集+ 右边的表中非关联部分

    例:from T1 left outer join T2 on T1.p_id =T2.p_id;

    自连接:速度很好,推荐使用

    可以通过子查询来实现,

    select

    from t

    where  t_id = {  }

    也可以通过不同的别名来实现;

    select

    from  t as t1, t as t2

    where  t1_id = t2_id

     

    组合查询:多个查询并将结果作为一个查询结果集返回,使用union操作字

    需要使用组合查询的情况:

    1. 在单个查询中从不同的表返回类似结构的数据;
    2. 对单个表执行多个查询,按单个查询返回数据;

    在各select语句之间放上关键字union,每个查询必须包含相同的列、表达式或聚集函数。

    它会从查询结果中自动去除重复的行,如果需要不取消行,可使用union all;

    注:使用uinon可以替代where,能够用较简单的方式去完成由where非常复杂才得到的结果;

    范式:

    第一范式(1NF):确保每列保持原子性

    第二范式(2NF):符合1NF,并且,确保表中的每列都和主键相关

    第三范式(3NF):符合2NF,并且,确保每列都和主键列直接相关,而不是间接相关;

    BC范式(BCNF):符合3NF,并且,主属性不依赖于主属性

    第四范式:要求把同一表内的多对多关系删除。

    第五范式:从最终结构重新建立原始结构。

    对表中数据的增删改操作:

    注:T代表某个表

    向表中增加行:有四种形式;

    第一种形式:插入完整行,必须按默认顺序为每个列提供一个值;

    insert into T

    values(……)

    注:若该列没有值则用null表示;

    第二种形式:插入部分行,可按自己指定的顺序为每个列赋值;

    insert into T(……)

    values(……)

    第三种形式:插入多行;

    insert into T(……)

    values(……) ;

    insert into T(……)

    values(……) ;

    (Mysql特有的)

    insert into T(……)

    values(……) ,(……);

    第四种形式:插入部分某些查询结果;

    insert into T(……)

    select ……

    修改表中的数据:

    update T set ……

    例:

    //修改编号为1002顾客的顾客名和顾客电话

    update customers set cust_name=’Tom’, cust_tele=”10086” where cust_id=1002;

    //删除编号为1001顾客的邮件地址

    updata customers set cust_email=null where cust_id=1001;

    从表中删除行:

    delete from T where……

    注:也可以用truncate table语句删除表中所有数据,它的速度更快,相当于删除原表,在建一个空表;

    视图:即:虚拟的表,它只是一个SQL查询,不包含任何数据;

    查看创建视图的语句show create view <视图名称>

    创建视图:

    create view <视图名称>

    as

    select查询语句

    删除视图drop view <视图名称>

    注: 通常视图都是和select语句使用的,

    虽然视图是可更新的,即可以对视图使用insert,update,delete;但其实更新一个视图,实际上是更新其基表,是对基表的增删改,所以并不推荐这样使用;

    优点:可重用SQL语句;

          化简了复杂的SQL操作

          使用的部分表,而不是整个表;

          能保护数据;

          可更改数据格式和表示;

    缺点:视图会影响性能,因此使用大量视图时要慎重;

    Mysql高级语言

    有三种形式的注释

    行注释:   #XXX     -- XXX(之间至少有一个空格符)

    块注释:   /* XXX */

     

    变量局部变量用@开头;全局变量用@@开头;

     

    声明变量: 用declare语句 , 变量不能加@符号;使用游标是只能用declare定义

    daclare var_name[,……]  type  (default value)

    注:declare语句必须用在begin……end语句块中且必须在最前面;变量名不区分大小写; mysql中是一般可以不用事先申明变量,可直接用setselect赋值,

     

    变量赋值:;使用变量时用“@var_name”表示即可; 打印时只能用以下的方式;

    set语句直接赋值:可以用”=”或”:=”赋值

    set  @var_name=value[,…] 或set  @var_name:=value[,…]

    select语句查询赋值:只能用”=”赋值,因为在select语句中=被看作比较运算符;

    ①select  @var_name:=value[,…]

    ②select  @var_name[,…]

    from……

    where……

    ③select  @col_name[,…] into var_name[,…]   #把选定的列赋值给变量

    from ……where……

    注:直接用set/select语句定义的变量必须加@符号,除非该变量已经被declare声明过;

    例://通过连续赋值,加起来赋为t1,并把每个值都打印出来;

    select @t1:=(@t2=1)+@t3:=4,@t1,@t2,@t3; from…where… 

     

    变量的分类:

    mysql手册将变量分系统变量和用户变量

    但实际中常有以下几种:

    局部变量(作用域是当前语句块,即:begin……end):必须用declare声明

    用户变量(作用域是当前整个连接):无需使用declare申明,可用select或set会话变量:(作用域是当前整个连接):

    定义:

    set @var_name=value;

    set session @var_name=value;

    set @@session var_name=value;

    查看:

    select @@var_name;

    select @@session.var_name;

    show session variables like “%var%”

    全局变量(作用域是整个数据库):

    set global @@var_name=value;

    查看:

    select @@global.var_name;

    show global variables like “%var%”

     

    存储过程中的控制语句

    if(expr1, expr2, expr3):相当于java中的三目运算符,

    expr1是true,则返回expr2,否则返回expr3;

    ifnull(expr1, expr2):

    若expr1非null,返回本身;否则返回expr2;

    nullif(expr1,expr2):

    若两者相等,返回null,否则返回expr1;

    分支语句之if

    if  condition  then  result

    [else  result]

    end if;

    分支语句2之case

    形式一:

    case value

    when compare-value  then  result

    [when compare-value  then  result

    ……]

    [else result]

    end case;

    形式二:====java中的if else语句

    case

    when condition  then  result

    [when condition  then  result

    ……]

    [else result]

    end case;

    注:在流程控制中end后不用写case;

             condition是一个表达式;

     

    循环语句之while循环:执行前检查是否满足循环条件

    while condition do

             ……

    end while;

    循环语句之repeat循环:执行前检查是否不满足循环条件

    repeat

             ……

             until condition (没有‘;’)

    end repeat;

    循环语句之loop循环:

    lable_1:loop

             ……

                       leave lable_1;

    end loop;

    注:

    leave语句:只能循环语句中使用,意思离开语句标号为lable_1的语句,相当于“跳出整个循环”(类似java中的break);当满足了特定条件时,通过“leave 循环标号”语句跳出整个循环;

    iterater语句:只能循环语句中使用,意思直接跳转到语句标号为lable_1的语句,相当于“跳过本次循环” (类似java中的continue);

    当满足了特定条件时,通过“iterater 循环标号”语句跳过本次循环;

    语句标号:lables可以用到while, repeat ,loop等循环控制语句中;

    存储过程和函数:统称为PL/SQL子程序,它们是被命名的PL/SQL块,均存储在数据库中,以便共享;

    唯一区别:函数向调用者返回数据,而过程不返回数据;函数可以在SQL语句内部被调用,而过程则不能被调用;

    存储过程和函数的优点简单,安全,高性能

     

    创建存储过程:

    注:为了安全可以先执行这句:drop procedure if exists  <过程名称>;

    delimiter //(有空格符)

    create procedure <过程名称> (

             参数声明

    )

    begin

             过程体

    end //

    delimiter ;(有空格符)

    注:

    ①delimiter意思是定义符号, 目的是用delimiter关键字申明当前段的自定义分隔符,将其之间的内容当作存储过程,使mysql编译器不会执行这些的代码;记得用完后要把分隔符还原;

    ②存储过程定义时有三种参数类型: in,  out,  inout

    in 输入参数:在调用时指定,执行中不能被修改并返回;

    out 输出参数:执行中能被修改并返回;

    inout 输入输出参数:在调用时指定,执行中能被修改并返回;

    调用存储过程:

    call proc_name (…);

    修改存储过程:

    alter procedure proc_name ……;

    删除存储过程:

    drop procedure proc_name ;

    查看存储过程:可以获取何时,有谁创建的信息

    查看所有存储过程的信息:

    show procedure status;

    查看指定的存储过程:

    show create procedure proc_name;

    函数:大体类似于存储过程,只是将关键字procedure变为function

    但注意创建函数时不能使用in,out,inout关键字,因为它默认其所有的参数都是in的;

    注:为了安全可以先执行这句:drop function if exists  <函数名称>;

    delimiter //(有空格符)

    create function <函数名称> (

             参数声明 (参数不能是带@的)

    )

    returns 参数

    begin

             过程体

             return 参数;

    end //

    delimiter ;(有空格符)

     

    函数不能用call调用外,但它能在SQL语句内部被调用

    例如:select func_name(…) from … where…

    使用存储过程和函数的选择:

    1.返回多个值或不返回值,用存储过程;返回一个值,用函数;

    2.存储过程一般用于执行一个指定的动作;

    函数一般用于计算和返回一个值;

    3.要在SQL语句内部被使用,只能用函数;

    游标cursor:只能用与存储过程或函数;

    能在检索出来的行中前进或后退一行或多行;

    它不是select语句,而是被该语句检索出来的结果;

    创建游标:定义时并未检索数据  只能用declare定义变量;

    decalar cur_name cursor for 定义使用的select语句;

    打开游标:打开时才按定义检索数据

    open cur_name;

    使用游标: 通常在while,repeat,loop循环中使用; 游标也可以嵌套;

    关闭游标

    close cur_name;

    注意:使用后必须关闭游标;存储过程或函数中定义的局部变量必须放在游标之前,而定义的句柄必须放在游标之后;

    例:创建一个存储过程,使用游标输出orders表中所有的order_num;

    但是这样会有多个结果窗口;

    delimiter //

    create procedure p_1()

    begin

     

    declare o int;  #局部变量最先定义

    declare done boolean default 0;

    declare ordernumbers cursor for #游标在其后定义

    select order_num from orders;

    declare continue handler for  #处理器在最后定义

    sqlstate '02000' set done = 1;

     

    open ordernumbers;

    fetch ordernumbers into o;

    repeat

    select o;

    #最好将fetch语句放在循环的最后,当其发生异常时能够立即终止循环;

    fetch ordernumbers into o;

    until done

    end repeat;

    close ordernumbers;

     

    end //

    delimiter ;

    注:

    fetch cursor  into var_name:获取游标当前指向的数据行并将指针指向下一行,然后赋给一个变量;(只能取一行数据)

    declare continue handler forsqlstate '02000' set done = 1;

    它表示fetch的执行过程中发生满足sql状态码所代表的异常时,会被自动执行的代码;

    触发器trigger: 让某些语句在事件发生前或后自动执行;

    创建触发器:

    delimiter $

    create trigger <触发器名称>

    [before|after] [insert|update|delete]  on <表名称>

    for ench row

    begin

    <触发器SQL语句>

    end $

    delimiter ;

    支持的事件类型:insert, update, delete;

    例:在增加tab1表记录后,自动将记录中的tab1_id列中的数据增加到tab2表中;

    delimiter $

    create trigger t_1

    after insert on tab1

    /* 一次只能定义一种事件类型;

    before update on tab1

    after delete on tab1

    */

    for each row

     

    begin

    #在增加tab1表中记录后,自动将在指定的新增数据添加到tab2表中;

    insert into tab2(tab2_id) values (new.tab1_id);

    /*

    #在tab1表中修改tab1_name列中数据时,会自动将数据变为大写;

    set tab1_name = Upper(new.tab1_name);

    #在删除tab1表中记录后,自动将指定的删除数据添加到tab2表中;

    insert into tab2(tab2_id) values (old.tab1_id);

    */

    end $

    delimiter ;
    注:

    在insert触发器中是不能使用old关键字的,只能用new;

    在delete触发器中是不能使用new关键字的,只能用old;

    在updeta触发器中,before时用new, after时用old;

    因为new中的值可被更新修改;而old中的值都是只读的,不能更新修改;

    事务处理:它是一种用来维护数据库完整性的机制,可以保证一组操作的原子性,即:要不整体执行,要不执行;如果成功,则写入数据库;如果发生错误,则可以进行回退到以前的某种状态;一般用于增删改操作;

    (内部实现的就是让操作在内存中执行,然后一次性将结果写入硬盘)

    涉及的关键字:

    transaction:事务

    rollback:回退

    commit:提交到硬盘

    savepoint:保留点,它是事务处理中设置的临时占位符,可以对它发布回退,使其恢复到之前的状态;

    例:

    start transaction; #开始事务处理

    delete from tab1 where id= 0;

    savepoint point1; #设置保留点

    delete from tab1 where id= 1;

    delete from tab1 where id= 2;

    rollback to point1; #回退到保留点point1之前的状态;

    rollback; #回退到开始事务处理之前的状态

     

    commit; #将结果提交到硬盘

    注:如果不用事务处理,Mysql默认是自动提交的,但可以用set autocommit=0 语句,取消自动提交;这样就可以使用回退操作;

     

    安全管理:

    创建MySql用户账号:

    create user 用户名 indentified by ‘密码’;

    更改用户名:

    rename user … to…;

    删掉用户名:

    drop user 用户名;

    设置访问权限:

    show grants for

    设置口令:

    set password for …… =password(‘ 口令’); //设置自己的口令

    set password for …… =password(‘ 口令’);

    数据库维护:

    备份数据库:使用mysqldump命令

    备份多个数据库:

    mysqldump –u username –p –all –database dbname1 dbname2 > Backup.sql

    备份所有数据库:

    mysqldump –u username –p –all --database > Backup.sql

    注:

    -n:不创建数据库

    -d:不导出任何数据,只导出数据库的表结构

    -t:只导出数据

    -r:导出存储过程以及自定义函数

    还原数据:

    mysql –u root –p dbname < backup.sql

    数据库易混点:

    数据库中用“=”表示是否相等而不是“==”;

    null和任何值操作的结果都是null;

    如果我引用您的博文记录,没有指出,请求您的原谅。可以私信告诉我,我一定改正! 注:我写博文的目的主要是记录得失,若有什么误人子弟的地方,请多多见谅指正;
  • 相关阅读:
    cmd设置代理
    移动端坐标定位tap
    T02-Django基本应用结构
    支持向量机算法的Sklearn完整复现
    T01-何为Django,入门"Hello World"
    决策树算法的Sklearn完整复现
    逻辑回归算法的Sklearn完整复现
    线性回归算法Sklearn完整复现
    K-近邻算法的Sklearn完整复现
    数据分析中的'疑难杂症'小结(三)
  • 原文地址:https://www.cnblogs.com/zhaojinxin/p/5722715.html
Copyright © 2011-2022 走看看