「最初からいらない列は読まない」という発想を持つ
現場のExcelには、なぜか「空白の列」「名前が付いていない列」「スペースだけの列」が平気で混ざっています。
それをそのまま read_excel で読むと、Unnamed: 3 みたいな謎の列が大量にできて、後の処理が一気に見づらくなります。
usecols=lambda x: x.strip() != '' は、
「列名が空(もしくは空白だけ)の列は、そもそも読み込まないでくれ」というフィルターです。
つまり、「空白列を削除する」のではなく、「最初から読み込まない」という、とても賢い入口の工夫です。
基本形:usecols=lambda x: x.strip() != ” の挙動を理解する
最小コードとイメージ
import pandas as pd
df = pd.read_excel(
"report.xlsx",
usecols=lambda x: x.strip() != ''
)
print(df.columns)
print(df.head())
Pythonここで usecols に渡しているのは「関数」です。
pandas は、Excelの各列の「列名」を1つずつこの関数に渡し、
戻り値が True の列だけを読み込みます。
lambda x: x.strip() != '' は、
「列名 x から前後の空白を取り除いて、それが空文字でなければ True」
つまり、「実質的に名前が空じゃない列だけ読む」という条件になっています。
ここが一番大事なポイントです。
どんな列が「読み飛ばされる」のか
具体例でイメージする
例えば、Excelのヘッダー行がこんな感じだとします。
| A列 | B列 | C列 | D列 |
|---|---|---|---|
| 日付 | 売上 | 備考 |
C列はヘッダーが空欄です。
この状態で usecols=lambda x: x.strip() != '' を使うと、
C列は「列名が空なので False」と判定され、読み込まれません。
結果として、DataFrame の列は ["日付", "売上", "備考"] だけになります。
もしヘッダーがスペースだけ(" ")でも、strip() で空文字になり、同じく除外されます。
「見た目は何か書いてあるように見えるけど、実はスペースだけ」という地味に厄介な列も、きれいに落とせます。
lambda を使う usecols の仕組みを一度整理する
普段の usecols と何が違うのか
usecols には、ふつうはこういう指定をします。
usecols=["日付", "売上"]
usecols="A:C"
usecols=[0, 1, 3]
Pythonこれは「この列だけ読みたい」という“列の指定”です。
一方、usecols=lambda x: 条件 は、「列名に対するフィルター関数」です。
pandas は内部でこんなことをしています(イメージ):
- Excelのヘッダー行から列名を1つずつ取り出す
- その列名を
lambda x: ...に渡す - 戻り値が True の列だけ残す
つまり、「列名を見て、読むかどうかを決める関数」を渡している、というイメージを持ってください。
実務での使いどころ
パターン1:帳票系Excelで「謎の空白列」が混ざる
帳票出力されたExcelには、見た目を整えるための空白列がよく入っています。
| A列 | B列 | C列 | D列 | E列 |
|---|---|---|---|---|
| 日付 | 売上 | 原価 |
このとき、何も考えずに読むと Unnamed: 2, Unnamed: 4 のような列が増えます。
import pandas as pd
df = pd.read_excel(
"report.xlsx",
usecols=lambda x: x.strip() != ''
)
print(df.columns)
Pythonこれで、実質的に名前のない列は最初から消えた状態で読み込めます。
後から drop するより、入口で落としてしまう方がスッキリです。
パターン2:ヘッダー行に「スペースだけ」の列が紛れている
人間の目には「何もない列」と「スペースだけの列」は区別がつきませんが、
pandas にとっては " " は立派な文字列です。
x.strip() != '' としておくことで、
スペースだけの列名も「空」とみなして除外できます。
他の引数との組み合わせ方
header と一緒に使うときの注意
usecols=lambda x: ... で渡される x は、「ヘッダーとして認識された列名」です。
つまり、header の指定によって、どの行が列名として使われるかが変わると、x の中身も変わります。
例えば、こんな構造のExcelを考えます。
1行目: タイトル
2行目: 空白列を含むヘッダー
3行目以降: データ
この場合は、こう書きます。
import pandas as pd
df = pd.read_excel(
"report.xlsx",
header=1, # 2行目をヘッダーにする
usecols=lambda x: x.strip() != ''
)
print(df.columns)
Pythonheader=1 で「2行目を列名として使う」と決めた上で、
その列名に対して strip() != '' を適用している、という順番です。
dtype や parse_dates とも普通に併用できる
import pandas as pd
df = pd.read_excel(
"report.xlsx",
header=1,
usecols=lambda x: x.strip() != '',
parse_dates=["日付"],
dtype={"店舗": "string"}
)
print(df.dtypes)
Pythonusecols は「どの列を読むか」を決めるだけなので、
残った列に対しては、これまで通り parse_dates や dtype を使えます。
実践テンプレート
テンプレ1:空白列を落としてから、日付と金額で集計する
import pandas as pd
df = pd.read_excel(
"sales_report.xlsx",
header=1,
usecols=lambda x: x.strip() != ''
)
df["日付"] = pd.to_datetime(df["日付"], errors="coerce")
df["金額"] = pd.to_numeric(df["金額"], errors="coerce")
monthly = (
df.assign(month=df["日付"].dt.to_period("M"))
.groupby("month", as_index=False)["金額"].sum()
)
print(df.columns)
print(monthly)
Pythonここでは、
2行目をヘッダーにする
空白列を最初から読み込まない
日付と金額を整える
月次集計をする
という流れを一気に書いています。
テンプレ2:空白列を落としつつ、特定列だけ型を指定して読む
import pandas as pd
df = pd.read_excel(
"customer_report.xlsx",
header=0,
usecols=lambda x: x.strip() != '',
dtype={
"顧客ID": "string",
"郵便番号": "string"
}
)
print(df.columns)
print(df.dtypes)
Pythonこのテンプレートは、「帳票に紛れた空白列を落としつつ、ID系の列を文字列で読む」という、
かなり実務的なパターンです。
つまずきやすいポイントと注意点
列名が NaN の場合の扱い
ヘッダー行が完全に空欄だと、その列名は NaN になることがあります。x.strip() を呼ぶ前に、x が文字列かどうかを確認した方が安全な場合もあります。
より堅牢に書くなら、こうです。
usecols=lambda x: isinstance(x, str) and x.strip() != ''
Pythonこれなら、「列名が NaN(float)」の列も安全に除外できます。
本当に必要な列まで落としていないか確認する
usecols=lambda x: x.strip() != '' は、「名前が空の列」を全部落とします。
もし「名前は空だけど、実は意味のある列」がある場合は、その列も消えてしまいます。
最初は一度 usecols なしで読み込んで df.columns を確認し、
「本当に空白列だけを落としていいか?」を目で見て判断してから、このフィルターを導入するのがおすすめです。
小さな練習問題
練習1:空白列を含む report.xlsx を usecols なし/ありで読み比べる
条件は次の通りです。
df1 = pd.read_excel("report.xlsx", header=1)df2 = pd.read_excel("report.xlsx", header=1, usecols=lambda x: x.strip() != '')- それぞれの
df.columnsを表示して、違いを確認する
「どの列が消えたか」を意識してみてください。
練習2:sales_report.xlsx で空白列を落とし、日付と金額を整えて月次集計する
条件は次の通りです。
headerを適切に指定するusecols=lambda x: x.strip() != ''を使う- 日付を
to_datetime、金額をto_numericで整える - 月次合計を計算して表示する
最後に
usecols=lambda x: x.strip() != '' は、
「Excelの“見た目調整用の空白列”を、最初から相手にしない」ための小さなフィルターです。
これを入口に一行足すだけで、
謎の Unnamed: n 列が消える
後の処理で余計な列を気にしなくてよくなる
DataFrame の構造がシンプルになる
という、地味だけど効き目の大きい効果が得られます。
あなたの手元のExcelで、「この空白列、正直いらないんだよな」と思うものがあったら、
一度この usecols=lambda x: x.strip() != '' を試してみてください。
データが、少しだけあなたの味方になります。
