给定两个矩阵 X1 (N,3136) 和 X2 (M,3136)(其中每一行中的每个元素都是一个二进制数)我正在尝试计算汉明距离,以便将 X1 中的每个元素与所有元素进行比较X2 中的行,使得结果矩阵为 (N,M)。
我已经为它编写了两个函数(第一个在 numpy 的帮助下,另一个没有 numpy):
def hamming_distance(X, X_train):
array = np.array([np.sum(np.logical_xor(x, X_train), axis=1) for x in X])
return array
def hamming_distance2(X, X_train):
a = len(X[:,0])
b = len(X_train[:,0])
hamming_distance = np.zeros(shape=(a, b))
for i in range(0, a):
for j in range(0, b):
hamming_distance[i,j] = np.count_nonzero(X[i,:] != X_train[j,:])
return hamming_distance
我的问题是 upper 函数比 lower 慢得多,我使用了两个 for 循环。是否可以改进第一个函数以便我只使用一个循环?
附言。对不起我的英语,它不是我的第一语言,尽管我正在努力做到最好!
最佳答案
只有使用 Numpy 来矢量化您的工作,Numpy 才会使您的代码更快。在你的情况下,你可以利用数组广播来向量化你的问题:比较你的两个数组并创建一个形状为 (N,M,K)
的辅助数组,你可以沿着它的第三维求和:
hamming_distance = (X[:,None,:] != X_train).sum(axis=-1)
我们在第一个数组中注入(inject)一个单一维度,使其具有 (N,1,K)
的形状,第二个数组与 (1,M,K) 的形状隐式兼容
,所以可以执行操作。
@ayhan 在评论中指出,这将为大型 M
和 N
创建一个巨大的辅助数组,这是事实。这就是矢量化的代价:您以内存为代价获得 CPU 时间。如果你有足够的内存让上面的工作,它会非常快。如果不这样做,则必须缩小矢量化的范围,并在 M
或 N
(或两者;这将是您当前的方法)中循环。但这与 numpy 本身无关,这是关于在可用资源和性能之间取得平衡。
关于python - Numpy 数组比列表慢得多,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44271576/