77

私は、同様にスケーリングできるPythonでランダムな文字列を生成する、よりpythonicな方法を見つけようとしています。通常、次のようなものが表示されます

''.join(random.choice(string.letters) for i in xrange(len))

長い文字列を生成したい場合は最悪です。

私はしばらく random.getrandombits について考えていて、それをビットの配列に変換する方法を考え出してから、それを 16 進エンコードします。Python 2.6 を使用して、文書化されていない bitarray オブジェクトに遭遇しました。どういうわけか私はそれを機能させました、そしてそれは本当に速いようです。

私のノートブックでは、約 3 秒で 50mil のランダムな文字列が生成されます。

def rand1(leng):
    nbits = leng * 6 + 1
    bits = random.getrandbits(nbits)
    uc = u"%0x" % bits
    newlen = int(len(uc) / 2) * 2 # we have to make the string an even length
    ba = bytearray.fromhex(uc[:newlen])
    return base64.urlsafe_b64encode(str(ba))[:leng]

編集

heikogerlach さんは、文字数が奇数であることが問題の原因であると指摘しました。fromhex から常に偶数の 16 進数を送信するようにするための新しいコードが追加されました。

これを同じくらい高速に行うためのより良い方法があるかどうか、まだ興味があります。

4

5 に答える 5

130
import os
random_string = os.urandom(string_length)

URLセーフ文字列が必要な場合:

import os
random_string = os.urandom(string_length).hex() 

(その場合、random_string の長さは string_length よりも大きいことに注意してください)

于 2009-04-24T09:09:39.070 に答える
10

uuid が十分に短い場合もあり、ダッシュが気に入らない場合はいつでも.replace('-', '') できます。

from uuid import uuid4

random_string = str(uuid4())

ダッシュなしで特定の長さが必要な場合

random_string_length = 16
str(uuid4()).replace('-', '')[:random_string_length]
于 2012-08-31T15:32:38.360 に答える
6

Python.org の1023290バグ レポートから抜粋:

junk_len = 1024
junk =  (("%%0%dX" % junk_len) % random.getrandbits(junk_len *
8)).decode("hex")

また、issue 923643および1023290も参照してください。

于 2009-04-24T17:04:55.170 に答える
2

最後の例に関して、次の修正により、junk_len の値に関係なく、行の長さが均等になるようにします。

junk_len = 1024
junk =  (("%%0%dX" % (junk_len * 2)) % random.getrandbits(junk_len * 8)).decode("hex")
于 2009-06-02T13:24:54.330 に答える
2

fromhex()メソッドは偶数の16進数を想定しているようです。文字列の長さは 75 文字です。最後の要素をsomething[:-1] 除外することに注意してください! を使用するだけsomething[:]です。

于 2009-04-24T09:09:45.420 に答える