Я бы хотел добавить координаты с плавающей точкой в массив numpy, разделив интенсивность, основанную на центре масс координаты, на соседние пиксели.
В качестве примера с целыми числами:
import numpy as np
arr = np.zeros((5, 5), dtype=float)
coord = [2, 2]
arr[coord[0], coord[1]] = 1
arr
>>> array([[0., 0., 0., 0., 0.],
[0., 0., 0., 0., 0.],
[0., 0., 1., 0., 0.],
[0., 0., 0., 0., 0.],
[0., 0., 0., 0., 0.]])
Однако я хотел бы распределить интенсивность по соседним пикселям, когда coord
- это данные с плавающей точкой, например. coord = [2.2, 1.7]
.
Я рассмотрел использование гауссиана, например:
grid = np.meshgrid(*[np.arange(i) for i in arr.shape], indexing='ij')
out = np.exp(-np.dstack([(grid[i]-c)**2 for i, c in enumerate(coord)]).sum(axis=-1) / 0.5**2)
, который дает хорошие результаты, но становится медленным для трехмерных данных и тысяч точек.
Спасибо за любые советы или идеи, спасибо.
Основываясь на предложении @rpoleski, возьмите местный регион и примените взвешивание по расстоянию. Это хорошая идея, хотя реализация, которую я имею, не поддерживает первоначальный центр масс координат, например:
from scipy.ndimage import center_of_mass
coord = [2.2, 1.7]
# get region coords
grid = np.meshgrid(*[range(2) for i in coord], indexing='ij')
# difference Euclidean distance between coords and coord
delta = np.linalg.norm(np.dstack([g-(c%1) for g, c, in zip(grid, coord)]), axis=-1)
value = 3 # pixel value of original coord
# create final array by 1/delta, ie. closer is weighted more
# normalise by sum of 1/delta
out = value * (1/delta) / (1/delta).sum()
out.sum()
>>> 3.0 # as expected
# but
center_of_mass(out)
>>> (0.34, 0.63) # should be (0.2, 0.7) in this case, ie. from coord
Есть идеи?