MySQL 笔记2
5 -- *************一、数据约束********************---- 6 -- 1.1 默认值 7 CREATE TABLE student( 8 id INT, 9 NAME VARCHAR(20), 10 address VARCHAR(20) DEFAULT '广州天河' -- 默认值 11 ) 12 13 DROP TABLE student; 14 -- 当字段没有插入值的时候,mysql自动给该字段分配默认值 15 INSERT INTO student(id,NAME) VALUES(1,'张三'); 16 17 -- 注意:默认值的字段允许为null 18 INSERT INTO student(id,NAME,address) VALUE(2,'李四',NULL); 19 INSERT INTO student(id,NAME,address) VALUE(3,'王五','广州番禺'); 20 21 SELECT * FROM student; 22 23 -- 1.2 非空 24 -- 需求: gender字段必须有值(不为null) 25 CREATE TABLE student( 26 id INT, 27 NAME VARCHAR(20), 28 gender VARCHAR(2) NOT NULL -- 非空 29 ) 30 31 -- 非空字段必须赋值 32 INSERT INTO student(id,NAME) VALUES(1,'李四'); 33 -- 非空字符不能插入null 34 INSERT INTO student(id,NAME,gender) VALUES(1,'李四',NULL); 35 36 SELECT * FROM student; 37 38 -- 1.3 唯一 39 CREATE TABLE student( 40 id INT UNIQUE, -- 唯一 41 NAME VARCHAR(20) 42 ) 43 44 INSERT INTO student(id,NAME) VALUES(1,'zs'); 45 INSERT INTO student(id,NAME) VALUES(1,'lisi'); -- ERROR 1062 (23000): Duplicate entry '1' for key 'id' 46 47 INSERT INTO student(id,NAME) VALUES(2,'lisi'); 48 49 SELECT * FROM student; 50 51 -- 1.4 主键(非空+唯一) 52 DROP TABLE student; 53 54 CREATE TABLE student( 55 id INT PRIMARY KEY, -- 主键 56 NAME VARCHAR(20) 57 ) 58 59 INSERT INTO student(id,NAME) VALUES(1,'张三'); 60 INSERT INTO student(id,NAME) VALUES(2,'张三'); 61 -- INSERT INTO student(id,NAME) VALUES(1,'李四'); -- 违反唯一约束: Duplicate entry '1' for key 'PRIMARY' 62 63 -- insert into student(name) value('李四'); -- 违反非空约束: ERROR 1048 (23000): Column 'id' cannot be null 64 65 -- 1.5 自增长 66 CREATE TABLE student( 67 id INT(4) ZEROFILL PRIMARY KEY AUTO_INCREMENT, -- 自增长,从0开始 ZEROFILL 零填充 68 NAME VARCHAR(20) 69 ) 70 71 -- 自增长字段可以不赋值,自动递增 72 INSERT INTO student(NAME) VALUES('张三'); 73 INSERT INTO student(NAME) VALUES('李四'); 74 INSERT INTO student(NAME) VALUES('王五'); 75 76 SELECT * FROM student; 77 -- 不能影响自增长约束 78 DELETE FROM student; 79 -- 可以影响自增长约束 80 TRUNCATE TABLE student; 81 82 -- 1.6 外键约束 83 -- 员工表 84 CREATE TABLE employee( 85 id INT PRIMARY KEY, 86 empName VARCHAR(20), 87 deptName VARCHAR(20) -- 部门名称 88 ) 89 90 INSERT INTO employee VALUES(1,'张三','软件开发部'); 91 INSERT INTO employee VALUES(2,'李四','软件开发部'); 92 INSERT INTO employee VALUES(3,'王五','应用维护部'); 93 94 SELECT * FROM employee; 95 96 -- 添加员工,部门名称的数据冗余高 97 INSERT INTO employee VALUES(4,'陈六','软件开发部'); 98 99 -- 解决数据冗余高的问题:给冗余的字段放到一张独立表中 100 -- 独立设计一张部门表 101 CREATE TABLE dept( 102 id INT PRIMARY KEY, 103 deptName VARCHAR(20) 104 ) 105 106 DROP TABLE employee; 107 108 -- 修改员工表 109 CREATE TABLE employee( 110 id INT PRIMARY KEY, 111 empName VARCHAR(20), 112 deptId INT,-- 把部门名称改为部门ID 113 -- 声明一个外键约束 114 CONSTRAINT emlyee_dept_fk FOREIGN KEY(deptId) REFERENCES dept(id) ON UPDATE CASCADE ON DELETE CASCADE -- ON CASCADE UPDATE :级联修改 115 -- 外键名称 外键 参考表(参考字段) 116 ) 117 118 INSERT INTO dept(id,deptName) VALUES(1,'软件开发部'); 119 INSERT INTO dept(id,deptName) VALUES(2,'应用维护部'); 120 INSERT INTO dept(id,deptName) VALUES(3,'秘书部'); 121 122 INSERT INTO employee VALUES(1,'张三',1); 123 INSERT INTO employee VALUES(2,'李四',1); 124 INSERT INTO employee VALUES(3,'王五',2); 125 INSERT INTO employee VALUES(4,'陈六',3); 126 127 -- 问题: 该记录业务上不合法,员工插入了一个不存在的部门数据 128 INSERT INTO employee VALUES(5,'陈六',4); -- 违反外键约束: Cannot add or update a child row: a foreign key constraint fails (`day16`.`employee`, CONSTRAINT `emlyee_dept_fk` FOREIGN KEY (`deptId`) REFERENCES `dept` (`id`)) 129 130 -- 1)当有了外键约束,添加数据的顺序: 先添加主表,再添加副表数据 131 -- 2)当有了外键约束,修改数据的顺序: 先修改副表,再修改主表数据 132 -- 3)当有了外键约束,删除数据的顺序: 先删除副表,再删除主表数据 133 -- 修改部门(不能直接修改主表) 134 UPDATE dept SET id=4 WHERE id=3; 135 -- 先修改员工表 136 UPDATE employee SET deptId=2 WHERE id=4; 137 138 -- 删除部门 139 DELETE FROM dept WHERE id=2; 140 141 -- 先删除员工表 142 DELETE FROM employee WHERE deptId=2; 143 144 SELECT * FROM dept; 145 SELECT * FROM employee; 146 147 -- 级联修改(修改) 148 -- 直接修改部门 149 UPDATE dept SET id=5 WHERE id=4; 150 151 -- 级联删除 152 -- 直接删除部门 153 DELETE FROM dept WHERE id=1; 154 155 156 157 -- **************二、关联查询(多表查询)****************---- 158 -- 需求:查询员工及其所在部门(显示员工姓名,部门名称) 159 -- 2.1 交叉连接查询(不推荐。产生笛卡尔乘积现象:4 * 4=16,有些是重复记录) 160 SELECT empName,deptName FROM employee,dept; 161 162 -- 需求:查询员工及其所在部门(显示员工姓名,部门名称) 163 -- 多表查询规则:1)确定查询哪些表 2)确定哪些哪些字段 3)表与表之间连接条件 (规律:连接条件数量是表数量-1) 164 -- 2.2 内连接查询:只有满足条件的结果才会显示(使用最频繁) 165 SELECT empName,deptName -- 2)确定哪些哪些字段 166 FROM employee,dept -- 1)确定查询哪些表 167 WHERE employee.deptId=dept.id -- 3)表与表之间连接条件 168 169 -- 内连接的另一种语法 170 SELECT empName,deptName 171 FROM employee 172 INNER JOIN dept 173 ON employee.deptId=dept.id; 174 175 -- 使用别名 176 SELECT e.empName,d.deptName 177 FROM employee e 178 INNER JOIN dept d 179 ON e.deptId=d.id; 180 181 -- 需求: 查询每个部门的员工 182 -- 预期结果: 183 -- 软件开发部 张三 184 -- 软件开发部 李四 185 -- 应用维护部 王五 186 -- 秘书部 陈六 187 -- 总经办 null 188 -- 2.2 左[外]连接查询: 使用左边表的数据去匹配右边表的数据,如果符合连接条件的结果则显示,如果不符合连接条件则显示null 189 -- (注意: 左外连接:左表的数据一定会完成显示!) 190 SELECT d.deptName,e.empName 191 FROM dept d 192 LEFT OUTER JOIN employee e 193 ON d.id=e.deptId; 194 195 -- 2.3 右[外]连接查询: 使用右边表的数据去匹配左边表的数据,如果符合连接条件的结果则显示,如果不符合连接条件则显示null 196 -- (注意: 右外连接:右表的数据一定会完成显示!) 197 SELECT d.deptName,e.empName 198 FROM employee e 199 RIGHT OUTER JOIN dept d 200 ON d.id=e.deptId; 201 202 -- 2.4 自连接查询 203 -- 需求:查询员工及其上司 204 -- 预期结果: 205 -- 张三 null 206 -- 李四 张三 207 -- 王五 李四 208 -- 陈六 王五 209 SELECT e.empName,b.empName 210 FROM employee e 211 LEFT OUTER JOIN employee b 212 ON e.bossId=b.id; 213 214 215 SELECT * FROM employee; 216 SELECT * FROM dept; 217 -- 添加上司ID 218 ALTER TABLE employee ADD bossId INT; 219 UPDATE employee SET bossId=1 WHERE id=2; 220 UPDATE employee SET bossId=2 WHERE id=3; 221 UPDATE employee SET bossId=3 WHERE id=4; 222 223 224 -- **************三、存储过程*******************- 225 -- 声明结束符 226 -- 创建存储过程 227 DELIMITER $ 228 CREATE PROCEDURE pro_test() 229 BEGIN 230 -- 可以写多个sql语句; 231 SELECT * FROM employee; 232 END $ 233 234 -- 执行存储过程 235 CALL pro_test(); 236 237 -- 3.1 带有输入参数的存储过程 238 -- 需求:传入一个员工的id,查询员工信息 239 DELIMITER $ 240 CREATE PROCEDURE pro_findById(IN eid INT) -- IN: 输入参数 241 BEGIN 242 SELECT * FROM employee WHERE id=eid; 243 END $ 244 245 -- 调用 246 CALL pro_findById(4); 247 248 -- 3.2 带有输出参数的存储过程 249 DELIMITER $ 250 CREATE PROCEDURE pro_testOut(OUT str VARCHAR(20)) -- OUT:输出参数 251 BEGIN 252 -- 给参数赋值 253 SET str='helljava'; 254 END $ 255 256 -- 删除存储过程 257 DROP PROCEDURE pro_testOut; 258 -- 调用 259 -- 如何接受返回参数的值?? 260 -- ***mysql的变量****** 261 -- 全局变量(内置变量):mysql数据库内置的变量 (所有连接都起作用) 262 -- 查看所有全局变量: show variables 263 -- 查看某个全局变量: select @@变量名 264 -- 修改全局变量: set 变量名=新值 265 -- character_set_client: mysql服务器的接收数据的编码 266 -- character_set_results:mysql服务器输出数据的编码 267 268 -- 会话变量: 只存在于当前客户端与数据库服务器端的一次连接当中。如果连接断开,那么会话变量全部丢失! 269 -- 定义会话变量: set @变量=值 270 -- 查看会话变量: select @变量 271 272 -- 局部变量: 在存储过程中使用的变量就叫局部变量。只要存储过程执行完毕,局部变量就丢失!! 273 274 -- 1)定义一个会话变量name, 2)使用name会话变量接收存储过程的返回值 275 CALL pro_testOut(@NAME); 276 -- 查看变量值 277 SELECT @NAME; 278 279 -- 3.3 带有输入输出参数的存储过程 280 DELIMITER $ 281 CREATE PROCEDURE pro_testInOut(INOUT n INT) -- INOUT: 输入输出参数 282 BEGIN 283 -- 查看变量 284 SELECT n; 285 SET n =500; 286 END $ 287 288 -- 调用 289 SET @n=10; 290 291 CALL pro_testInOut(@n); 292 293 SELECT @n; 294 295 -- 3.4 带有条件判断的存储过程 296 -- 需求:输入一个整数,如果1,则返回“星期一”,如果2,返回“星期二”,如果3,返回“星期三”。其他数字,返回“错误输入”; 297 DELIMITER $ 298 CREATE PROCEDURE pro_testIf(IN num INT,OUT str VARCHAR(20)) 299 BEGIN 300 IF num=1 THEN 301 SET str='星期一'; 302 ELSEIF num=2 THEN 303 SET str='星期二'; 304 ELSEIF num=3 THEN 305 SET str='星期三'; 306 ELSE 307 SET str='输入错误'; 308 END IF; 309 END $ 310 311 CALL pro_testIf(4,@str); 312 313 SELECT @str; 314 315 -- 3.5 带有循环功能的存储过程 316 -- 需求: 输入一个整数,求和。例如,输入100,统计1-100的和 317 DELIMITER $ 318 CREATE PROCEDURE pro_testWhile(IN num INT,OUT result INT) 319 BEGIN 320 -- 定义一个局部变量 321 DECLARE i INT DEFAULT 1; 322 DECLARE vsum INT DEFAULT 0; 323 WHILE i<=num DO 324 SET vsum = vsum+i; 325 SET i=i+1; 326 END WHILE; 327 SET result=vsum; 328 END $ 329 330 DROP PROCEDURE pro_testWhile; 331 332 333 CALL pro_testWhile(100,@result); 334 335 SELECT @result; 336 337 USE day16; 338 339 -- 3.6 使用查询的结果赋值给变量(INTO) 340 DELIMITER $ 341 CREATE PROCEDURE pro_findById2(IN eid INT,OUT vname VARCHAR(20) ) 342 BEGIN 343 SELECT empName INTO vname FROM employee WHERE id=eid; 344 END $ 345 346 CALL pro_findById2(1,@NAME); 347 348 SELECT @NAME; 349 350 351 USE day15; 352 353 SELECT * FROM student2; 354 355 -- 练习: 编写一个存储过程 356 如果学生的英语平均分小于等于70分,则输出'一般' 357 如果学生的英语平均分大于70分,且小于等于90分,则输出‘良好’ 358 如果学生的英语平均分大于90分,则输出‘优秀’ 359 360 DELIMITER $ 361 CREATE PROCEDURE pro_testAvg(OUT str VARCHAR(20)) 362 BEGIN 363 -- 定义局部变量,接收平均分 364 DECLARE savg DOUBLE; 365 -- 计算英语平方分 366 SELECT AVG(english) INTO savg FROM student2; 367 IF savg<=70 THEN 368 SET str='一般'; 369 ELSEIF savg>70 AND savg<=90 THEN 370 SET str='良好'; 371 ELSE 372 SET str='优秀'; 373 END IF; 374 END $ 375 376 CALL pro_testAvg(@str); 377 378 SELECT @str; 379 380 381 -- ************四、触发器***************** 382 SELECT * FROM employee; 383 384 -- 日志表 385 CREATE TABLE test_log( 386 id INT PRIMARY KEY AUTO_INCREMENT, 387 content VARCHAR(100) 388 ) 389 390 -- 需求: 当向员工表插入一条记录时,希望mysql自动同时往日志表插入数据 391 -- 创建触发器(添加) 392 CREATE TRIGGER tri_empAdd AFTER INSERT ON employee FOR EACH ROW -- 当往员工表插入一条记录时 393 INSERT INTO test_log(content) VALUES('员工表插入了一条记录'); 394 395 -- 插入数据 396 INSERT INTO employee(id,empName,deptId) VALUES(7,'扎古斯',1); 397 INSERT INTO employee(id,empName,deptId) VALUES(8,'扎古斯2',1); 398 399 -- 创建触发器(修改) 400 CREATE TRIGGER tri_empUpd AFTER UPDATE ON employee FOR EACH ROW -- 当往员工表修改一条记录时 401 INSERT INTO test_log(content) VALUES('员工表修改了一条记录'); 402 403 -- 修改 404 UPDATE employee SET empName='eric' WHERE id=7; 405 406 -- 创建触发器(删除) 407 CREATE TRIGGER tri_empDel AFTER DELETE ON employee FOR EACH ROW -- 当往员工表删除一条记录时 408 INSERT INTO test_log(content) VALUES('员工表删除了一条记录'); 409 410 -- 删除 411 DELETE FROM employee WHERE id=7; 412 413 SELECT * FROM employee; 414 SELECT * FROM test_log; 415 416 -- ***********五、mysql权限问题**************** 417 -- mysql数据库权限问题:root :拥有所有权限(可以干任何事情) 418 -- 权限账户,只拥有部分权限(CURD)例如,只能操作某个数据库的某张表 419 -- 如何修改mysql的用户密码? 420 -- password: md5加密函数(单向加密) 421 SELECT PASSWORD('root'); -- *81F5E21E35407D884A6CD4A731AEBFB6AF209E1B 422 423 -- mysql数据库,用户配置 : user表 424 USE mysql; 425 426 SELECT * FROM USER; 427 428 -- 修改密码 429 UPDATE USER SET PASSWORD=PASSWORD('123456') WHERE USER='root'; 430 431 -- 分配权限账户 432 GRANT SELECT ON day16.employee TO 'eric'@'localhost' IDENTIFIED BY '123456'; 433 GRANT DELETE ON day16.employee TO 'eric'@'localhost' IDENTIFIED BY '123456'; 434 435 -- ****** 六,mysql备份和还原******** 436 437 438 439 440 441
何事都只需坚持..
难?
维熟尔。
LZL的自学历程...只需坚持