python OS path fileの勘所(書き書き中)

pythonはマルチOSドリブンの言語なのだが、os固有の癖に捕まっって膨大な時間を浪費することがある。

時間の浪費で済めばよいが、「プログラムのバグが解決できない」と絶望してプログラミングを挫折した人が世界に数百万人か数千万人はいると思う。

絶対pathで読み書きすれば問題が出にくいが、長ーい固定のpath名をコード中に記述するのはプログラムとしてはダサダサですよね。


「作業フォルダ」と「カレントフォルダ」と「ファイル所在地」を区別して、ファイルの読み書きを行う。

(./filename.csvこれはなんだ?)

Windowsのパス

Windows ではバックスラッシュ (\) でパスを区切るので、Python で Windows のパスを文字列として扱う場合は、raw 文字 r などを使ってバックスラッシュ (\) をエスケープしておきます。

file_path = r"C:\Users\blogcat\mycode.ipynb"


パスを正規化し、同じパスに対していつも同じパス文字列を返すには os.path.normpath() 関数を使います。

import os
path = '/User/user1/docs/./games/my_file.txt'
s = os.path.normpath(path)
print(s) # /User/user1/docs/games/my_file.txt

カレントディレクトリを取得する

import os
print(os.getcwd())

 os.path.join() に複数の文字列を渡すと、実行中の OS の区切り文字を使ってパスを組み立てます。

from os import path

# 使用中のOSに合わせてパスを組み立てる
p = path.join("C:", "Users", "blogcat", "mycode.ipynb")

 ファイル名やフォルダ名のリストを作って os.path.join() に渡すこともできます。その場合は引数の先頭にアスタリスク (*) を付けます。

name_list = ["C:", "Users", "blogcat", "mycode.ipynb"]

# 使用中のOSに合わせてパスを組み立てる
p = path.join(*name_list)

print(p)


こちら様から丸パクリ(あとで直します)

ファイルの読み込み

# テキストファイルを読み込み専用で開く
f = open("pynote.txt", mode = "r")

# ファイルの内容を表示
print(f.read())

# ファイルを閉じる
f.close()

ファイルへの書き込み

# テキストファイルを新規作成して書き込み専用で開く
f = open("pynote.txt", mode = "w")

# ファイルに書き込み
f.write("Python")

# ファイルを閉じる
f.close()

ファイルへの追記

# テキストファイルを追記モードで開く
f = open("pynote.txt", mode = "a")

# ファイルの末尾に追記
f.write("\nAnaconda")

# ファイルを閉じる
f.close()

# テキストファイルを読み込み専用で開く
f = open("pynote.txt", mode = "r")

# ファイルの内容を表示
print(f.read())

# ファイルを閉じる
f.close()

読み書き両方

 mode の + オプションは “w”, “r”, “a” と組合わせて、ファイルを読み書き両方できる状態で開きます。次のコードでは、mode = “a+” でファイルを開いて内容を表示した後で、末尾に “\nJupyter Notebook” を書き込みます。そして再度 pnyote.txt を開いて内容を確認しておきます。

# テキストファイルを読み書き両用モードで開く
f = open("pynote.txt", mode = "a+")

# テキストの内容を読み込んで表示
print(f.read())

# ファイルの末尾に追記
f.write("\nJupyter Notebook")

# ファイルを閉じる
f.close()

# テキストファイルを読み込み専用で開く
f = open("pynote.txt", mode = "r")

# ファイルの内容を表示
print(f.read())

# ファイルを閉じる
f.close()

日本語の読み書き

 ファイルに書き込む文字列に日本語などの非アスキー文字が含まれていると、環境によっては変換がうまくいかずに文字化けすることがあります。open() の encoding で変換方式 (エンコード) を指定しておいたほうが安全です。現在最も広く使われている変換方式は utf-8 です。

# テキストファイルを新規作成して書き込み専用で開く
f = open("pybook.txt", mode = "w", encoding = "utf-8")

# ファイルに書き込み
f.write("Python 数値計算入門")

# ファイルを閉じる
f.close()

 非アスキー文字を含むファイルを開く場合も、encoding で変換方式を指定しておきます。

# テキストファイルを読み込み専用で開く
f = open("pybook.txt", mode = "r", encoding = "utf-8")

# ファイルの内容を表示
print(f.read())

# ファイルを閉じる
f.close()

with構文

ファイルを自動的に閉じる

with open(ファイルパス, モード) as 変数名:
   コード

# ファイルへの書き込み
with open("pyfile.txt", "w") as f:
    f.write("Matplotlib")

# ファイルの読み込み
with open("pyfile.txt", "r") as f:
    print(f.read())


ファイルオブジェクトのメソッド一覧

F.read()

 F.read() はファイルの内容をすべて読み込んで文字列として返します。

# ファイルへの書き込み
with open("pyfile_1.txt", "w", encoding = "utf-8") as f:
    f.write("今日もPython、明日もPython")

# ファイルの読み込み
with open("pyfile_1.txt", "r", encoding = "utf-8") as f:
    my_str = f.read()
    print(my_str)

F.readline()

F.readline() はファイルを一行読み込んで文字列として返します。

# ファイルへの書き込み
with open("pyfile_2.txt", "w", encoding = "utf-8") as f:
    # 3行の文章を書き込む
    f.write("NumPyを使うと難しい数値計算ができます。\n\
    SciPyを使うと、もっと難しい数値計算ができます。")

# ファイルの最初の行を読み込む
with open("pyfile_2.txt", "r", encoding = "utf-8") as f:
    my_str = f.readline()
    print(my_str)

 引数に整数を渡すと、読み込む文字列のバイトサイズを指定できます。アルファベットは 1 文字 1 バイトなので、以下のコードで “NumPy” という 5 文字を取り出すことができます。

# ファイルから一行を読み込む
with open("pyfile_2.txt", "r", encoding = "utf-8") as f:
    my_str = f.readline(5)
    print(my_str)

F.readlines()

 F.readlines() はファイルをすべて読み込んで行ごとに分割してリストで返します。

# ファイルへの書き込み
with open("pyfile_3.txt", "w", encoding = "utf-8") as f:
    # 3行の文章を書き込む(オブジェクト指向の四大要素)
    f.write("カプセル化\n抽象化\nポリモーフィズム\n継承")

# ファイルの一行を読み込む
with open("pyfile_3.txt", "r", encoding = "utf-8") as f:
    my_list = f.readlines()
    print(my_list)

F.write()

 F.write() はファイルに指定した文字列を書き込みます。

# ファイルへの書き込み
with open("pyfile_4.txt", "w", encoding = "utf-8") as f:
    f.write("Pythonは日本語で「ニシキヘビ」です")

# ファイルの読み込み
with open("pyfile_4.txt", "r", encoding = "utf-8") as f:
    my_str = f.read()
    print(my_str)

F.writelines()

 F.writelines() は受け取ったイテラブルオブジェクト (リストやタプルなど) の要素を連結してファイルに書き込みます。

# 文字列のリストを用意
my_list = ["NumPy, ", "SciPy, ", "SymPy"]

# ファイルへの書き込み
with open("pyfile_5.txt", "w") as f:
    f.writelines(my_list)

# ファイルの読み込み
with open("pyfile_5.txt", "r") as f:
    my_str = f.read()
    print(my_str)

F.close()

 開いた状態のファイルオブジェクトに対して F.colse() を用いると、ファイルを閉じます。

# ファイルを新規作成して読み込み専用モードで開く
f = open("pyfile_6.txt", mode = "w")

# ファイルを閉じる
f.close()