str.replace, 複雑化すると import re あたりを思いつくが,'l' を '1' に, 'k' を 'z' に,'y' を ';' に置換したいみたいな微妙な場合には
str.translate が便利よ,という話.上のはもちろんずらずらつなげて
mystring.replace('l','1').replace('k','z').replace('y',';')
でもいけるが,これはさすがにやりたくない.実は atcoder でのこの回答 (@regular contest #019-A) で知ったのだが,
translate というメソッドがある.python 2.x と 3.x で扱いが若干違うようで,python3.x なら
x = str.maketrans("lky", "1z;")
print(x, type(x))
# {121: 59, 107: 122, 108: 49} <class 'dict'>
mystring.translate(x)
という感じで使用できる.ここで str.maketrans は dict を返す static method で,引数は 1-3 個.引数は i) 本人が返してるような,Unicode ordinal/char => Unicode ordinal/string of arbitrary length/None な dict (str.maketrans({'l':"there"}) とかもできる), ii) 引数2つ(同じ長さの string)で 「こっちの文字列中の文字を」「対応するこっちの文字で置換」 iii)3つ目の引数を与えるとそれは None に map される文字群,ということになっている.そしてそれを str.translate が受け取る,という形で置換ができるわけだ.
一方 python 2 系で使うときはこんな感じ.
import string
x = string.maketrans("lky", "1z;")
print x, type(x)
# '\x00\x01\x02\x03\x04\x05\x06......ghijz1mn...\xff' <type 'str'>
mystring.translate(a)
ご覧の通り
string.maketrans は str の static method というわけではないようで,またここでは 256 文字の羅列で変換テーブルが作られている. str.translate が使えるのは同様だが,3.x ではこれは map だけを受け取るのに対して str.translate(table,[deletechars]) としてここで第二引数を受け取って文字列消去を行えるようだ(消去は置換より前に行われる). string.translate(s,table,[deletechars]) という書き方もできるみたい.というわけで案外便利そうな(そして 2.x と 3.x で扱いの違う)
translate method のお話でした. Atcoder みたいに他の人の回答も見られるやつは,簡単な問題でも案外たまにみるといいことがあったりする.
No comments:
Post a Comment