文字列だって、ただの文字の集まりじゃない
Pythonの文字列は文字の並びですが、おそらくどの型よりも頻繁に使うことになるはずです。名前、ラベル、メッセージ、URL、ファイルパス、APIのレスポンス — どれも、どこかのタイミングで必ず文字列として扱われます。
文字列を作るにはクォートで囲むだけ。シングル、ダブル、トリプルのいずれでもOKです:
シングルクォートとダブルクォートはどちらを使っても構いません。エスケープしなくて済むほうを選べばOKです。たとえば "don't" はそのまま書けますが、'don\'t' だとバックスラッシュが必要になります。
文字列は イミュータブル(変更不可) です。一度作った文字列は、あとから一部の文字だけを書き換えることはできません。変更しているように見える操作も、実際には新しい文字列を返しているだけです。だからこそ text.upper() だけでなく text = text.upper() と書くわけです。代入し直さないと、せっかく作った大文字の文字列がそのまま捨てられてしまいます。
文字列の結合と繰り返し
よく使う文字列の結合は、次の2つの演算子でだいたい事足ります。
+ で文字列を連結できて、* で文字列を繰り返せます。どちらも新しい文字列を返します。
ただ、+ でたくさんの要素をつなげていくと、すぐに読みにくくなってきます。異なる型の値を混ぜてメッセージを組み立てたいときは、f-string を使うのがおすすめです。次のセクションで詳しく見ていきましょう。
python f-string で文字列をフォーマットする
クォートの前に f を付けるだけで、その文字列はテンプレートとして扱われます。{...} の中に書いた式は、その評価結果に置き換えられます。
{...} の中には、変数でも四則演算でもメソッド呼び出しでも関数呼び出しでも、式ならなんでも書けます。ただし、欲張らずにシンプルに保つのがコツ。3行がかりの計算を {...} に押し込みたくなったら、一度わかりやすい名前の変数に入れてから埋め込みましょう。
さらに、f-string ではコロンのあとに書式指定子を付けて、数値のフォーマットや桁揃え、位置揃えを細かくコントロールできます。
これらのフォーマット指定子は str.format() で使われるものと同じで、基本に慣れてきたらサラッと目を通しておく価値があります。とはいえ、最初の一歩の段階では必要ありません。
python 文字列 スライス:一部分だけ取り出す
Python の文字列はシーケンスと同じようにインデックスでアクセスできます。各文字には 0 から始まる位置番号が振られていて、1 文字だけ取り出すことも、範囲を指定してまとめて取り出すこともできます。
[start:stop:step] というスライスのパターンは、リストをはじめとするシーケンス全般で共通して使えるので、ここで数分かけてしっかり身につけておくと後々ずっと役に立ちます。
押さえておきたいポイントが2つあります。
stopのインデックスは含まれません。word[0:2]が返すのはインデックス 0 と 1 で、2 は含まれない点に注意してください。- 負のインデックスは末尾から数えます。
-1が最後の文字、-2がその1つ前、という具合です。
Python 文字列の反転
Python の文字列はイミュータブル(変更不可)なので、.reverse() のようなメソッドは用意されていません。とはいえ、スライスのステップに -1 を指定すれば、たった1行で文字列を反転できます。
word[::-1] は「先頭から末尾まで、ステップを -1 で遡る」という意味ですね。返ってくるのは新しい文字列で、元の文字列はそのまま残ります。新しい文字列を作らずに文字を逆順に走査したいだけなら、reversed(word) で遅延評価のイテレータが手に入ります。
python 文字列の長さを len で取得する
len(text) を使うと、文字列の文字数を取得できます。
len が数えるのはバイト数ではなく Unicode のコードポイント数 である点に注意してください。たとえば len("café") は 5 ではなく 4 を返します。UTF-8 でエンコードすればバイト数はもっと多くなりますが、普通は「文字数」が欲しいはずなので、この挙動がちょうどいいわけです。
python 文字列に特定の文字列が含まれるか判定する方法
部分文字列が含まれているかを調べるなら、in 演算子を使うのがもっともPythonらしい書き方です。英文のようにそのまま読めるのも魅力です。
大文字小文字を区別せずに比較したい場合は、まず両辺を揃えてから判定します。
位置そのものが欲しい場合(「含まれているかどうか」だけでは足りないとき)は .find() を使います。部分文字列が見つかればそのインデックスを、見つからなければ -1 を返します。
よく使う文字列メソッド
Python の文字列にはたくさんのメソッドが用意されていますが、実際によく使うのは次のあたりです。
文字列の分割と結合:
.split(separator) は文字列をリストに変換し、separator.join(list_of_strings) はそれを再び1つの文字列に戻します。実務で文字列を扱うとき、この2つのメソッドが占める割合は想像以上に大きいです。
もう1組、覚えておくと便利なペアがあります。
1行の設定エントリをパースする処理が、たった3行で書けてしまいました。文字列は小さくても、使いこなせば大きな武器になります。
文字列の中身をチェックする
真偽値を返すメソッドがいくつかあり、if 文の条件としてそのまま使えます。
これらは控えめに使うのが無難です。というのも、Unicode 周りの細かい挙動まで完璧にカバーしてくれるわけではないからです。ASCII の範囲を超えた処理が必要になったら、re モジュールや unicodedata モジュールに頼るのが賢明です。
特殊文字のエスケープ
一部の文字は、文字列の中で使うときにバックスラッシュを添えてあげる必要があります。
Windowsのパスや正規表現を書くときは、raw文字列(生文字列)を使うとぐっと楽になります。クォートの前に r を付けるだけで、バックスラッシュがエスケープ文字として扱われなくなります。
文字列処理は頻出、だからこそ読みやすさを意識しよう
文字列まみれのコードをごちゃごちゃにしないための、3つの習慣を紹介します。
- 文字列の埋め込みには f-string を使う。 異なる型を
+で延々とつなげないこと。 - 「変更」したら代入し直す。
text.strip()だけではダメで、text = text.strip()と書きましょう。 - テキストを分解・組み立てるときは、まず
.split()と.join()を検討する。 自分でループを書くより速く、読みやすく、ミスも起きにくいです。
次は f-string を掘り下げていきます。ここまで何度か登場してきたフォーマットの強力なツールですが、数値や日付のフォーマット指定まで押さえると、本当に使いこなせるようになります。
よくある質問
Pythonのf-stringとは何ですか?
先頭にfを付けた文字列リテラルのことです。{...}の中に書いた式が、実行時にその値で置き換わります。例えば f"Hello, {name}!" と書くと、その時点のnameの値が文字列に埋め込まれます。
Pythonで文字列を反転(逆順)にするには?
ステップに-1を指定したスライスを使います。reversed_text = original[::-1] と書けば、同じ文字を逆順に並べた新しい文字列が返ります。Pythonの文字列はイミュータブル(変更不可)なので、元の文字列はそのまま残ります。
Pythonで文字列を分割するには?
文字列に対して.split()を呼び出します。引数なしなら空白文字で分割され、"a b c".split() は ['a', 'b', 'c'] を返します。区切り文字を指定することも可能で、"a,b,c".split(",") なら ['a', 'b', 'c'] になります。
Pythonの文字列はミュータブル(変更可能)ですか?
いいえ、イミュータブル(変更不可)です。一度作った文字列の中身を直接書き換えることはできません。文字列を「変更する」ように見えるメソッドは、すべて新しい文字列を返しているだけです。だからこそ text = text.strip() のように、結果を変数に代入し直すパターンが定番になっています。
Pythonで文字列を連結するには?
2つの文字列をつなぐだけなら+演算子でOKです(例:"hello" + " " + "world")。文の中に値を埋め込みたいときは f-string の方が読みやすく、f"Hello, {name}" のように書けます。リストの要素をまとめて連結する場合は separator.join(pieces) の方が高速で可読性も上がるのでおすすめです。
Pythonで文字列の長さを調べるには?
組み込み関数のlen(text)を使います。返るのは文字数(Unicodeのコードポイント数)なので、len("café") は 4 になります。バイト数が知りたい場合は、len(text.encode("utf-8")) のようにエンコードしてからlenを取ってください。