我有以下代码:
import random
import numpy as np
import pandas as pd
num_seq = 100
len_seq = 20
nts = 4
sequences = np.random.choice(nts, size = (num_seq, len_seq), replace=True)
sequences = np.unique(sequences, axis=0) #sorts the sequences
d = {}
pr = 5
for i in range(num_seq):
globals()['seq_' + str(i)] = np.tile(sequences[i,:],(pr,1))
d['seq_' + str(i)] = np.tile(sequences[i,:],(pr,1))
pool = np.empty((0,len_seq),dtype=int)
for i in range(num_seq):
pool = np.concatenate((pool,eval('seq_' +str(i))))
我想将字典d
转换为Numpy数组(或只有一个条目的字典(。我的代码工作,生成pool
。然而,在num_seq
、len_seq
和pr
的值较大时,这需要非常长的时间。
执行时间很关键,因此我的问题是:有更有效的方法吗?
以下是要点列表:
np.concatenate
在O(n)
中运行,因此您的第二个循环在O(n^2)
时间中运行。您可以将该值附加到列表中,并在最后(以O(n)
时间为单位(将所有值添加到np.vstack
中- 访问
globals()
很慢,而且众所周知是一种糟糕的做法(因为它很容易以恶劣的方式破坏代码( - 调用
eval(...)
也比较慢,也不安全,所以要避免 - 默认的CPython解释器不会优化重复的表达式(它会重新计算它们(
- 您可以使用Cython来稍微加快代码或Numba的速度(请注意,字典的支持在Numba中是实验性的(
下面是一个更快代码的例子(代替第二个循环(:
pool = np.vstack([d[f'seq_{i}'] for i in range(num_seq)])