2

我想在 Jenetics 中用两个背包实现一个多目标背包问题,但我遇到了一些打字问题。我查看了Jenetics 手册DTLZ1中的问题——据我所知,这是唯一可用的 MOO 示例——并将其映射到类:Problem

public class DTLZ1 implements Problem<double[], DoubleGene, Vec<double[]>> {

    // Constants...

    public static void main(String[] args) {
        // Engine setup and evolution stream execution...
    }

    @Override
    public Function<double[], Vec<double[]>> fitness() {
        // Original fitness function...
    }

    @Override
    public Codec<double[], DoubleGene> codec() {
        // Original codec...
    }

}

我之前使用以下类型签名(转换为 Java)在 Scala 中实现了单目标背包问题:

Problem<ISeq<BitGene>, BitGene, Integer>

在哪里:

  • <ISeq<BitGene>:作为(不可变的)位序列的背包。
  • BitGene:进化引擎的基因类型。
  • Integer:背包的适应度,即它的利润。

使用两个背包,我想到了类似的东西(基于DTLZ1示例):

Problem<ISeq<BitGene>[], BitGene, Vec<int[]>>

在哪里:

  • ISeq<BitGene>[]:多个背包作为(不可变的)位序列,包装在一个数组中。
  • BitGene:进化引擎的基因类型(同上)。
  • int[]:背包的适应度,即它们的利润。

除了ISeq<BitGene>[],这需要一些时间来适应(我也可以使用List或类似的东西吗?),我不知道如何创建一个合适的编解码器:

@Override
public Codec<ISeq<BitGene>[], BitGene> codec() {
    return Codecs.ofVector(
            () -> {
                // What kind of supplier do I need?
            },
            NUMBER_OF_KNAPSACKS);
}
4

1 回答 1

1

如果我正确理解您的问题,编解码器将如下所示:

public static <T> Codec<ISeq<ISeq<T>>, BitGene>
codec(final ISeq<? extends T> items, final int knapsackCount) {
    return Codec.of(
        Genotype.of(
            BitChromosome.of(items.length()).instances()
                .limit(knapsackCount)
                .collect(ISeq.toISeq())
        ),
        gt -> gt.stream()
            .map(ch -> ch.as(BitChromosome.class))
            .map(ch -> ch.ones()
                .<T>mapToObj(items)
                .collect(ISeq.toISeq()))
            .collect(ISeq.toISeq())
    );
}

ISeq<T>[]我使用的是,而不是数组,ISeq<ISeq<T>>但第一个序列knapsackCount的大小是 ,嵌套序列的大小是itmes.length()。您的问题的签名将是Problem<ISeq<ISeq<T>>, BitGene, Vec<double[]>>.

于 2018-11-16T17:29:32.370 回答