pandas
で"文字列"
をDatetime
に変換する方法、Datetime
の基本的な操作方法を解説します。
pandas
では"文字列"
のままの日時データでは、日時関連の計算などが自由にできません…。
Datetime
に変換して、日付の差分計算や便利な機能を使えるようにしましょう!
この記事では、次の内容について解説していきます
"文字列"
をDatetime
に変換する方法Datetime
の基本操作
※ Datetime
は、正確にはTimestamp
型です。この記事内ではpython
の基本文法とあわせてTimestamp
と呼んでいます。
文字列⇒Datetimeに変換|pd.to_datetime()
pandas
のpd.to_datetime()
関数を使用すると、"文字列"
を簡単にDatetime
に変換できます。
最も基本的な使用方法として、次のように使用します。
変換後Datetimeデータ = pd.to_datetime( 変換前の日付・時刻文字列データ )
例として、次のDataFrame
の"Date"
列のデータを変換してみます。
df = pd.DataFrame({"Date":["2021-11-29",
"2021-11-30",
"2021-12-01",
"2021-12-02"]})
print(df["Date"])
# 変換前のdf["Date"]の中身
# 0 2021-11-29
# 1 2021-11-30
# 2 2021-12-01
# 3 2021-12-02 # Name: Date, dtype: object
df.loc[1,"Date"] - df.loc[0,"Date"]
# TypeError: unsupported operand type(s) for -: 'str' and 'str'
# 日付の差を計算したくても、文字列同士なので差分が取れない
変換前のdf["Date"]
の型は"文字列"
なので、日付の差分などの計算はまだできませんね。
Datetime
に変換すると、日付や時刻に関する計算ができるようになります。
df = pd.DataFrame({"Date":["2021-11-29",
"2021-11-30",
"2021-12-01",
"2021-12-02"]})
# pd.to_datetime()でdf["Date"]の列をDatetimeに変換
df["Date"] = pd.to_datetime(df["Date"])
print(df["Date"])
# 変換前のdf["Date"]の中身
# 0 2021-11-29
# 1 2021-11-30
# 2 2021-12-01
# 3 2021-12-02
# Name: Date, dtype: datetime64[ns]
df.loc[1,"Date"] - df.loc[0,"Date"]
# Timedelta('1 days 00:00:00')
無事、日付の差分が計算できるようになっていますね。
このように日付や時刻の計算をするためには、"文字列"
からDatetime
に変換する必要があります。
以下では、まずデフォルト設定で変換可能な例を紹介します。
次に、デフォルトでは変換できない日付データの処理例を紹介します。
基本的な変換方法
pd.to_datetime()
のデフォルト設定で変換可能な"文字列"
の代表例を紹介します。
日付のみの代表的な形式は次の表のとおりです。
文字列のタイプ | YMDの形式 | 2021年11月23日の例 |
---|---|---|
区切りなし | YYYYMMDD |
20211123 |
ハイフン区切り | YYYY-MM-DD |
2021-11-23 |
スラッシュ区切り | YYYY/MM/DD |
2021/11/23 |
年が後ろパターン | MM-DD-YYYY MM/DD/YYYY |
11-23-2021 11/23/2021 |
日付のみの"文字列"
を変換するサンプルコードを見てみましょう。
df = pd.DataFrame({"Date":["20211123", "2021-11-24", "2011/11/25",
"11/26/2011","11/27/2011"]})
df["Date"] = pd.to_datetime(df["Date"])
print(df["Date"])
# 0 2021-11-23
# 1 2021-11-24
# 2 2011-11-25
# 3 2011-11-26
# 4 2011-11-27
# Name: Date, dtype: datetime64[ns]
この他にも年を2桁で表した形式でも、pd.to_datetime()
で変換できる場合があります。
しかし、年と月の区別がわかりにくいので、後述のformat
を指定した方がいいと思います。
時刻のみの代表的な形式は次の表のとおりです。
文字列のタイプ | YMDの形式 | 2021年11月23日13時10分45秒の例 |
---|---|---|
T後に時刻 | 日付文字列THH:MM:SS |
20211123T13:10:45 |
スペース▯後に時刻 | 日付文字列▯HH:MM:SS |
2021-11-23▯13:10:45 |
AM, PM表記 | 日付文字列THH:MM:SS PM 日付文字列▯HH:MM:SS PM ※午前の場合はAM |
2021/11/23T1:10:45 PM 2021/11/23▯1:10:45 PM |
:省略パターン | 日付文字列THHMMSS |
20211123T131045 |
MM、SSは省略可能です。省略するとそれぞれ0分、0秒になります。
日付+時刻の"文字列"
を変換するサンプルコードを見てみましょう。
df = pd.DataFrame({"Datetime":["2021-11-23T13:10:45", "2021/11/24 13:10:45",
"2011/11/25 1:10:45 PM", "20111126T131045"]})
df["Datetime"] = pd.to_datetime(df["Datetime"])
print(df["Datetime"])
# 0 2021-11-23 13:10:45
# 1 2021-11-24 13:10:45
# 2 2011-11-25 13:10:45
# 3 2011-11-26 13:10:45
# Name: Date, dtype: datetime64[ns]
時刻のみの"文字列"
を変換すると、自動で現在の日にちが追加されます。
df = pd.DataFrame({"Datetime":["13:10:45", "13:10:50"]})
df["Datetime"] = pd.to_datetime(df["Datetime"])
print(df["Datetime"])
# 0 2021-11-23 13:10:45
# 1 2021-11-23 13:10:50
# Name: Date, dtype: datetime64[ns]
#(ブログ執筆は2021-11-23です。)
次にデフォルト設定では対応できない形式への対応方法を紹介していきます。
formatを指定する方法
pd.to_datetime()のデフォルト設定で対応できない場合は、format
引数を指定します。
変換後Datetimeデータ = pd.to_datetime(変換前文字列, format)
format
にはフォーマット指定子(年:%Y
, 月:%m
など)を含んだ"文字列"
を渡します。
例えば、2021年11月23日に対応するformat
は"%Y年%m月%d日"
となります。
df = pd.DataFrame({"Date":["2021年11月23日", "2021年11月24日", "2021年11月25日"]})
df["Date"] = pd.to_datetime(df["Date"], format="%Y年%m月%d日")
# 0 2021-11-23
# 1 2021-11-24
# 2 2021-11-25
# Name: Date, dtype: datetime64[ns]
使用頻度が高そうなフォーマット指定子は下表のとおりです。
フォーマット指定子 | 指定内容 | 2021年11月23日13時10分45秒の例 |
---|---|---|
%Y |
4桁の年 | 2021 |
%y |
2桁の年 | 21 |
%m |
2桁の月 | 11 |
%B |
英語月名 | November |
%b |
英語月名(短縮) | Nov |
%d |
2桁の日にち | 23 |
%H |
2桁の時間(24時間) | 13 |
%I %p |
2桁の時間(12時間) AM or PM |
01 PM |
%M |
分 | 10 |
%S |
秒 | 45 |
%X |
HH:MM:SS のセット | 13:10:45 |
いろいろな形式のフォーマット指定子使用例を以下に整理したので、参考にしてください。
pd.to_datetime("2021年11月21日11時00分00秒", format="%Y年%m月%d日%H時%M分%S秒")
# Timestamp('2021-11-21 11:00:00')
pd.to_datetime("2021年11月21日 01:00PM", format="%Y年%m月%d日 %I:%M%p")
# Timestamp('2021-11-21 13:00:00')
pd.to_datetime("2021年11月21日11:00:00", format="%Y年%m月%d日%X")
# Timestamp('2021-11-21 11:00:00')
pd.to_datetime("November,10,21", format="%B,%d,%y")
# Timestamp('2021-11-10 00:00:00')
CSVやExcelのデータを読み込む場合に、format
を指定する必要がある場合がありますね。
データの読み込みについては、以下の記事を参考にしてみてください。
日付と時刻が別の列にある場合
CSVやExcelの読み取るとたまにあるのですが、日付と時刻が別の列にある時の対処法を紹介します。
例えば、次のDataFrame
のように日付と時刻が別の列にあるとします。
対処法はとてもシンプルで、"Date"
列と"Time"
列を結合してからDatetime
に変換します。
df = pd.DataFrame({"Date":["2021-11-01", "2021-11-02", "2021-11-03"],
"Time":["10:00:00", "12:00:00", "14:00:00"]})
df["Datetime"] = pd.to_datetime(df["Date"]+"T"+df["Time"])
print(df["Datetime"])
# 0 2021-11-01 10:00:00
# 1 2021-11-02 12:00:00
# 2 2021-11-03 14:00:00
# Name: Datetime, dtype: datetime64[ns]
生成したDatetime
をインデックスに設定することも可能です。
df = pd.DataFrame({"Date":["2021-11-01", "2021-11-02", "2021-11-03"],
"Time":["10:00:00", "12:00:00", "14:00:00"]})
df.index = pd.Index(pd.to_datetime(df["Date"]+"T"+df["Time"]), name="Datetime")
print(df)
# Date Time
# Datetime
# 2021-11-01 10:00:00 2021-11-01 10:00:00
# 2021-11-02 12:00:00 2021-11-02 12:00:00
# 2021-11-03 14:00:00 2021-11-03 14:00:00
インデックスの設定方法については、次の記事を参考にしてください。
Datetimeの基本操作
日時をDatetime
に変換すると、次のような便利な機能が使えるようになります。
- 日時の差分の計算
- 年・月・日・時刻の抽出
- 何月、何曜日、何日目の出力
- 特別な日か判定(月始まり?月終わり?)
それぞれサンプルコードと一緒に紹介していきます。
日時の差分の計算
Datetimeでは、日時の差分を計算することができます。
df = pd.DataFrame({"Datetime":["2021-11-23T13:00:00",
"2021-11-24T13:00:00",
"2021-11-30T17:10:00"]})
df["Datetime"] = pd.to_datetime(df["Datetime"])
df["Timedelta"] = df["Datetime"].diff() #隣り合う行の差分を計算
print(df["Timedelta"])
# 0 NaT
# 1 1 days 00:00:00
# 2 6 days 04:10:00
# Name: Timedelta, dtype: timedelta64[ns]
日時の差分のデータは、Timedelta
という型になっています。
年・月・日・時刻の抽出|df[ ].dt.year…
Datetime
では、日時データの一部を抽出することも可能です。
その場合は、df[ ].dt.XXX
の形式で抽出したいデータを指定します。
例として、年、月、日をそれぞれ抽出するサンプルを紹介します。
df = pd.DataFrame({"Date":["2021-10-20T12:00:00", "2021-11-21T12:00:00"]})
df["Date"] = pd.to_datetime(df["Date"])
print(df["Date"].dt.year)
# 0 2021
# 1 2021
# Name: Date, dtype: int64
print(df["Date"].dt.day)
# 0 20
# 1 21
# Name: Date, dtype: int64
主要な抽出可能データ一覧は以下の通りです。
項目 | プロパティ名 |
---|---|
年 | year |
月 | month |
日 | day |
時間 | hour |
分 | minute |
秒 | second |
マイクロ秒 | microsecond |
ナノ | nanosecond |
日付部分全体(datetime.date 型で出力) |
date |
時刻部分(datetime.time 型で出力) |
time |
df[ ].dt.date
、df[ ].dt.time
は、日付と日時のみを取り出す際に便利です。
df = pd.DataFrame({"Date":["2021-10-20T12:00:00", "2021-11-21T15:00:00"]})
df["Date"] = pd.to_datetime(df["Date"])
print(df["Date"].dt.date)
# 0 2021-10-20
# 1 2021-11-21
# Name: Date, dtype: int64
print(df["Date"].dt.time)
# 0 12:00:00
# 1 15:00:00
# Name: Date, dtype: object
何月、何曜日、何日目|df[ ].dt.day_of_year…
df[ ].dt.XXX
の形式で、月の英語名、曜日名、一年で何日目か等の出力もできます。
df = pd.DataFrame({"Date":["2021-11-20", "2021-12-21"]})
df["Date"] = pd.to_datetime(df["Date"])
print(df["Date"].dt.month_name())
# 0 November
# 1 December
# Name: Date, dtype: object
print(df["Date"].dt.day_name())
# 0 Saturday
# 1 Tuesday
# Name: Date, dtype: object
print(df["Date"].dt.day_of_year)
# 0 324
# 1 355
# Name: Date, dtype: int64
関連する項目は下表のとおりです。
項目 | プロパティorメソッド名 |
---|---|
月の英語名 | month_name() |
曜日名 | day_name() |
何クォーター? | quarter |
1年で何日目? | day_of_year |
ひと月で何日目? | days_in_month |
週で何日目 (0~6で番号を振る) |
day_of_week |
特別な日か判定(月始まり?月終わり?)
df[ ].dt.XXX
の形式で、月初めや月終わり、年末年始の判定も可能です。
df = pd.DataFrame({"Date":["2021-04-01", "2021-12-31"]})
df["Date"] = pd.to_datetime(df["Date"])
# 月初めか判定
print(df["Date"].dt.is_month_start)
# 0 True
# 1 False
# Name: Date, dtype: bool
# 四半期始まりか判定
print(df["Date"].dt.is_quarter_start)
# 0 True
# 1 False
# Name: Date, dtype: bool
# 年末か判定
print(df["Date"].dt.is_year_end)
# 0 False
# 1 True
# Name: Date, dtype: bool
関連する項目は下表のとおりです。
項目 | プロパティ名 |
---|---|
月初め | is_month_start |
月終わり | is_month_end |
四半期始まり | is_quarter_start |
四半期終わり | is_quarter_end |
年始 | is_year_start |
年末 | is_year_end |
うるう年 | is_leap_year |
おわりに|padans関連おススメ追加コンテンツ
今回は"文字列"
をDatetime
に変換する方法、Datetime
の基本的な操作方法を解説しました。pandas
は便利すぎて操作方法がわかりにくいことがよくあります…。
結局はコツコツ学ぶのが、pandas
マスターの近道ですよね!≫【ブログカテゴリー:pandas】
Twitter@YutaKaでは、ほぼ毎日pythonに関する情報を発信しています。
気楽にツイートしているので、気軽にフォローしてください!