亲测!史上最全数据库基础?!

为什么要学习数据库

以前在程序中存储数据是一个变量,对象;数据都存储在内存中,程序运行结束后就销毁。

后来学习IO之后,将数据存储在文件中,做到持久存储,但是使用不方便。

学习专业的数据存储软件——数据库软件

数据库概述

数据库(DataBase/db)为了方便数据的存储和管理,它将数据按照特定的规则存储在磁盘上,就是一个存储数据的仓库

相关概念:

DB:数据库;存储数据的容器,他保存了一系列有组织的数据

DBMS:数据库管理系统;又称为数据库软件或数据库产品,用于创建或管理DB。

常见的数据库产品:

国外

  • MySQL 开源版本,也有付费版

  • Oracle数据库 付费版

  • SQL Server(微软)

  • DB2 (IBM)

国内(一般是政府项目使用)

  • 南大通用GBASE: 天津南大通用数据技术股份有限公司

  • 达梦:武汉达梦数据库股份有限公司

  • 人大金仓:北京人大金仓信息技术股份有限公司

  • 神通:神舟通用公司

Mysql数据库

MySQL是一个关系型数据库管理系统,具有快速、可靠和易于使用的特点,支持多种操作系统,支持多种编程语言连接。

关系型数据库?

以数据表为单位,表与表之间存在关联关系

非关系型数据库 redis:缓存(key:value)

结构化查询语言(Structured Query Language)简称SQL,是一种特殊目的的编程语言,是一种数据库查询和程序设计语言,用于存取数据以及查询、更新和管理关系数据库系统。

三种语言

在sql语言中根据操作不同,又分为不同类型的sql语句:

DDL

DDL(数据定义语言):用于创建和修改数据库表结构的语言。

创建删除数据库

-- 创建数据库,并设置字符集编码 并判断数据库是否存在
CREATE DATABASE IF NOT EXISTS test CHARSET utf8;
-- 删除数据库
DROP DATABASE test;
-- mysql数据库一旦创建不能修改,只能修改字符集编码
ALTER DATABASE test CHARSET gbk

创建数据库表

/*
    表  表名
    列   特定信息  姓名、性别...
    行   数据      张三 男
创建表的步骤
    确定表名:学生信息--学生表
    确定列名:学生的具体信息  姓名、性别、生日...
    列的数据类型:
        字符串型:
            char(n) 长度为n的定长字符串
            varchar(n) 最大长度为n的变长字符串
        日期时间类型:
            date  日期--年 月 日
            datetime  时间--年 月 日 时分秒
        数值:
            整数
                TINYINT 一个字节
                SAMALLINT 两个字节
                MEDIUMINT 三个字节
                INT 四个字节
                BIGINT 八个字节
            浮点数
                decimal(M,D) M表示总长,D表示小数点后几位
        TEXT列字符字符串  长文本类型
*/
-- 学生表  学号,姓名,性别,生日,电话,地址,身高,注册时间
CREATE TABLE student(
    num INT,
    name VARCHAR(10),
    gender CHAR(1),
    birthday DATE,
    phone CHAR(11),
    address VARCHAR(30),
    height DECIMAL(3,2),
    reg_time DATETIME
)
​
-- 删除表
DROP TABLE student
​
-- 创建表,并为列添加约束
/*
    学号  唯一,不能为空,而且只能有一个学号;可以添加主键约束(唯一不能重复,不能为空,一个表中只能有一个主键约束)
    PRIMARY KEY 设置主键
    AUTO_INCREMENT 设置主键列自动增长,只修饰主键列,而且为整数
    NOT NULL 不能为空约束 可添加到多个列
    UNIQUE 唯一约束 可添加到多个列
    DEFAULT '默认值' 添加默认值
    COMMENT '注释'  添加注释
    姓名,性别,生日,电话,地址,身高,注册时间
*/
CREATE TABLE student(
    num INT PRIMARY KEY AUTO_INCREMENT,
    name VARCHAR(10) NOT NULL,
    gender CHAR(1) NOT NULL,
    birthday DATE,
    phone CHAR(11) NOT NULL UNIQUE,
    address VARCHAR(30),
    height DECIMAL(3,2) NOT NULL,
    reg_time DATETIME
)
​
-- 修改表名
RENAME TABLE student to stu
RENAME TABLE stu to student
​
-- 复制表结构
CREATE TABLE stu LIKE student
​
-- 修改表,添加列
ALTER TABLE student ADD id INT
​
-- 修改表,添加外键约束
ALTER TABLE student ADD CONSTRAINT 约束名 FOREIGN KEY(majorid) REFERENCES major(id)

DML

DML:数据操纵语言;常用语句insert,delete,update

-- insert 插入
/*
    方式1: INSERT INTO 表名(列1,列2……,列n) VALUES(值1,值2…..,值n);
    方式2: INSERT INTO 表名 set 列名1=值1,..列名n=值n;
    方式3: INSERT INTO 表名(列1,列2……,列n) VALUES(值1,值2…..,值n),(值1,值2…..,值n);
    方式4:INSERT INTO 表名(列1,列2……,列n) 查询语句(查询的列数与插入列数匹配)
*/
​
INSERT INTO student(NAME,gender,birthday,phone,address,height,reg_time) VALUES('王天乐','女','2004-5-3','2123456789322','汉中',1.75,'2024-5-3')
INSERT INTO student(NAME,gender,birthday,phone,address,height,reg_time) VALUES('Jim','女','2004-5-3','2123456789452','England',1.75,'2024-5-3')
​
INSERT INTO student(NAME,gender,birthday,phone,address,height,reg_time)
    VALUES('张三','男','2004-5-3','13488404582','汉中',1.75,'2024-5-3'),
          ('李四','女','2004-5-5','13488404552','汉中',1.65,'2024-2-3'),
          ('窦鑫锐','男','2001-5-3','13688404582','汉中',1.35,'2044-5-3')
          
​
INSERT INTO stu(NAME,gender,birthday,phone,address,height,reg_time) 
    SELECT NAME,gender,birthday,phone,address,height,reg_time FROM student
    
INSERT INTO student SET NAME='王天乐',gender='女',phone='2123456789321'
​
-- update  修改  需要注意条件的准确性,否则修改所有数据
UPDATE  student SET address = '窦鑫锐' WHERE num = 1
-- delete 删除
DELETE FROM student WHERE num=1

DQL

DQL:数据查询语言查询是使用频率最高的一个操作,可以从一个表中查询数据,也可以从多个表中查询数据

-- 基本查询语法
-- select 查询的列 from 表名 where 条件 排序 数量限制 分组......
-- select 结果处理 from 表名
-- 结果处理
-- 查询特定的列
SELECT num,NAME,gender FROM student
-- 查询所有的列,在开发中一般不建议,使用哪些列查询哪些
SELECT * FROM student
-- sql中+ - * / 只能做算数运算,+不能连接字符串
SELECT num+100,NAME FROM student
-- 去除查询结果中重复数据,即查询到所有列都相同
SELECT DISTINCT NAME,gender,birthday FROM student

查询结果中使用函数

  • 单行函数会对查询的每条记录进行操作

  • 分组函数也称为聚合函数,统计函数,把多行最终处理为一行

-- 字符函数
-- length():获取参数值的字节个数
SELECT LENGTH(NAME) FROM student
-- char_length()获取参数值的字符个数
SELECT CHAR_LENGTH(NAME) FROM student
-- concat(str1,str2,.....):拼接字符串 AS 后面为别名
SELECT num,CONCAT(NAME,':',gender) AS NAME FROM student
-- upper()/lower():将字符串变成大写/小写
SELECT UPPER(NAME),LOWER(NAME) FROM student
-- substring(str,pos,length):截取字符串 位置从1开始
SELECT SUBSTRING(NAME,2,3) FROM student
-- instr(str,指定字符):返回子串第一次出现的索引,如果找不到返回0
SELECT INSTR(NAME,'三') FROM student
-- trim(str):去掉字符串前后的空格或子串,trim(指定子串 from 字符串)
SELECT TRIM(NAME) FROM student
SELECT TRIM('张' FROM NAME) FROM student
-- lpad(str,length,填充字符):用指定的字符实现左填充将str填充为指定长度
SELECT LPAD(NAME,5,'a') FROM student
-- rpad(str,length,填充字符):用指定的字符实现右填充将str填充为指定长度
SELECT RPAD(NAME,5,'b') FROM student
-- replace(str,old,new):替换,替换所有的子串
SELECT REPLACE(NAME,'i','I') FROM student
-- 逻辑处理
-- case when 条件 then 结果1 else 结果2 end; 可以有多个when
SELECT NAME,
    (CASE WHEN height>=1.80 THEN '高个子'
          WHEN height>=1.50 THEN '正常身高'
          ELSE '低个子' END) AS height,
     gender FROM student
-- ifnull(被检测值,默认值)函数检测是否为null,如果为null,则返回指定的值,否则返回原本的值 
SELECT NAME,IFNULL(adress,'暂未录入') AS address FROM student
-- if函数:if else的 效果 if(条件,结果1,结果2)
SELECT NAME,IF(height>=1.80,'高个子','正常身高') AS height FROM student
-- 数学函数
-- round(数值,小数位数):四舍五入  不写小数位数相当于只保留整数
SELECT NAME,ROUND(height,1) FROM student
-- ceil(数值):向上取整,返回>=该参数的最小整数
SELECT NAME,CEIL(height) FROM student
-- floor(数值):向下取整,返回<=该参数的最大整数
SELECT NAME,FLOOR(height) FROM student
-- truncate(数值,保留小数的位数):截断,小数点后截断到几位,不会四舍五入
SELECT NAME,TRUNCATE(height,1) FROM student
-- mod(被除数,除数):取余,被除数为正,则为正;被除数为负,则为负
SELECT NAME,MOD(num,3) FROM student
-- rand():获取随机数,返回0-1之间的小数
SELECT NAME,RAND() FROM student
-- 日期函数
-- now():返回当前系统日期+时间
SELECT NAME,NOW() FROM student
-- curdate():返回当前系统日期,不包含时间
SELECT NAME,CURDATE() FROM student
-- curtime():返回当前时间,不包含日期
SELECT NAME,CURTIME() FROM student
-- 可以获取指定的部分,年、月、日、小时、分钟、秒YEAR(日期列),MONTH(日期列),DAY(日期列) ,HOUR(日期列) ,MINUTE(日期列)SECOND(日期列)
SELECT NAME,YEAR(reg_time),MONTH(reg_time),DAY(reg_time) FROM student
-- str_to_date(字符串格式日期,格式):将日期格式的字符转换成指定格式的日期
SELECT STR_TO_DATE('2001-2-6','%Y-%m') FROM student
-- date_format(日期列,格式):将日期转换成字符串
SELECT DATE_FORMAT(birthday,'%y-%m') FROM student
-- datediff(big,small):返回两个日期相差的天数
SELECT DATEDIFF(CURDATE(),birthday) FROM student
-- 分组函数/聚合函数、统计函数
-- sum,avg一般处理数值类型的值,max,min,count可处理任意类型的值
-- sum(列名)求和
SELECT SUM(height) FROM student
-- avg(列名)平均值
SELECT AVG(height) FROM student
-- max(列名)最大值
SELECT MAX(height) FROM student
-- min(列名)最小值
SELECT MIN(height) FROM student
-- 计数count(*)、count(1)、count(列名),列的值为空不统计,推荐使用第一个
SELECT COUNT(*) FROM student
-- 条件查询 select 结果列 from 表名 where 条件

SELECT * FROM student WHERE num=1
-- and 必须满足所有条件
SELECT * FROM student WHERE gender='男' AND height>=1.70 AND address='汉中'
-- or 满足一个条件即可
SELECT * FROM student WHERE gender='男' OR height>=1.70

-- 不等于 != / <>
SELECT * FROM student WHERE gender!='男'
SELECT * FROM student WHERE gender<>'男'

-- 模糊查询 LIKE 字符 %字符% 通配符
SELECT * FROM student WHERE NAME LIKE '张%'
SELECT * FROM student WHERE NAME LIKE '%三%'

-- between and 两者之间,包含临界值
SELECT * FROM student WHERE height BETWEEN 1.70 AND 2.0

-- in 判断某字段的值是否属于in列表中的某一项
SELECT * FROM student WHERE height IN(1.75,1.85,1.95)
-- not 取非
SELECT * FROM student WHERE height NOT IN(1.75,1.85,1.95)

-- is (not) null  为(非)空
SELECT * FROM student WHERE address IS NULL
SELECT * FROM student WHERE address IS NOT NULL
-- union 合并多个查询结果,可以去除重复项
SELECT num,NAME,gender FROM student WHERE gender='男'
UNION
SELECT num,NAME,gender FROM student WHERE height>1.60
-- union all 合并多个查询结果,但是不去重
SELECT num,NAME,gender FROM student WHERE gender='男'
UNION ALL
SELECT num,NAME,gender FROM student WHERE height=1.75
-- 排序
-- order by 排序列 ASC/DESC ASC代表的是升序,DESC代表的是降序,如果不写,默认是升序
SELECT * FROM student ORDER BY height
SELECT * FROM student ORDER BY height ASC
SELECT * FROM student ORDER BY height DESC
​
-- 多个条件排序
SELECT * FROM student ORDER BY height DESC,birthday ASC
-- 什么排序都不写默认按照主键升序排列
SELECT * FROM student
-- 数量限制  limit 开始位置(开始位置为0),查询的数量  实际使用场景为数据分页显示,一次只查询一部分数据,提高查询效率
SELECT * FROM student LIMIT 0,2
SELECT * FROM student LIMIT 2,2
SELECT * FROM student LIMIT 4,2
-- limit 在sql语句的末尾出现
-- 分组查询  在分组函数中也可以使用分组函数来进行相应的操作
-- 将某类数据分到一个组中进行处理,例如性别查询
-- 查询男生,女生各有多少人,按照性别分组
-- GROUP BY 分组条件(列名)  用谁分组谁就可以出现在结果中
SELECT COUNT(*),gender FROM student GROUP BY gender 
-- 统计每年出生的人数
SELECT COUNT(*)AS number,YEAR(birthday) FROM student GROUP BY YEAR(birthday)
SELECT COUNT(*)AS number,DATE_FORMAT(birthday,'%Y')AS YEAR FROM student GROUP BY DATE_FORMAT(birthday,'%Y') 
-- 分组统计姓名,查询哪些姓名重复
-- where 是对原始表中的数据进行过滤
-- HAVING在GROUP BY后面使用,可以直接对分组后的数据进行查询
SELECT * FROM (SELECT COUNT(*)AS number,NAME FROM student GROUP BY NAME)AS t WHERE t.number>1
SELECT COUNT(*)AS number,NAME FROM student GROUP BY NAME HAVING number>1

多表设计_关联查询

数据库设计范式,好的数据库设计,事半功倍,不会有歧义

第一范式

第一范式是最基本的范式(确保每列保持原子性)。如果数据库表中的所有字段值都是不可分解的原子值,就说明该数据库表满足了第一范式。

第二范式

简单的来说就是要有主键;也就是要求其他字段都依赖于主键

通过主键可以精确的定位到某一行的数据

第三范式

不用的信息可以放在不同的表中,如果两张表有关系的话,只需要在另一张表中放另一张表的主键进行关联,关联表中其他的非主键信息就不需要了。

外键

外键:引用另外一个数据表的某条记录。

外键列类型与主键列类型保持一致

数据表之间的关联/引用关系是依靠具体的主键(primary key)和外键(foreign key)建立起来的.

  • 当主表中没有对应的记录时,不能将记录添加到从表

  • 不能更改主表中的值而导致从表中的记录孤立

  • 从表存在与主表对应的记录,不能从主表中删除该行

  • 删除主表前,先删从表

关联查询

关联查询也称多表查询

-- 查询学生信息   学号,姓名,性别,生日,专业
-- 如果不佳任何关联条件,会导致出现笛卡尔乘积现象
SELECT * FROM student,major

-- 内连接,只把满足条件的筛选出来
SELECT * FROM student,major WHERE majorid=id
SELECT * FROM student s INNER JOIN major m ON s.majorid=m.id

-- 外连接,
-- 左外连接 把左边表中所有数据查询出来,右边表中只会查询满足条件的
SELECT * FROM student s LEFT JOIN major m ON s.majorid=m.id

-- 右外连接 把右边表中所有数据查询出来,左边表中只会查询满足条件的
SELECT * FROM student s RIGHT JOIN major m ON s.majorid=m.id

-- 统计每个专业的学生
SELECT COUNT(s.num),m.name FROM student s RIGHT JOIN major m ON s.majorid=m.id GROUP BY m.name

-- GROUP_CONCAT() 把同一组中,多个课程名称连接起来
-- 查询学生选课 
SELECT
  s.num,
  s.name,
  s.gender,
  m.name,
  GROUP_CONCAT(c.name) cname
  FROM student s LEFT JOIN major m ON s.majorid = m.mid
                 LEFT JOIN student_course sc ON s.num = sc.student_num
                 LEFT JOIN course c ON c.id = sc.courseid
  GROUP BY s.num,s.name,s.gender,m.name 
-- 自连接
SELECT * FROM AREA ap JOIN  AREA ac ON ap.id = ac.pid  JOIN AREA ax ON ac.id = ax.pid
-- 子查询 在一个查询语句中又出现了查询语句
-- 子查询可以出现在from 或者where后面
-- from之后称为表子查询(结果一般魏多行多列)把查询结果当作一张表
-- where  标量子查询(结果集只有一行一列)
--        列子查询(结果集只有一列多行)
-- 查询身高最高的学生 标量子查询
SELECT * from student WHERE height=(SELECT MAX(height) FROM student)
-- 列子查询
SELECT * from student WHERE height IN(SELECT height FROM student WHERE height=1.65 OR height=1.75)
-- 查询姓名重复  表子查询
SELECT * FROM (SELECT COUNT(*)AS number,NAME FROM student GROUP BY NAME)AS t WHERE t.number>1

  • 27
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值