Pythonのpathlib入門!os.pathより読みやすいファイル・フォルダ操作を実例で解説
「os.path.join と os.path.basename と os.listdir と…どれがどれだっけ?」
Pythonでファイルを扱っていると、こんなふうに関数名を調べ直すこと、ありますよね😅
そんなときに覚えておきたいのが、標準ライブラリの pathlib(パスリブ)です。パスを「文字列」ではなく「Pathオブジェクト」として扱うことで、ファイル・フォルダ操作をぐっと読みやすく書けるようになります。
この記事はPythonの基本文法がわかる初心者〜初級者向けです。インストール不要(Python 3.4以降に標準搭載)なので、手元のPythonですぐ試せます。一緒に見ていきましょう!
pathlibとは?os.pathとの違い

イメージとしては、「パスに便利なメソッドが最初から付いている」のがpathlibです。
os.pathでは「文字列のパス」をいろいろな関数に渡して処理します。pathlibでは、Pathオブジェクト自身が .name や .exists() といった属性・メソッドを持っているので、「パス.やりたいこと」の形で書けます。
よく使う操作を対応表にまとめるとこんな感じです。
| やりたいこと | os / os.path | pathlib |
|---|---|---|
| パスを結合 | os.path.join(a, b) |
Path(a) / b |
| ファイル名を取得 | os.path.basename(p) |
p.name |
| 親フォルダを取得 | os.path.dirname(p) |
p.parent |
| 拡張子を取得 | os.path.splitext(p)[1] |
p.suffix |
| 存在チェック | os.path.exists(p) |
p.exists() |
| フォルダ作成 | os.makedirs(p, exist_ok=True) |
p.mkdir(parents=True, exist_ok=True) |
| フォルダの中身一覧 | os.listdir(p) |
p.iterdir() |
右の列のほうが「何をしているか」が読み取りやすいですよね。
基本:パスを作って、情報を取り出す
まずは一番よく使う基本操作です。/ 演算子でパスをつなげられるのがpathlibの大きな特徴です。
from pathlib import Path
# 「/」演算子でパスをつなげられる
p = Path("reports") / "2026" / "sales_09.csv"
print("パス全体:", p)
print("ファイル名:", p.name) # 拡張子つきの名前
print("名前だけ:", p.stem) # 拡張子を除いた名前
print("拡張子:", p.suffix) # .csv
print("親フォルダ:", p.parent) # reports/2026
print("存在する?:", p.exists()) # まだ作っていないので False
# 拡張子だけ差し替えたパスを作る(元の p は変わらない)
print("拡張子変更:", p.with_suffix(".xlsx"))

ポイントをまとめるとこんな感じです。
/でつなぐだけで、OSに合った区切り文字(Windowsなら\、Mac・Linuxなら/)になるname(拡張子つき)とstem(拡張子なし)の違いは要チェックwith_suffix()は新しいPathを返すだけで、実際のファイル名は変わらない
実行結果の区切り文字が \ になっているのはWindowsで実行したためです。Macで実行すると reports/2026/sales_09.csv のように表示されます。
実践:ダウンロードフォルダを拡張子ごとに自動整理する
基本がわかったところで、ちょっと実用的なスクリプトを作ってみましょう。フォルダ内のファイルを拡張子ごとのサブフォルダに振り分ける整理ツールです。
いきなり本物のダウンロードフォルダで試すと危ないので、練習用のフォルダとダミーファイルを自動で作るところから始めています。
from pathlib import Path
# 練習用のフォルダとファイルを用意する
downloads = Path("sample_downloads")
downloads.mkdir(exist_ok=True)
for name in ["memo.txt", "photo.jpg", "report.pdf", "data.csv", "icon.png", "todo.txt"]:
(downloads / name).write_text("dummy", encoding="utf-8")
# 拡張子ごとにサブフォルダへ振り分ける
for f in sorted(downloads.iterdir()):
if not f.is_file():
continue # フォルダはスキップ
ext = f.suffix.lstrip(".").lower() or "no_ext"
dest_dir = downloads / ext
dest_dir.mkdir(exist_ok=True) # 既にあってもエラーにしない
f.rename(dest_dir / f.name) # ファイルを移動
print(f"{f.name} → {ext}/")
# 振り分け後の .txt を再帰的に数える
txt_files = list(downloads.rglob("*.txt"))
print("txtファイル数:", len(txt_files))

ここが重要です👇
iterdir()でフォルダの中身を1つずつ取り出せる(sorted()で一覧を先に確定させてから移動しているので、途中で中身が変わっても安全)is_file()でフォルダを除外している(2回目以降の実行で作成済みのサブフォルダを動かさないため)mkdir(exist_ok=True)ならフォルダが既にあってもエラーにならないrename()でファイルを移動できるrglob("*.txt")はサブフォルダの中まで探してくれる(今いるフォルダだけならglob())
本番のフォルダで使うときは、downloads = Path.home() / "Downloads" のように書き換えればOKです。ただし移動先に同じ名前のファイルがあると、Windowsではエラーに、Mac・Linuxでは上書きになります。大事なファイルがあるフォルダで使う前に、必ずコピーしたフォルダで動作を確認しておきましょう。
ファイルの読み書きもPathだけで完結
ちょっとしたテキストの読み書きなら、open() を使わずにPathのメソッドだけで済ませられます。
from pathlib import Path
log = Path("output") / "log.txt"
log.parent.mkdir(parents=True, exist_ok=True) # 途中のフォルダもまとめて作成
log.write_text("1行目\n2行目\n", encoding="utf-8") # 書き込み(上書き)
text = log.read_text(encoding="utf-8") # 読み込み
print(text.splitlines())
print("絶対パス?:", log.resolve().is_absolute())
parents=Trueを付けると、途中のフォルダもまとめて作成してくれるwrite_text()は上書き。追記したいときは従来どおりopen("a")を使うencoding="utf-8"は必ず指定しておく(Windowsでは省略すると文字化けの原因になることがある)
大きなファイルを1行ずつ処理したいときは、with log.open(encoding="utf-8") as fp: のように Pathの open() メソッドも使えます。with 文との組み合わせ方は、組み込みの open() とまったく同じです。
初心者がつまずきやすいポイント
① Pathを文字列として使いたいとき
最近のライブラリはほとんどPathをそのまま受け取れますが、文字列と連結したいときは str(p) で変換します。"保存先: " + p はエラーになるので、f文字列(f"保存先: {p}")を使うのがおすすめです。
② 相対パスの基準は「実行したフォルダ」
Path("data.csv") は、スクリプトの場所ではなくターミナルで実行したときのカレントフォルダが基準です。スクリプトと同じフォルダを基準にしたいなら Path(__file__).parent / "data.csv" と書きましょう。
まとめ
pathlibを使うと、「パス.やりたいこと」の形で直感的にファイル操作が書けるようになります。今回のポイントはこの3つです。
- パスの結合は
/演算子 - 名前・拡張子・親フォルダは
name/suffix/parent - フォルダ作成は
mkdir(parents=True, exist_ok=True)が定番
既存のスクリプトの os.path を1か所ずつpathlibに置き換えてみるだけでも、「むずかしそう」が「できそう」に変わるはずです。ぜひ手を動かして試してみてください🚀
こちらも読まれています
📚 関連商品・おすすめ書籍
※本記事にはアフィリエイトリンクが含まれます。






