001 /*
002 * Java Genetic Algorithm Library (jenetics-1.6.0).
003 * Copyright (c) 2007-2014 Franz Wilhelmstötter
004 *
005 * Licensed under the Apache License, Version 2.0 (the "License");
006 * you may not use this file except in compliance with the License.
007 * You may obtain a copy of the License at
008 *
009 * http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 *
017 * Author:
018 * Franz Wilhelmstötter (franz.wilhelmstoetter@gmx.at)
019 */
020 package org.jenetics;
021
022 import org.jenetics.util.Function;
023 import org.jenetics.util.StaticObject;
024
025 /**
026 * Some default GA termination strategies.
027 *
028 * @author <a href="mailto:franz.wilhelmstoetter@gmx.at">Franz Wilhelmstötter</a>
029 * @since 1.0
030 * @version 1.0 — <em>$Date: 2014-02-14 $</em>
031 */
032 public final class termination extends StaticObject {
033 private termination() {}
034
035 static class SteadyFitness<C extends Comparable<? super C>>
036 implements Function<Statistics<?, C>, Boolean>
037 {
038 private final int _generations;
039
040 private C _fitness;
041 private int _stableGenerations = 0;
042
043 public SteadyFitness(final int generations) {
044 _generations = generations;
045 }
046
047 @Override
048 public Boolean apply(final Statistics<?, C> statistics) {
049 boolean proceed = true;
050
051 if (_fitness == null) {
052 _fitness = statistics.getBestFitness();
053 _stableGenerations = 1;
054 } else {
055 final Optimize opt = statistics.getOptimize();
056 if (opt.compare(_fitness, statistics.getBestFitness()) >= 0) {
057 proceed = ++_stableGenerations <= _generations;
058 } else {
059 _fitness = statistics.getBestFitness();
060 _stableGenerations = 1;
061 }
062 }
063
064 return proceed ? Boolean.TRUE : Boolean.FALSE;
065 }
066 }
067
068 /**
069 * Create a <i>terminator</i> which returns {@code false} if the fitness
070 * hasn't improved for a given number of generations.
071 *
072 * @param <C> the fitness type.
073 * @param generation the number of generations the fitness don't have been
074 * improved.
075 * @return the GA terminator.
076 */
077 public static <C extends Comparable<? super C>>
078 Function<Statistics<?, C>, Boolean> SteadyFitness(final int generation) {
079 return new SteadyFitness<>(generation);
080 }
081
082 static class Generation implements Function<Statistics<?, ?>, Boolean> {
083 private final int _generation;
084
085 public Generation(final int generation) {
086 _generation = generation;
087 }
088
089 @Override
090 public Boolean apply(final Statistics<?, ?> statistics) {
091 return statistics.getGeneration() < _generation ?
092 Boolean.TRUE :
093 Boolean.FALSE;
094 }
095 }
096
097 /**
098 * Return a <i>termination predicate</i> which returns {@code false} if the
099 * current GA generation is {@code >=} as the given {@code generation}.
100 *
101 * [code]
102 * final GeneticAlgorithm<DoubleGene, Double> ga = ...
103 * ga.evolve(termination.Generation(100));
104 * [/code]
105 *
106 * @param generation the maximal GA generation.
107 * @return the termination predicate.
108 */
109 public static Function<Statistics<?, ?>, Boolean>
110 Generation(final int generation) {
111 return new Generation(generation);
112 }
113
114 }
|