DataScience

【Pandas】DataFrameやSeriesで1か月後の日付を計算する

Pandasでの日付計算はPythonの日付計算と同じようにできる部分もあるが、Seriesとして扱う必要があるので、処理によっては少し面倒だったりする。

日付計算は基本的に日数で行われる。

また気軽にmonthに+1したりができないので、1か月後などの計算がしにくかったりするのでメモ。

1か月後の日付を計算する

Series.dtのdays_in_month(daysinmonth)を使うことで1か月の日付を取得できるので、加算すれば1か月後の日付になる。

import pandas as pd

date1 = ["2020-1-1", "2020-2-2", "2020-3-3", "2020-4-4", "2020-5-5", "2020-6-6"]

df_date = pd.DataFrame(data={"date": date1})
# dateを日付型に変換
df_date["date"] = pd.to_datetime(df_date["date"], format="%Y-%m-%d", errors="coerce")

# days_in_monthで1か月の日数を取得し、加算する
df_date["date2"] = df_date["date"] + pd.to_timedelta(df_date["date"].dt.days_in_month, "D")
print(df_date)
        date      date2
0 2020-01-01 2020-02-01
1 2020-02-02 2020-03-02
2 2020-03-03 2020-04-03
3 2020-04-04 2020-05-04
4 2020-05-05 2020-06-05
5 2020-06-06 2020-07-06

1か月後の日付列が作成される。

なお、日数を減算することで前月が計算できそうに思えるが、当月が31日で前月が30日の場合や、前月が2月の場合(当月が3月)の場合などは上手く計算できないため、1か月前の日付計算には使用しない方が良い。

また、月末の日付から翌月を計算しようとする場合も、上手くいかないことが多いので注意。

上記記事の日付計算の不可逆性についてを参照。

to_timedeltaの単位について

to_timedeltaは単位に月や年を指定できないため、日数で計算する必要がある。

# dt.monthで月を取得して、単位にMを指定しようとするとエラーとなる。
df_date["date3"] = df_date["date"] + pd.to_timedelta(df_date["date"].dt.month, "M")
ValueError: Units 'M', 'Y', and 'y' are no longer supported, as they do not represent unambiguous timedelta values durations.

単位に週を指定することは可能だが、×7されて日数として計算される。

# 4週を指定すると28日となる。
df_date["date3"] = df_date["date"] + pd.to_timedelta(4, "W")
print(df_date)
        date      date2      date3
0 2020-01-01 2020-02-01 2020-01-29
1 2020-02-02 2020-03-02 2020-03-01
2 2020-03-03 2020-04-03 2020-03-31
3 2020-04-04 2020-05-04 2020-05-02
4 2020-05-05 2020-06-05 2020-06-02
5 2020-06-06 2020-07-06 2020-07-04

数か月後の日付を計算する方法