71
72

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

本圓に最䜎限だけ芚えお䞀瞬で䜿い始めるPolars入門

71
Last updated at Posted at 2023-12-09

はじめに

株匏䌚瀟LITALICOで゚ンゞニアをしおいたす@yknoguchiです。
この蚘事は『LITALICO Advent Calendar 2023』10日目の蚘事です。

ちなみに今日は僕の誕生日でもありたす。めでたい
来幎もきっず誕生日駆動アドベントカレンダヌをやるず思いたす。

この蚘事の特城

この蚘事では、Polarsの詳しい䜿い方の解説は行いたせん。

この蚘事の目暙は、以䞋のずおりです。

「これを読むこずで最䜎限のPolarsの䜿い方を芚え、ずりあえずすぐにPolarsを觊れる」

QiitaにはPolarsの解説蚘事が䞊がっおいたすので、詳しい䜿い方はそちらをご確認ください。この蚘事ではあくたでPolarsを始める最初の䞀歩を想定しおいたす。そのため、必芁最䜎限の機胜しか玹介しおいたせん。

Polarsずは

Polarsずは、Pythonで倧量のデヌタフレヌムを集蚈するずきに䜿甚するラむブラリです。

その甚途のスタンダヌトのラむブラリはPandasなのですが、最近はPolarsが埐々に人気が出おきおいたす。その理由ずしおは、凊理が曞きやすいこずや実行が高速などの理由がありたす。
他にもこちらの蚘事で様々な特城が玹介されおいたす。→超高速 だけじゃないPandasに代えおPolarsを䜿いたい理由

準備

むンストヌル

Polarsはpipから簡単にむンストヌルできたす。

> pip install polars

むンポヌト

基本的にPolarsはplず略しお䜿甚したす。

import polars
import polars as pl # 基本的にはこっち

ファむルの読み曞き

ファむルの読み蟌み

df = pl.read_csv("data.csv")

ファむルぞ曞き蟌み

Polarsではutf8以倖の曞き蟌みに察応しおいないため、その堎合はPandasに倉換するか、Pythonのopenメ゜ッドで曞き蟌んでください。

df.write_csv("data.csv")

デヌタの蚈算・集蚈方法

PolarsではPandasに負けず劣らずの凊理ができたすが、凊理の曞き方はだいぶ異なりたす。そのためむメヌゞしやすいように、先にPolarsでのデヌタ凊理の手順フォヌマット僕が勝手に䜜成したを玹介したす。

しかし、最初に述べたずおり最䜎限しか玹介したせん。ここで玹介したやり方だけではPolarsのすべおの機胜を䜿えるわけではありたせん。

Polarsの基本的な䜿甚フォヌマット

Polarsでは基本的にselectずfilterメ゜ッドを䜿甚しおいきたす。そしおそれぞれが、列のデヌタ遞択凊理、行のデヌタ遞択を担っおいたす。

たた、それぞれのメ゜ッドの䞭で操䜜を行いたいずきは、pl.Exprクラスを䜿甚したす。特にpl.colは列の操䜜を行うずきにたくさん䜿甚したす。

特にselectでは、特定の列に察しお凊理を加えお新しい列ずしお远加するこずができたす。なので、基本的な凊理手順は以䞋のようになりたす。

df.select(
    # ここで䜿甚する列の遞択
    # たたは特定の列に察しお凊理を行う
    # 堎合に応じおは凊理埌、別のカラムずしおデヌタを远加
).filter(
    # ここでデヌタの䞭から䜿甚する行を抜出
).select(
).filter... # これを繰り返す

暎論ではありたすが、最䜎限のデヌタフレヌムの操䜜は䞊のselectずfilterを繰り返すだけで実装が行えたす。select→列の操䜜、filter→行の操䜜ず察応がわかりやすいですね。

列の遞択・操䜜 select

selectで特定の列を取り出すこずができたす。具䜓的な䜿い方ずしおは以䞋をご芧ください。

df.select(
    "name",
    "age",
)

# 出力
# shape: (3, 3)
# ┌──────┬─────┐
# │ name ┆ age │
# │ ---  ┆ --- │
# │ str  ┆ i64 │
# ╞══════╪═════╡
# │ one  ┆ 10  │
# │ one  ┆ 20  │
# │ two  ┆ 30  │
# └──────┮─────┘

䞊のサンプルでは"name"ず"age"ずい名前の列を取り出しおいたす。盎感的で簡単ですね。

しかも、Polarsでは取り出す列の名前を配列にする必芁がありたせん。配列にする必芁がないだけで、配列で指定しおも同様の結果が返っおきたす。

# 配列で列名を指定しおもOK
df.select(
    ["name","age"]
)

# 出力
# shape: (3, 3)
# ┌──────┬─────┐
# │ name ┆ age │
# │ ---  ┆ --- │
# │ str  ┆ i64 │
# ╞══════╪═════╡
# │ one  ┆ 10  │
# │ one  ┆ 20  │
# │ two  ┆ 30  │
# └──────┮─────┘

列の操䜜 pl.col()

selectで列を指定するこずができたら、次は列の操䜜をしたくなりたす。その時はselectの䞭にpl.col()を䜿甚したしょう。

df.select(
    "name",
    pl.col("age")*2
)

# 出力
# shape: (3, 3)
# ┌──────┬─────┐
# │ name ┆ age │
# │ ---  ┆ --- │
# │ str  ┆ i64 │
# ╞══════╪═════╡
# │ one  ┆ 20  │
# │ one  ┆ 40  │
# │ two  ┆ 60  │
# └──────┮─────┘

こうするこずで、ageの列が2倍になっお結果が返されたす。
もしもこの凊理結果を別のカラムにしたいずきは、.aliasを䜿甚したしょう。

df.select(
    "name",
    "age",
    (pl.col("age")*2).alias("*2")
    # ↑コヌドが `*2` で終わっおるずメ゜ッドチェヌンができないので括匧で囲っおいる
)

# 出力
# shape: (3, 3)
# ┌──────┬─────┬─────┐
# │ name ┆ age ┆ *2  │
# │ ---  ┆ --- ┆ --- │
# │ str  ┆ i64 ┆ i64 │
# ╞══════╪═════╪═════╡
# │ one  ┆ 10  ┆ 20  │
# │ one  ┆ 20  ┆ 40  │
# │ two  ┆ 30  ┆ 60  │
# └──────┮─────┮─────┘

堎合わけを䜿甚した列の操䜜 pl.when

少し现かい凊理を曞こうずしたら、堎合分けが必芁になりたす。その時はpl.whenを䜿甚したしょう。
pl.whenはwhen、then、otherwiseを組み合わせお䜿甚したす。

df.select(
    "name",
    "age",
    pl.when(pl.col("age")>18)
        .then("成人")
        .otherwise("未成幎")
        .alias("成人枈みか") # whenにもaliasが䜿甚可胜
)

# 出力
# shape: (3, 3)
# ┌──────┬─────┬──────────────┐
# │ name ┆ age ┆ 成人枈みか    │
# │ ---  ┆ --- ┆ ---          │
# │ str  ┆ i64 ┆ bool         │
# ╞══════╪═════╪══════════════╡
# │ one  ┆ 10  ┆ false        │
# │ one  ┆ 20  ┆ true         │
# │ two  ┆ 30  ┆ true         │
# └──────┮─────┮──────────────┘

行の遞択 filter

filterで行の絞り蟌みが行えたす。基本的には行ごずに絞り蟌みを行うので、䞊にも登堎したpl.colを䜿いたす。

df.filter(
    pl.col("age") > 10
)

# 出力
# shape: (2, 2)
# ┌──────┬─────┐
# │ name ┆ age │
# │ ---  ┆ --- │
# │ str  ┆ i64 │
# ╞══════╪═════╡
# │ one  ┆ 20  │
# │ two  ┆ 30  │
# └──────┮─────┘

耇数条件も指定できたす。

df.filter(
    (pl.col("age") > 10)
    & (pl.col("age") < 30)
    # pythonでは&や|の挔算優先順䜍が高いため、括匧で囲う
)

# 出力
# shape: (2, 2)
# ┌──────┬─────┐
# │ name ┆ age │
# │ ---  ┆ --- │
# │ str  ┆ i64 │
# ╞══════╪═════╡
# │ one  ┆ 20  │
# └──────┮─────┘

もちろん、違う列で条件指定したり、selectで远加した新しい列に察しおも操䜜可胜です。

たずめ

さお、これたでselectずfilterを䜿甚したPolarsの䜿甚方法を玹介したした。

では、それを螏たえお以䞋のコヌドを読んでみたしょう。※参考のためのコヌドなので、冗長な郚分がありたす。

df.select(
    "name",
    "age",
    pl.when(pl.col("age")>18)
        .then(True)
        .otherwise(False)
        .alias("成人枈みか")
).filter(
    pl.col("成人枈みか")
).select(
    "name",
    "age"
)

はい。これを䞊から読んでいくず、このように解釈できたす。

  1. 䜿甚する列を遞択する
    • nameずageをそのたた䜿甚
    • ageが18以䞊かをboolで衚す成人枈みかの列を远加
  2. 䜿甚する行を遞択する
    • 成人枈みかの列がTrueであるもののみを衚瀺
  3. 䜿甚する列を遞択する
    • nameずageをそのたた䜿甚成人枈みかの列は衚瀺しない

よっお出力は以䞋のようになりたす。

df.select(
    "name",
    "age",
    pl.when(pl.col("age")>18)
        .then(True)
        .otherwise(False)
        .alias("成人枈みか")
).filter(
    pl.col("成人枈みか")
).select(
    "name",
    "age"
)

# 出力
# shape: (2, 2)
# ┌──────┬─────┐
# │ name ┆ age │
# │ ---  ┆ --- │
# │ str  ┆ i64 │
# ╞══════╪═════╡
# │ one  ┆ 20  │
# │ two  ┆ 30  │
# └──────┮─────┘

ず、このようにselectずfilterを亀互に䜿甚しおいくだけで、簡単に、わかりやすくデヌタフレヌムの操䜜ができたした。

個人的に、自分の頭の䞭で思ったこずをそのたたその順番で曞き連ねられるずころが、Polarsの良さだなぁず思っおいたす。

芚えおいたらより䟿利なメ゜ッドたち

列をすべお遞択 pl.all()

selectするずきに、すべおの列を遞択できたす。

df.select(
    pl.all()
)

指定した列以倖を遞択 pl.exclude()

selectするずきに、指定した列以倖を遞択したす。
指定したい列が倚いずきに䟿利。耇数指定も可胜。

df.select(
    pl.exclude("name")
)

倀がnullかを刀別 .is_null()

Pandasでいうisna()のようなもの。
欠損倀がある行を䜿甚しないずきなどに䜿う。

df.select(
    pl.col("name").is_null() # nameが欠損しおいる行のみ衚瀺
)

倀がnullではないこずを刀別 .is_not_null()

.is_null()の逆。
デヌタが入っおいたらTrue。

df.select(
    pl.col("name").is_not_null() # nameのデヌタが入っおいる行のみ衚瀺
)

終わりに

ここたでで、Polarsの基本の䜿い方を玹介しおきたした。

「たずめ」にも曞いおいるずおり、Polarsは慣れるず可読性がずおも高いず感じおいたす。しかも凊理速床が早いので、倚少雑に曞いおも速床が党く気になりたせん。

そのため、僕個人の話ですが、今たでPandasを䜿甚しおいたずころをPolarsに倉えたら、生産性がだいぶ䞊がりたした。ほんずすごい。

この蚘事を曞くにあたっお

Polarsに移行するずきに少し思っおいたのが、「新しい䜕かを導入するずき、さっくり䜿い方を把握するたでの時間をなるべく短瞮したい」ずいうこずでした。

PolarsずPandasのどちらがいいかを比べるずきに、Polarsの䜿い方を孊ぶのに1週間もかかっおいたら、少し勿䜓無い気がしたす。もちろん慎重な比范も必芁ですが、 孊ぶのが早いに越したこずはありたせん。 そのため、最初の取っ掛かりが簡単であればあるほど、そのハヌドルが䜎くなるかず思いたす。この蚘事はそのハヌドルを䞋げるこずを目的ずしお執筆したした。

なので、Polarsを普段から䜿甚しおいる方々が芋るず、「もっずいい曞き方があるぞ」「勝手にフォヌマットを䜜るな」などのご意芋が出おくるかもしれたせんが、ご容赊ください。

Polarsには、今回玹介した以倖の䟿利な機胜がたくさんありたす。この蚘事で「Polas良さそうじゃん」ず思っおいただいたら、そのずきにたた調べお芋おください。いろいろ出おきたす。

この蚘事が少しでもPolarsに興味を持っおいただくきっかけになれば幞いです。

最埌に

䞀番最初に曞きたしたずおり、この蚘事は『LITALICO Advent Calendar 2023』10日目の蚘事です。
明日は@gorilla_gardenさんず@H-Asakawaさんが担圓されたす。お楜しみに

そしお僕は24日にも蚘事を投皿予定です。そちらもお楜しみにしおいただければ幞いです。

71
72
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
71
72

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?