创建一组具有位置约束的随机点的基本方法是使用一个函数来调制放置点的概率,使其能够在指定位置上。该函数最初是常数,每当放置一个点时,禁止点周围的区域就被设置为零。如果您将问题离散化,则很难处理连续变量,但相对容易处理。
另一个需要注意的问题是如何在圆柱体上进行操作。将其视为在矩形区域上随机放置点,并且该矩形区域会周期性地重复出现可能更容易。这可以通过以下两种不同的方式来处理:
1. 最简单的方法是考虑不仅将点放置在主要矩形中,还要将其放置在相邻的矩形中,并计算它们对主矩形内的概率函数的影响。
2. 更复杂的方法是将概率函数视为编码禁止区域的卷积核,与已放置的点对应的delta函数之和。如果使用FFT计算,则周期性是自然产生的。
第一种方法可以按如下方式编码:
from __future__ import division
import numpy as np
r, h = 20, 300
w = 2*np.pi*r
int_w = int(np.rint(w))
mult = 10
pdf = np.ones((h*mult, int_w*mult), np.bool)
points = []
min_d, max_d = 230, 250
available_locs = pdf.sum()
while available_locs:
new_idx = np.random.randint(available_locs)
new_idx = np.nonzero(pdf.ravel())[0][new_idx]
new_point = np.array(np.unravel_index(new_idx, pdf.shape))
points += [new_point]
min_mask = np.ones_like(pdf)
if max_d is not None:
max_mask = np.zeros_like(pdf)
else:
max_mask = True
for p in [new_point - [0, int_w*mult], new_point +[0, int_w*mult],
new_point]:
rows = ((np.arange(pdf.shape[0]) - p[0]) / mult)**2
cols = ((np.arange(pdf.shape[1]) - p[1]) * 2*np.pi*r/int_w/mult)**2
dist2 = rows[:, None] + cols[None, :]
min_mask &= dist2 > min_d*min_d
if max_d is not None:
max_mask |= dist2 < max_d*max_d
pdf &= min_mask & max_mask
available_locs = pdf.sum()
points = np.array(points) / [mult, mult*int_w/(2*np.pi*r)]
如果您使用自己的值运行它,输出通常只有一个或两个点,因为较大的最小距离禁止所有其他点。但是,如果您使用更合理的值运行它,例如:
min_d, max_d = 50, 200
以下是前5个点放置后概率函数的样子:
![enter image description here](https://istack.dev59.com/ZzWLd.webp)
请注意,这些点作为坐标对返回,第一个是高度,第二个是沿圆柱体周长的距离。
r = math.sqrt(s)*R
中检索随机数的平方根? - furins