この記事ではPythonの文字列置換を、replace(回数指定・複数置換・交換・改行対応)、translate(複数文字の一括変換)、re.sub/subn(正規表現・件数取得)、スライス(位置指定)で整理。置換できない原因やデータ整形の悩みを解決できます。
目次
- 1 Pythonで文字列を置換する方法の全体像(replace・translate・正規表現)
- 2 replaceメソッドで固定文字列を置き換える
- 2.1 replaceの基本構文と特徴(元の文字列は変更されない)
- 2.2 1文字・単語・フレーズを置換する基本例
- 2.3 大文字・小文字の違いに注意して置換する
- 2.4 置換回数の上限を指定して置換する(count引数)
- 2.5 変数を使って置換条件を切り替える
- 2.6 空文字に置き換えて削除する(文字の除去)
- 2.7 複数パターンを置換する実装(連続replace/辞書で置換など)
- 2.8 2つの文字列を安全に入れ替える(スワップ)
- 2.9 改行コードを置換して整形する(\n・\r\nなど)
- 2.10 リスト(配列)内の文字列をまとめて置換する
- 2.11 replaceが期待どおりに動かないときの確認ポイント
- 3 translateメソッドで複数の文字を一括変換する
- 4 正規表現で柔軟に置換する(re.sub/re.subn)
- 5 スライスで位置を指定して差し替える・挿入する
- 6 タブ文字をスペースに展開して整形する(expandtabs)
- 7 目的別:最適な置換手法の選び方
- 8 まとめ:Pythonの文字列置換を使いこなす要点整理
Pythonで文字列を置換する方法の全体像(replace・translate・正規表現)

Pythonの文字列置換は、やりたいことに対して適切な手段を選ぶのが最重要です。なぜなら「一部の文字を固定で置き換えたい」のか、「複数の文字を一括で変換したい」のか、「パターンに合う箇所を柔軟に置換したい」のかで、最適なアプローチが変わるためです。
本記事で扱う「python 文字列 置換」の主要な選択肢は次の3つです。
- replace:固定文字列の置換に強い(直感的で読みやすい)
- translate:文字単位の一括変換に強い(大量変換で効率的)
- 正規表現(re.sub):パターンマッチを伴う置換に強い(柔軟だが複雑になりやすい)
この章では、それぞれが活躍する場面と、使い分けの結論を先に整理します。以降の章で個別手法を詳しく掘り下げていく前提として、全体像を押さえておきましょう。
置換が必要になる典型シーン(前処理・クレンジング・入力整形など)
文字列置換は、アプリ開発からデータ分析まで幅広く登場します。特に「外部から入ってくるテキスト」を扱うほど、置換処理は避けて通れません。典型的なシーンを目的別に整理すると、次のようになります。
- 前処理(データ分析・機械学習の準備)
- 表記ゆれの統一(例:全角/半角の混在、記号の統一)
- 不要な文字の除去(例:カンマ、引用符、余計なスペース)
- ログやテキストから特定表現だけ置き換え・マスキング
- クレンジング(入力データの整合性を上げる)
- 改行やタブの混入を整形して保存・表示しやすくする
- ユーザー入力の揺れを吸収(例:「ー」「−」「―」などのダッシュ類)
- 複数候補を同じ表現へ統一(例:「OK」「Ok」「okay」→「OK」)
- 入力整形(アプリ・業務システムでのバリデーション前)
- 郵便番号・電話番号などの区切り文字を統一(例:「-」の有無を揃える)
- コピペで混入しがちな不可視文字(連続スペース等)への対処
- テンプレート文字列の一部差し替え(固定文字列の置換)
ポイントは、置換対象が「固定の文字列」なのか、「文字単位で大量に変えたい」なのか、「条件に合うパターン」なのかを最初に見極めることです。これができると、実装が短くなり、バグも減り、性能面の無駄も抑えられます。
この記事で扱う置換手段と使い分けの結論
python 文字列 置換の手段は複数ありますが、迷ったときは次の結論で判断すると失敗しにくいです。
- 固定文字列をそのまま置き換えるなら replace
- 例:特定の単語・フレーズを別の文字列に変更したい
- メリット:読みやすく、意図が明確。保守しやすい
- 「文字」単位の大量変換・一括変換なら translate
- 例:記号をまとめて別の記号へ、特定の文字群をまとめて削除・変換したい
- メリット:変換ルールが表にまとまり、処理効率も良い
- 条件に一致した箇所を置換するなら 正規表現(re.sub)
- 例:数字列・複数表記候補・可変長パターンなどを対象にした置換
- メリット:柔軟で表現力が高い。一方で複雑化しやすいので必要なときに限定する
まとめると、まずはreplaceで済むかを検討し、次に文字単位の一括変換ならtranslate、最後にパターンが絡むなら正規表現という順で選ぶのが合理的です。この順序で考えることで、過剰に難しい実装(たとえば「固定置換なのに正規表現を使う」など)を避けられます。
replaceメソッドで固定文字列を置き換える

Pythonで文字列を置換したいとき、最初に覚えるべき定番がstr.replace()です。指定した「固定の文字列(部分文字列)」を、別の文字列へ一括で置き換えられます。正規表現のようなパターン指定はできませんが、その分シンプルで読みやすく、日常的なテキスト整形や軽いクレンジングに向きます。ここでは「python 文字列 置換」の基本として、replaceメソッドの使い方をケース別に整理します。
replaceの基本構文と特徴(元の文字列は変更されない)
replaceの基本構文は次のとおりです。
新しい文字列 = 元の文字列.replace(置換対象, 置換後[, count])重要な特徴は、元の文字列(str)は変更されず、置換後の新しい文字列が返ることです。Pythonの文字列はイミュータブル(不変)なので、結果を使うには変数へ代入するのが基本になります。
s = "Hello World"
t = s.replace("World", "Python")
print(s) # Hello World(元はそのまま)
print(t) # Hello Python(新しい文字列)1文字・単語・フレーズを置換する基本例
replaceは「1文字だけ」でも「単語」でも「複数語のフレーズ」でも、固定文字列として一致した部分を置換します。
# 1文字の置換
text = "a-b-c"
print(text.replace("-", "/")) # a/b/c
# 単語の置換
text = "I like coffee"
print(text.replace("coffee", "tea")) # I like tea
# フレーズの置換(スペース含む)
text = "Please log in now"
print(text.replace("log in", "sign in")) # Please sign in nowなお、置換対象が見つからない場合はエラーにはならず、元と同じ内容の文字列が返ります。
大文字・小文字の違いに注意して置換する
replaceは大文字・小文字を区別します。たとえば"Python"を"PYTHON"で探しても一致しません。
text = "Python is fun"
print(text.replace("python", "Java")) # Python is fun(置換されない)大文字・小文字の揺れがあるデータを扱う場合は、まず同じルールに揃えてから置換するのがコツです(例:全て小文字化してから置換し、必要なら表示用に整形)。
text = "Python, PYTHON, python"
normalized = text.lower()
result = normalized.replace("python", "ruby")
print(result) # ruby, ruby, rubyこの方法は「表記揺れをまとめる」という点で便利ですが、元の大文字情報は失われます。要件に合わせて選びましょう。
置換回数の上限を指定して置換する(count引数)
3つ目の引数countを指定すると、左から何回まで置換するか制限できます。先頭だけ置換したい、ログの最初の区切りだけ変えたい、といった場面で役立ちます。
text = "2025-12-26-10-30"
print(text.replace("-", "/", 1)) # 2025/12-26-10-30countを省略すると、見つかった箇所はすべて置換されます。
変数を使って置換条件を切り替える
置換対象や置換後の文字列を変数にすると、条件に応じて処理を切り替えやすくなります。例えば入力種別(ユーザー入力、ファイル名、URLなど)で置換ルールを変える場合、ルールを変数化しておくと保守性が上がります。
text = "price: 1,200円"
target = ","
replacement = "" # カンマを消す
result = text.replace(target, replacement)
print(result) # price: 1200円さらに条件分岐と組み合わせれば、同じ置換処理の枠組みで「どの文字を何に変えるか」だけを差し替えられます。
空文字に置き換えて削除する(文字の除去)
replaceは「削除」にも使えます。消したい部分を空文字""へ置換すれば、その文字列を取り除けます。
text = "user@example.com"
print(text.replace("@", "")) # userexample.com(@を削除)不要な記号の除去や、特定のラベル(例:"[DEBUG]")を消すといった前処理に便利です。ただし固定文字列の削除なので、揺れがある場合は対象が一致しているか事前に確認しましょう。
複数パターンを置換する実装(連続replace/辞書で置換など)
複数の固定文字列を置換したい場合、最も単純なのはreplaceを連続で呼ぶ方法です。
text = "A,B;C"
text = text.replace(",", "\t").replace(";", "\t")
print(text) # A B C置換ルールが増えるなら、辞書でルールをまとめてループする形にすると見通しが良くなります。
text = "https://example.com/path"
rules = {
"https://": "",
"http://": "",
"/": "_",
}
for src, dst in rules.items():
text = text.replace(src, dst)
print(text) # example.com_path注意点として、置換順序によって結果が変わることがあります(例:ある置換が別の置換対象を新たに作るケース)。ルールが依存しそうなら、順序を明示的に管理してください。
2つの文字列を安全に入れ替える(スワップ)
「AをBに、BをAに」入れ替えたいとき、単純に連続replaceすると途中で情報が消えることがあります。
# これは失敗例になりやすい
text = "A and B"
text = text.replace("A", "B").replace("B", "A")
print(text) # A and A(意図と違う可能性)安全にスワップするには、一時的に登場しない文字列(プレースホルダ)を挟みます。
text = "A and B"
placeholder = "__TEMP__"
text = text.replace("A", placeholder)
text = text.replace("B", "A")
text = text.replace(placeholder, "B")
print(text) # B and Aプレースホルダは、元の文字列に含まれないことが確実な値を選びましょう。
改行コードを置換して整形する(\n・\r\nなど)
OSや入力元によって改行コードが異なることがあります(例:\n、\r\n)。テキストを整形・統一したい場合はreplaceで揃えられます。
text = "line1\r\nline2\r\nline3"
normalized = text.replace("\r\n", "\n")
print(normalized)また、表示やCSV出力の都合で改行をスペースに置換する、といった整形にも使えます。
text = "line1\nline2\nline3"
single_line = text.replace("\n", " ")
print(single_line) # line1 line2 line3リスト(配列)内の文字列をまとめて置換する
複数の文字列データ(リスト)に同じ置換を適用したい場合は、リスト内包表記が簡潔です。各要素にreplaceを適用し、新しいリストを作ります。
items = ["apple,banana", "cat,dog", "red,blue"]
result = [s.replace(",", " / ") for s in items]
print(result) # ['apple / banana', 'cat / dog', 'red / blue']元のリスト要素(文字列)自体が書き換わるわけではないため、置換後のリストを変数で受け取るのがポイントです。
replaceが期待どおりに動かないときの確認ポイント
pythonの文字列置換で「replaceしたのに変わらない」「一部だけ変になる」と感じたら、次の点を順に確認すると切り分けしやすくなります。
- 置換対象が本当に含まれているか:全角半角、見えない空白、タブ(
\t)などが混ざっていないか確認します。 - 大文字・小文字が一致しているか:
replaceはケースセンシティブです。 - 置換結果を代入しているか:戻り値を受け取らないと、元の変数の中身は変わりません。
- 置換の順序で結果が変わっていないか:複数replaceを連続する場合、順序依存が起きていないか見直します。
- count指定が意図どおりか:
countを指定していると、途中から置換されないのは仕様です。
特に「置換結果を代入していない」ケースは初学者がつまずきやすいポイントです。まずはprint()で対象文字列そのものを表示し、置換前後を比較して確認すると確実です。
translateメソッドで複数の文字を一括変換する

Pythonで「文字列 置換」を行う場面では、単語やフレーズではなく「特定の文字を別の文字へ一括で置き換えたい」ケースがよくあります。たとえば、記号を統一したり、全角・半角の一部だけを機械的に揃えたり、不要な文字をまとめて削除したいときです。こうした「文字単位の一括変換」に強いのが、str.translate()(translateメソッド)です。
translateの基本的な使い方(変換テーブルの作成)
translateは、事前に「どの文字を何に変換するか」をまとめた変換テーブル(マッピング)を作り、そのテーブルに従って文字列全体を一度に変換します。変換テーブルは通常、str.maketrans()で作成します。
# 変換テーブルを作って translate する基本形
text = "abc-123"
table = str.maketrans({
"a": "A",
"-": "_",
})
result = text.translate(table)
print(result) # Abc_123
ポイントは次のとおりです。
translateは「文字ごとの変換」を対象にする(部分文字列の置換ではなく、1文字単位)。- 変換テーブルは「変換元1文字 → 変換先1文字(または削除)」の対応をまとめて持てる。
- 元の文字列(
text)自体は変更されず、変換後の新しい文字列が返る。
辞書形式以外にも、str.maketrans(from, to)のように2つの文字列で対応関係を作ることもできます。
# "abc" を "ABC" に対応づける(同じ長さである必要がある)
table = str.maketrans("abc", "ABC")
print("a-b-c".translate(table)) # A-B-C
1文字→1文字の高速な置換に向くケース
translateは、複数の「1文字→1文字」置換をまとめて適用するのが得意です。たとえば次のように、区切り文字や記号の揺れを一括で統一する用途に向きます。
# 記号をまとめて統一する例
text = "2025/12/26 (Fri) - ID:001"
table = str.maketrans({
"/": "-",
"(": "[",
")": "]",
":": ":", # コロンだけ全角にするなど
})
print(text.translate(table))
# 2025-12-26 [Fri] - ID:001
このように、置換対象が「固定の文字」かつ「複数種類ある」場合、python 文字列 置換をtranslateでまとめて処理すると、コードが簡潔になりやすく、繰り返しの置換にも適用しやすいのがメリットです。
文字の入れ替え(スワップ)をtranslateで行う
2種類の文字を入れ替える(スワップ)も、translateの得意分野です。置換を順番に書くと、途中で変換結果が次の置換に影響してしまうことがありますが、translateは変換テーブルに基づき文字単位で処理するため、意図通りに入れ替えやすくなります。
# "A" と "B" を入れ替える(スワップ)
text = "AABBAB"
table = str.maketrans({
"A": "B",
"B": "A",
})
print(text.translate(table)) # BBAABA
同様に、<と>の入れ替え、+/-の記号の入れ替えなど、「1文字同士のスワップ」はtranslateが読みやすく安全です。
削除(変換先をNone相当にする)などの応用
translateは「置換」だけでなく「削除」もできます。削除は、変換テーブルで対象文字を「削除指定」にすることで実現します。実務では、不要な記号や制御的な文字(例:タブ、特定の区切り記号)を取り除く前処理で役立ちます。
# 指定した文字を削除する(例:ハイフンとスペースを除去)
text = "TEL: 03-1234-5678"
table = str.maketrans({
"-": None,
" ": None,
})
print(text.translate(table)) # TEL:0312345678
また、削除と置換を同時に行うことも可能です。「この文字は消す」「この文字は別記号に揃える」といった複合ルールを、1回のtranslateにまとめられます。
# 削除と置換を同時に適用する例
text = "A B-C/D"
table = str.maketrans({
" ": None, # スペースは削除
"-": "_", # ハイフンはアンダースコアへ
"/": "_", # スラッシュもアンダースコアへ
})
print(text.translate(table)) # AB_C_D
このようにtranslateは、Pythonで文字列置換を行う際に「文字単位で複数ルールを一括適用したい」場合に非常に相性が良い手段です。
正規表現で柔軟に置換する(re.sub/re.subn)

「特定の単語を置き換える」だけならreplaceで十分ですが、実務のテキスト処理では「表記ゆれをまとめたい」「数字や日付などのパターン部分だけを差し替えたい」「条件によって置換結果を変えたい」といった要件が頻出します。こうした場面で活躍するのが、Pythonの正規表現を使った文字列置換です。
Pythonでは標準ライブラリreのre.sub(およびre.subn)を使うことで、パターンマッチに基づく柔軟な「python 文字列 置換」が実現できます。
re.subの基本構文(パターン・置換文字列・対象)
re.subは「正規表現にマッチした部分」を指定した内容へ置換します。基本形は次のとおりです。
import re
result = re.sub(pattern, repl, string, count=0, flags=0)
pattern:検索に使う正規表現(置換したい条件)repl:置換後の文字列(または関数)string:対象の文字列count:置換回数の上限(0なら全件)flags:挙動を変えるフラグ(例:re.IGNORECASEなど)
例えば、連続する空白(スペースやタブを含む)を1つの半角スペースに整形する置換は次のように書けます。
import re
text = "A B\t\tC"
result = re.sub(r"\s+", " ", text)
# "A B C"
ここでのポイントは、\s+が「空白類が1回以上続く」というパターンであり、単純な固定文字列では表現しづらい置換を一発で行える点です。
複数の候補を同じ文字列にまとめて置換する(ORパターン)
表記ゆれの統一など、「AでもBでもCでも、見つけたら同じ文字列に置き換えたい」ケースでは、正規表現のOR(|)が便利です。
import re
text = "カラー/カラ-/カラー の表記ゆれを統一する"
result = re.sub(r"カラー|カラ-|カラー", "カラー", text)
また、まとまりを明確にしたい場合はグルーピング((...))を使えます。
import re
text = "OK ok Ok oK"
result = re.sub(r"(OK|ok|Ok|oK)", "OK", text)
大小文字をまとめたいだけなら、ORを増やすよりフラグを使うほうが読みやすい場合があります。
import re
text = "OK ok Ok oK"
result = re.sub(r"ok", "OK", text, flags=re.IGNORECASE)
ORパターンは強力ですが、候補が多すぎるとパターンが肥大化しやすいので、後述の「使うべき場面/避けるべき場面」も踏まえて設計します。
マッチ結果(グループ)を参照して置換内容を変える
re.subでは、正規表現のキャプチャグループ((...))で拾った内容を使い、置換文字列を動的に組み立てられます。グループ参照には主に2つのやり方があります。
1) 置換文字列でグループ参照(\1や\g<1>)する
例えば、日付の区切りを「/」に統一し、年月日はそのまま使う置換は次のように書けます。
import re
text = "2025-12-26, 2025.12.27"
result = re.sub(r"(\d{4})[-.](\d{2})[-.](\d{2})", r"\1/\2/\3", text)
# "2025/12/26, 2025/12/27"
ここでは、(\d{4})・(\d{2})・(\d{2})で年・月・日をキャプチャし、置換側で\1〜\3として再利用しています。
2) 置換に関数(コールバック)を使う
マッチ内容に応じて条件分岐したい場合は、replに関数を渡します。関数はre.Matchを受け取り、返した文字列が置換結果になります。
import re
def mask_digits(m: re.Match) -> str:
s = m.group(0)
# 長い数字は末尾4桁だけ残す、などのルールを適用
return "*" * (len(s) - 4) + s[-4:]
text = "order=12345678, code=9876"
result = re.sub(r"\d{4,}", mask_digits, text)
# "order=****5678, code=9876"
この方法なら、「桁数に応じてマスク強度を変える」「特定の範囲だけ変換する」など、静的な置換文字列では難しい処理を安全に実装できます。
置換された件数も取得する(re.subn)
データクレンジングやログ整形では、「実際に何件置換されたか」を確認できると、想定どおりのルールが効いているかを検証しやすくなります。re.subnは、置換後文字列に加えて置換回数も返します。
import re
text = "ID: 001, ID: 002, No match"
new_text, n = re.subn(r"ID:\s*\d+", "ID: ***", text)
# new_text => "ID: ***, ID: ***, No match"
# n => 2
戻り値がタプル((置換後文字列, 置換回数))になる点がre.subとの違いです。置換結果と同時に件数をログに出す、しきい値を超えたら異常とみなす、といった運用にもつなげられます。
正規表現を使うべき場面/避けるべき場面
正規表現は「python 文字列 置換」の中でも非常に表現力が高い一方、乱用すると可読性や保守性を落とす原因になります。ここでは判断の目安を整理します。
使うべき場面
- 複数パターン(表記ゆれ、区切り文字違いなど)をまとめて処理したい
- 数字・日付・メールアドレスのように「形式(パターン)」で対象を特定したい
- 前後の文脈(境界、繰り返し、任意の空白など)を条件に含めて置換したい
- グループ参照やコールバックで、マッチ内容に応じて置換結果を変えたい
避けるべき場面
- 固定文字列をそのまま置き換えるだけで十分なケース(正規表現は過剰になりやすい)
- ルールが複雑化してパターンが読めなくなっているケース(後から修正できない“ブラックボックス化”)
- 入力が巨大で、複雑な正規表現を何度も適用する設計(性能劣化や想定外のバックトラッキングの温床)
正規表現を使うときは、パターンを短く書くことよりも「意図が読み取れること」を優先し、必要ならコメントやre.VERBOSEの利用も検討すると、長期運用での事故を減らせます。
スライスで位置を指定して差し替える・挿入する

Pythonの文字列はイミュータブル(変更不可)なため、特定位置だけを「直接書き換える」ことはできません。一方で、スライスを使えば「前半+差し替え文字列+後半」という形で新しい文字列を組み立てられます。これは、パターンに基づく置換ではなく、位置を指定して行う python 文字列 置換の手法として有効です。
インデックス指定で部分文字列を組み立て直す基本
スライスは s[start:end] の形で、文字列の一部を切り出します。これを利用して、差し替えたい範囲を除いた部分をつなぎ直すことで「置換」と同等の結果を作れます。
基本形は次のとおりです。
s = "ABCDEFG"
start = 2
end = 5
replacement = "xxx"
result = s[:start] + replacement + s[end:]
print(result) # ABxxxFG
ポイントは以下です。
s[:start]が「差し替え箇所より前」s[end:]が「差し替え箇所より後」- 差し替え対象は
startからend-1まで(endは含まれない)
また、インデックスは負数も使えます。末尾から数えて位置を指定できるため、後ろ側の固定位置を差し替えたい場合に便利です。
s = "user_202512"
# 末尾2文字を "--" に差し替える
result = s[:-2] + "--"
print(result) # user_2025--
さらに、対象範囲の長さと置換後の長さが一致している必要はありません。短くしても長くしても、単に「結合された新しい文字列」になるだけです。
s = "ID:12345"
result1 = s[:3] + "9" + s[4:] # 1文字だけ差し替え(位置3の1文字を置換)
result2 = s[:3] + "ABCDE" + s[4:] # 長い文字列に差し替え
print(result1) # ID:92345
print(result2) # ID:ABCDE2345
1文字だけを差し替える場合は、end = start + 1 と考えると理解しやすいです。
特定位置へ挿入・削除する実装例
スライスによる組み立て直しは「差し替え」だけでなく、挿入や削除にもそのまま応用できます。位置を指定して文字列を編集したいときの、実用的な python 文字列 置換(加工)として押さえておくと便利です。
挿入は、挿入位置の前後を分けて間に文字列を挟みます(start == end のイメージ)。
s = "HelloWorld"
pos = 5
result = s[:pos] + " " + s[pos:]
print(result) # Hello World
例えば、固定桁のコードに区切り文字を入れるようなケースにも使えます。
s = "20251226"
result = s[:4] + "-" + s[4:6] + "-" + s[6:]
print(result) # 2025-12-26
削除は、削除したい範囲を飛ばして前後を結合します。置換先を空文字にする考え方です。
s = "error[code=500]: failed"
start = 5
end = 15 # "[code=500]" を削除したい
result = s[:start] + s[end:]
print(result) # error: failed
1文字削除も同様に、削除したい位置 i を s[:i] + s[i+1:] で取り除けます。
s = "ABCDE"
i = 2 # "C" を削除
result = s[:i] + s[i+1:]
print(result) # ABDE
インデックスを計算して編集する処理では、範囲外の値が混ざると意図しない結果になりやすい点に注意が必要です。特に、start と end の大小関係(start <= end)や、どの文字が何番目か(0始まり)を確認しながら実装すると安全です。
タブ文字をスペースに展開して整形する(expandtabs)

ログやコード片、表形式のテキストを扱っていると、タブ文字(\t)が混ざって見た目の列がズレることがあります。Pythonではstr.expandtabs()を使うことで、タブを「指定した幅のカラム境界に揃える形で」スペース展開でき、読みやすい整形が可能です。単純な「python 文字列 置換」とは少し異なる挙動を理解しておくと、意図どおりに整形できます。
expandtabsの使い方と置換との違い
expandtabsは、文字列中のタブをスペースに展開するためのメソッドです。基本形は次のとおりで、引数tabsize(デフォルトは8)でタブ幅を指定します。
text = "a\tb\tc"
print(text.expandtabs()) # tabsize=8(既定)
print(text.expandtabs(4)) # タブ幅4
ここで重要なのは、replace("\t", " ")のような単純置換と違い、expandtabsは「次のタブ位置(カラム境界)まで」をスペースで埋める点です。つまり、タブが登場した時点の文字数(カラム位置)によって、挿入されるスペース数が変わります。
例えば、同じタブでも位置によって展開結果が変わるため、列揃えに向きます。
text = "ab\tc"
print(text.replace("\t", " "))
print(text.expandtabs(4))
replace:タブ1個を常にスペース1個にする(列揃えは保証されない)expandtabs(4):現在位置から「4の倍数のカラム」までスペースで埋める(列揃えしやすい)
また、文字列はイミュータブルなので、expandtabsも元の文字列自体は変更しません。整形後の値を変数に受けるのが基本です。
raw = "col1\tcol2\tcol3"
formatted = raw.expandtabs(4)
注意:expandtabsは「タブを消してスペースにする」だけで、全角文字の表示幅(ターミナルやフォント依存)まで厳密に揃える機能ではありません。見た目の揃い方は出力環境によって差が出ることがあります。
ログやテキスト整形での実用例
expandtabsが活躍するのは、タブ区切りのデータやログを「人が読むために整形したい」ときです。特に、列の開始位置を揃えたいケースでは、単純なpython 文字列 置換(replace)よりも意図に合うことが多いです。
例えば、タブ区切りの簡易ログを読みやすく整形する例です。
log = "INFO\t2025-12-26\tuser_id=12\taction=login\n" \
"WARN\t2025-12-26\tuser_id=7\taction=retry\n"
print(log.expandtabs(4))
タブ幅を揃えることで、INFO/WARNなどのレベル、日付、属性が縦に揃いやすくなります。タブ幅は用途に合わせて調整し、実際の出力で見やすい値を選ぶのがコツです。
また、TSV(タブ区切り)風の文字列を「目視確認用に整形して表示したい」場合にも有効です。たとえば、値が短い列が多いならtabsizeを小さめに、項目が長いなら大きめにすると読みやすくなります。
tsv_preview = "name\tage\tcity\nAlice\t30\tTokyo\nBob\t8\tOsaka\n"
print(tsv_preview.expandtabs(8))
置換という観点で見ると、expandtabsは「タブ→スペース」という変換を行いますが、目的は単なる置換ではなく整列(整形)です。ログ出力の見やすさ改善、レビューや調査時の可読性向上など、「見た目の列揃え」が必要な場面で選択すると効果的です。
目的別:最適な置換手法の選び方

Pythonで「文字列 置換」を行う方法は複数あり、目的に合わない手法を選ぶと、コードが読みにくくなったり処理が遅くなったりします。ここでは用途別に、replace・translate・re.subのどれを選ぶべきかを整理します。迷ったときは「置換対象が固定か/文字単位か/パターンか」「処理量がどれくらいか」の2軸で判断するとスムーズです。
固定文字列ならreplaceを選ぶ
「この単語をこの単語に変える」「このフレーズを削除する」といった固定文字列の置換なら、まずはstr.replaceを選ぶのが基本です。直感的で読みやすく、正規表現のような学習コストもありません。
- 向いているケース:単語・記号・定型フレーズなど、完全一致する文字列を置換したい
- メリット:記述が簡単で可読性が高い/意図が伝わりやすい
- 注意点:大文字・小文字や表記ゆれは別文字列扱いになるため、事前に統一するか複数回置換が必要
# 固定文字列の置換(例)
text = "Hello, Python!"
result = text.replace("Python", "World")
# "Hello, World!"
「固定の文字列を別の文字列へ」かどうかが判断基準です。パターン(例:数字の連続、空白の連続)を扱う必要が出てきたら、次のre.subを検討します。
文字単位の大量変換ならtranslateを選ぶ
多数の文字を「1文字ずつ」まとめて変換したい場合は、str.translateが有力です。特に、同種の変換を大量に行う(例:記号の正規化、全角/半角に近い単純変換、特定文字の一括削除)ときに効率的です。
- 向いているケース:文字単位での一括置換(例:「-」や「_」を統一、不要文字を削除)
- メリット:複数文字の変換を1回の走査で行いやすく、処理量が多い場面で有利になりやすい
- 注意点:「文字列」ではなく「文字」を対象にするため、複数文字のフレーズ置換には不向き
# 文字単位の一括置換(例)
table = str.maketrans({"-": "_", " ": ""}) # "-"→"_"、半角スペース削除
text = "user-name 01"
result = text.translate(table)
# "user_name01"
replaceを何度も連続で書いて「文字を1つずつ置換している」状態なら、translateへ寄せたほうが意図が明確になり、保守もしやすくなることがあります。
パターンマッチが必要ならre.subを選ぶ
「条件に合う部分を置換したい」「複数候補をまとめて置換したい」など、パターンマッチが必要ならre.sub(正規表現)を選びます。Pythonの文字列置換で最も柔軟ですが、その分だけ読みづらくなりやすいため、必要性があるときに使うのがコツです。
- 向いているケース:連続する空白、数字列、特定形式(例:日付っぽい並び)など、規則性で置換したい
- メリット:1回の置換で複雑な条件を表現できる/候補をまとめて扱える
- 注意点:正規表現は可読性が落ちやすく、チーム開発ではレビュー負荷が上がることがある
import re
# パターンに一致する部分を置換(例:連続空白を1つに)
text = "A B\t\tC"
result = re.sub(r"\s+", " ", text)
# "A B C"
固定文字列で済むのに正規表現を使うと過剰になりがちです。まずは「本当にパターンが必要か」を確認してから選ぶと失敗しにくくなります。
大量データ処理での性能と可読性の注意点
ログやCSV、テキストの前処理などで大量データに対して文字列置換を行う場合、「速さ」と同じくらい「読みやすさ・変更しやすさ」が重要です。置換の選び方と書き方次第で、処理時間と運用コストが大きく変わります。
- 置換ルールが単純:
replaceで十分。無理に正規表現へ寄せない - 文字単位の変換が多い:
translateで変換テーブルを作り、まとめて処理する - パターンが必要:
re.subを使うが、パターンは短く明確にし、意図が分かるよう命名やコメントを添える
また、大量処理では同じ置換を何度も実行することが多いため、ルールが増えてきたら「どの手法を選んでいるか」がコード全体の見通しに直結します。最小限の表現で目的が伝わる手法を選ぶことが、性能と可読性の両立につながります。
まとめ:Pythonの文字列置換を使いこなす要点整理

Pythonの文字列置換は、一見すると「replaceで置き換える」だけに見えますが、実務では置換対象の粒度(固定文字列か/文字単位か/パターンか)と、求める挙動(回数制限・安全な入れ替え・柔軟な条件)で選ぶべき手段が変わります。ここでは、python 文字列 置換の最終確認として、主要メソッドの違いと、つまずきやすい落とし穴への対処を要点として整理します。
主要メソッドの比較(replace/translate/re.sub)
文字列置換の主役は replace/translate/re.sub の3つです。違いを把握すると「どれを使うべきか」で迷いにくくなります。
| 手段 | 得意な置換 | 指定方法 | 代表的なメリット | 注意点 |
|---|---|---|---|---|
str.replace(old, new[, count]) | 固定文字列(部分文字列) | 文字列→文字列 | 直感的で読みやすい/正規表現不要 | パターン一致は不可(完全一致の部分文字列) |
str.translate(table) | 文字単位の一括変換(多対多) | 変換テーブル(辞書的) | 多数の文字を高速に置換しやすい | 基本は「文字単位」中心(部分文字列置換には不向き) |
re.sub(pattern, repl, string[, count]) | パターン(条件)に基づく置換 | 正規表現 | 柔軟(OR・繰り返し・前後関係など) | 正規表現の理解が必要/過剰に使うと可読性低下 |
選び方を一言でまとめると、以下の判断が安全です。
- 固定の文字列を置換するなら
replace - 文字単位の大量置換(例:記号の正規化、全角→半角の一部)なら
translate - ゆらぎや条件がある(例:数字のまとまり、複数表記、前後依存)なら
re.sub
また、どの方法でも共通して重要なのが「Pythonの文字列はイミュータブル(変更不可)」という点です。つまり、置換は常に新しい文字列を返すため、結果を変数に代入しないと反映されません。
s = "apple"
s.replace("a", "A")
print(s) # "apple"(変わらない)
s = s.replace("a", "A")
print(s) # "Apple"よくある落とし穴と対処(回数指定・スワップ・正規表現の扱い)
python 文字列 置換で「動いたけど期待と違う」原因は、典型パターンに集約されます。ここでは特に頻出の3点(回数指定・スワップ・正規表現)を、ミスの形と対処で整理します。
回数指定(count)の誤解:どこから何回置換されるのか
replace と re.sub には回数指定があり、「左から順に最大N回」だけ置換します。「特定の位置だけ置換したい」意図で回数指定をするとズレることがあるため、期待する対象が先頭側にあるかを確認しましょう。
s = "foo foo foo"
print(s.replace("foo", "bar", 1)) # "bar foo foo"(左から1回)対処としては、置換箇所を右側から数えたい場合、単純な回数指定ではなく「右側基準の設計(分割して再結合等)」が必要になります。回数指定はあくまで置換の上限として使うのが安全です。
スワップ(2つの文字列の入れ替え)の罠:連続replaceで壊れる
「AをBに、BをAに」と入れ替える処理を replace の連続で書くと、先に置換した結果が次の置換対象になり、意図しない最終結果になりがちです。
s = "A_B"
# 悪い例:A→Bのあと、元々のBも巻き込まれてAになり得る
s1 = s.replace("A", "B").replace("B", "A")
print(s1) # 期待とズレる可能性対処の基本は「一時的な退避(プレースホルダ)」か「衝突しない置換設計」です。プレースホルダは、元の文字列に絶対に含まれない値を選ぶのがポイントです。
s = "A_B"
tmp = "\u0000" # 通常含まれにくい制御文字など(例)
s2 = s.replace("A", tmp).replace("B", "A").replace(tmp, "B")
print(s2) # "B_A"「入れ替えたい対象が単一文字で、対象文字が多い」場合は、translate のような一括変換(同時置換の発想)が安全に働くケースもあります。いずれにせよ、連続replaceでスワップする場合は置換の干渉を必ず疑ってください。
正規表現の扱い:記号が「特別な意味」になる
re.sub は強力ですが、正規表現では . や +、*、? などがメタ文字として解釈されます。「文字としてのドットを置換したい」のに、パターンに . を書くと「任意の1文字」にマッチしてしまう、といった事故が起きます。
import re
s = "a.b"
print(re.sub(".", "_", s)) # "___"(. は任意の1文字)
print(re.sub(r"\.", "_", s)) # "a_b"(\ でエスケープ)もう一つの落とし穴は、置換後文字列(repl)側で \1 などが「グループ参照」になり得る点です。バックスラッシュを含む文字列をそのまま置換文字列に入れる場合、意図せず解釈されることがあるため、raw文字列(r"...")の利用や、必要に応じて関数置換(replに関数を渡す)を検討します。
まとめると、正規表現での置換は「柔軟さ」と引き換えに、メタ文字・エスケープ・参照の理解が必須です。固定文字列の置換で足りるのに re.sub を選ぶと、可読性と保守性を下げやすい点も含めて注意しましょう。

