-
Notifications
You must be signed in to change notification settings - Fork 244
Expand file tree
/
Copy pathRangeValue.cs
More file actions
140 lines (119 loc) · 4.29 KB
/
Copy pathRangeValue.cs
File metadata and controls
140 lines (119 loc) · 4.29 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
using kOS.Safe.Encapsulation;
using kOS.Safe.Encapsulation.Suffixes;
using kOS.Safe.Exceptions;
using kOS.Safe.Serialization;
using System;
using System.Collections.Generic;
namespace kOS.Safe
{
[kOS.Safe.Utilities.KOSNomenclature("Range")]
public class RangeValue : EnumerableValue<ScalarValue, Range>
{
private const string DumpStart = "start";
private const string DumpStop = "stop";
private const string DumpStep = "step";
private const string Label = "RANGE";
public static readonly int DEFAULT_START = 0;
public static readonly int DEFAULT_STOP = 1;
public static readonly int DEFAULT_STEP = 1;
public RangeValue()
: this(DEFAULT_STOP)
{
}
public RangeValue(ScalarValue stop)
: this(DEFAULT_START, stop)
{
}
public RangeValue(ScalarValue start, ScalarValue stop)
: this(start, stop, DEFAULT_STEP)
{
}
public RangeValue(ScalarValue start, ScalarValue stop, ScalarValue step)
: base(Label, new Range(start, stop, step))
{
InitializeRangeSuffixes();
if (step < 1)
{
throw new KOSException("Step must be a positive integer");
}
}
// Required for all IDumpers for them to work, but can't enforced by the interface because it's static:
public static RangeValue CreateFromDump(SafeSharedObjects shared, Dump d)
{
var newObj = new RangeValue();
newObj.LoadDump(d);
return newObj;
}
private void InitializeRangeSuffixes()
{
AddSuffix("START", new NoArgsSuffix<ScalarValue>(() => InnerEnumerable.Start));
AddSuffix("STOP", new NoArgsSuffix<ScalarValue>(() => InnerEnumerable.Stop));
AddSuffix("STEP", new NoArgsSuffix<ScalarValue>(() => InnerEnumerable.Step));
}
public override void LoadDump(Dump dump)
{
InnerEnumerable.Stop = Convert.ToDouble(dump[DumpStop]);
InnerEnumerable.Start = Convert.ToDouble(dump[DumpStart]);
InnerEnumerable.Step = Convert.ToDouble(dump[DumpStep]);
}
public override Dump Dump()
{
DumpWithHeader result = new DumpWithHeader();
result.Header = "RANGE";
result.Add(DumpStop, InnerEnumerable.Stop);
result.Add(DumpStart, InnerEnumerable.Start);
result.Add(DumpStep, InnerEnumerable.Step);
return result;
}
public override string ToString()
{
return "RANGE(" + InnerEnumerable.Start + ", " + InnerEnumerable.Stop + ", " + InnerEnumerable.Step + ")";
}
public override string ToStringIndented(int level)
{
// By default, an Enumerable's ToStringIndented() would print out a header line, but here it's
// not needed, so override it to just print the content line only:
return ToStringItems(level);
}
public override string ToStringItems(int level)
{
// Indent level is being ignored because this is single-line and
// never contains other things, despite being implemented as
// a EnumerableValue which needs a ToStringItems().
return ToString();
}
}
public class Range : IEnumerable<ScalarValue>
{
public ScalarValue Start { get; set; }
public ScalarValue Stop { get; set; }
public ScalarValue Step { get; set; }
public Range(ScalarValue start, ScalarValue stop, ScalarValue step)
{
Start = start;
Stop = stop;
Step = step;
}
IEnumerator<ScalarValue> IEnumerable<ScalarValue>.GetEnumerator()
{
if (Start < Stop)
{
for (ScalarValue i = Start; i < Stop; i += Step)
{
yield return i;
}
}
else
{
for (ScalarValue i = Start; i > Stop; i -= Step)
{
yield return i;
}
}
}
public System.Collections.IEnumerator GetEnumerator()
{
return GetEnumerator();
}
}
}