将随机点定位在2D平面上

时间:2015-03-06 20:28:49

标签: geometry

所以这里有一些几何形状供你使用。我现在已经坚持了一段时间了:

我需要编写一个脚本(在C#中,但随意回答你喜欢的任何脚本),它会生成随机点。点数必须为x和y值。

我必须总共生成N个点(其中N> 1且随机最多100个)。

点1必须是x = 0,y = 0.点2必须与点1的距离为1。因此Root(x2 + y2)= 1。 点3必须距离点2的距离为1,依此类推。

现在这里是棘手的部分 - 点N必须距离点1的距离为1。因此,如果要将所有点连接成单个形状,您将获得一个封闭的形状,每个顶点都是相同的长度。

(顶点可能交叉,你甚至可能在同一个位置有两个点。只要它是随机的)。

知道你是怎么做到的吗?

2 个答案:

答案 0 :(得分:1)

我会用链的模拟做到这一点,有2种基本方法,一种是从正多边形开始,然后稍微随机化一点(旋转一点),然后迭代其余部分以维持段size=1

第二个是以完全随机的开链(如在MBo答案中)开始,然后迭代地改变角度,直到最后一个点与第一个点相距所需的距离。我认为第二种方法比较简单......

如果你想要更复杂的东西,那么你可以生成M个随机点并将它们作为闭合的 Bezier 曲线立方体补丁循环控制点处理。然后只需找到N等距点(这是一项艰巨的任务)并重新调整整个事物以匹配段行大小= 1

如果你想尝试第一种方法,那么

  1. 常规多边形开始(闭环)

    从正多边形(圆上的等距点)开始。因此,将圆圈划分为N个角度段。选择半径r,使行长度匹配l=1

    start

    所以r=0.5/cos(pi/N) ...来自半角三角

  2. 使功能通过一个小步骤旋转i-th

    因此,只需将i-th点围绕(i-1)th点旋转半径1,然后迭代更改{i + 1,... N}点以匹配线段尺寸

  3. 您可以利用对称来避免子弹#2

    但这对于小N而言不会导致非常随机的结果。只需对随机点p(i)的2个触摸段进行反向旋转,然后循环多次。

    symmetry

    使它更随机你可以在整个部分(两个随机点之间)而不是仅仅在2行上应用对称性

  4. 第二种方法是这样的:

    1. 创建随机开放链(就像在MBo的回答中一样)

      因此所有细分受众群已经使用size=1.0。还要记住角度而不仅仅是位置

    2. i - 点迭代

      为简单起见,请将这些点称为p1,p2,...pn

      1. compute d0=||pn-p1|-1.0|
      2. 通过一些小的pi角度步骤
      3. 向左旋转da
      4. compute dl=||pn-p1|-1.0|
      5. pi转到2.0*da
      6. compute dr=||pn-p1|-1.0|
      7. 将点pi旋转到原始位置...左侧da
      8. 现在选择方向更接近解决方案(min dl,dr,d0)所以:

        • 如果d0最小,则根本不改变此点并停止
        • 如果dl最小,则dadl降低时向左旋转
        • 如果dr最小,则在da降低时向右旋转dr
      9. <强>溶液

        循环子弹#2 d=||pn-p0|-1.0|正在降低,然后将da更改为da*=0.1并再次循环播放。如果da步骤太小或在循环迭代后d没有变化,请停止。

      10. <强> [注释]

        Booth解决方案不准确您的距离非常接近1.0但可能+/-某些错误取决于最后da步长。如果您旋转点pi,则只需将/ sub角度添加到所有pi,pi+1,pi+2,..pn

答案 1 :(得分:0)

编辑:这不是答案,没有考虑到亲密度。

众所周知,Cos(Fi)^2 + Sin(Fi)^2 = 1对于任何角度Fi

所以你可以使用下一个方法:

P[0].X = 0
P[0].Y = 0
for i = 1 .. N - 1:
  RandomAngle = 2 * Pi * Random(0..1)
  P[i].X = P[i-1].X + Cos(RandomAngle)
  P[i].Y = P[i-1].Y + Sin(RandomAngle)