001    package org.jaga.selection;
002    
003    
004    import java.util.Arrays;
005    import org.jaga.definitions.*;
006    
007    /**
008     * TODO: Complete these comments.
009     *
010     * <p><u>Project:</u> JAGA - Java API for Genetic Algorithms.</p>
011     *
012     * <p><u>Company:</u> University College London and JAGA.Org
013     *    (<a href="http://www.jaga.org" target="_blank">http://www.jaga.org</a>).
014     * </p>
015     *
016     * <p><u>Copyright:</u> (c) 2004 by G. Paperin.<br/>
017     *    This program is free software; you can redistribute it and/or modify
018     *    it under the terms of the GNU General Public License as published by
019     *    the Free Software Foundation, ONLY if you include a note of the original
020     *    author(s) in any redistributed/modified copy.<br/>
021     *    This program is distributed in the hope that it will be useful,
022     *    but WITHOUT ANY WARRANTY; without even the implied warranty of
023     *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
024     *    GNU General Public License for more details.<br/>
025     *    You should have received a copy of the GNU General Public License
026     *    along with this program; if not, write to the Free Software
027     *    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
028     *    or see http://www.gnu.org/licenses/gpl.html</p>
029     *
030     * @author Greg Paperin (greg@jaga.org)
031     *
032     * @version JAGA public release 1.0 beta
033     */
034    
035    public class TournamentSelection implements SelectionAlgorithm {
036    
037            private static final Class applicableFitnessClass = AbsoluteFitness.class;
038    
039            private int competitorsNum = 2;
040            private double betterCandidateProbability = 0.7;
041    
042            public TournamentSelection() {
043            }
044    
045            public TournamentSelection(int oneOutOf, double betterCandProb) {
046                    setCompetitors(oneOutOf);
047            }
048    
049            public int getCompetitiors() {
050                    return this.competitorsNum;
051            }
052    
053            public void setCompetitors(int oneOutOf) {
054                    if (oneOutOf < 1)
055                            throw new IllegalArgumentException("Tournament must include at least 1 competitor");
056                    this.competitorsNum = oneOutOf;
057            }
058    
059            public double getBetterCandidateProbability() {
060                    return this.betterCandidateProbability;
061            }
062    
063            public void setBetterCandidateProbability(double betterCandProb) {
064                    if (betterCandProb < 0 || 1 < betterCandProb)
065                            throw new IllegalArgumentException("Better candidate selection "
066                                                                                               + "probability must be in [0, 1]");
067                    this.betterCandidateProbability = betterCandProb;
068            }
069    
070            public Class getApplicableFitnessClass() {
071                    return applicableFitnessClass;
072            }
073    
074            public Individual select(Population population, int age, GAParameterSet params) {
075                    RandomGenerator rnd = params.getRandomGenerator();
076                    int popSize = population.getSize();
077                    Individual [] competitors = new Individual[competitorsNum];
078                    for (int i = 0; i < competitorsNum; i++) {
079                            int p = rnd.nextInt(0, popSize);
080                            competitors[i] = population.getMember(p);
081                    }
082                    Arrays.sort(competitors, new AbsoluteFitnessIndividualComparator());
083    
084                    int ci = competitorsNum - 1;
085                    for (; ; ) {
086                            double dice = rnd.nextDouble();
087                            if (dice < betterCandidateProbability)
088                                    return competitors[ci];
089                            if(--ci < 0)
090                                    ci = competitorsNum - 1;
091                    }
092            }
093    
094            public Individual[] select(Population population, int howMany, int age, GAParameterSet params) {
095                    Individual [] selection = new Individual[howMany];
096                    for (int i = 0; i < howMany; i++) {
097                            selection[i] = select(population, age, params);
098                    }
099                    return selection;
100            }
101    
102    }