Free cookie consent management tool by TermsFeed Policy Generator

source: branches/2895_PushGP_GenealogyAnalysis/HeuristicLab.Problems.ProgramSynthesis/Push/Expressions/ExpressionTable.cs @ 16003

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

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

File size: 9.4 KB
RevLine 
[15771]1using System;
2using System.Collections.Generic;
3using System.Linq;
4
5namespace HeuristicLab.Problems.ProgramSynthesis {
[14727]6
7  public static class ExpressionTable {
[14952]8    public static readonly IReadOnlyDictionary<Type, Expression> StatelessExpressionTable;
9    public static readonly IReadOnlyDictionary<Type, Func<Expression>> StatefulExpressionFactory;
[14875]10    public static readonly IReadOnlyList<string> ExpressionNames;
11    public static readonly int ExpressionCount;
[14727]12
[14875]13    private static readonly Dictionary<int, string> indexToNameTable = new Dictionary<int, string>();
14    private static readonly Dictionary<Type, string> typeToNameTable = new Dictionary<Type, string>();
15    private static readonly Dictionary<string, Type> nameToTypeTable = new Dictionary<string, Type>();
16    private static readonly Dictionary<StackTypes, IList<string>> stackTypeToNamesTable = new Dictionary<StackTypes, IList<string>>();
17    private static readonly Dictionary<StackTypes, IList<string>> stackDependencyToNamesTable = new Dictionary<StackTypes, IList<string>>();
18    private static readonly Dictionary<Type, PushExpressionAttribute> typeToAttributeTable = new Dictionary<Type, PushExpressionAttribute>();
[15273]19    private static readonly List<Expression> inExpressionTable = new List<Expression>();
[14777]20
[14875]21    public static readonly IReadOnlyList<Type> StatelessExpressionTypes;
22    public static readonly IReadOnlyList<Type> StatefulExpressionTypes;
[14727]23
24    static ExpressionTable() {
[15189]25      StatelessExpressionTypes = GetExpressionTypes(typeof(StatelessExpression)).ToList();
26      StatefulExpressionTypes = GetExpressionTypes(typeof(StatefulExpression<>)).ToList();
[14777]27
[14727]28      StatelessExpressionTable = GetStatelessExpressionTable();
[14777]29      StatefulExpressionFactory = GetStatefulExpressionFactory();
[14727]30
[14952]31      ExpressionNames = StatelessExpressionTable.Keys
32        .Concat(StatefulExpressionFactory.Keys)
[15017]33        .Where(t => typeToNameTable.ContainsKey(t))
[14952]34        .Select(type => typeToNameTable[type])
[15189]35        .ToList();
[14952]36
[14875]37      ExpressionCount = StatelessExpressionTable.Count + StatefulExpressionFactory.Count;
[14727]38    }
39
[14875]40    public static IReadOnlyDictionary<int, string> IndexToNameTable { get { return indexToNameTable; } }
41    public static IReadOnlyDictionary<Type, string> TypeToNameTable { get { return typeToNameTable; } }
42    public static IReadOnlyDictionary<string, Type> NameToTypeTable { get { return nameToTypeTable; } }
[15273]43    public static IReadOnlyList<Expression> InExpressionTable { get { return inExpressionTable; } }
[14875]44    public static IReadOnlyDictionary<StackTypes, IList<string>> StackTypeToNamesTable { get { return stackTypeToNamesTable; } }
45    public static IReadOnlyDictionary<StackTypes, IList<string>> StackDependencyToNamesTable { get { return stackDependencyToNamesTable; } }
46    public static IReadOnlyDictionary<Type, PushExpressionAttribute> TypeToAttributeTable { get { return typeToAttributeTable; } }
[14727]47
[14952]48    private static Dictionary<Type, Expression> GetStatelessExpressionTable() {
49      var dictionary = new Dictionary<Type, Expression>();
[14727]50
[14777]51      foreach (var type in StatelessExpressionTypes) {
[14727]52        var expression = Activator.CreateInstance(type) as Expression;
53        var attribute = (PushExpressionAttribute)Attribute.GetCustomAttribute(type, typeof(PushExpressionAttribute));
54
[14875]55        typeToAttributeTable.Add(type, attribute);
[14952]56        dictionary.Add(type, expression);
[15017]57
[15032]58        indexToNameTable.Add(indexToNameTable.Keys.Count, attribute.Name);
59        typeToNameTable.Add(type, attribute.Name);
60        nameToTypeTable.Add(attribute.Name, type);
[14727]61
[15273]62        if (attribute.IsInExpression) {
63          // ReSharper disable once AssignNullToNotNullAttribute
64          // ReSharper disable once PossibleInvalidOperationException
65          inExpressionTable.Insert(attribute.InExpressionNr.Value - 1, expression);
66        }
67
[14875]68        if (!stackTypeToNamesTable.ContainsKey(attribute.StackType)) {
69          stackTypeToNamesTable.Add(attribute.StackType, new List<string>());
[14727]70        }
71
[15032]72        stackTypeToNamesTable[attribute.StackType].Add(attribute.Name);
[14777]73
[14834]74        var dependencies = attribute.StackType | attribute.AdditionalStackDependencies;
[14875]75        if (!stackDependencyToNamesTable.ContainsKey(dependencies)) {
76          stackDependencyToNamesTable.Add(dependencies, new List<string>());
[14777]77        }
78
[15032]79        stackDependencyToNamesTable[dependencies].Add(attribute.Name);
[14727]80      }
81
82      return dictionary;
83    }
84
[14952]85    private static Dictionary<Type, Func<Expression>> GetStatefulExpressionFactory() {
86      var dictionary = new Dictionary<Type, Func<Expression>>();
[14727]87
[14777]88      foreach (var type in StatefulExpressionTypes) {
[14727]89        // Make a NewExpression that calls the ctor
90        var newExp = System.Linq.Expressions.Expression.New(type);
91
92        // Create a lambda with the New expression as body
93        var creator = System.Linq.Expressions.Expression.Lambda<Func<Expression>>(newExp).Compile();
94        var attribute = (PushExpressionAttribute)Attribute.GetCustomAttribute(type, typeof(PushExpressionAttribute));
95
[14875]96        typeToAttributeTable.Add(type, attribute);
[14952]97        dictionary.Add(type, creator);
[15017]98
99        // do not index hidden expressions like push expression in tables
100        if (attribute.IsHidden) continue;
101
[15032]102        indexToNameTable.Add(indexToNameTable.Keys.Count, attribute.Name);
103        typeToNameTable.Add(type, attribute.Name);
104        nameToTypeTable.Add(attribute.Name, type);
[14727]105
[14875]106        if (!stackTypeToNamesTable.ContainsKey(attribute.StackType)) {
107          stackTypeToNamesTable.Add(attribute.StackType, new List<string>());
[14727]108        }
109
[15032]110        stackTypeToNamesTable[attribute.StackType].Add(attribute.Name);
[14777]111
[14834]112        var dependencies = attribute.StackType | attribute.AdditionalStackDependencies;
[14875]113        if (!stackDependencyToNamesTable.ContainsKey(dependencies)) {
114          stackDependencyToNamesTable.Add(dependencies, new List<string>());
[14777]115        }
116
[15032]117        stackDependencyToNamesTable[dependencies].Add(attribute.Name);
[14727]118      }
119
120      return dictionary;
121    }
122
123
124
125    private static IEnumerable<Type> GetExpressionTypes(Type baseType) {
126      return from domainAssembly in AppDomain.CurrentDomain.GetAssemblies()
127             from assemblyType in domainAssembly.GetTypes()
128             where !assemblyType.IsAbstract &&
[15334]129                   assemblyType.IsSubclass(baseType) &&
[14727]130                   assemblyType.GetConstructor(Type.EmptyTypes) != null
131             select assemblyType;
132    }
133
[14834]134    public static IReadOnlyList<string> GetExpressionsByStackTypes(StackTypes allowedTypes) {
[14875]135      return stackDependencyToNamesTable
[14909]136          .Where(entry => (entry.Key & ~allowedTypes) == 0x0)
[14777]137          .SelectMany(entry => entry.Value)
[15189]138          .ToList();
[14777]139    }
140
[14746]141    public static PushProgram GetProgram(IManagedPool<PushProgram> pool, int[] index) {
[14744]142      var expressions = new Expression[index.Length];
[14727]143
144      for (var i = 0; i < index.Length; i++) {
[14744]145        expressions[i] = GetExpression(index[i]);
[14727]146      }
147
[14746]148      return PushProgram.Create(pool, expressions);
[14727]149    }
150
151    public static Expression GetExpression(int index) {
[14875]152      return GetExpression(indexToNameTable[index]);
[14727]153    }
154
[14875]155    public static Expression GetExpression(Type type) {
156      var name = TypeToNameTable[type];
157      return GetExpression(name);
158    }
159
[14727]160    public static Expression GetExpression(string name) {
161      Expression expression;
162
163      if (!TryGetStatelessExpression(name, out expression) &&
[14777]164          !TryGetStatefulExpression(name, out expression))
[14727]165        throw new InvalidOperationException(string.Format("Expression with name {0} not found", name));
166
167      return expression;
168    }
169
170    public static Expression GetStatelessExpression<T>() where T : StatelessExpression {
[15341]171      Expression expression;
172      var type = typeof(T);
173
174      if (StatelessExpressionTable.TryGetValue(type, out expression))
175        return expression;
176
177      throw new NotSupportedException("Expression not supported: " + type.Name);
[14727]178    }
179
180    public static Expression GetStatelessExpression(string name) {
[15341]181      Type type;
182      Expression expression;
183
184      if (NameToTypeTable.TryGetValue(name, out type) && StatelessExpressionTable.TryGetValue(type, out expression))
185        return expression;
186
[14727]187      throw new NotSupportedException("Expression not supported: " + name);
188    }
189
190    public static bool TryGetStatelessExpression(string name, out Expression expression) {
[15341]191      Type type;
192      if (!NameToTypeTable.TryGetValue(name, out type) || !StatelessExpressionTable.TryGetValue(type, out expression)) {
[14777]193        expression = null;
194        return false;
195      }
196
197      return true;
[14727]198    }
199
[14777]200    public static Expression GetStatefulExpression<T>() {
[14875]201      return GetStatefulExpression(typeToNameTable[typeof(T)]);
[14727]202    }
203
[14777]204    public static Expression GetStatefulExpression(string name) {
[15341]205      Type type;
206      Func<Expression> creator;
[14952]207
[15341]208      if (NameToTypeTable.TryGetValue(name, out type) && StatefulExpressionFactory.TryGetValue(type, out creator)) {
209        return creator();
[14952]210      }
211
[14727]212      throw new NotSupportedException("Expression not supported: " + name);
213    }
214
[14777]215    public static bool TryGetStatefulExpression(string name, out Expression expression) {
[14952]216      if (NameToTypeTable.ContainsKey(name)) {
217        expression = StatefulExpressionFactory[NameToTypeTable[name]]();
[14727]218        return true;
219      }
220
221      expression = default(Expression);
222      return false;
223    }
224  }
225}
Note: See TracBrowser for help on using the repository browser.