Pandas: 时间转换器独立工作,但在读取 csv 文件时不工作
Pandas: time converter works in isolation but not when reading csv file
我想读取 csv 文件并将 Excel 序列时间值转换为 YYYY-MM-DD
字符串。该文件如下所示:
A B start_date
0 yes 42736
1 no 42751
2 yes 43039
我想用作转换器的函数是:
def convert_excel_time(excel_time):
return (pd.to_datetime('1900-01-01') + pd.to_timedelta(excel_time,unit='day')).strftime("%Y-%m-%d")
我是这样使用它的:
data = pd.read_csv("data.csv",encoding = "ISO-8859-1",
converters={'start_date': convert_excel_time})
当函数独立使用时,我得到了正确的结果:
excel_time = 42736
In[1]: (pd.to_datetime('1900-01-01')+pd.to_timedelta(excel_time,unit='day')).strftime("%Y-%m-%d")
Out[1]: '2017-01-03'
但是,如果我在读取 csv 文件时将该函数用作转换器,则我所有的开始日期都是“1900-01-01”。我做错了什么?
默认情况下,python 倾向于将文件读取为字符串。它通常会这样做,除非您告诉它不这样做。我不是特别熟悉 pandas
如何做事,但这似乎就是这里发生的事情:当 pd.read_csv()
读取您的文件时,它将 start_date
列解释为字符串。
documentation for pd.to_timedelta()
说它应该可以很好地读取字符串。但是当你实际测试这个方法时,它似乎在这种特殊情况下不起作用。
>>> pd.to_timedelta(44, "day")
Timedelta('44 days 00:00:00')
>>> pd.to_timedelta("44", "day")
Timedelta('0 days 00:00:00.000000')
我怀疑当它将 str
列为有效参数时,它指的是 TimeDelta 的字符串表示,而不是 int-as-a-str。无论出于何种原因,它都不会引发错误,而只是 returns 一个 zero-value 。
因此,您只需要确保传递的是 int
而不是 str
。最简单的方法就是在函数 convert_excel_time()
:
的开头投射 excel_time
def convert_excel_time(excel_time):
excel_time = int(excel_time)
return (pd.to_datetime('1900-01-01') + pd.to_timedelta(excel_time,unit='day')).strftime("%Y-%m-%d")
当实际读取数据时,pandas
似乎提供了一种机制来避免这个问题:pd.read_csv()
的 dtype
kwarg 允许您指定每一列的预期类型(str
大概是默认值)。问题是,如果你给出一个 converters
kwarg,它就会被应用,所以你必须自己处理转换。
我想读取 csv 文件并将 Excel 序列时间值转换为 YYYY-MM-DD
字符串。该文件如下所示:
A B start_date
0 yes 42736
1 no 42751
2 yes 43039
我想用作转换器的函数是:
def convert_excel_time(excel_time):
return (pd.to_datetime('1900-01-01') + pd.to_timedelta(excel_time,unit='day')).strftime("%Y-%m-%d")
我是这样使用它的:
data = pd.read_csv("data.csv",encoding = "ISO-8859-1",
converters={'start_date': convert_excel_time})
当函数独立使用时,我得到了正确的结果:
excel_time = 42736
In[1]: (pd.to_datetime('1900-01-01')+pd.to_timedelta(excel_time,unit='day')).strftime("%Y-%m-%d")
Out[1]: '2017-01-03'
但是,如果我在读取 csv 文件时将该函数用作转换器,则我所有的开始日期都是“1900-01-01”。我做错了什么?
默认情况下,python 倾向于将文件读取为字符串。它通常会这样做,除非您告诉它不这样做。我不是特别熟悉 pandas
如何做事,但这似乎就是这里发生的事情:当 pd.read_csv()
读取您的文件时,它将 start_date
列解释为字符串。
documentation for pd.to_timedelta()
说它应该可以很好地读取字符串。但是当你实际测试这个方法时,它似乎在这种特殊情况下不起作用。
>>> pd.to_timedelta(44, "day")
Timedelta('44 days 00:00:00')
>>> pd.to_timedelta("44", "day")
Timedelta('0 days 00:00:00.000000')
我怀疑当它将 str
列为有效参数时,它指的是 TimeDelta 的字符串表示,而不是 int-as-a-str。无论出于何种原因,它都不会引发错误,而只是 returns 一个 zero-value 。
因此,您只需要确保传递的是 int
而不是 str
。最简单的方法就是在函数 convert_excel_time()
:
excel_time
def convert_excel_time(excel_time):
excel_time = int(excel_time)
return (pd.to_datetime('1900-01-01') + pd.to_timedelta(excel_time,unit='day')).strftime("%Y-%m-%d")
当实际读取数据时,pandas
似乎提供了一种机制来避免这个问题:pd.read_csv()
的 dtype
kwarg 允许您指定每一列的预期类型(str
大概是默认值)。问题是,如果你给出一个 converters
kwarg,它就会被应用,所以你必须自己处理转换。