Better binding for index expressions
This commit is contained in:
parent
eeecd0225a
commit
65ae6f6f06
|
@ -1,6 +1,5 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Collections.Immutable;
|
using System.Collections.Immutable;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
@ -8,8 +7,6 @@ using Upsilon.BaseTypes.Number;
|
||||||
using Upsilon.BaseTypes.ScriptFunction;
|
using Upsilon.BaseTypes.ScriptFunction;
|
||||||
using Upsilon.BaseTypes.ScriptTypeInterfaces;
|
using Upsilon.BaseTypes.ScriptTypeInterfaces;
|
||||||
using Upsilon.BaseTypes.UserData;
|
using Upsilon.BaseTypes.UserData;
|
||||||
using Upsilon.BoundTypes;
|
|
||||||
using Upsilon.Text;
|
|
||||||
|
|
||||||
namespace Upsilon.BaseTypes
|
namespace Upsilon.BaseTypes
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Collections.Immutable;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using Upsilon.BaseTypes.Number;
|
using Upsilon.BaseTypes.Number;
|
||||||
using Upsilon.BaseTypes.ScriptTypeInterfaces;
|
using Upsilon.BaseTypes.ScriptTypeInterfaces;
|
||||||
|
@ -17,7 +18,27 @@ namespace Upsilon.BaseTypes.UserData
|
||||||
public DictionaryUserData(IDictionary dictionary)
|
public DictionaryUserData(IDictionary dictionary)
|
||||||
{
|
{
|
||||||
Dictionary = dictionary;
|
Dictionary = dictionary;
|
||||||
BoundTypeName = BoundTypeHandler.GetTypeName(dictionary.GetType());
|
var type = dictionary.GetType();
|
||||||
|
var generics = type.GetGenericArguments();
|
||||||
|
if (generics.Length == 2)
|
||||||
|
{
|
||||||
|
var keyType = generics[0];
|
||||||
|
var valueType = generics[1];
|
||||||
|
var boundKeyType = BoundTypeHandler.GetTypeName(keyType);
|
||||||
|
var boundValueType = BoundTypeHandler.GetTypeName(valueType);
|
||||||
|
var boundKey = boundKeyType == null
|
||||||
|
? new UndefinedUserDataTypeContainer(keyType)
|
||||||
|
: new TypeContainer(boundKeyType);
|
||||||
|
var boundValue = boundValueType == null
|
||||||
|
? new UndefinedUserDataTypeContainer(valueType)
|
||||||
|
: new TypeContainer(boundValueType);
|
||||||
|
Type = new CompositeTypeContainer(new[] {boundKey, boundValue}.ToImmutableArray());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
BoundTypeName = BoundTypeHandler.GetTypeName(type);
|
||||||
|
Type = BoundTypeName == null ? new UndefinedUserDataTypeContainer(type) : new TypeContainer(BoundTypeName);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public ScriptType Get(Diagnostics diagnostics, TextSpan span, ScriptType index, EvaluationScope scope)
|
public ScriptType Get(Diagnostics diagnostics, TextSpan span, ScriptType index, EvaluationScope scope)
|
||||||
|
@ -44,7 +65,7 @@ namespace Upsilon.BaseTypes.UserData
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public override TypeContainer Type => new TypeContainer(BoundTypeName);
|
public override TypeContainer Type { get; }
|
||||||
public override object ToCSharpObject()
|
public override object ToCSharpObject()
|
||||||
{
|
{
|
||||||
return Dictionary;
|
return Dictionary;
|
||||||
|
|
|
@ -504,10 +504,18 @@ namespace Upsilon.Binder
|
||||||
variable = new VariableSymbol(name, Type.Unknown, isLocal);
|
variable = new VariableSymbol(name, Type.Unknown, isLocal);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
{
|
||||||
|
var boundType = BoundTypeHandler.GetTypeDefinition(ud);
|
||||||
|
if (boundType != null)
|
||||||
{
|
{
|
||||||
variable = new UserDataVariableSymbol(name,
|
variable = new UserDataVariableSymbol(name,
|
||||||
BoundTypeHandler.GetTypeDefinition(ud), isLocal);
|
BoundTypeHandler.GetTypeDefinition(ud), isLocal);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
variable = new VariableSymbol(name, assignment.Type, isLocal);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -652,6 +660,12 @@ namespace Upsilon.Binder
|
||||||
_diagnostics.LogError($"Unknown type name '{variable.TypeName.Name}'", variable.Span);
|
_diagnostics.LogError($"Unknown type name '{variable.TypeName.Name}'", variable.Span);
|
||||||
variableSymbol = new UserDataVariableSymbol(variable.IdentifierName.Name, Type.Unknown, true);
|
variableSymbol = new UserDataVariableSymbol(variable.IdentifierName.Name, Type.Unknown, true);
|
||||||
}
|
}
|
||||||
|
else if (type.ScriptType == Type.Table)
|
||||||
|
{
|
||||||
|
variableSymbol = new TableVariableSymbol(variable.IdentifierName.Name, true,
|
||||||
|
new CompositeTypeContainer(
|
||||||
|
new TypeContainer[] {Type.Unknown, Type.Unknown}.ToImmutableArray()));
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
variableSymbol = new UserDataVariableSymbol(variable.IdentifierName.Name, type, true);
|
variableSymbol = new UserDataVariableSymbol(variable.IdentifierName.Name, type, true);
|
||||||
|
@ -843,6 +857,10 @@ namespace Upsilon.Binder
|
||||||
_diagnostics.LogError($"No variable '{realIndex.Value}' found in table '{realTable.VariableSymbol.Name}'.",
|
_diagnostics.LogError($"No variable '{realIndex.Value}' found in table '{realTable.VariableSymbol.Name}'.",
|
||||||
e.Span);
|
e.Span);
|
||||||
}
|
}
|
||||||
|
else if (expression.Type is CompositeTypeContainer compositeTypeContainer)
|
||||||
|
{
|
||||||
|
return new BoundIndexExpression(expression, index, compositeTypeContainer.Types[1], e.Span);
|
||||||
|
}
|
||||||
return new BoundIndexExpression(expression, index, Type.Unknown, e.Span);
|
return new BoundIndexExpression(expression, index, Type.Unknown, e.Span);
|
||||||
case Type.UserData:
|
case Type.UserData:
|
||||||
case Type.Unknown:
|
case Type.Unknown:
|
||||||
|
|
|
@ -7,7 +7,7 @@ namespace Upsilon.Binder
|
||||||
{
|
{
|
||||||
public class BoundIndexExpression : BoundExpression
|
public class BoundIndexExpression : BoundExpression
|
||||||
{
|
{
|
||||||
public BoundIndexExpression(BoundExpression identifier, BoundExpression index, Type type, TextSpan span) : base(span)
|
public BoundIndexExpression(BoundExpression identifier, BoundExpression index, TypeContainer type, TextSpan span) : base(span)
|
||||||
{
|
{
|
||||||
Identifier = identifier;
|
Identifier = identifier;
|
||||||
Index = index;
|
Index = index;
|
||||||
|
|
Loading…
Reference in New Issue