【Python基礎】ファイルのソートで順番がおかしい時に確認すること、試すこと(ゼロパディング、natsort)

  • URLをコピーしました!
目次

ファイルのソート

前回、ファイルかどうかの判定(os.path.isfile)、フォルダかどうかの判定(os.path.isdir)、ファイル・フォルダの存在の確認(os.path.exists)を解説しました。

今回はファイルのソートに関して解説していきます。

ファイル名やフォルダ名を取得するするのに、「os.listdir(フォルダ)」をよく使うのですが、この時に困るのがファイル名が並んでくれないことです。

例えば「test1」というフォルダの中に「1_text.txt」、「2_text.txt」、「3_text.txt」…という感じで連番のファイルを作成してみました。

これを「os.listdir(フォルダ)」を使って順番に表示してみます。

import os

dirname = 'test1'

for file in os.listdir(dirname):
    print(file)

実行結果
9_text.txt
8_text.txt
11_text.txt
10_text.txt
3_text.txt
2_text.txt
4_text.txt
5_text.txt
1_text.txt
12_text.txt
13_text.txt
7_text.txt
6_text.txt
15_text.txt
14_text.txt

結果としては全くランダムにファイルが表示されました。

今回はこれをどうやって並べるかというお話です。

ゼロパディングしてsorted

まず自分でファイル名を出力しているのなら、ゼロパディングしたファイル名を出力し、「os.listdir(フォルダ)」でファイル名(フォルダ名)を取得する際に「sorted」でソートする方法が考えられます。

「test2」フォルダに「01_text.txt」、「02_text.txt」、「03_text.txt」…というようにゼロパディングしたファイル名を用意しました。

これで試してみましょう。

import os

dirname = 'test2'

for file in sorted(os.listdir(dirname)):
    print(file)

実行結果
01_text.txt
02_text.txt
03_text.txt
04_text.txt
05_text.txt
06_text.txt
07_text.txt
08_text.txt
09_text.txt
10_text.txt
11_text.txt
12_text.txt
13_text.txt
14_text.txt
15_text.txt

確かに「01_text.txt」から「15_text.txt」まで順に出力されました。

ただこの方法で1点注意することがあります。

あくまでも「ゼロパディングしたファイル」なら「sorted」で順に並べることができるのですが、ゼロパディングしていないと並び順は先頭の数字の順になります。

先ほどの「test1」フォルダを使って試してみます。

import os

dirname = 'test1'

for file in sorted(os.listdir(dirname)):
    print(file)

実行結果
10_text.txt
11_text.txt
12_text.txt
13_text.txt
14_text.txt
15_text.txt
1_text.txt
2_text.txt
3_text.txt
4_text.txt
5_text.txt
6_text.txt
7_text.txt
8_text.txt
9_text.txt

こんな感じで先頭の数字が「1」のものが先に表示されるという結果になりました。

自分で作ったプログラムならゼロパディングして出力することは可能でしょう。

もしくはファイル名をゼロパディングするプログラムを書いて修正するということもありだと思います。

ちなみにゼロパディングに関してはこちらの記事で解説していますので、よかったらどうぞ。

natsort

ただ実はもう一つ「natsort」というライブラリを使うと、ゼロパディングしなくても並べることができます。

ということでまずはライブラリのインストール。

pip install natsort

インストールが完了したら、早速試していきましょう。

インポートは「from natsort import natsorted」で、「natsorted(ソートしたいリスト)」で使用することができます。

ということで先ほどの「test1」フォルダで試してみるとこんな感じです。

import os
from natsort import natsorted

dirname = 'test1'

for file in natsorted(os.listdir(dirname)):
    print(file)

実行結果
1_text.txt
2_text.txt
3_text.txt
4_text.txt
5_text.txt
6_text.txt
7_text.txt
8_text.txt
9_text.txt
10_text.txt
11_text.txt
12_text.txt
13_text.txt
14_text.txt
15_text.txt

ファイル名の数字が二桁になってもちゃんと認識して、1から順に並べることができました。

ちなみにゼロパディングしてあっても問題なく「natsort」 を使うことができます。

import os
from natsort import natsorted

dirname = 'test2'

for file in natsorted(os.listdir(dirname)):
    print(file)

実行結果
01_text.txt
02_text.txt
03_text.txt
04_text.txt
05_text.txt
06_text.txt
07_text.txt
08_text.txt
09_text.txt
10_text.txt
11_text.txt
12_text.txt
13_text.txt
14_text.txt
15_text.txt

ということで「natsort」を積極的に使っていく方が手間も減っていい気がします。

次回はnumpyの合計(sum)や平均値(mean)、標準偏差(std)を計算する際の方向に関して解説します。

ではでは今回はこんな感じで。

よかったらシェアしてね!
  • URLをコピーしました!

コメント

コメントする

目次