Neuron®
The Neuron® is the basis for the creation of open and secure federated networks for smart societies.
Loading...
Searching...
No Matches
Residue.cs
1using System;
2using System.Collections.Generic;
3using System.Threading.Tasks;
9
11{
15 public class Residue : BinaryOperator
16 {
26 : base(Left, Right, Start, Length, Expression)
27 {
28 }
29
36 {
37 IElement Left = this.left.Evaluate(Variables);
38 IElement Right = this.right.Evaluate(Variables);
39
40 return EvaluateResidue(Left, Right, this);
41 }
42
48 public override async Task<IElement> EvaluateAsync(Variables Variables)
49 {
50 if (!this.isAsync)
51 return this.Evaluate(Variables);
52
53 IElement Left = await this.left.EvaluateAsync(Variables);
54 IElement Right = await this.right.EvaluateAsync(Variables);
55
56 return EvaluateResidue(Left, Right, this);
57 }
58
66 public static IElement EvaluateResidue(IElement Left, IElement Right, ScriptNode Node)
67 {
68 if (Left.AssociatedObjectValue is double dl && Right.AssociatedObjectValue is double dr)
69 {
70 if (dl < long.MinValue || dl > long.MaxValue || dl != Math.Truncate(dl))
71 throw new ScriptRuntimeException("Modulus operator does not work on decimal numbers.", Node);
72
73 if (dr < long.MinValue || dr > long.MaxValue || dr != Math.Truncate(dr))
74 throw new ScriptRuntimeException("Modulus operator does not work on decimal numbers.", Node);
75
76 long l = (long)dl;
77 long r = (long)dr;
78
79 return new DoubleNumber(l % r);
80 }
81
82 if (Left.IsScalar)
83 {
84 if (Right.IsScalar)
85 {
86 ISet LeftSet = Left.AssociatedSet;
87 ISet RightSet = Right.AssociatedSet;
88
89 if (!LeftSet.Equals(RightSet))
90 {
91 if (Expression.UpgradeField(ref Left, ref LeftSet, ref Right, ref RightSet))
92 {
93 if (Left is IEuclidianDomainElement LE && Right is IEuclidianDomainElement RE)
94 {
95 ((IEuclidianDomain)LeftSet).Divide(LE, RE, out IEuclidianDomainElement Result);
96 return Result;
97 }
98 }
99 }
100
101 IElement Result2 = EvaluateNamedOperator("op_Modulus", Left, Right, Node);
102 if (!(Result2 is null))
103 return Result2;
104
105 throw new ScriptRuntimeException("Residue could not be computed.", Node);
106 }
107 else
108 {
109 LinkedList<IElement> Elements = new LinkedList<IElement>();
110
111 foreach (IElement RightChild in Right.ChildElements)
112 Elements.AddLast(EvaluateResidue(Left, RightChild, Node));
113
114 return Right.Encapsulate(Elements, Node);
115 }
116 }
117 else
118 {
119 if (Right.IsScalar)
120 {
121 LinkedList<IElement> Elements = new LinkedList<IElement>();
122
123 foreach (IElement LeftChild in Left.ChildElements)
124 Elements.AddLast(EvaluateResidue(LeftChild, Right, Node));
125
126 return Left.Encapsulate(Elements, Node);
127 }
128 else
129 {
130 ICollection<IElement> LeftChildren = Left.ChildElements;
131 ICollection<IElement> RightChildren = Right.ChildElements;
132
133 if (LeftChildren.Count == RightChildren.Count)
134 {
135 LinkedList<IElement> Elements = new LinkedList<IElement>();
136 IEnumerator<IElement> eLeft = LeftChildren.GetEnumerator();
137 IEnumerator<IElement> eRight = RightChildren.GetEnumerator();
138
139 try
140 {
141 while (eLeft.MoveNext() && eRight.MoveNext())
142 Elements.AddLast(EvaluateResidue(eLeft.Current, eRight.Current, Node));
143 }
144 finally
145 {
146 eLeft.Dispose();
147 eRight.Dispose();
148 }
149
150 return Left.Encapsulate(Elements, Node);
151 }
152 else
153 {
154 LinkedList<IElement> LeftResult = new LinkedList<IElement>();
155
156 foreach (IElement LeftChild in LeftChildren)
157 {
158 LinkedList<IElement> RightResult = new LinkedList<IElement>();
159
160 foreach (IElement RightChild in RightChildren)
161 RightResult.AddLast(EvaluateResidue(LeftChild, RightChild, Node));
162
163 LeftResult.AddLast(Right.Encapsulate(RightResult, Node));
164 }
165
166 return Left.Encapsulate(LeftResult, Node);
167 }
168 }
169 }
170 }
171
172 }
173}
Class managing a script expression.
Definition: Expression.cs:39
static bool UpgradeField(ref IElement E1, ref ISet Set1, ref IElement E2, ref ISet Set2)
Upgrades elements if necessary, to a common field extension, trying to make them compatible.
Definition: Expression.cs:5070
Base class for all binary operators.
ScriptNode right
Right operand.
ScriptNode left
Left operand.
static IElement EvaluateNamedOperator(string Name, IElement Left, IElement Right, ScriptNode Node)
Evaluates a named operator available in code-behind.
bool isAsync
If subtree is asynchroneous.
Base class for all nodes in a parsed script tree.
Definition: ScriptNode.cs:69
int Length
Length of expression covered by node.
Definition: ScriptNode.cs:101
int Start
Start position in script expression.
Definition: ScriptNode.cs:92
abstract IElement Evaluate(Variables Variables)
Evaluates the node, using the variables provided in the Variables collection. This method should be ...
virtual Task< IElement > EvaluateAsync(Variables Variables)
Evaluates the node, using the variables provided in the Variables collection. This method should be ...
Definition: ScriptNode.cs:158
static IElement EvaluateResidue(IElement Left, IElement Right, ScriptNode Node)
Divides the right operand from the left one.
Definition: Residue.cs:66
override IElement Evaluate(Variables Variables)
Evaluates the node, using the variables provided in the Variables collection.
Definition: Residue.cs:35
Residue(ScriptNode Left, ScriptNode Right, int Start, int Length, Expression Expression)
Residue operator.
Definition: Residue.cs:25
override async Task< IElement > EvaluateAsync(Variables Variables)
Evaluates the node, using the variables provided in the Variables collection.
Definition: Residue.cs:48
Collection of variables.
Definition: Variables.cs:25
Basic interface for all types of elements.
Definition: IElement.cs:20
object AssociatedObjectValue
Associated object value.
Definition: IElement.cs:33
ICollection< IElement > ChildElements
An enumeration of child elements. If the element is a scalar, this property will return null.
Definition: IElement.cs:49
IElement Encapsulate(ICollection< IElement > Elements, ScriptNode Node)
Encapsulates a set of elements into a similar structure as that provided by the current element.
bool IsScalar
If the element represents a scalar value.
Definition: IElement.cs:41
Basic interface for all types of Euclidian domain elements.
Basic interface for all types of euclidian domains.
Basic interface for all types of sets.
Definition: ISet.cs:10