Free cookie consent management tool by TermsFeed Policy Generator

source: branches/OKBJavaConnector/ECJClient/src/ec/Individual.java @ 12147

Last change on this file since 12147 was 6152, checked in by bfarka, 14 years ago

added ecj and custom statistics to communicate with the okb services #1441

File size: 18.5 KB
Line 
1/*
2  Copyright 2006 by Sean Luke
3  Licensed under the Academic Free License version 3.0
4  See the file "LICENSE" for more information
5*/
6
7
8package ec;
9import ec.util.Parameter;
10import java.io.*;
11import ec.util.*;
12
13/*
14 * Individual.java
15 * Created: Tue Aug 10 19:58:13 1999
16 */
17
18/**
19 * An Individual is an item in the EC population stew which is evaluated
20 * and assigned a fitness which determines its likelihood of selection.
21 * Individuals are created most commonly by the newIndividual(...) method
22 * of the ec.Species class.
23 *
24 * <P>In general Individuals are immutable.  That is, once they are created
25 * their genetic material should not be modified.  This protocol helps insure that they are
26 * safe to read under multithreaded conditions.  You can violate this protocol,
27 * but try to do so when you know you have only have a single thread.
28 *
29 * <p>In addition to serialization for checkpointing, Individuals may read and write themselves to streams in three ways.
30 *
31 * <ul>
32 * <li><b>writeIndividual(...,DataOutput)/readIndividual(...,DataInput)</b>&nbsp;&nbsp;&nbsp;This method
33 * transmits or receives an individual in binary.  It is the most efficient approach to sending
34 * individuals over networks, etc.  These methods write the evaluated flag and the fitness, then
35 * call <b>readGenotype/writeGenotype</b>, which you must implement to write those parts of your
36 * Individual special to your functions-- the default versions of readGenotype/writeGenotype throw errors.
37 * You don't need to implement them if you don't plan on using read/writeIndividual.
38 *
39 * <li><b>printIndividual(...,PrintWriter)/readIndividual(...,LineNumberReader)</b>&nbsp;&nbsp;&nbsp;This
40 * approach transmits or receives an indivdual in text encoded such that the individual is largely readable
41 * by humans but can be read back in 100% by ECJ as well.  To do this, these methods will encode numbers
42 * using the <tt>ec.util.Code</tt> class.  These methods are mostly used to write out populations to
43 * files for inspection, slight modification, then reading back in later on.  <b>readIndividual</b>reads
44 * in the fitness and the evaluation flag, then calls <b>parseGenotype</b> to read in the remaining individual.
45 * You are responsible for implementing parseGenotype: the Code class is there to help you.
46 * <b>printIndividual</b> writes out the fitness and evaluation flag, then calls <b>genotypeToString<b>
47 * and printlns the resultant string. You are responsible for implementing the genotypeToString method in such
48 * a way that parseGenotype can read back in the individual println'd with genotypeToString.  The default form
49 * of genotypeToString simply calls <b>toString</b>, which you may override instead if you like.  The default
50 * form of <b>parseGenotype</b> throws an error.  You are not required to implement these methods, but without
51 * them you will not be able to write individuals to files in a simultaneously computer- and human-readable fashion.
52 *
53 * <li><b>printIndividualForHumans(...,PrintWriter)</b>&nbsp;&nbsp;&nbsp;This
54 * approach prints an individual in a fashion intended for human consumption only.
55 * <b>printIndividualForHumans</b> writes out the fitness and evaluation flag, then calls <b>genotypeToStringForHumans<b>
56 * and printlns the resultant string. You are responsible for implementing the genotypeToStringForHumans method.
57 * The default form of genotypeToStringForHumans simply calls <b>toString</b>, which you may override instead if you like
58 * (though note that genotypeToString's default also calls toString).  You should handle one of these methods properly
59 * to ensure individuals can be printed by ECJ.
60 * </ul>
61 *
62 * <p>Since individuals should be largely immutable, why is there a <b>readIndividual</b> method?
63 * after all this method doesn't create a <i>new</i> individual -- it just erases the existing one.  This is
64 * largely historical; but the method is used underneath by the various <b>newIndividual</b> methods in Species,
65 * which <i>do</i> create new individuals read from files.  If you're trying to create a brand new individual
66 * read from a file, look in Species.
67 *
68 * <p> Individuals are Comparable: if you sort Individuals, the FITTER individuals will appear EARLIER in a list or array.
69 *
70 *
71 * @author Sean Luke
72 * @version 1.0
73 */
74
75public abstract class Individual implements Prototype, Comparable
76    {
77    /** A reasonable parameter base element for individuals*/
78    public static final String P_INDIVIDUAL = "individual";
79
80    /** A string appropriate to put in front of whether or not the individual has been printed. */
81    public static final String EVALUATED_PREAMBLE = "Evaluated: ";
82   
83    /** The fitness of the Individual. */
84    public Fitness fitness;
85
86    /** The species of the Individual.*/
87    public Species species;
88   
89    public static int count = 0;
90    /** Has the individual been evaluated and its fitness determined yet? */
91    public boolean evaluated;
92       
93    public int birthday = (count++);
94
95    public Object clone()
96        {
97        try
98            {
99            Individual myobj = (Individual) (super.clone());
100            if (myobj.fitness != null) myobj.fitness = (Fitness)(fitness.clone());
101            return myobj;
102            }
103        catch (CloneNotSupportedException e)
104            { throw new InternalError(); } // never happens
105        }
106
107   
108    /** Returns the "size" of the individual.  This is used for things like
109        parsimony pressure.  The default form of this method returns 0 --
110        if you care about parsimony pressure, you'll need to override the
111        default to provide a more descriptive measure of size. */
112
113    public long size() { return 0; }
114
115    /** Returns true if I am genetically "equal" to ind.  This should
116        mostly be interpreted as saying that we are of the same class
117        and that we hold the same data. It should NOT be a pointer comparison. */
118    public abstract boolean equals(Object ind);
119
120    /** Returns a hashcode for the individual, such that individuals which
121        are equals(...) each other always return the same
122        hash code. */
123    public abstract int hashCode();
124
125    /** This should be used to set up only those things which you share in common
126        with all other individuals in your species; individual-specific items
127        which make you <i>you</i> should be filled in by Species.newIndividual(...),
128        and modified by breeders.
129        @see Prototype#setup(EvolutionState,Parameter)
130    */
131   
132    /** Overridden here because hashCode() is not expected to return the pointer
133        to the object.  toString() normally uses hashCode() to print a unique identifier,
134        and that's no longer the case.   You're welcome to override this anyway you
135        like to make the individual print out in a more lucid fashion. */
136    public String toString()
137        {
138        return "" + this.getClass().getName() + "@" +
139            System.identityHashCode(this) + "{" + hashCode() + "}";
140        }
141       
142    /** Print to a string the genotype of the Individual in a fashion readable by humans, and not intended
143        to be parsed in again.  The fitness and evaluated flag should not be included.  The default form
144        simply calls toString(), but you'll probably want to override this to something else. */
145    public String genotypeToStringForHumans()
146        {
147        return toString();
148        }
149       
150    /** Print to a string the genotype of the Individual in a fashion intended
151        to be parsed in again via parseGenotype(...).
152        The fitness and evaluated flag should not be included.  The default form
153        simply calls toString(), which is almost certainly wrong, and you'll probably want to override
154        this to something else. */
155    public String genotypeToString()
156        {
157        return toString();
158        }
159             
160    public void setup(final EvolutionState state, final Parameter base)
161        {
162        // does nothing by default.
163        // So where is the species set?  The Species does so after it
164        // loads me but before it calls setup on me.
165        }
166
167    /** Should print the individual out in a pleasing way for humans,
168        with a verbosity of Output.V_NO_GENERAL.
169    */
170
171    public void printIndividualForHumans(final EvolutionState state,
172        final int log)
173        {
174        state.output.println(EVALUATED_PREAMBLE + Code.encode(evaluated), log);
175        fitness.printFitnessForHumans(state,log);
176        state.output.println( genotypeToStringForHumans(), log );
177        }
178               
179    /** Should print the individual out in a pleasing way for humans,
180        including its
181        fitness, using state.output.println(...,verbosity,log)
182        You can get fitness to print itself at the appropriate time by calling
183        fitness.printFitnessForHumans(state,log,verbosity);
184               
185        <p>The default form of this method simply prints out whether or not the
186        individual has been evaluated, its fitness, and then calls Individual.genotypeToStringForHumans().
187        Feel free to override this to produce more sophisticated behavior,
188        though it is rare to need to -- instead you could just override genotypeToStringForHumans().
189        @deprecated Verbosity no longer used.
190    */
191
192    public final void printIndividualForHumans(final EvolutionState state,
193        final int log,
194        final int verbosity)
195        {
196        printIndividualForHumans(state, log);
197        }
198
199    /** Should print the individual in a way that can be read by computer,
200        including its fitness, with a verbosity of Output.V_NO_GENERAL.
201    */
202
203    public void printIndividual(final EvolutionState state,
204        final int log)
205        {
206        state.output.println(EVALUATED_PREAMBLE + Code.encode(evaluated), log);
207        fitness.printFitness(state,log);
208        state.output.println( genotypeToString(), log );
209        }
210
211
212    /** Should print the individual in a way that can be read by computer,
213        including its fitness, using state.output.println(...,verbosity,log)
214        You can get fitness to print itself at the appropriate time by calling
215        fitness.printFitness(state,log,verbosity);
216               
217        <p>The default form of this method simply prints out whether or not the
218        individual has been evaluated, its fitness, and then calls Individual.genotypeToString().
219        Feel free to override this to produce more sophisticated behavior,
220        though it is rare to need to -- instead you could just override genotypeToString().
221        @deprecated Verbosity no longer used.
222    */
223
224    public final void printIndividual(final EvolutionState state,
225        final int log,
226        final int verbosity)
227        {
228        printIndividual( state, log,  Output.V_NO_GENERAL);
229        }
230
231    /** Should print the individual in a way that can be read by computer,
232        including its fitness.  You can get fitness to print itself at the
233        appropriate time by calling fitness.printFitness(state,log,writer);
234        Usually you should try to use printIndividual(state,log,verbosity)
235        instead -- use this method only if you can't print through the
236        Output facility for some reason.
237
238        <p>The default form of this method simply prints out whether or not the
239        individual has been evaluated, its fitness, and then calls Individual.genotypeToString().
240        Feel free to override this to produce more sophisticated behavior,
241        though it is rare to need to -- instead you could just override genotypeToString().
242    */
243
244    public void printIndividual(final EvolutionState state,
245        final PrintWriter writer)
246        {
247        writer.println(EVALUATED_PREAMBLE + Code.encode(evaluated));
248        fitness.printFitness(state,writer);
249        writer.println( genotypeToString() );
250        }
251
252    /** Reads in the individual from a form printed by printIndividual(), erasing the previous
253        information stored in this Individual.  If you are trying to <i>create</i> an Individual
254        from information read in from a stream or DataInput,
255        see the various newIndividual() methods in Species. The default form of this method
256        simply reads in evaluation information, then fitness information, and then
257        calls parseGenotype() (which you should implement).  The Species is not changed or
258        attached, so you may need to do that elsewhere.  Feel free to override
259        this method to produce more sophisticated behavior,
260        though it is rare to need to -- instead you could just override parseGenotype(). */
261
262    public void readIndividual(final EvolutionState state,
263        final LineNumberReader reader)
264        throws IOException
265        {
266        evaluated = Code.readBooleanWithPreamble(EVALUATED_PREAMBLE, state, reader);
267       
268        // Next, what's my fitness?
269        fitness.readFitness(state,reader);
270
271        // next, read me in
272        parseGenotype(state, reader);
273        }
274
275    /** This method is used only by the default version of readIndividual(state,reader),
276        and it is intended to be overridden to parse in that part of the individual that
277        was outputted in the genotypeToString() method.  The default version of this method
278        exits the program with an "unimplemented" error.  You'll want to override this method,
279        or to override readIndividual(...) to not use this method. */
280    protected void parseGenotype(final EvolutionState state,
281        final LineNumberReader reader) throws IOException
282        {
283        state.output.fatal("parseGenotype(EvolutionState, LineNumberReader) not implemented in " + this.getClass());
284        }
285       
286    /** Writes the binary form of an individual out to a DataOutput.  This is not for serialization:
287        the object should only write out the data relevant to the object sufficient to rebuild it from a DataInput.
288        The Species will be reattached later, and you should not write it.   The default version of this
289        method writes the evaluated and fitness information, then calls writeGenotype() to write the genotype
290        information.  Feel free to override this method to produce more sophisticated behavior,
291        though it is rare to need to -- instead you could just override writeGenotype().
292    */
293    public void writeIndividual(final EvolutionState state,
294        final DataOutput dataOutput) throws IOException
295        {
296        dataOutput.writeBoolean(evaluated);
297        fitness.writeFitness(state,dataOutput);
298        writeGenotype(state,dataOutput);
299        }
300   
301   
302    /** Writes the genotypic information to a DataOutput.  Largely called by writeIndividual(), and
303        nothing else.  The default simply throws an error.  Various subclasses of Individual override this as
304        appropriate. For example, if your custom individual's genotype consists of an array of
305        integers, you might do this:
306
307        * <pre><tt>
308        * dataOutput.writeInt(integers.length);
309        * for(int x=0;x<integers.length;x++)
310        *     dataOutput.writeInt(integers[x]);
311        * </tt></pre>
312        */
313    public void writeGenotype(final EvolutionState state,
314        final DataOutput dataOutput) throws IOException
315        {
316        state.output.fatal("writeGenotype(EvolutionState, DataOutput) not implemented in " + this.getClass());
317        }
318
319    /** Reads in the genotypic information from a DataInput, erasing the previous genotype
320        of this Individual.  Largely called by readIndividual(), and nothing else. 
321        If you are trying to <i>create</i> an Individual
322        from information read in from a stream or DataInput,
323        see the various newIndividual() methods in Species.
324        The default simply throws an error.  Various subclasses of Individual override this as
325        appropriate.  For example, if your custom individual's genotype consists of an array of
326        integers, you might do this:
327       
328        * <pre><tt>
329        * integers = new int[dataInput.readInt()];
330        * for(int x=0;x<integers.length;x++)
331        *     integers[x] = dataInput.readInt();
332        * </tt></pre>
333        */
334
335    public void readGenotype(final EvolutionState state,
336        final DataInput dataInput) throws IOException
337        {
338        state.output.fatal("readGenotype(EvolutionState, DataOutput) not implemented in " + this.getClass());
339        }
340
341    /** Reads the binary form of an individual from a DataInput, erasing the previous
342        information stored in this Individual.  This is not for serialization:
343        the object should only read in the data written out via printIndividual(state,dataInput). 
344        If you are trying to <i>create</i> an Individual
345        from information read in from a stream or DataInput,
346        see the various newIndividual() methods in Species. The default form of this method
347        simply reads in evaluation information, then fitness information, and then
348        calls readGenotype() (which you will need to override -- its default form simply throws an error).
349        The Species is not changed or attached, so you may need to do that elsewhere.  Feel free to override
350        this method to produce more sophisticated behavior, though it is rare to need to -- instead you could
351        just override readGenotype().
352    */
353    public void readIndividual(final EvolutionState state,
354        final DataInput dataInput) throws IOException
355        {
356        evaluated = dataInput.readBoolean();
357        fitness.readFitness(state,dataInput);
358        readGenotype(state,dataInput);
359        }
360   
361    /** Returns the metric distance to another individual, if such a thing can be measured.
362        Subclassess of Individual should implement this if it exists for their representation.
363        The default implementation here, which isn't very helpful, returns 0 if the individuals are equal
364        and infinity if they are not.
365    */
366
367    public double distanceTo(Individual otherInd)
368        {
369        return (equals(otherInd) ? 0 : Double.POSITIVE_INFINITY);
370        }
371
372    /**
373       Returns -1 if I am BETTER in some way than the other Individual, 1 if the other Individual is BETTER than me,
374       and 0 if we are equivalent.  The default implementation assumes BETTER means FITTER, by simply calling
375       compareTo on the fitnesses themse.ves
376    */
377    public int compareTo(Object o)
378        {
379        Individual other = (Individual) o;
380        return fitness.compareTo(other.fitness);
381        }
382    }
383
Note: See TracBrowser for help on using the repository browser.