将网格拆分为随机大小的矩形

时间:2011-09-04 02:28:01

标签: ruby algorithm geometry sinatra

我有一个500 x 400像素的正方形,里面有一个100像素的网格。现在我想用较小的随机大小的正方形填充该正方形,该正方形与网格对齐。这意味着较小的正方形可以是100,200,300或400像素。它们的大小和位置需要是随机的,因此每次运行时输出都会有所不同。

此图像显示了大正方形,网格和可能的输出以及我正在尝试创建的较小正方形。

Image Test

我在Ruby / Sinatra中使用DIV生成了这个,但我想这个问题对于使用的实际算法更为通用。

有关如何使用最少的代码执行此操作的任何建议吗?

2 个答案:

答案 0 :(得分:1)

你可以采用一种简单的递归方法,产生一个相当好的随机分布,如下所示:作为基本情况,任何100x100的网格都必须填充100x100的正方形。否则,如果网格对于某些小到足以容纳正方形的n为n x n,则可以选择使用该大小的正方形来平铺它。否则,选择不是100的矩形的某一侧,选择一个100的倍数的随机位置,然后将其分成两半并递归地平铺两半。

这种方法的主要优点是你永远不必跟踪你把旧矩形放在哪里以避免撞击它们。您始终使用空矩形并以确保区域永远不会重叠的方式递归地细分问题。

这可能并不总能给出好的结果,但编码非常简单(我假设可能总共有15到25行代码)并且可以轻松调整以改变输出。

希望这有帮助!

答案 1 :(得分:1)

这个方法需要很多代码,但我想我会做的是使用Donald Knuth的Dancing Links算法(DLX)(或其他一些算法)来查找 all 正方形的可能安排。您可以提前计算安排,然后您可以在需要时快速/随机选择一个。

你可以在这里阅读他关于算法及其对pentominoes(与你的问题非常相似)的应用的论文:

http://www-cs-faculty.stanford.edu/~uno/papers/dancing-color.ps.gz

http://en.wikipedia.org/wiki/Dancing_Links