Python/C APIを使用してPython文字列を作成することができます。これは、Python自体がPython/Cで実装されているため、排他的にPythonを使用する方法よりもはるかに高速です。パフォーマンスは、主に乱数ジェネレータの効率に依存します。あなたは、このようなthe one in glibcとして合理的なランダム(3)実装、とのシステム上にある場合は、ランダムな文字列の効率的な実装は次のようになります。
#include <Python.h>
/* gcc -shared -fpic -O2 -I/usr/include/python2.7 -lpython2.7 rnds.c -o rnds.so */
static PyObject *rnd_string(PyObject *ignore, PyObject *args)
{
const char choices[] = {'0', '1'};
PyObject *s;
char *p, *end;
int size;
if (!PyArg_ParseTuple(args, "i", &size))
return NULL;
// start with a two-char string to avoid the empty string singleton.
if (!(s = PyString_FromString("xx")))
return NULL;
_PyString_Resize(&s, size);
if (!s)
return NULL;
p = PyString_AS_STRING(s);
end = p + size;
for (;;) {
unsigned long rnd = random();
int i = 31; // random() provides 31 bits of randomness
while (i-- > 0 && p < end) {
*p++ = choices[rnd & 1];
rnd >>= 1;
}
if (p == end)
break;
}
return s;
}
static PyMethodDef rnds_methods[] = {
{"rnd_string", rnd_string, METH_VARARGS },
{NULL, NULL, 0, NULL}
};
PyMODINIT_FUNC initrnds(void)
{
Py_InitModule("rnds", rnds_methods);
}
テストハレックスのベンチマークと、このコードは、それがより280x高速であることを示しています元のコード、および(私のマシン上)ハレックスのコードよりも速く2.3倍:
# the above code
>>> t1 = Timer("rnds.rnd_string(2**20)", "import rnds")
>>> sorted(t1.repeat(10,1))
[0.0029861927032470703, 0.0029909610748291016, ...]
# original generator
>>> t2 = Timer("''.join(random.choice('01') for x in xrange(2**20))", "import random")
>>> sorted(t2.repeat(10,1))
[0.8376679420471191, 0.840252161026001, ...]
# halex's generator
>>> t3 = Timer("bin(random.getrandbits(2**20-1))[2:].zfill(2**20-1)", "import random")
>>> sorted(t3.repeat(10,1))
[0.007007122039794922, 0.007027149200439453, ...]
プロジェクトにCコードを追加するには、合併症であるが、重要な操作の280x高速化のために、それがうまく価値があるかもしれません。
効率をさらに向上させるために、より高速のRNGを調べて、別のスレッドから呼び出すようにして、乱数生成を並列化して並列化します。後者は、スレッド間通信がそうでなければ高速の生成プロセスを妨げないことを保証するために、ロックフリー同期メカニズムの恩恵を受けるであろう。
ありがとうございました。 – marshall
@マーシャル:あなたは['b2a_bin(os.urandom(2 ** i/8))'(Cythonで書かれたC拡張子)を使ってさらに高速化できます。](https://gist.github.com/zed/ 3526111)。 [Multiplying a huge number times random()(Python)](http://stackoverflow.com/q/12161988/4279) – jfs
@ J.F.Sebastianありがとう! – marshall