この記事はBrainPad Advent Calendar20日目の記事になります
こんにちは@nissy0409240です
@BrainPadProductの中の人として
エンジニアMeetUpの運営と告知をしています
趣味は音楽鑑賞です!
よろしくお願いします!
2022年もあと一ヶ月を切りましたが
皆様いかがお過ごしでしょうか
私は今年もETLツールの中の人として様々なデータ加工などを行っています
ツールはPythonで作られており、Pandasをよく使ってます
Pandasは現在もバージョンアップされており、今年もいくつかの機能が追加されました
本エントリーでは2022年に入ってから追加されたPandasの機能を2つ紹介します
tar.gzファイルもそのまま読み込める
Pandasではcsvファイルの読み込み・書き込みが行えるのは周知の事実ですが
>>> import pandas as pd
>>> df = pd.read_csv("./test.csv")
>>> df.to_csv("./out_test.csv")
$ cat ./out_test.csv
hoge,fuga
1,2
3,4
1.5.0にバージョンアップされた際にtar.gz形式のファイルもそのまま読み込めるようになりました
バージョンアップ前はtar.gzファイルを読もうとすると以下のようなエラーが出ていましたが
>>> import pandas as pd
>>> df = pd.read_csv("./test.tar.gz")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/local/lib/python3.9/site-packages/pandas/util/_decorators.py", line 311, in wrapper
return func(*args, **kwargs)
File "/usr/local/lib/python3.9/site-packages/pandas/io/parsers/readers.py", line 680, in read_csv
return _read(filepath_or_buffer, kwds)
File "/usr/local/lib/python3.9/site-packages/pandas/io/parsers/readers.py", line 575, in _read
parser = TextFileReader(filepath_or_buffer, **kwds)
File "/usr/local/lib/python3.9/site-packages/pandas/io/parsers/readers.py", line 933, in __init__
self._engine = self._make_engine(f, self.engine)
File "/usr/local/lib/python3.9/site-packages/pandas/io/parsers/readers.py", line 1235, in _make_engine
return mapping[engine](f, **self.options)
File "/usr/local/lib/python3.9/site-packages/pandas/io/parsers/c_parser_wrapper.py", line 75, in __init__
self._reader = parsers.TextReader(src, **kwds)
File "pandas/_libs/parsers.pyx", line 544, in pandas._libs.parsers.TextReader.__cinit__
File "pandas/_libs/parsers.pyx", line 633, in pandas._libs.parsers.TextReader._get_header
File "pandas/_libs/parsers.pyx", line 847, in pandas._libs.parsers.TextReader._tokenize_rows
File "pandas/_libs/parsers.pyx", line 1952, in pandas._libs.parsers.raise_parser_error
UnicodeDecodeError: 'utf-8' codec can't decode byte 0x80 in position 1132: invalid start byte
バージョンアップ後はご覧の通りです
# 先ほど使用したtest.csvを圧縮したtest.tar.gzを使用します
>>> import pandas as pd
>>> df = pd.read_csv("./test.tar.gz")
>>> df.to_csv("./out_test_tar_gz.csv")
$ cat ./out_test_tar_gz.csv
hoge,fuga
1,2
3,4
DataFrameでダミーデータを生成する
1.5.0バージョンアップ時にfrom_dummies関数が実装されました
この関数によりダミーデータ生成時にDataFrameを使用することが可能になり
DataFrameでどの値をどう格納するか記述出来るようになりました
実装例は以下の通りです
>>> import pandas as pd
>>> df = pd.DataFrame({"hoge_1": [1, 0, 1], "hoge_2": [0, 1, 0],
... "fuga_1": [1, 0, 0], "fuga_2": [0, 1, 0],
... "fuga_3": [0, 0, 1]})
>>> pd.from_dummies(df, sep="_")
hoge fuga
0 1 1
1 2 2
2 1 3
カラム名や値に記号を使うことも可能です
>>> import pandas as pd
>>> df = pd.DataFrame({"太郎_○": [1, 0, 1], "太郎_×": [0, 1, 0],
... "花子_○": [1, 0, 0], "花子_×": [0, 1, 0],
... "花子_△": [0, 0, 1]})
>>> pd.from_dummies(df, sep="_")
太郎 花子
0 ○ ○
1 × ×
2 ○ △
注意点はvalueにboolean型以外の値以外の値が格納されたり欠損がある場合は
ダミーデータ生成に失敗します
boolean型以外の値が格納されている場合
>>> import pandas as pd
>>> df = pd.DataFrame({"hoge_1": [1, 0, 1], "hoge_2": [0, 2, 0],
... "fuga_1": [1, 0, 0], "fuga_2": [0, 1, 0],
... "fuga_3": [0, 0, 1]})
>>> pd.from_dummies(df, sep="_")
Traceback (most recent call last):
File "/usr/local/lib/python3.9/site-packages/pandas/core/reshape/encoding.py", line 450, in from_dummies
data_to_decode = data.astype("boolean", copy=False)
(中略)
File "/usr/local/lib/python3.9/site-packages/pandas/core/arrays/boolean.py", line 185, in coerce_to_array
raise TypeError("Need to pass bool-like values")
TypeError: Need to pass bool-like values
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/local/lib/python3.9/site-packages/pandas/core/reshape/encoding.py", line 452, in from_dummies
raise TypeError("Passed DataFrame contains non-dummy data")
TypeError: Passed DataFrame contains non-dummy data
欠損がある場合
>>> df = pd.DataFrame({"太郎_○": [1, 0, 1], "太郎_×": [0, 1, 0],
... "花子_○": [1, 0, 0], "花子_×": [0, 1, 0],
... })
>>> pd.from_dummies(df, sep="_")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/local/lib/python3.9/site-packages/pandas/core/reshape/encoding.py", line 507, in from_dummies
raise ValueError(
ValueError: Dummy DataFrame contains unassigned value(s); First instance in row: 2
参考