遗传算法 - 对人员进行分组:仅查找包含标准X,Y和Z的解决方案

时间:2013-07-05 12:13:13

标签: java algorithm sorting genetic-algorithm

我正在尝试解决以下问题:

  • 我有一个30人的名单。
  • 这些人需要分成6组。
  • 每个人都给出了其他3个人的名字。

我想过用遗传算法解决这个问题。 健身功能可以评估所有组,并根据每个房间有多少人满足他们的所有偏好来分配健身分数。 (或类似的评分系统)

实施例: 产生的解决方案之一是:1,3,19,5,22,2,7,8,11,12,13,14,15,13,​​17 ......等 我假设前5个人在第一组中,接下来的5个在下一组中,并从中计算出适合度值。

我认为这个解决方案可行 - 有没有人看到更好的方法呢?

我的主要问题是: 如果我想确保人A和B肯定在同一组中,我可以实现健身功能来检查这一点,如果不满足这个条件就分配一个糟糕的健身。这是最好的方法吗?这看起来效率很低。 有没有办法'锁定'解决方案的某些部分(“某些基因”),只是解决或其余部分?

任何帮助或见解将不胜感激。

提前致谢。 AK

4 个答案:

答案 0 :(得分:0)

只是澄清一点,你的问题不是遗传编程,而是遗传算法,这是两个不同的事情。遗传编程是关于生成(使用进化算法)可执行个体,这些个体将生成您的解决方案,而遗传算法个体直接代表您的解决方案。

话虽如此,你的两个假设是纠正。数据表示通常是进化算法的关键元素,不良表示可能会妨碍有效的解空间探索。您当前的数据表示对我来说似乎是正确的,因为组只允许有5个人。你对执行某些标准的方法的第二个想法也是正确的。如果无穷大(如果你的图书馆/语言容易使用),那么在文献中表达无效解决方案的首选方法就是设置一个较大的适应值(最好是一个不能代表潜在有效的即使是坏的解决方案)。与简单删除无效个体相比,这有许多优点:在选择阶段,不会选择坏人,因此他们所代表的解决方案空间不会像有趣的那样被探索,这在计算上是好的,因为它肯定不会包含最佳解决方案毕竟,了解解决方案是不好的知识。同时,遗传多样性在进化算法中非常重要,以避免停滞。为了探索当前代表区域之间的解空间,至少应保留一些不良个体以保持遗传多样性。

遗传算法的目标是计算不可能或难以通过分析或蛮力计算的解决方案。试图用启发式方法动态锁定一些基因需要了解你的问题的内在工作以及潜在的进化机制,并且会破坏使用进化算法的目的。进化算法的有效目标是来锁定似乎正确的基​​因。

事实上,如果您先验绝对肯定某些特定基因必须具有给定值,请不要在您的个体中代表它们。例如,如果您确定其他2个人必须具有某个给定值,则让您的第一组3个人长。然后,您可以对评估函数进行编码,就像第一组中有5个人一样,但不会进化/搜索以替换2个固定的个体。

答案 1 :(得分:0)

你的交叉操作是什么样的?你在描述中列出的方式,我不确定你是如何干净地实现它的。例如,如果您有两个解决方案:

1,2,3,4,5,.....,30

1,2,30,29,......,10

假设您正在使用单点交叉功能,您将有可能为同一个人和其他未使用上述基因组分配的人分配多个分配。

我将拥有一个包含30个值的基因组,其中每个值定义一个人的组分配(1-6)。它看起来像656324113255632 ....等。因此,人员1被分配了组6,人员2组5等。这将使交叉操作更容易实现,因为您不必确保在交叉之后每个新解决方案都是有效的分配,无论它是否是最佳的。

适应度函数将为不具有适当数量的成员的每个组分配惩罚(5),并且对于次优的组成员分配额外处罚。我会使第一个惩罚明显大于第二个,然后调整这些以获得你想要的结果。

答案 2 :(得分:0)

这可以建模为广义二次分配问题(GQAP)。该问题允许指定需要一定容量的多个设备(人),提供容量的多个位置(组)和指定设备与指定位置之间距离的距离矩阵之间的接近度的权重矩阵。此外,还有安装成本,但这些不是您的问题所必需的。我在HeuristicLab中实现了这个问题。它不是主干的一部分,但如果你感兴趣(或者你自己编译),我可以发送你的插件。

答案 3 :(得分:0)

对于这个问题,使用遗传算法最具挑战性的部分似乎是实现交叉。我就是这样做的:

首先选择一个常数,C。C将在所有世代保持不变,我将在一瞬间解释它的目的。

我将使用一个比5组6更小的例子来演示这种交叉,但前提是相同的。假设我们有2个父母,每个父母由3组3组成。让我们做一个[[1,2,3],[4,5,6],[7,8,9]],另一个[[9, 4,3],[5,7,8],[6,1,2]。

  1. 列出可能的数字(1到总人数),在这种情况下它只是[1,2,3,4,5,6,7,8,9]。从列表中删除1个随机数。假设我们删除2.该列表变为[1,3,4,5,6,7,8,9]

  2. 我们为每个剩余数字分配一个概率。概率从1开始,并且与父母的任何匹配上升C。例如,在父级1,3和2属于同一组,因此3将具有1 + C的概率。与6相同,因为它在父2中形成匹配.1将具有1 + 2C的概率,因为它在父母的同一组中为2。根据这些概率,使用轮盘赌类型选择。假设我们选择6。

  3. 现在,我们在同一组中有2个和6个。我们同样寻找与这些数字匹配并创造概率。对于每个父级,如果它仅匹配2或仅匹配6,则添加C,如果匹配,则添加2C。继续这个直到小组完成(对于3x3这是最后一个选择,但对于5x6,还会有一些选择)

    4.选择一个尚未被选中的新随机数,并继续其他组

  4. 这种交叉的好处之一是它基本上已经包含了突变。对于没有归入父母的人群,可能会有内在的机会

    信用:I adapted the idea from the Omicron Genetic Algorithm