pandas.Series
は1つのデータ型dtype
、pandas.DataFrame
は各列ごとにデータ型dtype
を持っています。
各列に対して、要約統計量を求めたり文字列メソッドや時系列メソッドを使用したりするとき、列のデータ型が正しくないとそれらのメソッドは正常に動作しません。
つまり、前処理をしたり集計したりするときは、列のdtype
を目的に沿ったデータ型に変換する必要があるという訳です。
この記事では
- 時系列以外に型変換するastypeメソッド
- 時系列に型変換するto_datetimeメソッド
について、サンプルコードを添えて紹介します。
目次
時系列以外に変換|astypeメソッド
列のdtype
を時系列データ以外に変換するときは、pandas.Series.astype
メソッドを使用します。
この章では、以下のデータフレームを使用し、各列を時系列データ以外の型に変換します。
import pandas as pd
df = pd.DataFrame(
data={
'a': [1, 4, 9, 16, 25],
'b': [2.4, 5.1, 10.3, 17.9, 26.0],
'c': [0, 1, np.nan, 2, None],
'd': [True, True, False, False, True],
})
print(df.to_markdown())
# | | a | b | c | d |
# |---:|----:|------:|------:|:------|
# | 0 | 1 | 2.4 | 0.0 | True |
# | 1 | 4 | 5.1 | 1.0 | True |
# | 2 | 9 | 10.3 | NaN | False |
# | 3 | 16 | 17.9 | 2.0 | False |
# | 4 | 25 | 26.0 | NaN | True |
pandas.DataFrame.dtypes
でデータフレームの各列はint
型やfloat
型、bool
型で格納されていることが確認できます。
print(df.dtypes)
# a int64
# b float64
# c float64
# d bool
# dtype: object
整数型に変換
astype
メソッドのdtype
パラメータに'int'
を指定すると、データフレームの列(シリーズ)が整数型に変換されます。dtype
パラメータは省略可能。
float
型→int
型:小数点切り捨てbool
型→int
型:True
を1
、False
を0
に変換- 変換前のシリーズの要素に欠損値が含まれるとエラー
浮動小数点型→整数型
float
型にastype('int')
を指定すると、小数点は切り捨てられます。小数点を切り捨てたい前処理のときに役立ちます。
print(df['b'])
# 0 2.4
# 1 5.1
# 2 10.3
# 3 17.9
# 4 26.0
# Name: b, dtype: float64
# int型に変換
print(df['b'].astype('int'))
# 0 2
# 1 5
# 2 10
# 3 17
# 4 26
# Name: b, dtype: int64
ブール型→整数型
bool
型にastype('int')
を指定すると、True
を1
、False
を0
に変換します。
print(df['d'])
# 0 True
# 1 True
# 2 False
# 3 False
# 4 True
# Name: d, dtype: bool
# int型に変換
print(df['d'].astype('int'))
# 0 1
# 1 1
# 2 0
# 3 0
# 4 1
# Name: d, dtype: int64
変換前のシリーズの要素に欠損値が含まれるとエラー
print(df['c'])
# 0 0.0
# 1 1.0
# 2 NaN
# 3 2.0
# 4 NaN
# Name: c, dtype: float64
# int型に変換
print(df['c'].astype('int'))
# ValueError: Cannot convert non-finite values (NA or inf) to integer
浮動小数点型に変換
astype
メソッドのdtype
パラメータに'float'
を指定すると、データフレームの列(シリーズ)が浮動小数点型に変換されます。実務であんまり使うことは無いかな。
int
型→float
型:小数点第1位に0
を付けるbool
型→float
型:True
を1.0
、False
を0.0
に変換
整数型→浮動小数点型
int
型にastype('float')
を指定すると、小数点第1位に0
が付与されます。
print(df['a'])
# 0 1
# 1 4
# 2 9
# 3 16
# 4 25
# Name: a, dtype: int64
# float型に変換
print(df['a'].astype('float'))
# 0 1.0
# 1 4.0
# 2 9.0
# 3 16.0
# 4 25.0
# Name: a, dtype: float64
ブール型→浮動小数点型
bool
型にastype('float')
を指定すると、True
を1.0
、False
を0.0
に変換します。
print(df['d'])
# 0 True
# 1 True
# 2 False
# 3 False
# 4 True
# Name: d, dtype: bool
# float型に変換
print(df['d'].astype('float'))
# 0 1.0
# 1 1.0
# 2 0.0
# 3 0.0
# 4 1.0
# Name: d, dtype: float64
文字列型に変換
astype
メソッドのdtype
パラメータに'str'
を指定すると、データフレームの列(シリーズ)が文字列型に変換されます。
実務では、数値やブール型の列に対して文字列メソッドを使用したいときなどにしています。この型変換が一番使うかな。
欠損値は'nan'
、'NaT'
という文字列に置き換わるので、欠損値関係のメソッドが使えません。欠損値に対して何らかの処理を行いたい場合は、キャストする前に行っておきましょう。
print(df['c'])
# 0 0.0
# 1 1.0
# 2 NaN
# 3 2.0
# 4 NaN
# Name: c, dtype: float64
print(df['c'].astype('str'))
# 0 0.0
# 1 1.0
# 2 nan
# 3 2.0
# 4 nan
# Name: c, dtype: object
print(df['c'].astype('str').apply(type))
# 0 <class 'str'>
# 1 <class 'str'>
# 2 <class 'str'>
# 3 <class 'str'>
# 4 <class 'str'>
# Name: c, dtype: object
ブール型に変換
astype
メソッドのdtype
パラメータに'bool'
を指定すると、データフレームの列(シリーズ)がブール型に変換されます。0
以外をTrue
、0
をFalse
に変換します。
※欠損値はTrue
に変換されるので、注意が必要です。
print(df['c'])
# 0 0.0
# 1 1.0
# 2 NaN
# 3 2.0
# 4 NaN
# Name: c, dtype: float64
# bool型に変換
print(df['c'].astype('bool'))
# 0 False
# 1 True
# 2 True
# 3 True
# 4 True
# Name: c, dtype: bool
複数列まとめて型変換
複数の列のdtype
を時系列データ以外に変換するときは、pandas.DataFrame.astype
メソッドを使用します。
列ごとに変換するdtypeを決めて、複数列まとめて型変換する
print(df.dtypes)
# a int64
# b float64
# c float64
# d bool
# dtype: object
# 列ごとに変換するdtypeを決めて、複数列まとめて型変換
print(df.astype({'a':'float', 'b':'int'}).dtypes)
# a float64
# b int64
# c float64
# d bool
# dtype: object
1つのdtypeで全ての列をまとめて型変換する
print(df.dtypes)
# a int64
# b float64
# c float64
# d bool
# dtype: object
# bool型に変換
print(df.astype('bool').dtypes)
# a bool
# b bool
# c bool
# d bool
# dtype: object
時系列に変換|to_datetimeメソッド
日時(日付)の文字列や数値(シリアル値)を時系列データに変換するときは、pandas.to_datetime
メソッドを使用します。
この章では、以下のデータフレームを使用し、各列を時系列データに変換します。
import pandas as pd
df = pd.DataFrame(
data={
'a':['2018-03-01 15:19:02', '2019-04-02 18:31:16', '2019-04-15 17:32:58'],
'b':['2018-03-01', '2019-04-02', '2019-04-15'],
'c':[43889, 43573, 43568],
})
print(df.to_markdown())
# | | a | b | c |
# |---:|:--------------------|:-----------|------:|
# | 0 | 2018-03-01 15:19:02 | 2018-03-01 | 43889 |
# | 1 | 2019-04-02 18:31:16 | 2019-04-02 | 43573 |
# | 2 | 2019-04-15 17:32:58 | 2019-04-15 | 43568 |
pandas.DataFrame.dtypes
でデータフレームの各列はobject
型やint
型で格納されていることが確認できます。
print(df.dtypes)
# a object
# b object
# c int64
# dtype: object
文字列をdatetime型に変換
日時(日付)の文字列が格納されている列を時系列データに型変換する場合、to_datetime
メソッドの引数にその列(シリーズ)を指定するだけで、時系列データに変換されたpandas.Series
が返されます。
df['a'] = pd.to_datetime(df['a'])
df['b'] = pd.to_datetime(df['b'])
print(df.dtypes)
# a datetime64[ns]
# b datetime64[ns]
# c int64
# dtype: object
数値(シリアル値)をdatetime型に変換
シリアル値が格納されている列を時系列データに型変換する場合、to_timedelta
メソッドでシリアル値を日数に変換し、基準になる日付('1900-01-01'
)と足し合わせます。
df['c'] = pd.to_timedelta(df['c'], unit='D') + pd.to_datetime('1900-01-01')
print(df.dtypes)
# a object
# b object
# c timedelta64[ns]
# dtype: object
'1899-12-30'
になることに気を付けましょう。