有没有办法从 pandas read_csv 中“提取”dtype 转换功能?
Posted
技术标签:
【中文标题】有没有办法从 pandas read_csv 中“提取”dtype 转换功能?【英文标题】:Is there any way to "extract" the dtype conversion functionality from pandas read_csv? 【发布时间】:2022-01-18 20:17:21 【问题描述】:我有以下数据框,其中所有列都是对象类型。 我的目标是推断每列的真实类型并进行转换。
我找到了一个“解决方法”并将其保存为 csv,然后再次加载。
有什么方法可以使用pandas read_csv 类型转换功能而不需要保存和加载文件?
'A': 0: nan,
1: nan,
2: nan,
3: nan,
4: nan,
5: nan,
6: nan,
7: 'true',
8: nan,
9: 'true',
'B': 0: nan,
1: nan,
2: nan,
3: nan,
4: nan,
5: nan,
6: nan,
7: 'true',
8: nan,
9: 'true',
'C': 0: 'CustomersData',
1: 'CustomersData',
2: 'CustomersData',
3: 'CustomersData',
4: 'CustomersData',
5: 'CustomersData',
6: 'CustomersData',
7: 'TestData',
8: 'CustomersData',
9: 'CustomersData',
'D': 0: '4014',
1: '4014',
2: '4014',
3: '4014',
4: '4014',
5: '4014',
6: '4014',
7: '500',
8: '4014',
9: '500',
'E': 0: '8',
1: '8',
2: '8',
3: '8',
4: '8',
5: '8',
6: '13',
7: '13',
8: '8',
9: '13'
这是我正在做的事情:
df.to_csv('test.csv')
test_df = pd.read_csv('test.csv')
test_df.dtypes
仅当我使用此解决方法时,pandas read_csv 才会正确推断像“1”和“4044”这样的字符串为整数。
我试过 convert_dtypes()
将所有列都转换为字符串,infer_objects()
也没有做任何事情。
【问题讨论】:
当您转换为 csv 时,它可能会删除单引号,而当您读回它时, read_csv 会将它们作为整数。如果在创建数据框时删除单引号,convert_dtypes() 也会假定它们是整数。 @Jayvee 感谢您的评论,但实际上上述结果是一个长键值表/数据框的数据透视表。如何配置数据透视表以删除它们?实际上它转向了对象。请指教。 我不确定如何在数据透视表中执行此操作,但您始终可以使用 astype 在数据框中显式更改类型,例如 df['D'] = df['D '].astype(int) @Jayvee 但我不知道类型,这就是我需要 pandas 来推断这个系统中的类型的点。它将自动从数据库加载,转换为数据透视表,推断类型,填充缺失值......并执行所有其他逻辑。 【参考方案1】:根据 cmets,有利于推断类型的实际过程是 to_csv,因为它去除了单引号。可能你可以使用一些底层的 to_csv 类和函数(DataFrameFormatter、DataFrameRenderer、CSVFormatter 等),但它会更多的代码和更多出错的风险。 您可以做的是写入和读取缓冲区,以避免 IO 开销。
d='A': 0: np.NaN,
1: np.NaN,
2: np.NaN,
3: np.NaN,
4: np.NaN,
5: np.NaN,
6: np.NaN,
7: 'true',
8: np.NaN,
9: 'true',
'B': 0: np.NaN,
1: np.NaN,
2: np.NaN,
3: np.NaN,
4: np.NaN,
5: np.NaN,
6: np.NaN,
7: 'true',
8: np.NaN,
9: 'true',
'C': 0: 'CustomersData',
1: 'CustomersData',
2: 'CustomersData',
3: 'CustomersData',
4: 'CustomersData',
5: 'CustomersData',
6: 'CustomersData',
7: 'TestData',
8: 'CustomersData',
9: 'CustomersData',
'D': 0: '4014',
1: '4014',
2: '4014',
3: '4014',
4: '4014',
5: '4014',
6: '4014',
7: '500',
8: '4014',
9: '500',
'E': 0: '8',
1: '8',
2: '8',
3: '8',
4: '8',
5: '8',
6: '13',
7: '13',
8: '8',
9: '13'
df=pd.DataFrame(d)
from io import StringIO
buffer=StringIO()
df.to_csv(buffer, index=False)
df_new=pd.read_csv(StringIO(buffer.getvalue()))
df_new.dtypes
输出:
A object
B object
C object
D int64
E int64
dtype: object
然后您可以使用 convert_types 来获得最佳推理:
df_new.convert_dtypes().dtypes
输出:
A boolean
B boolean
C string
D Int64
E Int64
dtype: object
【讨论】:
以上是关于有没有办法从 pandas read_csv 中“提取”dtype 转换功能?的主要内容,如果未能解决你的问题,请参考以下文章
pandas使用read_csv函数随机从文件中读取N行数据pandas使用read_csv函数读取空格分割的文件(space)自定义设置sep参数
python pandas 中文件的读写——read_csv()读取文件
当我通过 skip_footer arg 时,Pandas read_csv 忽略列 dtypes
如何让 pandas.read_csv() 从 CSV 文件列中推断 datetime 和 timedelta 类型?
使用 pandas.read_csv 从 URL 读取压缩的 CSV 文件时出错
解决错误:pandas.read_csv() 报错 OSError: Initializing from file failed