
Pandas 的 read_parquet 不支持以 datetime.time 对象作为 DataFrame 列名,保存后读取会报错“data type 'time' not understood”;本文提供简洁可靠的字符串化转换方案,并说明原理与注意事项。
pandas 的 `read_parquet` 不支持以 `datetime.time` 对象作为 dataframe 列名,保存后读取会报错“data type 'time' not understood”;本文提供简洁可靠的字符串化转换方案,并说明原理与注意事项。
Parquet 是一种列式存储格式,广泛用于高性能数据分析场景,但其元数据规范(如 Apache Parquet 标准)并未定义对 Python 原生 datetime.time 类型的直接支持。当使用 time(9) 或 time(10, 30) 等对象作为 DataFrame 的列名时,to_parquet() 虽能暂存(依赖 pandas 内部序列化机制),但在后续 read_parquet() 过程中,Arrow 或 fastparquet 后端无法将该类型反序列化为合法的 pandas 数据类型,从而抛出 TypeError: data type 'time' not understood。
最直接、安全且无需额外依赖的解决方式是:在构造 DataFrame 前,将 time 对象显式转换为标准字符串格式(如 '09:00:00')。这既保留了语义可读性,又完全兼容 Parquet 的类型系统:
from datetime import time
import pandas as pd
# ✅ 正确做法:列名转为字符串
df = pd.DataFrame(
index=['ABC', 'DEF'],
data={str(time(9, 0)): [2, 4], str(time(10, 30)): [6, 8]}
)
df.to_parquet('MWE.parquet')
df1 = pd.read_parquet('MWE.parquet')
print(df1)
# 输出:
# 09:00:00 10:30:00
# ABC 2 6
# DEF 4 8
⚠️ 注意事项:
- 不建议使用
pd.to_datetime()或pd.to_timedelta()替代——它们会改变数据语义(如将时间点转为日期时间戳或时长,丢失纯“时刻”上下文); - 若需后续按时间逻辑排序列,可利用字符串的字典序(
'09:00:00' 成立)或通过pd.to_datetime(df1.columns, format='%H:%M:%S')临时解析; - 此方案适用于所有基于 Arrow 的 Parquet 引擎(默认 pyarrow),也兼容 fastparquet;
- 若列数据本身含
time类型(而非列名),应统一转为timedelta64[ns]或字符串,但本例中问题仅出在列索引层面。
总结:Parquet 本质是跨语言存储格式,优先保障类型互通性而非 Python 特有对象的保真度。将 time 列名转为 ISO 风格字符串是最小侵入、最大兼容的工程实践。










