数据的存储离不开数据库,常见的数据库有关系型数据库和非关系型数据库,前者有MySQL系列,Oracle,以及阿里的oceanbase等,而后者主要以mongodb,redis,mamcached为主,做缓存使用。下面以最常见的MySQL为例,进行简单的学习总结:
一、MySQL的安装与开启
首先需要做的是在本地或服务器上安装好MySQL-server等数据库,以本地安装为例,具体安装教程可以参考https://blog.csdn.net/bobo553443/article/details/81383194,在进行简单的安装配置后,(如默认安装),将C:\Program Files\MySQL\MySQL Server 8.0\bin添加到环境变量中,重启生效后,在cmd下输入"mysql -u root -p",然后输入初始设置的密码,接着进入数据库,在输入"show databases;",如果出现以下类似界面即表示安装成功。
补充一句,安装MySQL一般会一个自带的数据库登录可视化的软件MySQL workbench,如果不喜欢的话可以试试navicat premium。
如果想在服务器上安装配置mysql服务器,以ubuntu系统为例,运行以下指令即可
sudo apt-get install mysql-server
sudo apt-get install mysql-client
sudo apt-get install libmysqlclient-dev
安装成功后可以通过下面的命令测试是否安装成功:
sudo netstat -tap | grep mysql
正常输出端口信息即表示成功,接下来利用mysql -uroot -p考虑登陆数据库,但是由于刚开始没有设置初始密码,在秘密行直接回车有时会出现以下错误,
-
ERROR 1698 (28000): Access denied for user 'root'@'localhost'
这时候可以考虑先设置免密登陆,然后在进行修改的错略,该方法同样适用于windows安装。
-
###进入配置文件 sudo vim /etc/mysql/mysql.conf.d/mysqld.cnf #然后在这个配置文件中的[mysqld]这一块中最后位置加入skip-grant-tables这句话,然后退出保存
- service mysql restart,重新启动mysql,然后再登陆即可实现免密登陆了
- 通过mysql -uroot -p免密登陆进入数据库后,输入以下指令
show databases; ##查看数据库详情,回车生效
use mysql; ##回车生效
update user set authentication_string=password("你的密码") where user="root"; ##替换新的密码,回车生效
flush privileges; ##回车生效
quit; ##退出数据库
- 接着再次进入配置文件,将刚才添加的skip-grant-tables注释掉即可,再次登陆就可以实现以新密码登陆了。
- 有时在这一步还会出现一个如下错误,
ERROR 1524 (HY000): Plugin 'auth_socket' is not loaded
这是因为user表的plugin root的字段是auth_socket,需要替换为mysql_native_password就行了,修改指令如下
update user set authentication_string=password("刚才设定的密码"),plugin='mysql_native_password' where user='root';
然后回车执行以下,再输入select user,plugin from user;回车,我们能看到root用户的字段改成功了,quit退出,然后重启mysql再登陆即可。
启动 | 停止 | 重启 |
1、使用 service 启动:service mysql start 2、使用 mysqld 脚本启动:/etc/inint.d/mysql start 3、使用 safe_mysqld 启动:safe_mysql& | 1、使用 service 启动:service mysql stop 2、使用 mysqld 脚本启动:/etc/inint.d/mysql stop 3、mysqladmin shutdown | 1、使用 service 启动:service mysql restart 2、使用 mysqld 脚本启动:/etc/inint.d/mysql restart |
二、mysql基础知识
(1) 、常用操作数据库的命令
- show databases; 查看所有的数据库
- create database test; 创建一个叫test的数据库
- drop database test;删除一个叫test的数据库
- use test;选中库 ,在建表之前必须要选择数据库
- show tables; 在选中的数据库之中查看所有的表
- create table 表名 (字段1 类型, 字段2 类型);
- desc 表名;查看所在的表的字段
- drop table 表名; 删除表
- show create databases 库名;查看创建库的详细信息
- show create table 表名; 查看创建表的详细信息
use my_dataset1; ###开始启用my_dataset1数据库
create table my_form(
sid integer primary key,
sname varchar(18),
); ###在数据内创建表
desc my_form ; ###查看生成的表
(2)、修改表的命令
- 修改字段类型 alter table 表名 modify 字段 字段类型;
- 添加新的字段 alter table 表名 add 字段 字段类型
- 添加字段并指定位置 alter table 表名 add 字段 字段类型 after 字段;
- 删除表字段 alter table 表名 drop 字段名;
- 修改指定的字段 alter table 表名 change 原字段名字 新的字段名字 字段类型
SQL语言包括四种主要程序设计语言类别的语句:数据定义语言(DDL),数据操作语言(DML),数据控制语言(DCL)和事务控制语言(TCL)。
-
update是DML语句,是修改表中数据的语句。UPDATE table_name SET field1=new-value1, field2=new-value2
(3)、对数据的操作(增删查排)
1.增加数据(insert)3种方式
1.1 insert into 表名 values(值1,值2,...)(很少用)
1.2 insert into 表名(字段1,字段2...) values(值1,值2,....);(较常用)
1.3 insert into 表名(字段1,字段2...) values(值1,值2,....),(值1,值2,....),(值1,值2,....);
1.4 insert ignore into 表名(字段1,字段2...) values(值1,值2,....) ##插入未存在的新数据
2.删除数据(delete) delete from 表名 where 条件 注意:where 条件必须加,否则数据会被全部删除
3.更新数据(update) update 表名 set字段1 = 值1, 字段2 = 值2 where 条件
4.查询数据(select)
4.1 查询表中的所有数据 select * from 表名
4.2 指定数据查询 select 字段 from 表名
根据条件查询出来的数据 select 字段 from 表名 where 条件 (最常用的)
where 条件后面跟的条件
关系:>,<,>=,<=,!=
逻辑:or, and
区间:id between 4 and 6 ;闭区间,包含边界
distinct这个关键字来过滤掉多余的重复记录只保留一条,但往往只用它来返回不重复记录的条数,而不是用它来返回不重复记录的所有值。
5.排序
select 字段 from 表 order by 字段 排序关键词(desc | asc)
排序关键词 desc 降序 asc 升序(默认)
5.1 通过字段来排序
例如 :select * from star order by money desc, age asc;
5.2 多字段排序
select 字段 from 表 order by 字段1 desc |asc,...字段n desc| asc;
6.常用的统计函数 sum,avg,count,max,min
只分组:select * from 表 group by 字段
例子: select count(sex) as re,sex from star group by sex having re > 3;
分组统计: select count(sex) from star group by sex;
补:条件判断函数
select e.emp_no,e.first_name,e.last_name,eb.btype,s.salary,
(case eb.btype when 1 then s.salary*0.1
when 2 then s.salary*0.2
else s.salary*0.3 end) as bonus
from employees as e join emp_bonus as eb on e.emp_no=eb.emp_no
join salaries as s on e.emp_no=s.emp_no
and s.to_date="9999-01-01";
7.分组 select * from 表名 limit 偏移量,数量
说明:
8.1.不写偏移量的话就是默认的为0
8.2.实现分页的时候必须写偏移量
偏移量怎么计算?:
limit (n-1)*数量 ,数量
8、having与where
having字句可以让我们筛选成组后的各种数据,where字句在聚合前先筛选记录,也就是说作用在group by
和having字句前。而 having子句在聚合后对组记录进行筛选。
9、给已经创建的表添加主键ID字段
alter table xxx add id int
alter table xxx change id id int not null auto_increment primary key;
10、给表添加索引
create unique index uniq_idx_firstname on actor (first_name);
create index idx_lastname on actor (last_name);
11、视图
create view actor_name_view as
select first_name first_name_v,last_name last_name_v
from actor;
(4)、多表联合查询
>>内连接
隐式内连接 select username,name from user,goods where user,gid=gods,gid;
显示内连接 select username,from user inner join goods on user.gid=goods.gid;
>>外链接
左连接 包含所有的左边表中的记录以及右边表中没有和他匹配的记录 select * from user left join goods on user.gid=goods.gid;
右连接 select * from user right join goods on user.gid=goods.gid;
子嵌套查询 select * from user where gid in(select gid from goods);
>>数据联合查询
select * from user left join goods on user.gid=goods.gid union select * from user right join goods on user.gid=goods.gid;
>>两个表同时更新 update user u, goods g set u.gid=12,g.price=1 where u.id=2 and u.gid=g.gid;
- 一对多:从球队角度来说一个球队拥有多个球员 即为一对多
- 多对一:从球员角度来说多个球员属于一个球队 即为多对一
- 而多对多,例如学生与选修课之间的关系,一个学生可以选择多门选修课,而每个选修课又可以被多名学生选择。 数据库中的多对多关联关系一般需采用中间表的方式处理,将多对多转化为两个一对多。
(5)、DCL 数据控制语言
1.创建用户:create user'xiaoming'@'localhost' identified by '666666';
2.授权用户:grant all on test.*to'xiaoming'@'localhost';
3.刷新权限:flush privileges;
4.取消授权:revoke all on test.* from 'xiaoming'@'localhost';
5.删除用户: drop user'xiaoming'@'localhost';
(6)、DTL 数据事务语言
开启事务:set autocommit=0;
操作回滚:rollback;
提交事务:commit;
事务:是数据库操作的最小工作单元,是作为单个逻辑工作单元执行的一系列操作;这些操作作为一个整体一起向系统提交,要么都执行、要么都不执行;事务是一组不可再分割的操作集合(工作逻辑单元)
事务的四大特性:
- 1 、原子性
事务是数据库的逻辑工作单位,事务中包含的各操作要么都做,要么都不做 。比如a账户500,b账户500,从a账户转账100到到b账户,这笔钱要么转账成功a变为400,b变为600,要么转账失败维持原状。
- 2 、一致性
事 务执行的结果必须是使数据库从一个一致性状态变到另一个一致性状态。因此当数据库只包含成功事务提交的结果时,就说数据库处于一致性状态。如果数据库系统 运行中发生故障,有些事务尚未完成就被迫中断,这些未完成事务对数据库所做的修改有一部分已写入物理数据库,这时数据库就处于一种不正确的状态,或者说是 不一致的状态。比如 在转账之前,A和B的账户中共有500+500=1000元钱。在转账之后,A和B的账户中共有400+600=1000元。也就是说,数据的状态在执行该事务操作之后从一个状态改变到了另外一个状态。同时一致性还能保证账户余额不会变成负数等。
- 3 、隔离性
一个事务的执行不能其它事务干扰。即一个事务内部的操作及使用的数据对其它并发事务是隔离的,并发执行的各个事务之间不能互相干扰。
- 4 、持续性
也称永久性,指一个事务一旦提交,它对数据库中的数据的改变就应该是永久性的。接下来的其它操作或故障不应该对其执行结果有任何影响。
事务处理流程一般如下:
try{
connection.setAutoCommit( false);
数据库操作...
connection.commit();
}catch(Exception ex){
connection.rollback();
}finally{
connection.setAutoCommit( true);
}
(7)索引
当数据库数据量达到一个量级后,普通查询会变得很慢,这时候考虑加入索引来对数据库查询进行优化,常见的添加索引的方式有以下三种,
a. 建表的时候一起创建
CREATE TABLE mytable ( name VARCHAR(32) , INDEX index_mytable_name (name) );
b. 建表后,直接创建索引
CREATE INDEX index_mytable_name ON mytable(name);
c. 修改表结构
ALTER TABLE mytable ADD INDEX index_mytable_name (name);
注:如果是字符串字段,还可以指定索引的长度,在列命令后面加上索引长度就可以了(例如:name(11))
常见的索引类型有普通索引、唯一索引、主键索引、组合索引、全文索引等,虽然索引可以增加查询数据,但对于更新、创建或者删除的时候,需要去维护索引,导致性能会受影响,因此,索引也不能建立太多。
三、Python之MySQL操作实例(linux下)
(1)安装数据库
下载安装pymyql库或者mysqlclient库
pip install pymysql
pip install mysqlclient
(2)使用示例
import pymysql ##导库
DBHOST = 'localhost'
DBUSER = 'root'
DBPASS = 'root'
DBNAME = 'dbtest'
try:
db = pymysql.connect(host=DBHOST, user=DBUSER,password=DBPASS,database=DBNAME,charset="utf8")
print('数据库连接成功!')
except pymysql.Error as e:
print('数据库连接失败'+str(e))
###创建游标执行sql语句
cur = db.cursor()
cur.execute('DROP TABLE IF EXISTS Student') ###创建表之前先检查是否存在,如果存在则删除
sqlQuery = "CREATE TABLE Student(Name CHAR(20) NOT NULL ,Email CHAR(20),Age int )"
cur.execute(sqlQuery) ###建表
###向表中插入数据
sqlQuery=" INSERT INTO Student (Name, Email, Age) VALUE (%s,%s,%s) "
value=('Mike','123456@163.com',20)
try:
cur.execute(sqlQuery,value)
db.commit() ###事务提交
print('数据插入成功!')
except pymysql.Error as e:
print("数据插入失败:"+e )
db.rollback() ##事务回滚
####查询表内容
sqlQuery = "SELECT * FROM Student"
try:
cur.execute(sqlQuery)
results=cur.fetchall()
for row in results:
name=row[0]
email=row[1]
age=row[2]
print('Name:%s,Email:%s,Age:%s'%(name,email,age))
except pymysql.Error as e:
print("数据查询失败:"+str(e))
###更新数据
sqlQuery = "UPDATE Student SET Name= %s WHERE Name=%s"
value = ('John', 'updated name')
try:
cur.execute(sqlQuery, value)
db.commit()
print('数据更新成功!')
except pymysql.Error as e:
print("数据更新失败:"+str(e))
# 发生错误时回滚
db.rollback()
###删除表
sqlQuery='DROP TABLE IF EXISTS Student'
cur.execute(sqlQuery)
print('表删除成功!')
补充:
》错误:ERROR 1093 (HY000): You can't specify target table 'posts' for update in FROM clause
mysql>delete from twhere id in (select idfrom t where id < 5);
ERROR1093 (HY000): You can't specify target table 't' for update in FROM clause
改为下面就OK
delete from t where id in( select * from (select idfrom twhere id <5) tmp ); ##主句( select * from (从句) temp) )
未完,待续。
参考链接:
https://blog.csdn.net/hzw6991/article/details/87893761(Python连接MySQL数据库)
https://blog.csdn.net/weixin_44282031/article/details/96474285(pyqt5做的页面与MySQL数据库交互)
https://blog.csdn.net/u011146423/article/details/85242887(Python GUI教程:在PyQt5中使用数据库)
https://blog.csdn.net/linshijun33/article/details/88677305(pymysql数据库之建库建表、增删改查)
https://blog.csdn.net/yyx3214/article/details/97097696(mysql连接错误)