使用asyncpg读取PostgreSQL表转DataFrame时列名丢失问题解决
解决asyncpg查询结果转DataFrame列名显示为序号的问题
错误原因
你之前的代码错误在于,将asyncpg返回的Record列表先转成了DataFrame,然后试图调用get_attributes()方法——但DataFrame对象并没有这个方法,get_attributes()是asyncpg的Record对象的方法,必须在转成DataFrame之前处理原始查询结果。
解决方案
下面提供两种可靠的解决方法:
方法一:使用pd.DataFrame.from_records自动识别列名
asyncpg的Record对象可以被pandas自动解析为带列名的结构,直接用from_records方法即可:
import pandas as pd import asyncpg async def fetch_data(): conn = await asyncpg.connect(user='user', password='pass', database='dba', host='host', port='5432') # 获取原始Record列表 records = await conn.fetch('''SELECT * FROM my_table''') # 自动识别列名构造DataFrame df = pd.DataFrame.from_records(records) await conn.close() return df
方法二:手动获取列名后构造DataFrame
如果需要更精细的控制(比如处理空表的情况),可以先从原始查询结果或数据库元数据中获取列名,再传入DataFrame构造函数:
import pandas as pd import asyncpg async def fetch_data(): conn = await asyncpg.connect(user='user', password='pass', database='dba', host='host', port='5432') records = await conn.fetch('''SELECT * FROM my_table''') # 获取列名 if records: # 非空表直接从第一个Record获取列名 columns = records[0].keys() else: # 空表从information_schema查询列名 columns_info = await conn.fetch(''' SELECT column_name FROM information_schema.columns WHERE table_schema = 'public' AND table_name = 'my_table' ORDER BY ordinal_position ''') columns = [info['column_name'] for info in columns_info] df = pd.DataFrame(records, columns=columns) await conn.close() return df
关键说明
- asyncpg的
fetch()返回的是Record对象的列表,每个Record包含查询结果的一行数据,且自带列名信息(通过keys()方法获取)。 - 不要先将
Record列表转成普通DataFrame再处理列名,否则会丢失原始的列名关联信息。
内容的提问来源于stack exchange,提问作者adamekcerv
相关产品推荐
相关产品推荐

