Free cookie consent management tool by TermsFeed Policy Generator

source: branches/2895_PushGP_GenealogyAnalysis/HeuristicLab.Problems.ProgramSynthesis/Push/Data/Tree/TreeExtensions.cs @ 17709

Last change on this file since 17709 was 15771, checked in by bburlacu, 7 years ago

#2895: Add solution skeleton for PushGP with genealogy analysis.

File size: 2.8 KB
Line 
1using System;
2using System.Collections.Generic;
3
4namespace HeuristicLab.Problems.ProgramSynthesis {
5  using System.Linq;
6
7  public static class TreeExtensions {
8    private static readonly Expression ExecNoop = ExpressionTable.GetStatelessExpression<ExecNoopExpression>();
9    private static readonly Expression CodeNoop = ExpressionTable.GetStatelessExpression<CodeNoopExpression>();
10
11    public static TreeNode<T> ToTree<T>(
12      this IEnumerable<T> items,
13      Predicate<T> isChild,
14      Func<T, IReadOnlyList<T>> childrenResolver) {
15      var tree = new TreeNode<T>();
16
17      foreach (var item in items) {
18        if (isChild(item)) {
19          var subNode = childrenResolver(item).ToTree(isChild, childrenResolver);
20          subNode.Value = item;
21          tree.AddNode(subNode);
22        } else {
23          tree.Add(item);
24        }
25      }
26
27      return tree;
28    }
29
30    public static IEnumerable<TreeNode<T>> DepthLast<T>(this TreeNode<T> node) {
31      foreach (var child in node.Children) {
32        if (child.Children.Count > 0) {
33          foreach (var subChild in child.DepthLast()) {
34            yield return subChild;
35          }
36        } else yield return child;
37      }
38
39      yield return node;
40    }
41
42    public static IEnumerable<T> DepthLast<T>(this TreeNode<T> node, Func<IEnumerable<T>, T> resolveParent) {
43      foreach (var child in node.Children) {
44        if (child.Children.Count > 0) {
45          var subExpressions = child.DepthLast(resolveParent);
46          yield return resolveParent(subExpressions);
47        } else yield return child.Value;
48      }
49    }
50
51    public static PushProgram ToPushProgramWithoutNoopExpressions(this TreeNode<Expression> tree) {
52      return ToPushProgram(tree, e => !ReferenceEquals(e, ExecNoop) && !ReferenceEquals(e, CodeNoop));
53    }
54
55    public static PushProgram ToPushProgram(this TreeNode<Expression> tree, Func<Expression, bool> condition = null) {
56      // wrap into program as depthlast expects that tree represents program and not a single expression
57      if (tree.Count == 1) {
58        var tmp = tree;
59        tree = new TreeNode<Expression>();
60        tree.AddNode(tmp);
61      }
62
63      var expressions = tree.DepthLast(e => ResolveProgram(e, condition));
64
65      return ResolveProgram(expressions, condition);
66    }
67
68    public static TreeNode<Expression> ToTree(this PushProgram program) {
69      var tree = program.Expressions.ToTree(e => e.IsProgram, e => ((PushProgram)e).Expressions);
70      tree.Value = program;
71
72      return tree;
73    }
74
75    private static PushProgram ResolveProgram(IEnumerable<Expression> expressions, Func<Expression, bool> condition = null) {
76
77      if (condition != null) {
78        expressions = expressions.Where(condition);
79      }
80
81      return new PushProgram(expressions.ToList());
82    }
83  }
84
85}
Note: See TracBrowser for help on using the repository browser.