跳转到主内容
趣航编程网 - 趣学编程,启航技术之路!

Python如何读取SQL数据库并保存为CSV_通过pandas的to_csv

pandas.read_sql连接对象必须是SQLAlchemy Engine;直接传sqlite3或pymysql的Connection会报错,因pandas要求底层支持execute方法。 用
pandas.read_sql
读取数据库时,连接对象必须是 SQLAlchemy Engine 直接传
sqlite3.connect(...)
或 pymysql 的
Connection
会报错:
AttributeError: 'Connection' object has no attribute 'execute'
。pandas 要求底层是
sqlalchemy.engine.Engine
。 正确做法是用
sqlalchemy.create_engine
构建连接:
from sqlalchemy import create_engine import pandas as pd

engine = create_engine("sqlite:///example.db")

或 MySQL:engine = create_engine("mysql+pymysql://user:pass@localhost/dbname")

df = pd.read_sql("SELECT * FROM users", engine)

立即学习 “ Python免费学习笔记(深入) ”; SQLite 路径支持相对路径,但注意当前工作目录可能不是脚本所在目录 MySQL/PostgreSQL 需要安装对应驱动(
pymysql
、
psycopg2
),否则
create_engine
会抛
ModuleNotFoundError
如果 SQL 语句含参数,别用 Python 字符串格式化,改用
pd.read_sql("SELECT * FROM t WHERE id = :id", engine, params={"id": 123})
to_csv
默认不写表头和索引,但生产环境通常需要显式控制 直接调
df.to_csv("out.csv")
会把 DataFrame 的行索引(index)也写进去,且列名作为第一行——这常被误认为“多了一列”或“首行错位”。 常见组合: Python 3.14.3 微软官方的 Python 扩展,是 VS Code 安装量最高的扩展(209M+)。集成 IntelliSense(通过 Pylance)、调试(通过 Python Debugger)、代码检查、格式化、重构和单元测试等功能。支持 Jupyter Notebook、虚拟环境管理和多 Python 版本切换。 下载
df.to_csv("out.csv", index=False, header=True) # 推荐:无索引,有列名 df.to_csv("out.csv", index=False, header=False) # 纯数据,无列名(适合后续程序解析) df.to_csv("out.csv", index=True, header=True) # 保留索引(如需溯源 row_id)
index=False
是最常用选项,尤其导出给 Excel 或其他系统消费时 中文列名或数据导出乱码?加
encoding="utf-8-sig"
(Windows Excel 友好),不要用
utf-8
数值列含 NaN,默认转为空字符串;若需统一为
NULL
或
0
,先用
df.fillna(...)
大数据量导出 CSV 容易内存爆掉,得流式处理 当表有百万行以上,
pd.read_sql
一次性加载全量到内存,再
to_csv
,很可能触发
MemoryError
或拖慢整个流程。 替代方案:用
chunksize
分批读 + 追加写入:
with open("large_out.csv", "w", encoding="utf-8-sig") as f: first_chunk = True for chunk in pd.read_sql("SELECT * FROM logs", engine, chunksize=50000): chunk.to_csv(f, header=first_chunk, index=False, mode="a") first_chunk = False
chunksize
值不是越大越好,5k–50k 之间较稳妥,取决于单行平均大小和可用内存 首次写入需
header=True
,后续必须
header=False
,否则 CSV 每块都带列名 不能用
df.to_csv(..., mode="a")
直接追加,因为
to_csv
会重写整个文件头逻辑 导出后 CSV 列顺序/类型和数据库不一致?问题出在 SQL 查询本身 pandas 不会自动按数据库字段定义顺序或类型映射 CSV。比如某列在 DB 是
DATE
,读出来是
datetime64[ns]
,但
to_csv
默认转成字符串(ISO 格式),且毫秒部分可能被截断。 确保 SELECT 明确写出字段名,避免
*
导致顺序不可控 时间列要保留精度?用
parse_dates
参数或导出前
chunk["created_at"].dt.strftime("%Y-%m-%d %H:%M:%S.%f")
整数列含 NULL,pandas 会转成
float64
(因 NaN 是浮点),导出后带
.0
。解决:先
astype("Int64")
(注意是大写 I)再导出 真正卡住的往往不是语法,而是对 SQL 结果结构、pandas 类型推断、CSV 文本本质这三层之间隐式转换的误判。

相关文章