У меня есть следующий код:
# positions: np.ndarray of shape(N,d)
# fitness: np.ndarray of shape(N,)
# mass: np.ndarray of shape(N,)
iteration = 1
while iteration <= maxiter:
K = round((iteration-maxiter)*(N-1)/(1-maxiter) + 1)
for i in range(N):
displacement = positions[:K]-positions[i]
dist = np.linalg.norm(displacement, axis=-1)
if i<K:
dist[i] = 1.0 # prevent 1/0
force_i = (mass[:K]/dist)[:,np.newaxis]*displacement
rand = np.random.rand(K,1)
force[i] = np.sum(np.multiply(rand,force_i), axis=0)
Итак, у меня есть массив, в котором хранятся координаты N
частиц в d
измерениях. Мне нужно сначала вычислить евклидово расстояние между частицей i
и первыми K
частицами, а затем вычислить «силу» каждой из K
частиц. Затем мне нужно просуммировать по K
частицам, чтобы найти общую силу, действующую на частицу i
, и повторить для всех N
частиц. Это только части кода, но после некоторого профилирования эта часть является наиболее критичным по времени шагом.
Итак, мой вопрос в том, как я могу оптимизировать приведенный выше код. Я попытался как можно лучше векторизовать его, и я не уверен, есть ли еще возможности для улучшения. Результаты профилирования говорят, что {method 'reduce' of 'numpy.ufunc' objects}
, fromnumeric.py:1778(sum)
и linalg.py:2103(norm)
выполняются дольше всего. Первый умрет от массивного вещания? Как я могу оптимизировать эти три вызова функций?
cdist
. в scipy - person xdze2   schedule 10.09.2018N
иd
? - person Divakar   schedule 10.09.2018N
обычно составляет от 50 до 100, аd
— от 2 до 50, но было бы здорово, если бы оптимизацию можно было применить, даже еслиN
достигает ~2000, аd
достигает ~100. - person Physicist   schedule 11.09.2018