/// <summary>
        /// Looks for the child that gets activated for the given value.
        /// </summary>
        /// <param name="value">The value to find the fitting child for.</param>
        /// <param name="child">Outputs the child if one was found, else null.</param>
        /// <exception cref="ArgumentException">Thrown if the given value is not a legal value for the node.</exception>
        /// <returns>Whether the child was found.</returns>
        public bool TryGetChild(object value, out IParameterTreeNode child)
        {
            // Check given value's type.
            if (!(value is T))
            {
                throw new ArgumentException(
                          $"Tried to get child of {typeof(T)} OR node for a value of type {value.GetType()}");
            }

            // If correct type, check if value is legal and throw an exception if it isn't.
            var typedValue = (T)value;

            this.ThrowIfIllegal(typedValue);

            // Correct type & legal value --> set child and return.
            return(this._children.TryGetValue(typedValue, out child));
        }
Beispiel #2
0
        public void ChildrenAreReturnedCorrectly()
        {
            // Add several children...
            var children     = new List <IParameterTreeNode>();
            var domainValues = OrNodeTest.Domain.PossibleValues;

            for (int i = 0; i < domainValues.Count; i++)
            {
                IParameterTreeNode child = OrNodeTest.CreateNode(domainValues[i] + "_child");
                children.Add(child);
                this._decisionNode.AddChild(domainValues[i], child);
            }

            // ..and compare them with the returned set when querying for the node's children.
            Assert.True(
                TestUtils.SetsAreEquivalent(children, this._decisionNode.Children),
                $"Added children {TestUtils.PrintList(children)}, but return value was {TestUtils.PrintList(this._decisionNode.Children)}");
        }
Beispiel #3
0
        public void ChildrenAreReturnedCorrectly()
        {
            var andNode = new AndNode();

            // Add several children...
            var childIdentifiers = new List <string> {
                "a", "b", "c", "d"
            };
            var children = new List <IParameterTreeNode>();

            for (int i = 0; i < childIdentifiers.Count; i++)
            {
                IParameterTreeNode child = AndNodeTest.CreateNode(childIdentifiers[i]);
                children.Add(child);
                andNode.AddChild(child);
            }

            // ..and compare them with the returned set when querying for the node's children.
            Assert.True(
                TestUtils.SetsAreEquivalent(children, andNode.Children),
                $"Added children {TestUtils.PrintList(children)}, but return value was {TestUtils.PrintList(andNode.Children)}");
        }
 /// <summary>
 /// Sets the node's child. Overwrites it if it was already set.
 /// </summary>
 /// <param name="child">The child.</param>
 public void SetChild(IParameterTreeNode child)
 {
     this._child = child;
 }
        /// <summary>
        /// Sets the value for the specified gene on the given child,
        /// respecting its parents and the latest parameter origin.
        /// </summary>
        /// <param name="node">
        /// Specifies the gene to set the value for.
        /// Is allowed to be an <see cref="AndNode" />. In this case, nothing happens.
        /// </param>
        /// <param name="parent1">The first parent.</param>
        /// <param name="parent2">The second parent.</param>
        /// <param name="child">The child. Genome will be modified.</param>
        /// <param name="lastParameterOrigin">
        /// The latest parameter origin.
        /// Influences the probability which parent's gene the child inherits.
        /// </param>
        /// <returns>
        /// The origin of the inherited gene value.
        /// For an <see cref="AndNode" />, returns the given parameter origin.
        /// </returns>
        private ParameterOrigin SetGeneValue(
            IParameterTreeNode node,
            Genome parent1,
            Genome parent2,
            Genome child,
            ParameterOrigin lastParameterOrigin = ParameterOrigin.Open)
        {
            // If the node is not a parameter node, we do not have to set a value.
            // The parameter origin does not change.
            var nodeAsParameter = node as IParameterNode;

            if (nodeAsParameter == null)
            {
                return(lastParameterOrigin);
            }

            // If it is a parameter node, find the parents' gene values.
            var parameterName    = nodeAsParameter.Identifier;
            var parent1GeneValue = parent1.GetGeneValue(parameterName);
            var parent2GeneValue = parent2.GetGeneValue(parameterName);

            // If they are equal and the last parameter's origin is open, set child's parameter value to it
            // and keep the origin.
            if (lastParameterOrigin == ParameterOrigin.Open && object.Equals(parent1GeneValue, parent2GeneValue))
            {
                child.SetGene(parameterName, parent1GeneValue);
                return(lastParameterOrigin);
            }

            // Otherwise, randomly decide on one of the two parents.
            // The probability for the parents is dependent on the last parameter's origin.
            double probabilityForFirstParent;

            switch (lastParameterOrigin)
            {
            case ParameterOrigin.FirstParent:
                probabilityForFirstParent = 1 - this._crossoverSwitchProbability;
                break;

            case ParameterOrigin.SecondParent:
                probabilityForFirstParent = this._crossoverSwitchProbability;
                break;

            case ParameterOrigin.Open:
                probabilityForFirstParent = 0.5;
                break;

            default:
                throw new ArgumentException($"Parameter origin {lastParameterOrigin} is unknown.");
            }

            // Throw a (biased) coin and decide on one parent to inherit the gene value from.
            var useFirstParent = Randomizer.Instance.Decide(probabilityForFirstParent);

            if (useFirstParent)
            {
                child.SetGene(parameterName, parent1GeneValue);
                return(ParameterOrigin.FirstParent);
            }

            child.SetGene(parameterName, parent2GeneValue);
            return(ParameterOrigin.SecondParent);
        }
Beispiel #6
0
 /// <summary>
 /// Initializes a new instance of the <see cref="ParameterTree" /> class.
 /// </summary>
 /// <param name="root">The tree's root.</param>
 public ParameterTree(IParameterTreeNode root)
 {
     this.Root = root;
     this.ReplacedParameterFilter = new ReplacedParameterFilter();
 }
 /// <summary>
 /// Adds child for the specified value.
 /// </summary>
 /// <param name="value">Value from the domain.</param>
 /// <param name="child">The child to add.</param>
 /// <exception cref="ArgumentException">
 /// Thrown if the value is not from the domain or
 /// another child was already added for the value.
 /// </exception>
 public void AddChild(T value, IParameterTreeNode child)
 {
     this.ThrowIfIllegal(value);
     this._children.Add(value, child);
 }
Beispiel #8
0
 /// <summary>
 /// Adds a child.
 /// </summary>
 /// <param name="node">The child to add.</param>
 public void AddChild(IParameterTreeNode node)
 {
     this._children.Add(node);
 }
 /// <summary>
 /// Returns whether the given <see cref="IParameterTreeNode"/> represents the parameter described by the given
 /// identifier.
 /// </summary>
 /// <param name="node">The node to check.</param>
 /// <param name="identifier">The identifier to check for.</param>
 /// <returns>True if and only if the node is an <see cref="IParameterNode"/> with identifier equal to the given
 /// one.
 /// </returns>
 public static bool RepresentsParameter(IParameterTreeNode node, string identifier)
 {
     return(node is IParameterNode parameterNode && parameterNode.Identifier == identifier);
 }