【解説】日付データの変換方法を学ぶ | データサイエンス100本ノック【問45〜問48 回答】

【解説】日付データの変換方法を学ぶ | データサイエンス100本ノック【問45〜問48 回答】

当ページのリンクには広告が含まれています。




目次

この記事の対象者



・ データサイエンティストを目指している人

・ Pythonで日付データの型を変換する方法(to_datetime関数やastypeメソッド)を学びたい人



以降はデータサイエンス100本ノックの問題を題材に、日付データの変換方法について学んでいきます。


データサイエンス100本ノックの始め方は、以下の記事を参考にしていただければと思います。


>>データサイエンス100本ノックの始め方を確認する


第45問目: 日付型→YYYYMMDD形式(文字列型)に変換する方法

P-045: 顧客データフレーム(df_customer)の生年月日(birth_day)は日付型(Date)でデータを保有している。これをYYYYMMDD形式の文字列に変換し、顧客ID(customer_id)とともに抽出せよ。データは10件を抽出すれば良い。

この問題は、日付型→YYYYMMDD形式に変換する問題です。

to_datetime関数を使って、df_customerbirth_day列のデータを日付を表す特有のdatetime64型に変換します。

その後、dtメソッドを使うことで、列全体に一括処理することにし、strtimeでフォーマットを指定します。

まずは、df_customerデータの構造を確認します。

df_customerの構造を確認
1
df_customer.head(5)
出力
1
2
3
4
5
6
customer_id	customer_name	gender_cd	gender	birth_day	age	postal_cd	address	application_store_cd	application_date	status_cd
0 CS021313000114 大野 あや子 1 女性 1981-04-29 37 259-1113 神奈川県伊勢原市粟窪********** S14021 20150905 0-00000000-0
1 CS037613000071 六角 雅彦 9 不明 1952-04-01 66 136-0076 東京都江東区南砂********** S13037 20150414 0-00000000-0
2 CS031415000172 宇多田 貴美子 1 女性 1976-10-04 42 151-0053 東京都渋谷区代々木********** S13031 20150529 D-20100325-C
3 CS028811000001 堀井 かおり 1 女性 1933-03-27 86 245-0016 神奈川県横浜市泉区和泉町********** S14028 20160115 0-00000000-0
4 CS001215000145 田崎 美紀 1 女性 1995-03-29 24 144-0055 東京都大田区仲六郷********** S13001 20170605 6-20090929-2

birth_dayカラムを抽出してdatetime64型に変換し、tmpに代入します。

birth_dayカラムを抽出
1
2
tmp = pd.to_datetime(df_customer['birth_day'])
tmp
出力
1
2
3
4
5
6
7
8
9
10
11
12
0       1981-04-29
1 1952-04-01
2 1976-10-04
3 1933-03-27
4 1995-03-29
...
21966 1959-10-12
21967 1970-10-19
21968 1972-12-16
21969 1964-06-05
21970 1996-08-16
Name: birth_day, Length: 21971, dtype: datetime64[ns]

次に、YYYY-MM-DDとなっている日付データを、YYYYMMDD形式の文字列に変換します。

一括処理はdtメソッドを使用し、日付から文字列への変換はstrftimeメソッドを使用します。フォーマットは%Y%m%dとします。フォーマットについては、Pythonの公式ドキュメントを参照してください。

1
2
tmp = tmp.dt.strftime('%Y%m%d')
tmp
出力
1
2
3
4
5
6
7
8
9
10
11
12
0        19810429
1 19520401
2 19761004
3 19330327
4 19950329
...
21966 19591012
21967 19701019
21968 19721216
21969 19640605
21970 19960816
Name: birth_day, Length: 21971, dtype: object

tmpデータフレームをcustomer_idとともに出力するために、concatを用いてデータフレームの結合を行います。

>> concatの使い方を復習する

1
pd.concat([df_customer['customer_id'], tmp], axis = 1).head(10)
出力
1
2
3
4
5
6
7
8
9
10
11
customer_id	birth_day
0 CS021313000114 19810429
1 CS037613000071 19520401
2 CS031415000172 19761004
3 CS028811000001 19330327
4 CS001215000145 19950329
5 CS020401000016 19740915
6 CS015414000103 19770809
7 CS029403000008 19730817
8 CS015804000004 19310502
9 CS033513000180 19620711

第46問目: YYYYMMDD形式(文字列型)→日付型に変換する方法

P-046: 顧客データフレーム(df_customer)の申し込み日(application_date)はYYYYMMDD形式の文字列型でデータを保有している。これを日付型(dateやdatetime)に変換し、顧客ID(customer_id)とともに抽出せよ。データは10件を抽出すれば良い。



この問題は、第45問目の逆パタンだね!

まずは、df_customerの構造を確認しましょう。

df_customerの構造を確認
1
df_customer.head(5)
出力
1
2
3
4
5
6
	customer_id	customer_name	gender_cd	gender	birth_day	age	postal_cd	address	application_store_cd	application_date	status_cd
0 CS021313000114 大野 あや子 1 女性 1981-04-29 37 259-1113 神奈川県伊勢原市粟窪********** S14021 20150905 0-00000000-0
1 CS037613000071 六角 雅彦 9 不明 1952-04-01 66 136-0076 東京都江東区南砂********** S13037 20150414 0-00000000-0
2 CS031415000172 宇多田 貴美子 1 女性 1976-10-04 42 151-0053 東京都渋谷区代々木********** S13031 20150529 D-20100325-C
3 CS028811000001 堀井 かおり 1 女性 1933-03-27 86 245-0016 神奈川県横浜市泉区和泉町********** S14028 20160115 0-00000000-0
4 CS001215000145 田崎 美紀 1 女性 1995-03-29 24 144-0055 東京都大田区仲六郷********** S13001 20170605 6-20090929-2

application_date列の文字列データ型をdatetime64型に変換するには、to_datetime関数を使えばOKでした。

変換したデータフレームはtmpに格納しておきます。

application_date列をdatetime64型に変換
1
2
tmp = pd.to_datetime(df_customer['application_date'], format='%Y%m%d')
tmp
出力
1
2
3
4
5
6
7
8
9
10
11
12
0       2015-09-05
1 2015-04-14
2 2015-05-29
3 2016-01-15
4 2017-06-05
...
21966 2017-11-10
21967 2015-03-13
21968 2015-04-06
21969 2016-02-06
21970 2015-04-24
Name: application_date, Length: 21971, dtype: datetime64[ns]

これをcustomer_idとともに出力させるために、concatを用いて結合します。

>> concatの使い方を復習する

customer_idをtmpと結合させて10件表示
1
pd.concat([df_customer['customer_id'], tmp], axis=1).head(10)
出力
1
2
3
4
5
6
7
8
9
10
11
	customer_id	application_date
0 CS021313000114 2015-09-05
1 CS037613000071 2015-04-14
2 CS031415000172 2015-05-29
3 CS028811000001 2016-01-15
4 CS001215000145 2017-06-05
5 CS020401000016 2015-02-25
6 CS015414000103 2015-07-22
7 CS029403000008 2015-05-15
8 CS015804000004 2015-06-07
9 CS033513000180 2015-07-28

第47問目: YYYYMMDD形式(数値型)→日付型に変換する方法

P-047: レシート明細データフレーム(df_receipt)の売上日(sales_ymd)はYYYYMMDD形式の数値型でデータを保有している。これを日付型(dateやdatetime)に変換し、レシート番号(receipt_no)、レシートサブ番号(receipt_sub_no)とともに抽出せよ。データは10件を抽出すれば良い。

YYYYMMDDが文字型ではなく数値型になっている点が第46問目と異なる点ですが、基本的な処理はほぼ同じです。

まずは、df_receiptの全体像を確認します。

df_receiptの全体像を確認
1
df_receipt.head(5)
出力
1
2
3
4
5
6
	sales_ymd	sales_epoch	store_cd	receipt_no	receipt_sub_no	customer_id	product_cd	quantity	amount
0 20181103 1541203200 S14006 112 1 CS006214000001 P070305012 1 158
1 20181118 1542499200 S13008 1132 2 CS008415000097 P070701017 1 81
2 20170712 1499817600 S14028 1102 1 CS028414000014 P060101005 1 170
3 20190205 1549324800 S14042 1132 1 ZZ000000000000 P050301001 1 25
4 20180821 1534809600 S14025 1102 2 CS025415000050 P060102007 1 90

前問と同様の方法でsales_ymdto_datetime関数を用いて日付型に変換します。

1
2
tmp = pd.to_datetime(df_receipt['sales_ymd'], format='%Y%m%d')
tmp
出力
1
2
3
4
5
6
7
8
9
10
11
12
0        2018-11-03
1 2018-11-18
2 2017-07-12
3 2019-02-05
4 2018-08-21
...
104676 2018-02-21
104677 2019-09-11
104678 2017-03-11
104679 2017-03-31
104680 2019-04-23
Name: sales_ymd, Length: 104681, dtype: datetime64[ns]

そしてconcatを用いて結合します。

1
pd.concat([df_receipt[['receipt_no', 'receipt_sub_no']], tmp], axis=1).head(10)
出力
1
2
3
4
5
6
7
8
9
10
11
	receipt_no	receipt_sub_no	sales_ymd
0 112 1 2018-11-03
1 1132 2 2018-11-18
2 1102 1 2017-07-12
3 1132 1 2019-02-05
4 1102 2 2018-08-21
5 1112 1 2019-06-05
6 1102 2 2018-12-05
7 1102 1 2019-09-22
8 1112 2 2017-05-04
9 1102 1 2019-10-10

別解: astypeメソッドを用いたパタン

別解としてastypeメソッドを用いた解放も紹介します。

>> astypeの詳しい使い方

astype('str')とすることで、数値型のデータをstring型に変更することが出来ます。

1
2
tmp1 = pd.to_datetime(df_receipt['sales_ymd'].astype('str'))
tmp1
出力
1
2
3
4
5
6
7
8
9
10
11
12
0        2018-11-03
1 2018-11-18
2 2017-07-12
3 2019-02-05
4 2018-08-21
...
104676 2018-02-21
104677 2019-09-11
104678 2017-03-11
104679 2017-03-31
104680 2019-04-23
Name: sales_ymd, Length: 104681, dtype: datetime64[ns]

抽出したtmp1df_receipt[['receipt_no', 'receipt_sub_no']]concatで結合します。

1
pd.concat([df_receipt[['receipt_no', 'receipt_sub_no']], tmp1], axis=1).head(10)
出力
1
2
3
4
5
6
7
8
9
10
11
12

receipt_no receipt_sub_no sales_ymd
0 112 1 2018-11-03
1 1132 2 2018-11-18
2 1102 1 2017-07-12
3 1132 1 2019-02-05
4 1102 2 2018-08-21
5 1112 1 2019-06-05
6 1102 2 2018-12-05
7 1102 1 2019-09-22
8 1112 2 2017-05-04
9 1102 1 2019-10-10

第48問目: 数値型のUNIX秒データ→日付型に変換する方法

P-048: レシート明細データフレーム(df_receipt)の売上エポック秒(sales_epoch)は数値型のUNIX秒でデータを保有している。これを日付型(dateやdatetime)に変換し、レシート番号(receipt_no)、レシートサブ番号(receipt_sub_no)とともに抽出せよ。データは10件を抽出すれば良い。

UNIX秒とは、協定世界時(UTC)での1970年1月1日午前0時0分0秒からの秒数です。

処理としては問47問目とほぼ同じ処理になりますが、UNIX秒を日付型に変換する方法が異なります。

本問を解きながら、UNIX秒を日付型に変換する方法を学びましょう。

to_datetime関数を使用し、引数unitをunit = 's'とすることで日付型に変換できます。

1
2
tmp = pd.to_datetime(df_receipt['sales_epoch'], unit='s')
tmp
出力
1
2
3
4
5
6
7
8
9
10
11
12
0        2018-11-03
1 2018-11-18
2 2017-07-12
3 2019-02-05
4 2018-08-21
...
104676 2018-02-21
104677 2019-09-11
104678 2017-03-11
104679 2017-03-31
104680 2019-04-23
Name: sales_epoch, Length: 104681, dtype: datetime64[ns]

あとは、これまで同様にconcatで結合すればOKです。

1
pd.concat([df_receipt[['receipt_no', 'receipt_sub_no']], tmp], axis=1).head(10)
出力
1
2
3
4
5
6
7
8
9
10
11
12

receipt_no receipt_sub_no sales_epoch
0 112 1 2018-11-03
1 1132 2 2018-11-18
2 1102 1 2017-07-12
3 1132 1 2019-02-05
4 1102 2 2018-08-21
5 1112 1 2019-06-05
6 1102 2 2018-12-05
7 1102 1 2019-09-22
8 1112 2 2017-05-04
9 1102 1 2019-10-10


まとめ: 日付型のデータ変換の方法を学びました。

本記事は、「【Python】日付データの変換方法を学ぶ | データサイエンス100本ノック【問45〜問48 回答】」というテーマでまとめました。

本記事で紹介した方法を元に、日付型のデータの取り扱いを深めていただければと思います。

なお、データサイエンティストに必要な知識は、TechAcademyのデータサイエンスコースでの学習がおすすめです。

コメント