source: branches/3026_IntegrationIntoSymSpace/HeuristicLab.JsonInterface/JsonItem.cs @ 17353

Last change on this file since 17353 was 17353, checked in by dpiringe, 11 months ago

#3026:

  • relocated GetMaxValue and GetMinValue from ValueTypeValueConverter into BaseConverter
  • fixed a bug in ConstrainedValueParameterConverter (from GetType().Name to ToString())
  • printing now PrettyNames for types
  • added comments
  • added StorableConverter.cs (not finished, maybe not a good converter)
  • added ValueRangeConverter.cs for DoubleRange and IntRange
  • added ParameterConverter.cs for default parameter conversion
File size: 4.0 KB
Line 
1using System;
2using System.Collections.Generic;
3using System.Linq;
4using System.Text;
5using System.Threading.Tasks;
6using HeuristicLab.Core;
7using Newtonsoft.Json;
8using Newtonsoft.Json.Linq;
9
10namespace HeuristicLab.JsonInterface {
11  /// <summary>
12  /// Main data class for json interface.
13  /// </summary>
14  public class JsonItem {
15
16    #region Private Fields
17    private string name;
18    private object value;
19    private IEnumerable<object> range;
20    #endregion
21   
22    public string Name {
23      get => name;
24      set {
25        name = value;
26        Path = Name;
27        UpdatePath();
28      }
29    }
30    public string Type { get; set; }
31    public string Path { get; set; }
32    public IList<JsonItem> Parameters { get; set; } // -> für flachen aufbau -> childs?
33    public IList<JsonItem> Operators { get; set; }
34    public object Value {
35      get => value;
36      set {
37        if (value is JContainer)
38          this.value = ((JContainer)value).ToObject<object[]>();
39        else
40          this.value = value;
41        CheckConstraints();
42      }
43    }
44    public IEnumerable<object> Range {
45      get => range;
46      set {
47        range = value;
48        CheckConstraints();
49      }
50    }
51    public string ActualName { get; set; }
52
53    #region JsonIgnore Properties
54    [JsonIgnore]
55    public JsonItem Reference { get; set; }
56
57    [JsonIgnore]
58    public bool IsConfigurable => (Value != null && Range != null);
59
60    [JsonIgnore]
61    public bool IsParameterizedItem => Parameters != null;
62    #endregion
63
64    #region Public Static Methods
65    public static void Merge(JsonItem target, JsonItem from) {
66      target.Name = from.Name ?? target.Name;
67      target.Type = from.Type ?? target.Type;
68      target.Range = from.Range ?? target.Range;
69      target.Path = from.Path ?? target.Path;
70      target.Value = from.Value ?? target.Value;
71      target.Reference = from.Reference ?? target.Reference;
72      target.ActualName = from.ActualName ?? target.ActualName;
73      target.Parameters = from.Parameters ?? target.Parameters;
74      target.Operators = from.Operators ?? target.Operators;
75    }
76    #endregion
77
78    #region Public Methods
79    public void UpdatePath() {
80      if (Parameters != null)
81        UpdatePathHelper(Parameters);
82
83      if (Operators != null)
84        UpdatePathHelper(Operators);
85
86      if(Reference != null)
87        UpdatePathHelper(Reference);
88    }
89    #endregion
90
91    #region Helper
92    private void UpdatePathHelper(params JsonItem[] items) =>
93      UpdatePathHelper((IEnumerable<JsonItem>)items);
94
95    private void UpdatePathHelper(IEnumerable<JsonItem> items) {
96      foreach (var item in items) {
97        item.Path = $"{Path}.{item.Name}";
98        item.UpdatePath();
99      }
100    }
101
102    private void CheckConstraints() {
103      if (Range != null && Value != null && !IsInRange())
104        throw new ArgumentOutOfRangeException(nameof(Value), $"{nameof(Value)} is not in range.");
105    }
106
107    private bool IsInRange() => IsInRangeList() ||
108      (Value.GetType().IsArray && ((object[])Value).All(x => IsInNumericRange(x))) ||
109      (!Value.GetType().IsArray && IsInNumericRange(Value));
110
111    private bool IsInRangeList() {
112      foreach (var x in Range)
113        if (x.Equals(Value)) return true;
114      return false;
115    }
116
117    private bool IsInNumericRange(object value) =>
118      IsInNumericRange<long>(value)
119      || IsInNumericRange<int>(value)
120      || IsInNumericRange<short>(value)
121      || IsInNumericRange<byte>(value)
122      || IsInNumericRange<float>(value)
123      || IsInNumericRange<double>(value);
124
125    private bool IsInNumericRange<T>(object value) where T : IComparable {
126      object min = Range.First(), max = Range.Last();
127      return value != null && min != null && max != null && value is T && min is T && max is T &&
128            (((T)min).CompareTo(value) == -1 || ((T)min).CompareTo(value) == 0) &&
129            (((T)max).CompareTo(value) == 1 || ((T)max).CompareTo(value) == 0);
130    }
131     
132    #endregion
133  }
134}
Note: See TracBrowser for help on using the repository browser.