Fix patterns not working with yields
This commit is contained in:
parent
5486f6b6ea
commit
038d6fe839
|
|
@ -1172,6 +1172,11 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
DefaultVisit(_recursive_deconstructor_parameter);
|
||||
}
|
||||
|
||||
public virtual void visit(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
DefaultVisit(_deconstruction_variables_definition);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -1869,6 +1869,14 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
}
|
||||
|
||||
public virtual void pre_do_visit(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
}
|
||||
|
||||
public virtual void post_do_visit(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
}
|
||||
|
||||
public override void visit(expression _expression)
|
||||
{
|
||||
DefaultVisit(_expression);
|
||||
|
|
@ -3847,8 +3855,8 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
DefaultVisit(_desugared_deconstruction);
|
||||
pre_do_visit(_desugared_deconstruction);
|
||||
for (int i = 0; i < definitions.Count; i++)
|
||||
visit(desugared_deconstruction.definitions[i]);
|
||||
visit(desugared_deconstruction.variables);
|
||||
visit(desugared_deconstruction.deconstruction_target);
|
||||
post_do_visit(_desugared_deconstruction);
|
||||
}
|
||||
|
||||
|
|
@ -3868,6 +3876,15 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
visit(recursive_deconstructor_parameter.pattern);
|
||||
post_do_visit(_recursive_deconstructor_parameter);
|
||||
}
|
||||
|
||||
public override void visit(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
DefaultVisit(_deconstruction_variables_definition);
|
||||
pre_do_visit(_deconstruction_variables_definition);
|
||||
for (int i = 0; i < definitions.Count; i++)
|
||||
visit(deconstruction_variables_definition.definitions[i]);
|
||||
post_do_visit(_deconstruction_variables_definition);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -486,6 +486,8 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
return new var_deconstructor_parameter();
|
||||
case 232:
|
||||
return new recursive_deconstructor_parameter();
|
||||
case 233:
|
||||
return new deconstruction_variables_definition();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
|
@ -4076,20 +4078,8 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
public void read_desugared_deconstruction(desugared_deconstruction _desugared_deconstruction)
|
||||
{
|
||||
read_statement(_desugared_deconstruction);
|
||||
if (br.ReadByte() == 0)
|
||||
{
|
||||
_desugared_deconstruction.definitions = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
_desugared_deconstruction.definitions = new List<var_def_statement>();
|
||||
Int32 ssyy_count = br.ReadInt32();
|
||||
for(Int32 ssyy_i = 0; ssyy_i < ssyy_count; ssyy_i++)
|
||||
{
|
||||
_desugared_deconstruction.definitions.Add(_read_node() as var_def_statement);
|
||||
}
|
||||
}
|
||||
_desugared_deconstruction.deconstruction_target = (object)br.ReadByte();
|
||||
_desugared_deconstruction.variables = _read_node() as deconstruction_variables_definition;
|
||||
_desugared_deconstruction.deconstruction_target = _read_node() as expression;
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -4117,6 +4107,30 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
_recursive_deconstructor_parameter.pattern = _read_node() as pattern_node;
|
||||
}
|
||||
|
||||
|
||||
public void visit(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
read_deconstruction_variables_definition(_deconstruction_variables_definition);
|
||||
}
|
||||
|
||||
public void read_deconstruction_variables_definition(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
read_declaration(_deconstruction_variables_definition);
|
||||
if (br.ReadByte() == 0)
|
||||
{
|
||||
_deconstruction_variables_definition.definitions = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
_deconstruction_variables_definition.definitions = new List<var_def_statement>();
|
||||
Int32 ssyy_count = br.ReadInt32();
|
||||
for(Int32 ssyy_i = 0; ssyy_i < ssyy_count; ssyy_i++)
|
||||
{
|
||||
_deconstruction_variables_definition.definitions.Add(_read_node() as var_def_statement);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -6386,28 +6386,24 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
public void write_desugared_deconstruction(desugared_deconstruction _desugared_deconstruction)
|
||||
{
|
||||
write_statement(_desugared_deconstruction);
|
||||
if (_desugared_deconstruction.definitions == null)
|
||||
if (_desugared_deconstruction.variables == null)
|
||||
{
|
||||
bw.Write((byte)0);
|
||||
}
|
||||
else
|
||||
{
|
||||
bw.Write((byte)1);
|
||||
bw.Write(_desugared_deconstruction.definitions.Count);
|
||||
for(Int32 ssyy_i = 0; ssyy_i < _desugared_deconstruction.definitions.Count; ssyy_i++)
|
||||
{
|
||||
if (_desugared_deconstruction.definitions[ssyy_i] == null)
|
||||
{
|
||||
bw.Write((byte)0);
|
||||
}
|
||||
else
|
||||
{
|
||||
bw.Write((byte)1);
|
||||
_desugared_deconstruction.definitions[ssyy_i].visit(this);
|
||||
}
|
||||
}
|
||||
_desugared_deconstruction.variables.visit(this);
|
||||
}
|
||||
if (_desugared_deconstruction.deconstruction_target == null)
|
||||
{
|
||||
bw.Write((byte)0);
|
||||
}
|
||||
else
|
||||
{
|
||||
bw.Write((byte)1);
|
||||
_desugared_deconstruction.deconstruction_target.visit(this);
|
||||
}
|
||||
bw.Write((byte)_desugared_deconstruction.deconstruction_target);
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -6461,6 +6457,39 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
public void visit(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
bw.Write((Int16)233);
|
||||
write_deconstruction_variables_definition(_deconstruction_variables_definition);
|
||||
}
|
||||
|
||||
public void write_deconstruction_variables_definition(deconstruction_variables_definition _deconstruction_variables_definition)
|
||||
{
|
||||
write_declaration(_deconstruction_variables_definition);
|
||||
if (_deconstruction_variables_definition.definitions == null)
|
||||
{
|
||||
bw.Write((byte)0);
|
||||
}
|
||||
else
|
||||
{
|
||||
bw.Write((byte)1);
|
||||
bw.Write(_deconstruction_variables_definition.definitions.Count);
|
||||
for(Int32 ssyy_i = 0; ssyy_i < _deconstruction_variables_definition.definitions.Count; ssyy_i++)
|
||||
{
|
||||
if (_deconstruction_variables_definition.definitions[ssyy_i] == null)
|
||||
{
|
||||
bw.Write((byte)0);
|
||||
}
|
||||
else
|
||||
{
|
||||
bw.Write((byte)1);
|
||||
_deconstruction_variables_definition.definitions[ssyy_i].visit(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -49078,7 +49078,7 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
|
||||
|
||||
///<summary>
|
||||
///Представляет объединение объявлений пременных, порожденных деконструкцией. Деконструируемое выражение необходимо хранить для выведения типа на этапе семантики, однако оно не должно входить в обход дерева.
|
||||
///Представляет объединение объявлений пременных, порожденных деконструкцией. Деконструируемое выражение необходимо хранить для выведения типа на этапе семантики.
|
||||
///</summary>
|
||||
[Serializable]
|
||||
public partial class desugared_deconstruction : statement
|
||||
|
|
@ -49095,9 +49095,9 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
///<summary>
|
||||
///Конструктор с параметрами.
|
||||
///</summary>
|
||||
public desugared_deconstruction(List<var_def_statement> _definitions,object _deconstruction_target)
|
||||
public desugared_deconstruction(deconstruction_variables_definition _variables,expression _deconstruction_target)
|
||||
{
|
||||
this._definitions=_definitions;
|
||||
this._variables=_variables;
|
||||
this._deconstruction_target=_deconstruction_target;
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
|
|
@ -49105,41 +49105,35 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
///<summary>
|
||||
///Конструктор с параметрами.
|
||||
///</summary>
|
||||
public desugared_deconstruction(List<var_def_statement> _definitions,object _deconstruction_target,SourceContext sc)
|
||||
public desugared_deconstruction(deconstruction_variables_definition _variables,expression _deconstruction_target,SourceContext sc)
|
||||
{
|
||||
this._definitions=_definitions;
|
||||
this._variables=_variables;
|
||||
this._deconstruction_target=_deconstruction_target;
|
||||
source_context = sc;
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
public desugared_deconstruction(var_def_statement elem, SourceContext sc = null)
|
||||
{
|
||||
Add(elem, sc);
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
|
||||
protected List<var_def_statement> _definitions=new List<var_def_statement>();
|
||||
protected object _deconstruction_target;
|
||||
protected deconstruction_variables_definition _variables;
|
||||
protected expression _deconstruction_target;
|
||||
|
||||
///<summary>
|
||||
///Объявления порожденных переменных
|
||||
///</summary>
|
||||
public List<var_def_statement> definitions
|
||||
public deconstruction_variables_definition variables
|
||||
{
|
||||
get
|
||||
{
|
||||
return _definitions;
|
||||
return _variables;
|
||||
}
|
||||
set
|
||||
{
|
||||
_definitions=value;
|
||||
_variables=value;
|
||||
}
|
||||
}
|
||||
|
||||
///<summary>
|
||||
///Деконструируемое выражение
|
||||
///</summary>
|
||||
public object deconstruction_target
|
||||
public expression deconstruction_target
|
||||
{
|
||||
get
|
||||
{
|
||||
|
|
@ -49152,154 +49146,6 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
}
|
||||
|
||||
|
||||
public desugared_deconstruction Add(var_def_statement elem, SourceContext sc = null)
|
||||
{
|
||||
definitions.Add(elem);
|
||||
if (elem != null)
|
||||
elem.Parent = this;
|
||||
if (sc != null)
|
||||
source_context = sc;
|
||||
return this;
|
||||
}
|
||||
|
||||
public void AddFirst(var_def_statement el)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
definitions.Insert(0, el);
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
|
||||
public void AddFirst(IEnumerable<var_def_statement> els)
|
||||
{
|
||||
if (els == null)
|
||||
throw new ArgumentNullException(nameof(els));
|
||||
definitions.InsertRange(0, els);
|
||||
foreach (var el in els)
|
||||
if (el != null)
|
||||
el.Parent = this;
|
||||
}
|
||||
|
||||
public void AddMany(params var_def_statement[] els)
|
||||
{
|
||||
if (els == null)
|
||||
throw new ArgumentNullException(nameof(els));
|
||||
definitions.AddRange(els);
|
||||
foreach (var el in els)
|
||||
if (el != null)
|
||||
el.Parent = this;
|
||||
}
|
||||
|
||||
private int FindIndexInList(var_def_statement el)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
var ind = definitions.FindIndex(x => x == el);
|
||||
if (ind == -1)
|
||||
throw new Exception(string.Format("У списка {0} не найден элемент {1} среди дочерних\n", this, el));
|
||||
return ind;
|
||||
}
|
||||
|
||||
public void InsertAfter(var_def_statement el, var_def_statement newel)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newel == null)
|
||||
throw new ArgumentNullException(nameof(newel));
|
||||
definitions.Insert(FindIndexInList(el) + 1, newel);
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void InsertAfter(var_def_statement el, IEnumerable<var_def_statement> newels)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newels == null)
|
||||
throw new ArgumentNullException(nameof(newels));
|
||||
definitions.InsertRange(FindIndexInList(el) + 1, newels);
|
||||
foreach (var newel in newels)
|
||||
if (newel != null)
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void InsertBefore(var_def_statement el, var_def_statement newel)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newel == null)
|
||||
throw new ArgumentNullException(nameof(newel));
|
||||
definitions.Insert(FindIndexInList(el), newel);
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void InsertBefore(var_def_statement el, IEnumerable<var_def_statement> newels)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newels == null)
|
||||
throw new ArgumentNullException(nameof(newels));
|
||||
definitions.InsertRange(FindIndexInList(el), newels);
|
||||
foreach (var newel in newels)
|
||||
if (newel != null)
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public bool Remove(var_def_statement el)
|
||||
{
|
||||
return definitions.Remove(el);
|
||||
}
|
||||
|
||||
public void ReplaceInList(var_def_statement el, var_def_statement newel)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newel == null)
|
||||
throw new ArgumentNullException(nameof(newel));
|
||||
definitions[FindIndexInList(el)] = newel;
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void ReplaceInList(var_def_statement el, IEnumerable<var_def_statement> newels)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newels == null)
|
||||
throw new ArgumentNullException(nameof(newels));
|
||||
var ind = FindIndexInList(el);
|
||||
definitions.RemoveAt(ind);
|
||||
definitions.InsertRange(ind, newels);
|
||||
foreach (var newel in newels)
|
||||
if (newel != null)
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public int RemoveAll(Predicate<var_def_statement> match)
|
||||
{
|
||||
return definitions.RemoveAll(match);
|
||||
}
|
||||
|
||||
public var_def_statement Last()
|
||||
{
|
||||
if (definitions.Count > 0)
|
||||
return definitions[definitions.Count - 1];
|
||||
throw new InvalidOperationException("Список пуст");
|
||||
}
|
||||
|
||||
public int Count
|
||||
{
|
||||
get { return definitions.Count; }
|
||||
}
|
||||
|
||||
public void Insert(int pos, var_def_statement el)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
definitions.Insert(pos,el);
|
||||
if (el != null)
|
||||
el.Parent = this;
|
||||
}
|
||||
|
||||
|
||||
/// <summary> Создает копию узла </summary>
|
||||
public override syntax_tree_node Clone()
|
||||
{
|
||||
|
|
@ -49312,20 +49158,16 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
copy.attributes = (attribute_list)attributes.Clone();
|
||||
copy.attributes.Parent = copy;
|
||||
}
|
||||
if (definitions != null)
|
||||
if (variables != null)
|
||||
{
|
||||
foreach (var_def_statement elem in definitions)
|
||||
{
|
||||
if (elem != null)
|
||||
{
|
||||
copy.Add((var_def_statement)elem.Clone());
|
||||
copy.Last().Parent = copy;
|
||||
}
|
||||
else
|
||||
copy.Add(null);
|
||||
}
|
||||
copy.variables = (deconstruction_variables_definition)variables.Clone();
|
||||
copy.variables.Parent = copy;
|
||||
}
|
||||
if (deconstruction_target != null)
|
||||
{
|
||||
copy.deconstruction_target = (expression)deconstruction_target.Clone();
|
||||
copy.deconstruction_target.Parent = copy;
|
||||
}
|
||||
copy.deconstruction_target = deconstruction_target;
|
||||
return copy;
|
||||
}
|
||||
|
||||
|
|
@ -49340,12 +49182,10 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
if (attributes != null)
|
||||
attributes.Parent = this;
|
||||
if (definitions != null)
|
||||
{
|
||||
foreach (var child in definitions)
|
||||
if (child != null)
|
||||
child.Parent = this;
|
||||
}
|
||||
if (variables != null)
|
||||
variables.Parent = this;
|
||||
if (deconstruction_target != null)
|
||||
deconstruction_target.Parent = this;
|
||||
}
|
||||
|
||||
///<summary> Заполняет поля Parent во всем поддереве </summary>
|
||||
|
|
@ -49353,11 +49193,8 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
FillParentsInDirectChilds();
|
||||
attributes?.FillParentsInAllChilds();
|
||||
if (definitions != null)
|
||||
{
|
||||
foreach (var child in definitions)
|
||||
child?.FillParentsInAllChilds();
|
||||
}
|
||||
variables?.FillParentsInAllChilds();
|
||||
deconstruction_target?.FillParentsInAllChilds();
|
||||
}
|
||||
|
||||
///<summary>
|
||||
|
|
@ -49367,7 +49204,7 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
get
|
||||
{
|
||||
return 0;
|
||||
return 2;
|
||||
}
|
||||
}
|
||||
///<summary>
|
||||
|
|
@ -49377,7 +49214,7 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
get
|
||||
{
|
||||
return 0 + (definitions == null ? 0 : definitions.Count);
|
||||
return 2;
|
||||
}
|
||||
}
|
||||
///<summary>
|
||||
|
|
@ -49389,13 +49226,12 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
if(subnodes_count == 0 || ind < 0 || ind > subnodes_count-1)
|
||||
throw new IndexOutOfRangeException();
|
||||
Int32 index_counter=ind - 0;
|
||||
if(definitions != null)
|
||||
switch(ind)
|
||||
{
|
||||
if(index_counter < definitions.Count)
|
||||
{
|
||||
return definitions[index_counter];
|
||||
}
|
||||
case 0:
|
||||
return variables;
|
||||
case 1:
|
||||
return deconstruction_target;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
|
@ -49403,14 +49239,14 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
{
|
||||
if(subnodes_count == 0 || ind < 0 || ind > subnodes_count-1)
|
||||
throw new IndexOutOfRangeException();
|
||||
Int32 index_counter=ind - 0;
|
||||
if(definitions != null)
|
||||
switch(ind)
|
||||
{
|
||||
if(index_counter < definitions.Count)
|
||||
{
|
||||
definitions[index_counter]= (var_def_statement)value;
|
||||
return;
|
||||
}
|
||||
case 0:
|
||||
variables = (deconstruction_variables_definition)value;
|
||||
break;
|
||||
case 1:
|
||||
deconstruction_target = (expression)value;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -49752,6 +49588,337 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
}
|
||||
|
||||
|
||||
///<summary>
|
||||
///Список объявлений для deconstructor pattern
|
||||
///</summary>
|
||||
[Serializable]
|
||||
public partial class deconstruction_variables_definition : declaration
|
||||
{
|
||||
|
||||
///<summary>
|
||||
///Конструктор без параметров.
|
||||
///</summary>
|
||||
public deconstruction_variables_definition()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
///<summary>
|
||||
///Конструктор с параметрами.
|
||||
///</summary>
|
||||
public deconstruction_variables_definition(List<var_def_statement> _definitions)
|
||||
{
|
||||
this._definitions=_definitions;
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
|
||||
///<summary>
|
||||
///Конструктор с параметрами.
|
||||
///</summary>
|
||||
public deconstruction_variables_definition(List<var_def_statement> _definitions,SourceContext sc)
|
||||
{
|
||||
this._definitions=_definitions;
|
||||
source_context = sc;
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
public deconstruction_variables_definition(var_def_statement elem, SourceContext sc = null)
|
||||
{
|
||||
Add(elem, sc);
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
|
||||
protected List<var_def_statement> _definitions=new List<var_def_statement>();
|
||||
|
||||
///<summary>
|
||||
///
|
||||
///</summary>
|
||||
public List<var_def_statement> definitions
|
||||
{
|
||||
get
|
||||
{
|
||||
return _definitions;
|
||||
}
|
||||
set
|
||||
{
|
||||
_definitions=value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public deconstruction_variables_definition Add(var_def_statement elem, SourceContext sc = null)
|
||||
{
|
||||
definitions.Add(elem);
|
||||
if (elem != null)
|
||||
elem.Parent = this;
|
||||
if (sc != null)
|
||||
source_context = sc;
|
||||
return this;
|
||||
}
|
||||
|
||||
public void AddFirst(var_def_statement el)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
definitions.Insert(0, el);
|
||||
FillParentsInDirectChilds();
|
||||
}
|
||||
|
||||
public void AddFirst(IEnumerable<var_def_statement> els)
|
||||
{
|
||||
if (els == null)
|
||||
throw new ArgumentNullException(nameof(els));
|
||||
definitions.InsertRange(0, els);
|
||||
foreach (var el in els)
|
||||
if (el != null)
|
||||
el.Parent = this;
|
||||
}
|
||||
|
||||
public void AddMany(params var_def_statement[] els)
|
||||
{
|
||||
if (els == null)
|
||||
throw new ArgumentNullException(nameof(els));
|
||||
definitions.AddRange(els);
|
||||
foreach (var el in els)
|
||||
if (el != null)
|
||||
el.Parent = this;
|
||||
}
|
||||
|
||||
private int FindIndexInList(var_def_statement el)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
var ind = definitions.FindIndex(x => x == el);
|
||||
if (ind == -1)
|
||||
throw new Exception(string.Format("У списка {0} не найден элемент {1} среди дочерних\n", this, el));
|
||||
return ind;
|
||||
}
|
||||
|
||||
public void InsertAfter(var_def_statement el, var_def_statement newel)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newel == null)
|
||||
throw new ArgumentNullException(nameof(newel));
|
||||
definitions.Insert(FindIndexInList(el) + 1, newel);
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void InsertAfter(var_def_statement el, IEnumerable<var_def_statement> newels)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newels == null)
|
||||
throw new ArgumentNullException(nameof(newels));
|
||||
definitions.InsertRange(FindIndexInList(el) + 1, newels);
|
||||
foreach (var newel in newels)
|
||||
if (newel != null)
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void InsertBefore(var_def_statement el, var_def_statement newel)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newel == null)
|
||||
throw new ArgumentNullException(nameof(newel));
|
||||
definitions.Insert(FindIndexInList(el), newel);
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void InsertBefore(var_def_statement el, IEnumerable<var_def_statement> newels)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newels == null)
|
||||
throw new ArgumentNullException(nameof(newels));
|
||||
definitions.InsertRange(FindIndexInList(el), newels);
|
||||
foreach (var newel in newels)
|
||||
if (newel != null)
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public bool Remove(var_def_statement el)
|
||||
{
|
||||
return definitions.Remove(el);
|
||||
}
|
||||
|
||||
public void ReplaceInList(var_def_statement el, var_def_statement newel)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newel == null)
|
||||
throw new ArgumentNullException(nameof(newel));
|
||||
definitions[FindIndexInList(el)] = newel;
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public void ReplaceInList(var_def_statement el, IEnumerable<var_def_statement> newels)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
if (newels == null)
|
||||
throw new ArgumentNullException(nameof(newels));
|
||||
var ind = FindIndexInList(el);
|
||||
definitions.RemoveAt(ind);
|
||||
definitions.InsertRange(ind, newels);
|
||||
foreach (var newel in newels)
|
||||
if (newel != null)
|
||||
newel.Parent = this;
|
||||
}
|
||||
|
||||
public int RemoveAll(Predicate<var_def_statement> match)
|
||||
{
|
||||
return definitions.RemoveAll(match);
|
||||
}
|
||||
|
||||
public var_def_statement Last()
|
||||
{
|
||||
if (definitions.Count > 0)
|
||||
return definitions[definitions.Count - 1];
|
||||
throw new InvalidOperationException("Список пуст");
|
||||
}
|
||||
|
||||
public int Count
|
||||
{
|
||||
get { return definitions.Count; }
|
||||
}
|
||||
|
||||
public void Insert(int pos, var_def_statement el)
|
||||
{
|
||||
if (el == null)
|
||||
throw new ArgumentNullException(nameof(el));
|
||||
definitions.Insert(pos,el);
|
||||
if (el != null)
|
||||
el.Parent = this;
|
||||
}
|
||||
|
||||
|
||||
/// <summary> Создает копию узла </summary>
|
||||
public override syntax_tree_node Clone()
|
||||
{
|
||||
deconstruction_variables_definition copy = new deconstruction_variables_definition();
|
||||
copy.Parent = this.Parent;
|
||||
if (source_context != null)
|
||||
copy.source_context = new SourceContext(source_context);
|
||||
if (attributes != null)
|
||||
{
|
||||
copy.attributes = (attribute_list)attributes.Clone();
|
||||
copy.attributes.Parent = copy;
|
||||
}
|
||||
if (definitions != null)
|
||||
{
|
||||
foreach (var_def_statement elem in definitions)
|
||||
{
|
||||
if (elem != null)
|
||||
{
|
||||
copy.Add((var_def_statement)elem.Clone());
|
||||
copy.Last().Parent = copy;
|
||||
}
|
||||
else
|
||||
copy.Add(null);
|
||||
}
|
||||
}
|
||||
return copy;
|
||||
}
|
||||
|
||||
/// <summary> Получает копию данного узла корректного типа </summary>
|
||||
public new deconstruction_variables_definition TypedClone()
|
||||
{
|
||||
return Clone() as deconstruction_variables_definition;
|
||||
}
|
||||
|
||||
///<summary> Заполняет поля Parent в непосредственных дочерних узлах </summary>
|
||||
public override void FillParentsInDirectChilds()
|
||||
{
|
||||
if (attributes != null)
|
||||
attributes.Parent = this;
|
||||
if (definitions != null)
|
||||
{
|
||||
foreach (var child in definitions)
|
||||
if (child != null)
|
||||
child.Parent = this;
|
||||
}
|
||||
}
|
||||
|
||||
///<summary> Заполняет поля Parent во всем поддереве </summary>
|
||||
public override void FillParentsInAllChilds()
|
||||
{
|
||||
FillParentsInDirectChilds();
|
||||
attributes?.FillParentsInAllChilds();
|
||||
if (definitions != null)
|
||||
{
|
||||
foreach (var child in definitions)
|
||||
child?.FillParentsInAllChilds();
|
||||
}
|
||||
}
|
||||
|
||||
///<summary>
|
||||
///Свойство для получения количества всех подузлов без элементов поля типа List
|
||||
///</summary>
|
||||
public override Int32 subnodes_without_list_elements_count
|
||||
{
|
||||
get
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
///<summary>
|
||||
///Свойство для получения количества всех подузлов. Подузлом также считается каждый элемент поля типа List
|
||||
///</summary>
|
||||
public override Int32 subnodes_count
|
||||
{
|
||||
get
|
||||
{
|
||||
return 0 + (definitions == null ? 0 : definitions.Count);
|
||||
}
|
||||
}
|
||||
///<summary>
|
||||
///Индексатор для получения всех подузлов
|
||||
///</summary>
|
||||
public override syntax_tree_node this[Int32 ind]
|
||||
{
|
||||
get
|
||||
{
|
||||
if(subnodes_count == 0 || ind < 0 || ind > subnodes_count-1)
|
||||
throw new IndexOutOfRangeException();
|
||||
Int32 index_counter=ind - 0;
|
||||
if(definitions != null)
|
||||
{
|
||||
if(index_counter < definitions.Count)
|
||||
{
|
||||
return definitions[index_counter];
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
set
|
||||
{
|
||||
if(subnodes_count == 0 || ind < 0 || ind > subnodes_count-1)
|
||||
throw new IndexOutOfRangeException();
|
||||
Int32 index_counter=ind - 0;
|
||||
if(definitions != null)
|
||||
{
|
||||
if(index_counter < definitions.Count)
|
||||
{
|
||||
definitions[index_counter]= (var_def_statement)value;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
///<summary>
|
||||
///Метод для обхода дерева посетителем
|
||||
///</summary>
|
||||
///<param name="visitor">Объект-посетитель.</param>
|
||||
///<returns>Return value is void</returns>
|
||||
public override void visit(IVisitor visitor)
|
||||
{
|
||||
visitor.visit(this);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -91,17 +91,6 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Переименовывает все идентификаторы с данным значением в поддереве
|
||||
/// </summary>
|
||||
/// <param name="from">Исходное значение</param>
|
||||
/// <param name="to">Новое значение</param>
|
||||
public void RenameIdentifierInDescendants(string from, string to, bool includingThis = true)
|
||||
{
|
||||
foreach (var identifier in DescendantNodes(TraversalType.PostOrder, null, includingThis).OfType<ident>().Where(x => x.name == from))
|
||||
identifier.name = to;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Получает коллекцию предков текущего узла
|
||||
/// </summary>
|
||||
|
|
@ -1762,23 +1751,27 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
|
||||
public partial class desugared_deconstruction
|
||||
{
|
||||
public bool HasAllExplicitTypes => definitions.All(x => x.vars_type != null);
|
||||
public bool HasAllExplicitTypes => variables.definitions.All(x => x.vars_type != null);
|
||||
|
||||
public desugared_deconstruction(List<var_def_statement> variables, expression target, SourceContext context = null)
|
||||
: this(new deconstruction_variables_definition(variables), target, context)
|
||||
{ }
|
||||
|
||||
public var_statement[] WithTypes(type_definition[] types)
|
||||
{
|
||||
var_statement[] result = new var_statement[types.Length];
|
||||
Debug.Assert(types.Length == definitions.Count, "Inconsistent types count");
|
||||
Debug.Assert(types.Length == variables.definitions.Count, "Inconsistent types count");
|
||||
|
||||
for (int i = 0; i < definitions.Count; i++)
|
||||
for (int i = 0; i < variables.definitions.Count; i++)
|
||||
{
|
||||
definitions[i].vars_type = types[i];
|
||||
result[i] = new var_statement(definitions[i]);
|
||||
variables.definitions[i].vars_type = types[i];
|
||||
result[i] = new var_statement(variables.definitions[i]);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public override string ToString() => $"var {string.Join(", ", definitions)}";
|
||||
public override string ToString() => $"var {string.Join(", ", variables.definitions)}";
|
||||
}
|
||||
|
||||
public partial class is_pattern_expr
|
||||
|
|
|
|||
|
|
@ -1402,6 +1402,12 @@ namespace PascalABCCompiler.SyntaxTree
|
|||
///<param name="_recursive_deconstructor_parameter">Node to visit</param>
|
||||
///<returns> Return value is void </returns>
|
||||
void visit(recursive_deconstructor_parameter _recursive_deconstructor_parameter);
|
||||
///<summary>
|
||||
///Method to visit deconstruction_variables_definition.
|
||||
///</summary>
|
||||
///<param name="_deconstruction_variables_definition">Node to visit</param>
|
||||
///<returns> Return value is void </returns>
|
||||
void visit(deconstruction_variables_definition _deconstruction_variables_definition);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -2972,8 +2972,8 @@
|
|||
</SyntaxNode>
|
||||
<SyntaxNode Name="desugared_deconstruction" BaseName="statement">
|
||||
<Fields>
|
||||
<ExtendedField Name="definitions" Type="List<var_def_statement>" CreateVariable="true" DeleteVariable="false" />
|
||||
<ExtendedField Name="deconstruction_target" Type="object" CreateVariable="false" DeleteVariable="false" />
|
||||
<SyntaxField Name="variables" SyntaxType="deconstruction_variables_definition" />
|
||||
<SyntaxField Name="deconstruction_target" SyntaxType="expression" />
|
||||
</Fields>
|
||||
<Methods />
|
||||
<Tags>
|
||||
|
|
@ -3014,6 +3014,20 @@
|
|||
</TagIndices>
|
||||
</Tags>
|
||||
</SyntaxNode>
|
||||
<SyntaxNode Name="deconstruction_variables_definition" BaseName="declaration">
|
||||
<Fields>
|
||||
<ExtendedField Name="definitions" Type="List<var_def_statement>" CreateVariable="true" DeleteVariable="false" />
|
||||
</Fields>
|
||||
<Methods />
|
||||
<Tags>
|
||||
<CategoryIndices>
|
||||
<CategoryIndex>0</CategoryIndex>
|
||||
</CategoryIndices>
|
||||
<TagIndices>
|
||||
<TagIndex>9</TagIndex>
|
||||
</TagIndices>
|
||||
</Tags>
|
||||
</SyntaxNode>
|
||||
</SyntaxNodes>
|
||||
<Settings>
|
||||
<FileName>Tree.cs</FileName>
|
||||
|
|
@ -3039,7 +3053,7 @@
|
|||
<Tag Name="Важнейшие" ReferenceCount="207" />
|
||||
<Tag Name="Method_Procedure_Call" ReferenceCount="2" />
|
||||
<Tag Name="Yield" ReferenceCount="8" />
|
||||
<Tag Name="Patterns" ReferenceCount="11" />
|
||||
<Tag Name="Patterns" ReferenceCount="12" />
|
||||
</Tags>
|
||||
</FilterCategory>
|
||||
</TagCategories>
|
||||
|
|
@ -3062,6 +3076,7 @@
|
|||
<HelpData Key=".char_num" Value="Номер символа." />
|
||||
<HelpData Key=".count" Value="" />
|
||||
<HelpData Key=".def" Value="" />
|
||||
<HelpData Key=".definitions" Value="" />
|
||||
<HelpData Key=".defs" Value="" />
|
||||
<HelpData Key=".directives" Value="" />
|
||||
<HelpData Key=".el" Value="" />
|
||||
|
|
@ -3341,6 +3356,8 @@
|
|||
<HelpData Key="declarations.void Add(declaration d, SourceContext sc)" Value="" />
|
||||
<HelpData Key="declarations_as_statement" Value="" />
|
||||
<HelpData Key="declarations_as_statement.defs" Value="" />
|
||||
<HelpData Key="deconstruction_variables_definition" Value="Список объявлений для deconstructor pattern" />
|
||||
<HelpData Key="deconstruction_variables_definition.definitions" Value="" />
|
||||
<HelpData Key="deconstructor_pattern" Value="" />
|
||||
<HelpData Key="deconstructor_pattern.parameters" Value="Результат деконструирования" />
|
||||
<HelpData Key="deconstructor_pattern.type" Value="Деконструируемый тип" />
|
||||
|
|
@ -3356,12 +3373,13 @@
|
|||
<HelpData Key="dereference.dereferencing_value" Value="" />
|
||||
<HelpData Key="dereference.override string ToString()" Value="" />
|
||||
<HelpData Key="destructor" Value="" />
|
||||
<HelpData Key="desugared_deconstruction" Value="Представляет объединение объявлений пременных, порожденных деконструкцией. Деконструируемое выражение необходимо хранить для выведения типа на этапе семантики, однако оно не должно входить в обход дерева." />
|
||||
<HelpData Key="desugared_deconstruction" Value="Представляет объединение объявлений пременных, порожденных деконструкцией. Деконструируемое выражение необходимо хранить для выведения типа на этапе семантики." />
|
||||
<HelpData Key="desugared_deconstruction.deconstruct_call" Value="Вызов метода Deconstruct" />
|
||||
<HelpData Key="desugared_deconstruction.deconstruction_target" Value="Деконструируемое выражение" />
|
||||
<HelpData Key="desugared_deconstruction.definitions" Value="Объявления порожденных переменных" />
|
||||
<HelpData Key="desugared_deconstruction.destruct_call" Value="" />
|
||||
<HelpData Key="desugared_deconstruction.expressionVariableName" Value="Деконструируемое выражение" />
|
||||
<HelpData Key="desugared_deconstruction.variables" Value="Объявления порожденных переменных" />
|
||||
<HelpData Key="diap_expr" Value="" />
|
||||
<HelpData Key="diap_expr." Value="" />
|
||||
<HelpData Key="diap_expr.left" Value="" />
|
||||
|
|
|
|||
|
|
@ -46,12 +46,15 @@ namespace PascalABCCompiler.SyntaxTreeConverters
|
|||
PatternsDesugaringVisitor.New.ProcessNode(root);
|
||||
|
||||
|
||||
new SimplePrettyPrinterVisitor("G:\\Tree.txt").ProcessNode(root);
|
||||
|
||||
|
||||
// Всё, связанное с yield
|
||||
MarkMethodHasYieldAndCheckSomeErrorsVisitor.New.ProcessNode(root);
|
||||
ProcessYieldCapturedVarsVisitor.New.ProcessNode(root);
|
||||
|
||||
new SimplePrettyPrinterVisitor("G:\\Tree.txt").ProcessNode(root);
|
||||
FillParentNodeVisitor.New.ProcessNode(root);
|
||||
|
||||
#if DEBUG
|
||||
|
||||
/*var cv = CollectLightSymInfoVisitor.New;
|
||||
|
|
|
|||
|
|
@ -68,7 +68,10 @@ namespace SyntaxVisitors.SugarVisitors
|
|||
private const string IsTestMethodName = compiler_string_consts.is_test_function_name;
|
||||
private const string GeneratedPatternNamePrefix = "<>pattern";
|
||||
|
||||
private int _variableCounter = 0;
|
||||
private int generalVariableCounter = 0;
|
||||
private int successVariableCounter = 0;
|
||||
private int labelVariableCounter = 0;
|
||||
|
||||
private if_node _previousIf;
|
||||
private statement desugaredMatchWith;
|
||||
|
||||
|
|
@ -123,11 +126,11 @@ namespace SyntaxVisitors.SugarVisitors
|
|||
AddDesugaredCaseToResult(ifCheck, ifCheck);
|
||||
}
|
||||
|
||||
private ident NewGeneralName() => new ident(GeneratedPatternNamePrefix + "GenVar" + _variableCounter++);
|
||||
private ident NewGeneralName() => new ident(GeneratedPatternNamePrefix + "GenVar" + generalVariableCounter++);
|
||||
|
||||
private ident NewSuccessName() => new ident(GeneratedPatternNamePrefix + "Success" + _variableCounter++);
|
||||
private ident NewSuccessName() => new ident(GeneratedPatternNamePrefix + "Success" + generalVariableCounter++);
|
||||
|
||||
private ident NewEndIfName() => new ident(GeneratedPatternNamePrefix + "EndIf" + _variableCounter++);
|
||||
private ident NewEndIfName() => new ident(GeneratedPatternNamePrefix + "EndIf" + generalVariableCounter++);
|
||||
|
||||
private bool IsGenerated(string name) => name.StartsWith(GeneratedPatternNamePrefix);
|
||||
|
||||
|
|
@ -282,8 +285,6 @@ namespace SyntaxVisitors.SugarVisitors
|
|||
// if e then <then>
|
||||
// end
|
||||
|
||||
//ifNode = ifNode.TypedClone();
|
||||
|
||||
// Добавляем, чтобы на конвертировать еще раз, если потребуется
|
||||
processedIfNodes.Add(ifNode);
|
||||
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ namespace PascalABCCompiler.TreeConverter
|
|||
public override void visit(desugared_deconstruction deconstruction)
|
||||
{
|
||||
var invokationTarget = convert_strong(deconstruction.deconstruction_target as expression);
|
||||
var types = InferAndCheckPatternVariableTypes(deconstruction.definitions, invokationTarget, deconstruction);
|
||||
var types = InferAndCheckPatternVariableTypes(deconstruction.variables.definitions, invokationTarget, deconstruction);
|
||||
if (types == null)
|
||||
return;
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue