fpspreadsheet: remove type check in TsExpressionParser to be more compatible with Office applications. Fix parser to correctly handle exotic expressions such as "=50%^200%"
git-svn-id: https://svn.code.sf.net/p/lazarus-ccr/svn@4180 8e941d3f-bd1b-0410-a28a-d453659cc2b4
This commit is contained in:
parent
5d6bea6a85
commit
9fbe0f7b4e
@ -110,14 +110,14 @@ type
|
|||||||
private
|
private
|
||||||
FParser: TsExpressionParser;
|
FParser: TsExpressionParser;
|
||||||
protected
|
protected
|
||||||
procedure CheckNodeType(ANode: TsExprNode; Allowed: TsResultTypes);
|
// procedure CheckNodeType(ANode: TsExprNode; Allowed: TsResultTypes);
|
||||||
// A procedure with var saves an implicit try/finally in each node
|
// A procedure with var saves an implicit try/finally in each node
|
||||||
// A marked difference in execution speed.
|
// A marked difference in execution speed.
|
||||||
procedure GetNodeValue(out Result: TsExpressionResult); virtual; abstract;
|
procedure GetNodeValue(out Result: TsExpressionResult); virtual; abstract;
|
||||||
public
|
public
|
||||||
function AsRPNItem(ANext: PRPNItem): PRPNItem; virtual; abstract;
|
function AsRPNItem(ANext: PRPNItem): PRPNItem; virtual; abstract;
|
||||||
function AsString: string; virtual; abstract;
|
function AsString: string; virtual; abstract;
|
||||||
procedure Check; virtual; abstract;
|
procedure Check; virtual; //abstract;
|
||||||
function NodeType: TsResultType; virtual; abstract;
|
function NodeType: TsResultType; virtual; abstract;
|
||||||
function NodeValue: TsExpressionResult;
|
function NodeValue: TsExpressionResult;
|
||||||
property Parser: TsExpressionParser read FParser;
|
property Parser: TsExpressionParser read FParser;
|
||||||
@ -131,11 +131,11 @@ type
|
|||||||
FLeft: TsExprNode;
|
FLeft: TsExprNode;
|
||||||
FRight: TsExprNode;
|
FRight: TsExprNode;
|
||||||
protected
|
protected
|
||||||
procedure CheckSameNodeTypes; virtual;
|
//procedure CheckSameNodeTypes; virtual;
|
||||||
public
|
public
|
||||||
constructor Create(AParser: TsExpressionParser; ALeft, ARight: TsExprNode);
|
constructor Create(AParser: TsExpressionParser; ALeft, ARight: TsExprNode);
|
||||||
destructor Destroy; override;
|
destructor Destroy; override;
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
property Left: TsExprNode read FLeft;
|
property Left: TsExprNode read FLeft;
|
||||||
property Right: TsExprNode read FRight;
|
property Right: TsExprNode read FRight;
|
||||||
end;
|
end;
|
||||||
@ -144,16 +144,16 @@ type
|
|||||||
{ TsBooleanOperationExprNode }
|
{ TsBooleanOperationExprNode }
|
||||||
TsBooleanOperationExprNode = class(TsBinaryOperationExprNode)
|
TsBooleanOperationExprNode = class(TsBinaryOperationExprNode)
|
||||||
public
|
public
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TsBooleanResultExprNode }
|
{ TsBooleanResultExprNode }
|
||||||
TsBooleanResultExprNode = class(TsBinaryOperationExprNode)
|
TsBooleanResultExprNode = class(TsBinaryOperationExprNode)
|
||||||
protected
|
protected
|
||||||
procedure CheckSameNodeTypes; override;
|
// procedure CheckSameNodeTypes; override;
|
||||||
public
|
public
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
TsBooleanResultExprNodeClass = class of TsBooleanResultExprNode;
|
TsBooleanResultExprNodeClass = class of TsBooleanResultExprNode;
|
||||||
@ -179,7 +179,7 @@ type
|
|||||||
{ TsOrderingExprNode }
|
{ TsOrderingExprNode }
|
||||||
TsOrderingExprNode = class(TsBooleanResultExprNode)
|
TsOrderingExprNode = class(TsBooleanResultExprNode)
|
||||||
public
|
public
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TsLessExprNode }
|
{ TsLessExprNode }
|
||||||
@ -221,21 +221,21 @@ type
|
|||||||
{ TsConcatExprNode }
|
{ TsConcatExprNode }
|
||||||
TsConcatExprNode = class(TsBinaryOperationExprNode)
|
TsConcatExprNode = class(TsBinaryOperationExprNode)
|
||||||
protected
|
protected
|
||||||
procedure CheckSameNodeTypes; override;
|
// procedure CheckSameNodeTypes; override;
|
||||||
procedure GetNodeValue(out Result: TsExpressionResult); override;
|
procedure GetNodeValue(out Result: TsExpressionResult); override;
|
||||||
public
|
public
|
||||||
function AsRPNItem(ANext: PRPNItem): PRPNItem; override;
|
function AsRPNItem(ANext: PRPNItem): PRPNItem; override;
|
||||||
function AsString: string ; override;
|
function AsString: string ; override;
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TsMathOperationExprNode }
|
{ TsMathOperationExprNode }
|
||||||
TsMathOperationExprNode = class(TsBinaryOperationExprNode)
|
TsMathOperationExprNode = class(TsBinaryOperationExprNode)
|
||||||
protected
|
protected
|
||||||
procedure CheckSameNodeTypes; override;
|
// procedure CheckSameNodeTypes; override;
|
||||||
public
|
public
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -317,7 +317,7 @@ type
|
|||||||
{ TsConvertToIntExprNode }
|
{ TsConvertToIntExprNode }
|
||||||
TsConvertToIntExprNode = class(TsConvertExprNode)
|
TsConvertToIntExprNode = class(TsConvertExprNode)
|
||||||
public
|
public
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TsIntToFloatExprNode }
|
{ TsIntToFloatExprNode }
|
||||||
@ -341,7 +341,7 @@ type
|
|||||||
protected
|
protected
|
||||||
procedure GetNodeValue(out Result: TsExpressionResult); override;
|
procedure GetNodeValue(out Result: TsExpressionResult); override;
|
||||||
public
|
public
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -352,7 +352,7 @@ type
|
|||||||
public
|
public
|
||||||
function AsRPNItem(ANext: PRPNItem): PRPNItem; override;
|
function AsRPNItem(ANext: PRPNItem): PRPNItem; override;
|
||||||
function AsString: String; override;
|
function AsString: String; override;
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -363,7 +363,7 @@ type
|
|||||||
public
|
public
|
||||||
function AsRPNItem(ANext: PRPNItem): PRPNItem; override;
|
function AsRPNItem(ANext: PRPNItem): PRPNItem; override;
|
||||||
function AsString: String; override;
|
function AsString: String; override;
|
||||||
procedure Check; override;
|
// procedure Check; override;
|
||||||
function NodeType: TsResultType; override;
|
function NodeType: TsResultType; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -729,6 +729,7 @@ type
|
|||||||
function Level4: TsExprNode;
|
function Level4: TsExprNode;
|
||||||
function Level5: TsExprNode;
|
function Level5: TsExprNode;
|
||||||
function Level6: TsExprNode;
|
function Level6: TsExprNode;
|
||||||
|
function Level7: TsExprNode;
|
||||||
function Primitive: TsExprNode;
|
function Primitive: TsExprNode;
|
||||||
function TokenType: TsTokenType;
|
function TokenType: TsTokenType;
|
||||||
procedure CreateHashList;
|
procedure CreateHashList;
|
||||||
@ -1572,34 +1573,82 @@ end;
|
|||||||
|
|
||||||
function TsExpressionParser.Level5: TsExprNode;
|
function TsExpressionParser.Level5: TsExprNode;
|
||||||
var
|
var
|
||||||
isPlus, isMinus: Boolean;
|
tt: TsTokenType;
|
||||||
|
right: TsExprNode;
|
||||||
begin
|
begin
|
||||||
{$ifdef debugexpr} Writeln('Level 5 ',TokenName(TokenType),': ',CurrentToken);{$endif debugexpr}
|
{$ifdef debugexpr} Writeln('Level 5 ',TokenName(TokenType),': ',CurrentToken);{$endif debugexpr}
|
||||||
isPlus := false;
|
|
||||||
isMinus := false;
|
|
||||||
if (TokenType in [ttPlus, ttMinus]) then
|
|
||||||
begin
|
|
||||||
isPlus := (TokenType = ttPlus);
|
|
||||||
isMinus := (TokenType = ttMinus);
|
|
||||||
GetToken;
|
|
||||||
end;
|
|
||||||
Result := Level6;
|
Result := Level6;
|
||||||
if isPlus then
|
try
|
||||||
Result := TsUPlusExprNode.Create(self, Result);
|
while (TokenType = ttPower) do
|
||||||
if isMinus then
|
begin
|
||||||
Result := TsUMinusExprNode.Create(self, Result);
|
tt := TokenType;
|
||||||
if TokenType = ttPercent then begin
|
GetToken;
|
||||||
Result := TsPercentExprNode.Create(self, Result);
|
right := Level6;
|
||||||
GetToken;
|
CheckNodes(Result, right);
|
||||||
|
Result := TsPowerExprNode.Create(self, Result, right);
|
||||||
|
end;
|
||||||
|
except
|
||||||
|
Result.Free;
|
||||||
|
Raise;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TsExpressionParser.Level6: TsExprNode;
|
function TsExpressionParser.Level6: TsExprNode;
|
||||||
|
var
|
||||||
|
//isPlus, isMinus: Boolean;
|
||||||
|
signs: String;
|
||||||
|
i: Integer;
|
||||||
|
begin
|
||||||
|
{$ifdef debugexpr} Writeln('Level 6 ',TokenName(TokenType),': ',CurrentToken);{$endif debugexpr}
|
||||||
|
// isPlus := false;
|
||||||
|
// isMinus := false;
|
||||||
|
signs := '';
|
||||||
|
while (TokenType in [ttPlus, ttMinus]) do
|
||||||
|
begin
|
||||||
|
case TokenType of
|
||||||
|
ttPlus : signs := signs + '+';
|
||||||
|
ttMinus : signs := signs + '-';
|
||||||
|
end;
|
||||||
|
{
|
||||||
|
isPlus := (TokenType = ttPlus);
|
||||||
|
isMinus := (TokenType = ttMinus);
|
||||||
|
}
|
||||||
|
GetToken;
|
||||||
|
end;
|
||||||
|
Result := Level7;
|
||||||
|
i := Length(signs);
|
||||||
|
while (i > 0) do begin
|
||||||
|
case signs[i] of
|
||||||
|
'+': Result := TsUPlusExprNode.Create(self, Result);
|
||||||
|
'-': Result := TsUMinusExprNode.Create(self, Result);
|
||||||
|
end;
|
||||||
|
dec(i);
|
||||||
|
end;
|
||||||
|
{
|
||||||
|
if isPlus then
|
||||||
|
Result := TsUPlusExprNode.Create(self, Result);
|
||||||
|
if isMinus then
|
||||||
|
Result := TsUMinusExprNode.Create(self, Result);
|
||||||
|
}
|
||||||
|
|
||||||
|
while TokenType = ttPercent do begin
|
||||||
|
Result := TsPercentExprNode.Create(self, Result);
|
||||||
|
GetToken;
|
||||||
|
end;
|
||||||
|
{
|
||||||
|
if TokenType = ttPercent then begin
|
||||||
|
Result := TsPercentExprNode.Create(self, Result);
|
||||||
|
GetToken;
|
||||||
|
end;
|
||||||
|
}
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TsExpressionParser.Level7: TsExprNode;
|
||||||
var
|
var
|
||||||
Right: TsExprNode;
|
Right: TsExprNode;
|
||||||
currToken: String;
|
currToken: String;
|
||||||
begin
|
begin
|
||||||
{$ifdef debugexpr} Writeln('Level 6 ',TokenName(TokenType),': ',CurrentToken);{$endif debugexpr}
|
{$ifdef debugexpr} Writeln('Level 7 ',TokenName(TokenType),': ',CurrentToken);{$endif debugexpr}
|
||||||
if (TokenType = ttLeft) then
|
if (TokenType = ttLeft) then
|
||||||
begin
|
begin
|
||||||
GetToken;
|
GetToken;
|
||||||
@ -1618,13 +1667,13 @@ begin
|
|||||||
end
|
end
|
||||||
else
|
else
|
||||||
Result := Primitive;
|
Result := Primitive;
|
||||||
|
{
|
||||||
if TokenType = ttPower then
|
if TokenType = ttPower then
|
||||||
begin
|
begin
|
||||||
try
|
try
|
||||||
CheckEOF;
|
CheckEOF;
|
||||||
GetToken;
|
GetToken;
|
||||||
Right := Primitive;
|
Right := Level1; //Primitive;
|
||||||
CheckNodes(Result, right);
|
CheckNodes(Result, right);
|
||||||
Result := TsPowerExprNode.Create(self, Result, Right);
|
Result := TsPowerExprNode.Create(self, Result, Right);
|
||||||
//GetToken;
|
//GetToken;
|
||||||
@ -1632,7 +1681,13 @@ begin
|
|||||||
Result.Free;
|
Result.Free;
|
||||||
raise;
|
raise;
|
||||||
end;
|
end;
|
||||||
|
end; }
|
||||||
|
{
|
||||||
|
if TokenType = ttPercent then begin
|
||||||
|
Result := TsPercentExprNode.Create(self, Result);
|
||||||
|
GetToken;
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ Checks types of todo and match. If ToDO can be converted to it matches
|
{ Checks types of todo and match. If ToDO can be converted to it matches
|
||||||
@ -2554,7 +2609,11 @@ end;
|
|||||||
{------------------------------------------------------------------------------}
|
{------------------------------------------------------------------------------}
|
||||||
|
|
||||||
{ TsExprNode }
|
{ TsExprNode }
|
||||||
|
procedure TsExprNode.Check;
|
||||||
|
begin
|
||||||
|
end;
|
||||||
|
|
||||||
|
{
|
||||||
procedure TsExprNode.CheckNodeType(ANode: TsExprNode; Allowed: TsResultTypes);
|
procedure TsExprNode.CheckNodeType(ANode: TsExprNode; Allowed: TsResultTypes);
|
||||||
var
|
var
|
||||||
S: String;
|
S: String;
|
||||||
@ -2575,7 +2634,7 @@ begin
|
|||||||
RaiseParserError(SInvalidNodeType, [ResultTypeName(ANode.NodeType), S, ANode.AsString]);
|
RaiseParserError(SInvalidNodeType, [ResultTypeName(ANode.NodeType), S, ANode.AsString]);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
function TsExprNode.NodeValue: TsExpressionResult;
|
function TsExprNode.NodeValue: TsExpressionResult;
|
||||||
begin
|
begin
|
||||||
GetNodeValue(Result);
|
GetNodeValue(Result);
|
||||||
@ -2620,7 +2679,7 @@ begin
|
|||||||
FreeAndNil(FRight);
|
FreeAndNil(FRight);
|
||||||
inherited Destroy;
|
inherited Destroy;
|
||||||
end;
|
end;
|
||||||
|
{
|
||||||
procedure TsBinaryOperationExprNode.Check;
|
procedure TsBinaryOperationExprNode.Check;
|
||||||
begin
|
begin
|
||||||
if not Assigned(Left) then
|
if not Assigned(Left) then
|
||||||
@ -2638,10 +2697,11 @@ begin
|
|||||||
if (RT <> LT) then
|
if (RT <> LT) then
|
||||||
RaiseParserError(SErrTypesDoNotMatch, [ResultTypeName(LT), ResultTypeName(RT), Left.AsString, Right.AsString])
|
RaiseParserError(SErrTypesDoNotMatch, [ResultTypeName(LT), ResultTypeName(RT), Left.AsString, Right.AsString])
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
|
|
||||||
{ TsBooleanOperationExprNode }
|
{ TsBooleanOperationExprNode }
|
||||||
|
|
||||||
|
{
|
||||||
procedure TsBooleanOperationExprNode.Check;
|
procedure TsBooleanOperationExprNode.Check;
|
||||||
begin
|
begin
|
||||||
inherited Check;
|
inherited Check;
|
||||||
@ -2649,7 +2709,7 @@ begin
|
|||||||
CheckNodeType(Right, [rtBoolean, rtCell, rtError, rtEmpty]);
|
CheckNodeType(Right, [rtBoolean, rtCell, rtError, rtEmpty]);
|
||||||
CheckSameNodeTypes;
|
CheckSameNodeTypes;
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
function TsBooleanOperationExprNode.NodeType: TsResultType;
|
function TsBooleanOperationExprNode.NodeType: TsResultType;
|
||||||
begin
|
begin
|
||||||
Result := Left.NodeType;
|
Result := Left.NodeType;
|
||||||
@ -2806,7 +2866,7 @@ function TsUPlusExprNode.AsString: String;
|
|||||||
begin
|
begin
|
||||||
Result := '+' + TrimLeft(Operand.AsString);
|
Result := '+' + TrimLeft(Operand.AsString);
|
||||||
end;
|
end;
|
||||||
|
{
|
||||||
procedure TsUPlusExprNode.Check;
|
procedure TsUPlusExprNode.Check;
|
||||||
const
|
const
|
||||||
AllowedTokens = [rtInteger, rtFloat, rtCell, rtEmpty, rtError];
|
AllowedTokens = [rtInteger, rtFloat, rtCell, rtEmpty, rtError];
|
||||||
@ -2815,7 +2875,7 @@ begin
|
|||||||
if not (Operand.NodeType in AllowedTokens) then
|
if not (Operand.NodeType in AllowedTokens) then
|
||||||
RaiseParserError(SErrNoUPlus, [ResultTypeName(Operand.NodeType), Operand.AsString])
|
RaiseParserError(SErrNoUPlus, [ResultTypeName(Operand.NodeType), Operand.AsString])
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
procedure TsUPlusExprNode.GetNodeValue(out Result: TsExpressionResult);
|
procedure TsUPlusExprNode.GetNodeValue(out Result: TsExpressionResult);
|
||||||
var
|
var
|
||||||
cell: PCell;
|
cell: PCell;
|
||||||
@ -2865,7 +2925,7 @@ function TsUMinusExprNode.AsString: String;
|
|||||||
begin
|
begin
|
||||||
Result := '-' + TrimLeft(Operand.AsString);
|
Result := '-' + TrimLeft(Operand.AsString);
|
||||||
end;
|
end;
|
||||||
|
{
|
||||||
procedure TsUMinusExprNode.Check;
|
procedure TsUMinusExprNode.Check;
|
||||||
const
|
const
|
||||||
AllowedTokens = [rtInteger, rtFloat, rtCell, rtEmpty, rtError];
|
AllowedTokens = [rtInteger, rtFloat, rtCell, rtEmpty, rtError];
|
||||||
@ -2874,7 +2934,7 @@ begin
|
|||||||
if not (Operand.NodeType in AllowedTokens) then
|
if not (Operand.NodeType in AllowedTokens) then
|
||||||
RaiseParserError(SErrNoNegation, [ResultTypeName(Operand.NodeType), Operand.AsString])
|
RaiseParserError(SErrNoNegation, [ResultTypeName(Operand.NodeType), Operand.AsString])
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
procedure TsUMinusExprNode.GetNodeValue(out Result: TsExpressionResult);
|
procedure TsUMinusExprNode.GetNodeValue(out Result: TsExpressionResult);
|
||||||
var
|
var
|
||||||
cell: PCell;
|
cell: PCell;
|
||||||
@ -3020,17 +3080,17 @@ end;
|
|||||||
|
|
||||||
|
|
||||||
{ TsBooleanResultExprNode }
|
{ TsBooleanResultExprNode }
|
||||||
|
{
|
||||||
procedure TsBooleanResultExprNode.Check;
|
procedure TsBooleanResultExprNode.Check;
|
||||||
begin
|
begin
|
||||||
inherited Check;
|
inherited Check;
|
||||||
CheckSameNodeTypes;
|
//CheckSameNodeTypes;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsBooleanResultExprNode.CheckSameNodeTypes;
|
procedure TsBooleanResultExprNode.CheckSameNodeTypes;
|
||||||
begin
|
begin
|
||||||
// Same node types are checked in GetNodevalue
|
// Same node types are checked in GetNodevalue
|
||||||
end;
|
end; }
|
||||||
|
|
||||||
function TsBooleanResultExprNode.NodeType: TsResultType;
|
function TsBooleanResultExprNode.NodeType: TsResultType;
|
||||||
begin
|
begin
|
||||||
@ -3115,7 +3175,7 @@ end;
|
|||||||
|
|
||||||
|
|
||||||
{ TsOrderingExprNode }
|
{ TsOrderingExprNode }
|
||||||
|
{
|
||||||
procedure TsOrderingExprNode.Check;
|
procedure TsOrderingExprNode.Check;
|
||||||
const
|
const
|
||||||
AllowedTypes = [rtBoolean, rtInteger, rtFloat, rtDateTime, rtString, rtEmpty, rtError, rtCell];
|
AllowedTypes = [rtBoolean, rtInteger, rtFloat, rtDateTime, rtString, rtEmpty, rtError, rtCell];
|
||||||
@ -3124,7 +3184,7 @@ begin
|
|||||||
CheckNodeType(Right, AllowedTypes);
|
CheckNodeType(Right, AllowedTypes);
|
||||||
inherited Check;
|
inherited Check;
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
{ TsLessExprNode }
|
{ TsLessExprNode }
|
||||||
@ -3281,19 +3341,19 @@ function TsConcatExprNode.AsString: string;
|
|||||||
begin
|
begin
|
||||||
Result := Left.AsString + '&' + Right.AsString;
|
Result := Left.AsString + '&' + Right.AsString;
|
||||||
end;
|
end;
|
||||||
|
{
|
||||||
procedure TsConcatExprNode.Check;
|
procedure TsConcatExprNode.Check;
|
||||||
begin
|
begin
|
||||||
inherited Check;
|
inherited Check;
|
||||||
CheckNodeType(Left, [rtString, rtCell, rtEmpty, rtError]);
|
//CheckNodeType(Left, [rtString, rtCell, rtEmpty, rtError]);
|
||||||
CheckNodeType(Right, [rtString, rtCell, rtEmpty, rtError]);
|
//CheckNodeType(Right, [rtString, rtCell, rtEmpty, rtError]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsConcatExprNode.CheckSameNodeTypes;
|
procedure TsConcatExprNode.CheckSameNodeTypes;
|
||||||
begin
|
begin
|
||||||
// Same node types are checked in GetNodevalue
|
// Same node types are checked in GetNodevalue
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
procedure TsConcatExprNode.GetNodeValue(out Result: TsExpressionResult);
|
procedure TsConcatExprNode.GetNodeValue(out Result: TsExpressionResult);
|
||||||
var
|
var
|
||||||
RRes : TsExpressionResult;
|
RRes : TsExpressionResult;
|
||||||
@ -3302,6 +3362,11 @@ begin
|
|||||||
if (Result.ResultType = rtError)
|
if (Result.ResultType = rtError)
|
||||||
then exit;
|
then exit;
|
||||||
Right.GetNodeValue(RRes);
|
Right.GetNodeValue(RRes);
|
||||||
|
if RRes.ResultType = rtError then
|
||||||
|
Result := ErrorResult(RRes.ResError);
|
||||||
|
|
||||||
|
Result := StringResult(ArgToString(Result) + ArgToString(RRes));
|
||||||
|
{
|
||||||
if (Result.ResultType in [rtString, rtCell]) and (RRes.ResultType in [rtString, rtCell])
|
if (Result.ResultType in [rtString, rtCell]) and (RRes.ResultType in [rtString, rtCell])
|
||||||
then Result := StringResult(ArgToString(Result) + ArgToString(RRes))
|
then Result := StringResult(ArgToString(Result) + ArgToString(RRes))
|
||||||
else
|
else
|
||||||
@ -3309,6 +3374,7 @@ begin
|
|||||||
then Result := ErrorResult(RRes.ResError)
|
then Result := ErrorResult(RRes.ResError)
|
||||||
else
|
else
|
||||||
Result := ErrorResult(errWrongType);
|
Result := ErrorResult(errWrongType);
|
||||||
|
}
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TsConcatExprNode.NodeType: TsResultType;
|
function TsConcatExprNode.NodeType: TsResultType;
|
||||||
@ -3318,7 +3384,7 @@ end;
|
|||||||
|
|
||||||
|
|
||||||
{ TsMathOperationExprNode }
|
{ TsMathOperationExprNode }
|
||||||
|
{
|
||||||
procedure TsMathOperationExprNode.Check;
|
procedure TsMathOperationExprNode.Check;
|
||||||
const
|
const
|
||||||
AllowedTypes = [rtInteger, rtFloat, rtDateTime, rtCell, rtEmpty, rtError];
|
AllowedTypes = [rtInteger, rtFloat, rtDateTime, rtCell, rtEmpty, rtError];
|
||||||
@ -3333,6 +3399,7 @@ procedure TsMathOperationExprNode.CheckSameNodeTypes;
|
|||||||
begin
|
begin
|
||||||
// Same node types are checked in GetNodevalue
|
// Same node types are checked in GetNodevalue
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
|
|
||||||
function TsMathOperationExprNode.NodeType: TsResultType;
|
function TsMathOperationExprNode.NodeType: TsResultType;
|
||||||
begin
|
begin
|
||||||
@ -3579,13 +3646,13 @@ end;
|
|||||||
|
|
||||||
|
|
||||||
{ TsIntToFloatExprNode }
|
{ TsIntToFloatExprNode }
|
||||||
|
{
|
||||||
procedure TsConvertToIntExprNode.Check;
|
procedure TsConvertToIntExprNode.Check;
|
||||||
begin
|
begin
|
||||||
inherited Check;
|
inherited Check;
|
||||||
CheckNodeType(Operand, [rtInteger, rtCell])
|
CheckNodeType(Operand, [rtInteger, rtCell])
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
procedure TsIntToFloatExprNode.GetNodeValue(out Result: TsExpressionResult);
|
procedure TsIntToFloatExprNode.GetNodeValue(out Result: TsExpressionResult);
|
||||||
begin
|
begin
|
||||||
Operand.GetNodeValue(Result);
|
Operand.GetNodeValue(Result);
|
||||||
@ -3615,13 +3682,13 @@ end;
|
|||||||
|
|
||||||
|
|
||||||
{ TsFloatToDateTimeExprNode }
|
{ TsFloatToDateTimeExprNode }
|
||||||
|
{
|
||||||
procedure TsFloatToDateTimeExprNode.Check;
|
procedure TsFloatToDateTimeExprNode.Check;
|
||||||
begin
|
begin
|
||||||
inherited Check;
|
inherited Check;
|
||||||
CheckNodeType(Operand, [rtFloat, rtCell]);
|
CheckNodeType(Operand, [rtFloat, rtCell]);
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
function TsFloatToDateTimeExprNode.NodeType: TsResultType;
|
function TsFloatToDateTimeExprNode.NodeType: TsResultType;
|
||||||
begin
|
begin
|
||||||
Result := rtDateTime;
|
Result := rtDateTime;
|
||||||
|
Loading…
Reference in New Issue
Block a user