Refactoring

This commit is contained in:
Michael Schimmel
2025-09-19 09:03:02 +02:00
parent 565742275c
commit ef16003971
4 changed files with 83 additions and 34 deletions
+16 -14
View File
@@ -126,8 +126,6 @@ var
i: Integer;
sourceAddresses: TArray<TResolvedAddress>;
closureScope: IExecutionScope;
[weak]
closure: TDataValue.TFunc;
visitorFactory: TVisitorFactory;
begin
sourceAddresses := Node.Upvalues;
@@ -146,7 +144,9 @@ begin
var scopeDescriptor := Node.ScopeDescriptor;
var params := Node.Parameters;
// weak reference to break cyclic referencing
// declare closure as weak to break cyclic referencing when it is captured by itself
var [weak] closure: TDataValue.TFunc;
closure :=
TDataValue.TFunc(
function(const ArgValues: TArray<TDataValue>): TDataValue
@@ -182,35 +182,37 @@ begin
end
);
Result := TDataValue(closure);
Result := closure;
end;
function TEvaluatorVisitor.VisitFunctionCall(const Node: IFunctionCallNode): TDataValue;
var
calleeValue: TDataValue;
[weak]
callee: TDataValue.TFunc;
begin
calleeValue := Node.Callee.Accept(Self);
if calleeValue.Kind <> vkMethod then
case calleeValue.Kind of
vkMethod: callee := calleeValue.AsMethod();
else
raise EArgumentException.Create('Expression is not invokable in this context.');
end;
var argNodes := Node.Arguments;
case Length(argNodes) of
0: Result := (calleeValue.AsMethod)([]);
1: Result := (calleeValue.AsMethod)([argNodes[0].Accept(Self)]);
2: Result := (calleeValue.AsMethod)([argNodes[0].Accept(Self), argNodes[1].Accept(Self)]);
3: Result := (calleeValue.AsMethod)([argNodes[0].Accept(Self), argNodes[1].Accept(Self), argNodes[2].Accept(Self)]);
4:
Result :=
(calleeValue.AsMethod)
([argNodes[0].Accept(Self), argNodes[1].Accept(Self), argNodes[2].Accept(Self), argNodes[3].Accept(Self)]);
0: Result := callee([]);
1: Result := callee([argNodes[0].Accept(Self)]);
2: Result := callee([argNodes[0].Accept(Self), argNodes[1].Accept(Self)]);
3: Result := callee([argNodes[0].Accept(Self), argNodes[1].Accept(Self), argNodes[2].Accept(Self)]);
4: Result := callee([argNodes[0].Accept(Self), argNodes[1].Accept(Self), argNodes[2].Accept(Self), argNodes[3].Accept(Self)]);
else
var argValues: TArray<TDataValue>;
SetLength(argValues, Length(argNodes));
for var i := 0 to High(argNodes) do
argValues[i] := argNodes[i].Accept(Self);
Result := (calleeValue.AsMethod)(argValues);
Result := callee(argValues);
end;
end;
+66 -1
View File
@@ -78,7 +78,7 @@ type
// Creates a new scalar from a kind and a value.
constructor Create(AKind: TScalarKind; const AValue: TScalarValue);
// Factory methods for specific scalar types.
// Factory methods for specific scalar types (do not use anymore, these may become deprecated in the future)
class function FromInteger(AValue: Integer): TScalar; static; inline;
class function FromInt64(AValue: Int64): TScalar; static; inline;
class function FromUInt64(AValue: UInt64): TScalar; static; inline;
@@ -93,6 +93,17 @@ type
class function FromBytes(const AValue: TScalarBytes): TScalar; static; inline;
class function FromDecimal(const AValue: TDecimal): TScalar; static; inline;
// Implicit casts from primitive types to TScalar.
class operator Implicit(AValue: Integer): TScalar; overload; inline;
class operator Implicit(AValue: Int64): TScalar; overload; inline;
class operator Implicit(AValue: UInt64): TScalar; overload; inline;
class operator Implicit(AValue: Single): TScalar; overload; inline;
class operator Implicit(AValue: Double): TScalar; overload; inline;
class operator Implicit(AValue: TDateTime): TScalar; overload; inline;
class operator Implicit(AValue: Boolean): TScalar; overload; inline;
class operator Implicit(AValue: Char): TScalar; overload; inline;
class operator Implicit(const AValue: TDecimal): TScalar; overload; inline;
class function StringToKind(const AName: string): TScalarKind; static;
function ToString: String;
@@ -405,6 +416,60 @@ begin
Result.Value := TScalarValue.FromDouble(AValue);
end;
class operator TScalar.Implicit(AValue: Boolean): TScalar;
begin
Result.Kind := skBoolean;
Result.Value := TScalarValue.FromBoolean(AValue);
end;
class operator TScalar.Implicit(AValue: Char): TScalar;
begin
Result.Kind := skChar;
Result.Value := TScalarValue.FromChar(AValue);
end;
class operator TScalar.Implicit(AValue: TDateTime): TScalar;
begin
Result.Kind := skDateTime;
Result.Value := TScalarValue.FromDateTime(AValue);
end;
class operator TScalar.Implicit(const AValue: TDecimal): TScalar;
begin
Result.Kind := skDecimal;
Result.Value := TScalarValue.FromDecimal(AValue);
end;
class operator TScalar.Implicit(AValue: Double): TScalar;
begin
Result.Kind := skDouble;
Result.Value := TScalarValue.FromDouble(AValue);
end;
class operator TScalar.Implicit(AValue: Int64): TScalar;
begin
Result.Kind := skInt64;
Result.Value := TScalarValue.FromInt64(AValue);
end;
class operator TScalar.Implicit(AValue: Integer): TScalar;
begin
Result.Kind := skInteger;
Result.Value := TScalarValue.FromInteger(AValue);
end;
class operator TScalar.Implicit(AValue: Single): TScalar;
begin
Result.Kind := skSingle;
Result.Value := TScalarValue.FromSingle(AValue);
end;
class operator TScalar.Implicit(AValue: UInt64): TScalar;
begin
Result.Kind := skUInt64;
Result.Value := TScalarValue.FromUInt64(AValue);
end;
class function TScalar.FromInt64(AValue: Int64): TScalar;
begin
Result.Kind := skInt64;
+1 -10
View File
@@ -15,7 +15,7 @@ uses
{$ENDIF }
DUnitX.TestFramework,
TestNotifier in 'TestNotifier.pas',
TestNotifier_Threading in 'TestNotifier_Threading.pas' {/TestNotifier_ChaosStress in 'TestNotifier_ChaosStress.pas',},
TestNotifier_Threading in 'TestNotifier_Threading.pas',
TestNotifier_ChaosStress in 'TestNotifier_ChaosStress.pas',
TestTasks in 'TestTasks.pas',
TestCoreFutures in 'TestCoreFutures.pas',
@@ -25,17 +25,8 @@ uses
Myc.Test.Signals.Dirty in '..\Src\Myc.Test.Signals.Dirty.pas',
Test.Core.Mutable in 'Test.Core.Mutable.pas',
TestDataArray in 'TestDataArray.pas',
Myc.Data.Types in '..\Src\Myc.Data.Types.pas',
Myc.Data.Types.Ordinal in 'Myc.Data.Types.Ordinal.pas',
Myc.Data.Types.Records in 'Myc.Data.Types.Records.pas',
Myc.Data.Types.Float in 'Myc.Data.Types.Float.pas',
Myc.Data.Types.Arrays in 'Myc.Data.Types.Arrays.pas',
TestDataTypes in '..\Src\Data\TestDataTypes.pas',
Myc.Data.Types.Method in '..\Src\Data\Myc.Data.Types.Method.pas',
Myc.Data.Types.Void in '..\Src\Data\Myc.Data.Types.Void.pas',
Myc.Data.Types.Decimal in '..\Src\Data\Myc.Data.Types.Decimal.pas',
Myc.Ast in '..\Src\AST\Myc.Ast.pas',
Myc.Data.Types.JSON in '..\Src\Data\Myc.Data.Types.JSON.pas',
TestDataTypes.JSON in '..\Src\Data\TestDataTypes.JSON.pas',
Myc.Data.POD in '..\Src\Data\Myc.Data.Scalar.pas',
Myc.Data.Decimal in '..\Src\Data\Myc.Data.Decimal.pas',
-9
View File
@@ -126,17 +126,8 @@ $(PreBuildEvent)]]></PreBuildEvent>
<DCCReference Include="..\Src\Myc.Test.Signals.Dirty.pas"/>
<DCCReference Include="Test.Core.Mutable.pas"/>
<DCCReference Include="TestDataArray.pas"/>
<DCCReference Include="..\Src\Myc.Data.Types.pas"/>
<DCCReference Include="Myc.Data.Types.Ordinal.pas"/>
<DCCReference Include="Myc.Data.Types.Records.pas"/>
<DCCReference Include="Myc.Data.Types.Float.pas"/>
<DCCReference Include="Myc.Data.Types.Arrays.pas"/>
<DCCReference Include="..\Src\Data\TestDataTypes.pas"/>
<DCCReference Include="..\Src\Data\Myc.Data.Types.Method.pas"/>
<DCCReference Include="..\Src\Data\Myc.Data.Types.Void.pas"/>
<DCCReference Include="..\Src\Data\Myc.Data.Types.Decimal.pas"/>
<DCCReference Include="..\Src\AST\Myc.Ast.pas"/>
<DCCReference Include="..\Src\Data\Myc.Data.Types.JSON.pas"/>
<DCCReference Include="..\Src\Data\TestDataTypes.JSON.pas"/>
<DCCReference Include="..\Src\Data\Myc.Data.Scalar.pas">
<ModuleName>Myc.Data.POD</ModuleName>