Suppose I have an input point cloud X, represented by an array of dimensions N x 3. Each row in this array corresponds to a single point in XYZ space, between -1 and 1. Now, let k be a parameter which defines the resolution of a voxel grid (e.g. k = 3 corresponds to a voxel grid of dimensions 3 x 3 x 3). I am looking for an efficient way to compute the index for each point's corresponding voxel. This is more or less the current way I'm currently doing it using NumPy (written more expressively for sake of clarity):
# Generate some random input point cloud, 100 points
X = np.random.randn(100, 3)
# Define the resolution of the grid (e.g. say 3 x 3 x 3)
k = 3
# Iterate through points of input point cloud
for j, point in enumerate(X):
# Placeholder for voxel membership
partitions = np.zeros(3,)
for i, p in enumerate(point):
for d in range(k):
# Points are between -1 and 1, so the interval for each dimension is [-1, 1]
# Length 2, "left"/"lower" end is -1
if p <= (-1 + (d + 1) * 2 / k):
partitions[i] = d
# Compute the index of the voxel this point belongs to
# Can think of this as the base 10 representation of the base k number given by (x, y, z) in partitions
# Voxels are indexed such that (0, 0, 0) --> index 0, (0, 0, 1) --> index 1, (0, 0, 2) -->
# index 2, (0, 1, 0) --> index 3, etc.
p_reversed = np.flip(partitions)
idx= 0
for d in range(3):
idx += (k ** d) * p_reversed[d]
# Now idx corresponds to the index of the voxel to which point j belongs
This clearly scales poorly with increasing N and increasing k; is there a more efficient implementation?