package ec.gp.push;
import ec.*;
import ec.gp.*;
import ec.util.*;
import java.util.*;

/* 
 * PushBuilder.java
 * 
 * Created: Fri Feb 15 23:00:04 EST 2013
 * By: Sean Luke
 */
 
/**
 *
 * PushBuilder implements the Push-style tree building algorithm, which permits nonterminals of arbitrary arity.
 * This algorithm is as follows:

 

 BUILD-TREE(size)
 If size == 1, return a terminal
 Else
 .... Make a parent nonterminal p
 .... while (size > 0)
 .... .... a <- random number from 1 to size
 .... .... size <- size - a
 .... .... c <- BUILD-TREE(a)
 .... .... Add c as a child of p
 shuffle order of children of p
 return p
 

You must specify a size distribution for PushBuilder.

Default Base
gp.push.builder * @author Sean Luke * @version 1.0 */ public class PushBuilder extends GPNodeBuilder { public static final String P_PUSHBUILDER = "builder"; public Parameter defaultBase() { return PushDefaults.base().push(P_PUSHBUILDER); } public void setup(final EvolutionState state, final Parameter base) { super.setup(state,base); Parameter def = defaultBase(); // we use size distributions -- did the user specify any? if (!canPick()) state.output.fatal("PushBuilder needs a distribution of tree sizes to pick from. You can do this by either setting a distribution (with " + P_NUMSIZES + ") or with " + P_MINSIZE + " and " + P_MAXSIZE + ".", base, def); } // shuffles the children of the node, if any, and returns the node public GPNode[] shuffle(GPNode[] objs, EvolutionState state, int thread) { int numObjs = objs.length; MersenneTwisterFast random = state.random[thread]; GPNode obj; int rand; for(int x=numObjs-1; x >= 1 ; x--) { rand = random.nextInt(x+1); obj = objs[x]; objs[x] = objs[rand]; objs[rand] = obj; } return objs; } GPNode[] dummy = new GPNode[0]; public GPNode newRootedTree(final EvolutionState state, final GPType type, final int thread, final GPNodeParent parent, final GPFunctionSet set, final int argposition, int requestedSize) { int t = type.type; GPNode[] terminals = set.terminals[t]; GPNode[] nonterminals = set.nonterminals[t]; if (requestedSize == NOSIZEGIVEN) requestedSize = pickSize(state,thread); GPNode n = null; if (requestedSize == 1) { // pick a random terminal n = (GPNode)(terminals[state.random[thread].nextInt(terminals.length)].lightClone()); } else { n = (GPNode)(nonterminals[state.random[thread].nextInt(nonterminals.length)].lightClone()); // it's always going to be the Dummy // do decomposition byte pos = 0; // THIS WILL HAVE TO BE MODIFIED TO AN INT LATER ON AND THIS WILL AFFECT ARGPOSITIONS!!! ArrayList list = new ArrayList(); // dunno if this is too expensive while(requestedSize >= 1) { int amount = state.random[thread].nextInt(requestedSize) + 1; requestedSize -= amount; GPNode f = newRootedTree(state, type, thread, parent, set, pos, amount); list.add(f); } // shuffle and reassign argument position n.children = (GPNode[])(list.toArray(dummy)); n.children = shuffle(n.children, state, thread); for(int i = 0; i < n.children.length; i++) n.children[i].argposition = (byte) i; } n.resetNode(state,thread); // give ERCs a chance to randomize n.argposition = (byte)argposition; n.parent = parent; return n; } }

Ads help maintain this website.