Tôi muốn tạo lưới từ dữ liệu được lấy mẫu. Tôi có thể sử dụng thuật toán phân cụm học máy, như k-means, nhưng tôi muốn hạn chế các trung tâm được phân bố đồng đều.Xây dựng lưới xấp xỉ đồng nhất từ mẫu ngẫu nhiên (trăn)
Tôi đã tìm ra cách tiếp cận bằng cách sử dụng tìm kiếm hàng xóm gần nhất để tìm kiếm: chọn một điểm ngẫu nhiên, xóa tất cả các điểm trong bán kính r rồi lặp lại. Điều này hoạt động tốt, nhưng tự hỏi nếu có ai có cách làm tốt hơn (nhanh hơn).
Đáp lại ý kiến Tôi đã thử hai phương pháp thay thế, một hóa ra chậm hơn người kia là như nhau ...
Phương pháp 0 (nỗ lực đầu tiên của tôi):
def get_centers0(X, r):
N = X.shape[0]
D = X.shape[1]
grid = np.zeros([0,D])
nearest = near.NearestNeighbors(radius = r, algorithm = 'auto')
while N > 0:
nearest.fit(X)
x = X[int(random()*N), :]
_, del_x = nearest.radius_neighbors(x)
X = np.delete(X, del_x[0], axis = 0)
grid = np.vstack([grid, x])
N = X.shape[0]
return grid
Phương pháp 1 (sử dụng đồ thị precomputed):
def get_centers1(X, r):
N = X.shape[0]
D = X.shape[1]
grid = np.zeros([0,D])
nearest = near.NearestNeighbors(radius = r, algorithm = 'auto')
nearest.fit(X)
graph = nearest.radius_neighbors_graph(X)
#This method is very slow even before doing any 'pruning'
Cách 2:
def get_centers2(X, r, k):
N = X.shape[0]
D = X.shape[1]
k = k
grid = np.zeros([0,D])
nearest = near.NearestNeighbors(radius = r, algorithm = 'auto')
while N > 0:
nearest.fit(X)
x = X[np.random.randint(0,N,k), :]
#min_dist = near.NearestNeighbors().fit(x).kneighbors(x, n_neighbors = 1, return_distance = True)
min_dist = dist(x, k, 2, np.ones(k)) # where dist is a cython compiled function
x = x[min_dist < 0.1,:]
_, del_x = nearest.radius_neighbors(x)
X = np.delete(X, del_x[0], axis = 0)
grid = np.vstack([grid, x])
N = X.shape[0]
return grid
Chạy những như sau:
N = 50000
r = 0.1
x1 = np.random.rand(N)
x2 = np.random.rand(N)
X = np.vstack([x1, x2]).T
tic = time.time()
grid0 = get_centers0(X, r)
toc = time.time()
print 'Method 0: ' + str(toc - tic)
tic = time.time()
get_centers1(X, r)
toc = time.time()
print 'Method 1: ' + str(toc - tic)
tic = time.time()
grid2 = get_centers2(X, r)
toc = time.time()
print 'Method 1: ' + str(toc - tic)
Phương pháp 0 và 2 là như nhau ...
Method 0: 0.840130090714
Method 1: 2.23365592957
Method 2: 0.774812936783
Điểm tốt. Tôi đã có một phiên bản thay thế, nơi mà tôi chỉ vừa với đối tượng 'gần nhất' ngay từ đầu, sau đó theo dõi những điểm tôi đã xóa cho đến giờ. Nó thực sự là chậm hơn mặc dù, tôi nghĩ rằng vấn đề là khi bạn tái trang bị bạn nhận được một tốc độ lên khi mẫu còn lại co lại. Ý tưởng của bạn có thể giải quyết vấn đề này. Tôi sẽ thử nó. –
Đã có một nỗ lực tại phương pháp này (xem chỉnh sửa) dường như không giúp được gì nhiều ... –