
简介面向高校Python课程的一份数据库操作教学课件聚焦Python与数据库的交互重点讲解SQLite这一轻量级关系型数据库的使用。内容从数据库基础入手介绍常见数据库类型关系型、键值存储、文档型、图数据库及DBMS的主要功能系统梳理SQL语法包括创建表、删除表、查询、where条件过滤、分组统计等并说明SQLite五种数据类型及灵活存储机制。课件详细讲解Python操作数据库的核心API涵盖sqlite3连接、游标执行、数据插入、查询获取、连接关闭等步骤最后通过一个综合案例完整演示从建库、建表到增删改查的实践流程案例贴近教学与复习场景。资源包内为1个pptx课件压缩包大小3.46MB结构紧凑、即下即用。目前已有853人学习下载内容系统、示例直观能帮助读者快速构建Python数据库操作知识体系适合高校教师备课、课堂教学以及学生期末复习巩固。1. 为什么教学课件里的 SQLite 反而是最值得拆的数据库期末复习最怕什么不是语法背不住而是数据库连接这一步就把人劝退了。MySQL 要装服务、配账号、处理字符集折腾半小时还没看到一行数据。这个课件没有选那些重型数据库而是从 Python 标准库自带的 sqlite3 讲起把数据库基础、SQL 语法、Python DB-API 和操作流程串成一条线。它面向高校教师教学也适合学生课后复习核心价值在于用最小的环境成本把建表、增删改查、分组统计、事务提交这些高频动作全部跑通。无论你是在做数据库课程设计还是准备 Python 期末复习都可以把它当作一份可复现的实操笔记。2. 先理清关系型数据库的模型二维表、主键与 SQLite 的类型亲和2.1 关系模型中的基础概念课件开篇就从数据库基础入手这其实是很关键的铺垫。关系型数据库把复杂的数据结构归结成二维表一张表就是一组行和列行在数据库中称为记录或元组列称为字段或属性。比如 school 表一行就是一所高校school_code 是唯一标识这就是主键。这个模型的好处是无论是 MySQL、SQL Server 还是 SQLite操作的对象和返回的结果都是二维表所以 SQL 语句可以在不同数据库之间直接移植。需要说明的是关系模型里的域指字段的取值范围分量是某个记录里某个字段的具体值。这些概念在课件里一笔带过但如果你要在期末复习或课程设计答辩里解释表结构设计能把这些术语和实际表字段对应上会显得你对数据库基础有真正的理解。另外表与表之间通过外键建立关联虽然 SQLite 默认不强制启用外键约束但设计表结构时仍然要有一对多或多对多的意识。比如后续要建学生表学生表里就可以加一个 school_code 字段指向这里的主键。2.2 SQLite 的五种存储类型与类型亲和SQLite 与 MySQL 的一个显著差异在于存储类型。SQLite 内部只支持五种基本数据类型NULL、INTEGER、REAL、TEXT、BLOB。它虽然也接受 varchar(n)、char(n) 这类写法但本质上不会像 MySQL 那样严格校验字段长度和类型。也就是说你在建表语句里写 school_code char(6)SQLite 实际存储时仍按 TEXT 处理存一个 10 个字符的字符串也不会报错。这种设计叫类型亲和对教学场景是好事你不用一开始就纠结字段长度、精度、字符集可以先把注意力放在 SQL 逻辑和 Python 代码上。但也要提醒生产环境里如果依赖 SQLite 做严格数据校验需要自己在应用层控制或者改用 MySQL、Oracle 这类字段约束更严格的数据库。另外如果声明 integer primary keySQLite 会自动把它变成自增 rowid 的别名适合做学生表、成绩表这类需要自动编号的场景。下面的表列出了五种类型的典型用途。类型用途示例NULL空值未填写的字段INTEGER整数、自增主键age、idREAL浮点数成绩、评分TEXT字符串学校名称、省份BLOB二进制对象图片、序列化数据2.3 用建表语句把概念落成实践把概念落到代码最常见的就是课件里的 school 表创建。这里我一般会强调两条规则建表前用 if not exists 判断删表前用 if exists 判断。否则重复执行脚本时会直接报错浪费排错时间。create table if not exists school ( school_code char(6) primary key, school varchar(50), province varchar(30), is_985 varchar(10), is_211 varchar(10), is_self_marking varchar(10), school_type varchar(10) );这段 SQL 里primary key 指定 school_code 作为主键它是每条记录的唯一标识。varchar(50) 这类声明在 SQLite 中不强制长度但建议保留因为当你要把表结构迁移到 MySQL 时这些声明就是现成的类型模板。删除表使用 drop table if exists school执行后表结构连同数据一起消失和 delete 只删数据的行为完全不同。这里还需要注意一个容易混淆的点drop table 是删除整张表delete from 是删除数据但保留表结构。课件里专门强调了这个区别实际写代码时也要先想清楚。建表语句中的字段顺序同样重要它决定了 insert 省略字段列表时的默认插入顺序这一点会和后面的 SQL 实操直接相关。3. 从增删改查开始SQL 语句在 Python 课件里的高频用法3.1 select 查询的完整结构与 where 条件组合SQL 里最常用、也最能体现数据库能力的是 select 查询。课件给出的语法结构是select 字段列表 from 表名 where 查询条件 group by 分组字段 order by 字段 [asc|desc]。实际执行时数据库会先过滤 where再分组再排序最后投影出字段列表。理解这个执行顺序对排查查询结果异常很有帮助。where 子句支持五类常见条件可以把它们整理成一张速查表。比较运算用于精确匹配between 用于范围筛选in 用于匹配一组值and 和 or 组合多条件like 配合百分号做模糊匹配。下面这张表覆盖了课件中的例子和最常见的扩展。运算符类型语法示例说明比较where province 江西省等值或大小比较范围where school_code between 10404 and 10410闭区间筛选列表where province in (江西省,湖南省)匹配多个离散值逻辑where is_985是 and is_211是多条件组合模糊where school like %师范%包含关键字搜索这里最容易犯的错误是把单引号和双引号混用。SQL 标准里字符串一般用单引号SQLite 也兼容双引号但推荐统一用单引号避免和 Python 字符串的引号产生冲突。模糊匹配里的百分号是通配符%师范% 表示包含师范二字的任意字符串这类写法在爬虫数据过滤和关键词匹配场景中非常常见。3.2 分组统计与排序聚合函数是期末复习的重点如果只做条件查询还体会不到 SQL 的统计能力。group by 子句用于把相同字段值的记录合并成一组通常和聚合函数一起使用。课件里的例子是统计各个省份的高校数量语句本身很简短但信息密度很高。select province, count(*) as 学校数 from school group by province order by 学校数 desc;这条语句的逻辑是先按 province 分组再对每组调用 count(*) 统计行数最后按别名学校数降序排列。as 关键字可以省略但建议保留因为 Python 端通过游标读取结果时列名就是这里的别名后续配合 Row 对象按字段名访问会更方便。常见的聚合函数还有 sum(列名)、max(列名)、min(列名)、avg(列名)。这里有一个容易被忽略的细节count() 统计的是记录行数count(列名) 会跳过该列为 NULL 的行。如果字段允许为空两个写法可能得到不同结果。另外group by 之后如果还想过滤分组结果需要用到 having而不是 where。where 在分组前执行having 在分组后执行例如只显示高校数大于 10 的省份就要写成 having count() 10。3.3 insert、update、delete 的注意点增删改查里的增删改虽然语法简单但坑最多。insert 语句有两种写法指定字段列表或者省略字段列表直接给全部值。指定字段时字段顺序和 values 里的值顺序必须一一对应省略字段列表时值的顺序必须和建表语句里的字段顺序完全一致否则数据就错位了。insert into school(school, province) values(江西财经大学, 江西省); update school set school 赣南师范大学 where school 赣南师范学院; delete from school where province 江西省;update 和 delete 都要求必须带上明确的 where 条件否则会更新或删除整张表。实际开发中我建议先写 where 条件再写 set 或 delete 关键字从书写顺序上避免误操作。如果你确实要清空表delete from 表名 仍然会保留表结构而 drop table 表名 会把表彻底删掉。提示update 和 delete 语句在正式环境执行前最好先用同条件 select 确认一下匹配范围。再补充一个批量插入场景。如果数据来自爬虫或外部文件逐条 insert 效率很低。更好的做法是在 Python 端用 executemany把数据整理成列表再一次性写入这个内容在下一章展开。4. 深入 Python DB-API从连接对象到游标的执行链路4.1 DB-API 规范与三类核心对象Python 操作数据库并不需要为每种数据库单独记一套语法因为 PEP 249 定义了 DB-API 规范sqlite3、PyMySQL、psycopg2 都实现了同一套接口。这个抽象层的价值在于业务代码里只依赖 connect()、cursor()、execute()、commit() 这些通用方法未来从 SQLite 换到 MySQL只需要改连接方式和驱动包SQL 部分和数据处理逻辑基本不用动。DB-API 规范里最常用的是三个类Connection 负责管理连接和事务Cursor 负责执行 SQL 并获取结果Row 表示结果集中的一行。实际开发中很多人容易忽略 rowcount 和 arraysize。cursor.rowcount 返回的是受影响行数比如 update 匹配了多少行arraysize 控制 fetchmany(size) 一次取多少行。处理几十万行数据时用 fetchall 一次性加载会占用大量内存改成循环 fetchmany(500) 会平滑很多。教学中我会把三个类的核心方法整理成一张速查表。类核心方法或属性说明Connectionclose()、commit()、rollback()、cursor()管理连接和事务Cursorexecute()、executemany()、fetchall()、fetchmany(size)执行 SQL、获取结果Rowkeys()、下标访问按字段名或位置取值4.2 Python 操作 SQLite 的标准流程课件给出了一个标准七步流程我在项目里会把它浓缩成四个阶段连接、游标、执行、清理。下面是一个可以完整运行的示例代码。import sqlite3 # 1. 连接数据库文件不存在时会自动创建 conn sqlite3.connect(school.db) # 2. 创建游标 cursor conn.cursor() # 3. 执行 SQL创建表 cursor.execute( create table if not exists school ( school_code char(6) primary key, school varchar(50), province varchar(30), is_985 varchar(10) ) ) # 4. 提交事务注意关键一步 conn.commit() # 5. 关闭游标和连接 cursor.close() conn.close()代码里的注释已经标出最关键的点对数据库结构或数据做了修改必须执行 conn.commit()否则关闭连接后修改会丢失。sqlite3 模块默认不开启自动提交这一点和很多人的直觉相反。如果是查询操作不 commit 也没关系但为了代码一致我通常都会在需要持久化的操作后补上 commit。关闭顺序也有讲究先关游标再关连接避免持有未释放的资源。还有一个容易被忽略的配置conn.row_factory sqlite3.Row 可以让查询结果支持字段名访问。默认 fetchall 返回的是元组想取 school 字段只能靠下标改成 Row 后可以直接写 row[school]配合 Row.keys() 在构建 JSON 返回结果时非常方便。4.3 参数样式与 executemany 批量写入执行带条件的 SQL 时千万别用字符串拼接来构造语句。比如下面这种写法很容易引发注入问题或者因为引号转义出错。# 不推荐字符串拼接 school 江西财经大学 cursor.execute(select * from school where school school )正确做法是使用参数占位符。sqlite3 模块支持 ? 作为参数样式这也是 DB-API 规范里的 paramstyle 之一。代码可以改成下面这样。cursor.execute(select * from school where school ?, (school,))? 对应第二个参数里的元组元素一个 ? 占一个位置。这样做有两个好处一是 SQL 语句和参数分离避免注入风险二是字符串里的单引号不需要手动转义驱动会帮你处理。需要注意的是不同数据库模块的参数占位符有差异psycopg2 和 MySQLdb 都用 %s所以在写跨数据库代码时最好把 SQL 和参数封装在同一个函数里不要散落在业务各处。批量写入是 executemany 的高频使用场景。假设你从爬虫结果里拿到上千所高校信息逐条 execute 要往返数据库上千次而 executemany 只需一次调用。data [ (10421, 江西财经大学, 江西省, 否), (10422, 华东交通大学, 江西省, 否), ] cursor.executemany( insert into school(school_code, school, province, is_985) values (?, ?, ?, ?) , data)data 是列表每个元素是一个元组元组内的字段顺序和 SQL 中的字段顺序一致。executemany 会自动复用同一条 SQL 模板把参数依次绑定执行适合批量导入、批量初始化的场景。需要留意的是executemany 也是事务操作结束后记得 commit否则数据不会落盘。5. 综合案例用 sqlite3 封装一个高校信息查询小工具5.1 表结构与初始化数据最后用一个完整案例把前面的知识点串起来。我们要在本地文件中创建一个学校信息库包含 school_code、school、province、is_985 四个核心字段然后导入少量数据。这样可以模拟数据库课程设计里最常见的初始化流程。import sqlite3 def init_db(db_pathschool.db): conn sqlite3.connect(db_path) cursor conn.cursor() cursor.execute( create table if not exists school ( school_code text primary key, school text, province text, is_985 text ) ) # 清空旧数据保证 init_db 可重复执行 cursor.execute(delete from school) data [ (10401, 北京大学, 北京市, 是), (10402, 清华大学, 北京市, 是), (10421, 江西财经大学, 江西省, 否), (10422, 南昌大学, 江西省, 否), ] cursor.executemany(insert into school values (?, ?, ?, ?), data) conn.commit() cursor.close() conn.close()init_db 函数里先建表再清空旧数据最后批量插入。这样每次调用都会回到干净的初始状态。如果不清空重复运行脚本会产生重复记录导致后续统计结果翻倍。5.2 封装查询函数并处理事务接下来把查询和更新封装成函数。查询函数返回结果更新函数要处理异常回滚。下面这个实现里用 try/except 把 execute 和 commit 包在一起一旦出错就 rollback避免数据库停留在部分更新状态。def query_by_province(conn, province): cursor conn.cursor() cursor.execute(select school, is_985 from school where province ?, (province,)) rows cursor.fetchall() cursor.close() return rows def update_school_name(conn, old_name, new_name): cursor conn.cursor() try: cursor.execute(update school set school ? where school ?, (new_name, old_name)) conn.commit() return cursor.rowcount except Exception: conn.rollback() raise finally: cursor.close()query_by_province 里的参数绑定把 province 传入 where 条件返回的是列表每个元素是一个元组。update_school_name 通过 rowcount 得到受影响行数用来判断更新是否真的匹配到了记录。如果 rowcount 为 0说明 old_name 不存在调用方可以据此给出业务提示。5.3 验证与排错最后一步这样检查完成封装后最直接的验证方式是打开交互式 Python 环境逐步调用函数并观察返回结果。conn sqlite3.connect(school.db) print(query_by_province(conn, 江西省)) print(update_school_name(conn, 南昌大学, 南昌大学前湖校区)) conn.close()如果结果不符合预期优先检查三个地方一是建表语句是否真的执行成功可以查 sqlite_master 表二是事务是否提交没 commit 的话数据只存在内存里三是参数占位符的数量是否与字段数量一致多一个或少一个都会抛出 ProgrammingError。最后一个检查技巧是打印 cursor.rowcount很多更新无效的问题其实是因为 where 条件没有匹配到任何记录。这个排查思路同样适用于 PyMySQL、psycopg2 等数据库模块因为它们的错误信息都遵循 DB-API 规范。本文还有配套的精品资源点击获取