Рефакторинг таблицы символов, чтобы заполнялся только один словарь (#3417)
* Refactor SymbolTable to improve architecture * Fix PABCSystem function calls in SPython standard modules * Fix names search in SymbolTable and CollectNamesFromUsedUnits in Compiler * Add SemanticRulesConstants.SymbolTableCaseSensitive setting in pcu reader * Fix case sensitive search in DSSymbolTable class * Add case sensitive search test cases for SPython * Leave only one dictionary in SymbolsDictionary class * Refactor Find function in SymbolsDictionary * Fix math.pys module * Fix str.pys * Imrove Find method in SymbolsDictionary * DefaultIfEmpty was wrong - need to use Any()
This commit is contained in:
parent
1a787952e9
commit
c69daac622
|
|
@ -2,7 +2,7 @@
|
|||
import PABCSystem
|
||||
|
||||
def random() -> float:
|
||||
return PABCSystem.random()
|
||||
return PABCSystem.Random()
|
||||
|
||||
def randint(a: int, b: int) -> int:
|
||||
return PABCSystem.random(a, b)
|
||||
return PABCSystem.Random(a, b)
|
||||
|
|
@ -3073,30 +3073,44 @@ namespace PascalABCCompiler
|
|||
|
||||
var unitScope = (unit.SemanticTree as common_unit_node).scope;
|
||||
|
||||
foreach (var names in unitScope.Symbols.DictCaseSensitive.Skip(1))
|
||||
// Skip(1) для пропуска имени самого скоупа
|
||||
foreach (var symbolInfos in unitScope.GetAllSymbolInfos().Skip(1))
|
||||
{
|
||||
definition_node symInfo = names.Value.InfoList[0].sym_info;
|
||||
// Составляем список отличающихся по регистру в имени символов из InfoList
|
||||
var distinctNames = new List<TreeConverter.SymbolInfo>();
|
||||
|
||||
foreach (var symInfo in symbolInfos.InfoList)
|
||||
{
|
||||
if (distinctNames.Find(info => info.Name == symInfo.Name) == null)
|
||||
distinctNames.Add(symInfo);
|
||||
}
|
||||
|
||||
foreach (var symInfo in distinctNames)
|
||||
{
|
||||
var node = symInfo.sym_info;
|
||||
|
||||
// Если достаем из pcu, то надо восстановить полную информацию
|
||||
if (symInfo is wrapped_definition_node wdn)
|
||||
if (node is wrapped_definition_node wdn)
|
||||
{
|
||||
// У некоторых дубликатов sym_info offset не задан, ищем тот, где задан
|
||||
symInfo = names.Value.InfoList.Find(si => ((wrapped_definition_node)si.sym_info).offset > 0)?.sym_info;
|
||||
node = symbolInfos.InfoList.Find(si => si.Name == symInfo.Name
|
||||
&& ((wrapped_definition_node)si.sym_info).offset > 0)?.sym_info;
|
||||
|
||||
if (symInfo == null)
|
||||
if (node == null)
|
||||
continue;
|
||||
|
||||
wdn = (wrapped_definition_node)symInfo;
|
||||
wdn = (wrapped_definition_node)node;
|
||||
|
||||
// Если это не синоним типа, то восстанавливаем семантическую информацию
|
||||
if (!wdn.is_synonim)
|
||||
symInfo = wdn.PCUReader.CreateInterfaceMember(wdn.offset, names.Key);
|
||||
node = wdn.PCUReader.CreateInterfaceMember(wdn.offset, symInfo.Name);
|
||||
}
|
||||
|
||||
currentUnit.NamesFromUsedUnits[unitName].Add(names.Key,
|
||||
symInfo.general_node_type == general_node_type.variable_node
|
||||
|| symInfo.general_node_type == general_node_type.constant_definition
|
||||
|| symInfo.general_node_type == general_node_type.event_node);
|
||||
currentUnit.NamesFromUsedUnits[unitName].Add(symInfo.Name,
|
||||
node.general_node_type == general_node_type.variable_node
|
||||
|| node.general_node_type == general_node_type.constant_definition
|
||||
|| node.general_node_type == general_node_type.event_node);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -279,12 +279,14 @@ namespace PascalABCCompiler.PCU
|
|||
return null; // return comp.RecompileUnit(file_name);
|
||||
}
|
||||
ChangeState(this, PCUReaderWriterState.BeginReadTree, unit);
|
||||
|
||||
var unitLanguage = LanguageProvider.Instance.SelectLanguageByName(pcu_file.languageName);
|
||||
|
||||
// Задаем регистрозависимость таблицы символов для правильного добавления и поиска
|
||||
SemanticRulesConstants.SymbolTableCaseSensitive = unitLanguage.CaseSensitive;
|
||||
|
||||
cun.scope = new WrappedUnitInterfaceScope(this);
|
||||
|
||||
bool unitLanguageCaseSensitive = LanguageProvider.Instance.SelectLanguageByName(pcu_file.languageName).CaseSensitive;
|
||||
|
||||
cun.scope.CaseSensitive = unitLanguageCaseSensitive;
|
||||
|
||||
if (string.Compare(unit_name, StringConstants.pascalSystemUnitName, true)==0)
|
||||
PascalABCCompiler.TreeConverter.syntax_tree_visitor.init_system_module(cun);
|
||||
//ssyy
|
||||
|
|
@ -292,8 +294,6 @@ namespace PascalABCCompiler.PCU
|
|||
cun.implementation_scope = new WrappedUnitImplementationScope(this, cun.scope);
|
||||
//\ssyy
|
||||
|
||||
cun.implementation_scope.CaseSensitive = unitLanguageCaseSensitive;
|
||||
|
||||
string SourceFileName = pcu_file.SourceFileName;
|
||||
if (Path.GetDirectoryName(SourceFileName) == "")
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
s = '123#4\'#\'' #1212
|
||||
s.IndexOf('3').print() #12121
|
||||
s.IndexOf('3').Print() #12121
|
||||
print(s) #1212
|
||||
if True:
|
||||
print(2)
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
from case_sensitive_names_search_helper import *
|
||||
from PABCSystem import Assert
|
||||
|
||||
Assert(FUNC(0) == 'integer')
|
||||
Assert(func(0.0) == 'real')
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
unit case_sensitive_names_search_helper;
|
||||
|
||||
function FUNC(a: integer) : string := 'integer';
|
||||
|
||||
function func(a: real) : string := 'real';
|
||||
|
||||
end.
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
#!Неизвестное имя 'random'
|
||||
from PABCSystem import *
|
||||
|
||||
print(Random(0))
|
||||
print(random(0))
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
#!В модуле 'PABCSystem' не объявлено имя 'random'
|
||||
from PABCSystem import random as rnd
|
||||
|
||||
print(rnd(0))
|
||||
|
|
@ -3,6 +3,7 @@
|
|||
using System;
|
||||
using System.Linq;
|
||||
using System.Collections.Generic;
|
||||
using PascalABCCompiler.TreeConverter;
|
||||
|
||||
namespace SymbolTable
|
||||
{
|
||||
|
|
@ -12,106 +13,72 @@ namespace SymbolTable
|
|||
/// </summary>
|
||||
public class SymbolsDictionary
|
||||
{
|
||||
public override string ToString() => dictCaseInsensitive.SkipWhile(x => x.Key != "").Skip(1).JoinIntoString(Environment.NewLine);
|
||||
public override string ToString() => namesToInfos.SkipWhile(x => x.Key != "").Skip(1).JoinIntoString(Environment.NewLine);
|
||||
|
||||
private Dictionary<string, HashTableNode> dictCaseSensitive;
|
||||
// Регистронезависимый словарь символов
|
||||
private readonly Dictionary<string, HashTableNode> namesToInfos = new Dictionary<string, HashTableNode>(StringComparer.OrdinalIgnoreCase);
|
||||
|
||||
public Dictionary<string, HashTableNode> DictCaseSensitive
|
||||
{
|
||||
get
|
||||
{
|
||||
if (dictCaseSensitive.Count == 0)
|
||||
{
|
||||
dictCaseSensitive = new Dictionary<string, HashTableNode>(dictCaseInsensitive);
|
||||
}
|
||||
|
||||
return dictCaseSensitive;
|
||||
}
|
||||
}
|
||||
|
||||
private Dictionary<string, HashTableNode> dictCaseInsensitive;
|
||||
|
||||
public SymbolsDictionary()
|
||||
{
|
||||
dictCaseSensitive = new Dictionary<string, HashTableNode>();
|
||||
|
||||
dictCaseInsensitive = new Dictionary<string, HashTableNode>(StringComparer.OrdinalIgnoreCase);
|
||||
}
|
||||
|
||||
public SymbolsDictionary(int start_size)
|
||||
{
|
||||
dictCaseInsensitive = new Dictionary<string, HashTableNode>(start_size, StringComparer.OrdinalIgnoreCase);
|
||||
}
|
||||
//public SymbolsDictionary(int start_size)
|
||||
//{
|
||||
// dictCaseInsensitive = new Dictionary<string, HashTableNode>(start_size, StringComparer.OrdinalIgnoreCase);
|
||||
//}
|
||||
|
||||
/// <summary>
|
||||
/// Очистка сохраненных символов
|
||||
/// </summary>
|
||||
public void ClearTable()
|
||||
{
|
||||
dictCaseSensitive.Clear();
|
||||
|
||||
dictCaseInsensitive.Clear();
|
||||
namesToInfos.Clear();
|
||||
}
|
||||
|
||||
public HashTableNode Add(string name, bool toCaseSensitive, PascalABCCompiler.TreeConverter.SymbolInfo info)
|
||||
/// <summary>
|
||||
/// Добавить информацию info о символе с именем name
|
||||
/// </summary>
|
||||
public void Add(string name, SymbolInfo info)
|
||||
{
|
||||
HashTableNode node;
|
||||
|
||||
if (toCaseSensitive)
|
||||
{
|
||||
bool exists = dictCaseSensitive.TryGetValue(name, out node);
|
||||
bool exists = namesToInfos.TryGetValue(name, out var node);
|
||||
|
||||
if (!exists)
|
||||
{
|
||||
node = new HashTableNode(name);
|
||||
node = new HashTableNode();
|
||||
|
||||
dictCaseSensitive[name] = node;
|
||||
|
||||
bool existsInInsensitive = dictCaseInsensitive.TryGetValue(name, out var node2);
|
||||
|
||||
if (existsInInsensitive)
|
||||
{
|
||||
node2.InfoList.Add(info);
|
||||
}
|
||||
else
|
||||
{
|
||||
var nodeCopy = new HashTableNode(name);
|
||||
|
||||
nodeCopy.InfoList.Add(info);
|
||||
|
||||
dictCaseInsensitive[name] = nodeCopy;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
bool exists = dictCaseInsensitive.TryGetValue(name, out node);
|
||||
|
||||
if (!exists)
|
||||
{
|
||||
node = new HashTableNode(name);
|
||||
|
||||
dictCaseInsensitive[name] = node;
|
||||
}
|
||||
namesToInfos[name] = node;
|
||||
}
|
||||
|
||||
node.InfoList.Add(info);
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
public HashTableNode Find(string name, bool inCaseSensitive)
|
||||
/// <summary>
|
||||
/// Найти информацию о символе с именем name.
|
||||
/// caseSensitiveSearch определяет регистрозависимость поиска
|
||||
/// </summary>
|
||||
public IEnumerable<SymbolInfo> Find(string name, bool caseSensitiveSearch)
|
||||
{
|
||||
HashTableNode node;
|
||||
|
||||
if (inCaseSensitive)
|
||||
// Если ищем регистрозависимо
|
||||
if (caseSensitiveSearch)
|
||||
{
|
||||
if (namesToInfos.TryGetValue(name, out var node))
|
||||
{
|
||||
// Если есть точные совпадения, то надо взять только их
|
||||
var infos = node.InfoList.Where(info => info.Name == name);
|
||||
|
||||
DictCaseSensitive.TryGetValue(name, out node);
|
||||
if (infos.Any())
|
||||
return infos;
|
||||
}
|
||||
}
|
||||
// Если ищем регистронезависимо
|
||||
else
|
||||
{
|
||||
dictCaseInsensitive.TryGetValue(name, out node);
|
||||
if (namesToInfos.TryGetValue(name, out var node))
|
||||
return node.InfoList;
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Получить информацию обо всех сохраненных символах
|
||||
/// </summary>
|
||||
public IEnumerable<HashTableNode> GetAllSymbolInfos() => namesToInfos.Values;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ using PascalABCCompiler.TreeConverter;
|
|||
using System.Collections.Generic;
|
||||
using SymbolTable;
|
||||
using System.Reflection;
|
||||
using PascalABCCompiler.TreeRealization;
|
||||
using static PascalABCCompiler.TreeConverter.SemanticRulesConstants;
|
||||
|
||||
namespace PascalABCCompiler.TreeRealization
|
||||
{
|
||||
|
|
@ -245,7 +245,13 @@ namespace SymbolTable
|
|||
public void AddSymbol(string Name, SymbolInfo Inf)
|
||||
{
|
||||
SymbolTable.Add(this, Name, Inf);
|
||||
Inf.Name = Name;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Получить информацию обо всех символах скоупа
|
||||
/// </summary>
|
||||
public IEnumerable<HashTableNode> GetAllSymbolInfos() => Symbols.GetAllSymbolInfos();
|
||||
}
|
||||
|
||||
public class BlockScope : Scope
|
||||
|
|
@ -472,13 +478,17 @@ namespace SymbolTable
|
|||
#region HashTableNode элемент хеш-таблицы
|
||||
public class HashTableNode
|
||||
{
|
||||
public string Name;
|
||||
public List<SymbolInfo> InfoList;
|
||||
public HashTableNode(string name)
|
||||
public HashTableNode()
|
||||
{
|
||||
Name = name;
|
||||
InfoList = new List<SymbolInfo>(SymbolTableConstants.InfoList_StartSize);
|
||||
}
|
||||
|
||||
public HashTableNode(List<SymbolInfo> infoList)
|
||||
{
|
||||
InfoList = infoList;
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
System.Text.StringBuilder str = new System.Text.StringBuilder();
|
||||
|
|
@ -596,8 +606,6 @@ namespace SymbolTable
|
|||
{
|
||||
public List<Scope> ScopeTable;
|
||||
|
||||
internal bool CaseSensitive;
|
||||
|
||||
private Scope CurrentScope;
|
||||
private int ScopeIndex = -1;
|
||||
|
||||
|
|
@ -642,9 +650,8 @@ namespace SymbolTable
|
|||
}*/
|
||||
|
||||
#region DSSymbolTable(int hash_size,bool case_sensitive)
|
||||
public DSSymbolTable(int hash_size,bool case_sensitive)
|
||||
public DSSymbolTable(int hash_size)
|
||||
{
|
||||
CaseSensitive = case_sensitive;
|
||||
Clear();
|
||||
}
|
||||
#endregion
|
||||
|
|
@ -720,8 +727,8 @@ namespace SymbolTable
|
|||
public void Add(Scope InScope, string Name, SymbolInfo Inf)
|
||||
{
|
||||
Inf.scope = InScope;
|
||||
// if (!InScope.CaseSensitive) Name = Name.ToLower();
|
||||
var hn = InScope.Symbols.Add(Name, InScope.CaseSensitive, Inf);//ЗДЕСЬ ВОЗНИКАЕТ НЕДЕТЕРМЕНИРОВАННАЯ ОШИБКА - SSM 07.10.17 - странный комментарий. Вроде всё нормально.
|
||||
InScope.Symbols.Add(Name, Inf);
|
||||
|
||||
// SSM 07.10.17 - переделал внутреннее представление HashTable на основе Dictionary
|
||||
//if (hn == null)
|
||||
// throw new Exception("Попытка добавить уже добавленное имя " + Name + " в HashTable. Обратитесь к разработчикам");
|
||||
|
|
@ -745,10 +752,13 @@ namespace SymbolTable
|
|||
scope.TopScope.InternalScopes.Remove(scope);
|
||||
}
|
||||
|
||||
// Пока что считаем, что caseaSensitiveSearch совпадает с SymbolTableCaseSensitive EVA
|
||||
public List<SymbolInfo> FindOnlyInScope(Scope scope, string Name, bool FindInUpperBlocks) => FindOnlyInScope(scope, Name, FindInUpperBlocks, SymbolTableCaseSensitive);
|
||||
|
||||
//Этот метод ищет ТОЛЬКО В УКАЗАННОЙ ОВ, и не смотрит есть ли имя выше.
|
||||
//Если это ОВ типа UnitImplementationScope то имя ищется также и
|
||||
//в верней ОВ, которая типа UnitInterfaceScope
|
||||
public List<SymbolInfo> FindOnlyInScope(Scope scope, string Name, bool FindInUpperBlocks)
|
||||
public List<SymbolInfo> FindOnlyInScope(Scope scope, string Name, bool FindInUpperBlocks, bool caseSensitiveSearch)
|
||||
{
|
||||
// if (!scope.CaseSensitive) Name = Name.ToLower();
|
||||
CurrentScope = null;
|
||||
|
|
@ -762,7 +772,7 @@ namespace SymbolTable
|
|||
}
|
||||
|
||||
Scope CurrentArea = scope, bs;
|
||||
HashTableNode tn;
|
||||
IEnumerable<SymbolInfo> infos;
|
||||
do
|
||||
{
|
||||
if (CurrentArea is UnitPartScope) //мы очутились в модуле
|
||||
|
|
@ -770,38 +780,38 @@ namespace SymbolTable
|
|||
//мы в ImplementationPart?
|
||||
if (CurrentArea is UnitImplementationScope)
|
||||
{
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
AddToSymbolInfo(infos, Result);
|
||||
CurrentArea = CurrentArea.TopScope;
|
||||
}
|
||||
//сейча мы в InterfacePart
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
AddToSymbolInfo(infos, Result);
|
||||
|
||||
if (Result.Count() > 0)
|
||||
return Result;
|
||||
}
|
||||
if (CurrentArea is WithScope)//мы очутились в With
|
||||
{
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
AddToSymbolInfo(infos, Result);
|
||||
|
||||
if (Result.Count() > 0) //если что-то нашли то заканчиваем
|
||||
return Result;
|
||||
|
||||
FindAllInAreaList(Name, (CurrentArea as WithScope).WithScopes, true, true, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, (CurrentArea as WithScope).WithScopes, true, true, Result, caseSensitiveSearch);
|
||||
if (Result.Count() > 0) //если что-то нашли то заканчиваем
|
||||
return Result;
|
||||
}
|
||||
else
|
||||
{
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
{
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
AddToSymbolInfo(infos, Result);
|
||||
return Result.Count() > 0 ? Result : null;
|
||||
}
|
||||
}
|
||||
|
|
@ -811,13 +821,13 @@ namespace SymbolTable
|
|||
|
||||
return null;
|
||||
}
|
||||
private void FindAllInClass(string name, Scope ClassArea, bool OnlyInThisClass, List<SymbolInfo> Result, bool fromCaseSensitive)
|
||||
private void FindAllInClass(string name, Scope ClassArea, bool OnlyInThisClass, List<SymbolInfo> Result, bool caseSensitiveSearch)
|
||||
{
|
||||
HashTableNode tn;
|
||||
IEnumerable<SymbolInfo> infos;
|
||||
Scope ar = ClassArea;
|
||||
|
||||
if ((tn = ar.Symbols.Find(name, fromCaseSensitive)) != null)
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
if ((infos = ar.Symbols.Find(name, caseSensitiveSearch)) != null)
|
||||
AddToSymbolInfo(infos, Result);
|
||||
|
||||
if (ar is DotNETScope)
|
||||
{
|
||||
|
|
@ -832,16 +842,16 @@ namespace SymbolTable
|
|||
{
|
||||
while (cl.BaseClassScope != null)
|
||||
{
|
||||
tn = cl.BaseClassScope.Symbols.Find(name, fromCaseSensitive); // SSM 30/06/20 - надо исключать generis-параметры из поиска - их не существует в производном классе!!!
|
||||
if (tn != null)
|
||||
infos = cl.BaseClassScope.Symbols.Find(name, caseSensitiveSearch); // SSM 30/06/20 - надо исключать generis-параметры из поиска - их не существует в производном классе!!!
|
||||
if (infos != null)
|
||||
{
|
||||
if (tn.InfoList[0].sym_info is PascalABCCompiler.TreeRealization.common_type_node cctt && cctt.is_generic_parameter)
|
||||
if (infos.First().sym_info is PascalABCCompiler.TreeRealization.common_type_node cctt && cctt.is_generic_parameter)
|
||||
{
|
||||
// пропустить!!!
|
||||
}
|
||||
else
|
||||
{
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
AddToSymbolInfo(infos, Result);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -938,7 +948,7 @@ namespace SymbolTable
|
|||
);
|
||||
}
|
||||
|
||||
private void AddToSymbolInfo(List<SymbolInfo> from, List<SymbolInfo> to)
|
||||
private void AddToSymbolInfo(IEnumerable<SymbolInfo> from, List<SymbolInfo> to)
|
||||
{
|
||||
bool CheckVisible = CurrentScope != null, NeedAdd = false;
|
||||
SymbolInfo last_sym = to.LastOrDefault();
|
||||
|
|
@ -964,11 +974,11 @@ namespace SymbolTable
|
|||
to.AddRange(sil);
|
||||
}
|
||||
|
||||
private void FindAllInAreaList(string name, Scope[] arr, bool need, List<SymbolInfo> Result, bool fromCaseSensitive)
|
||||
private void FindAllInAreaList(string name, Scope[] arr, bool need, List<SymbolInfo> Result, bool caseSensitiveSearch)
|
||||
{
|
||||
FindAllInAreaList(name, arr, false, need, Result, fromCaseSensitive);
|
||||
FindAllInAreaList(name, arr, false, need, Result, caseSensitiveSearch);
|
||||
}
|
||||
public void FindAllInAreaList(string name, Scope[] arr, bool StopIfFind, bool NotOnlyInNetScopes, List<SymbolInfo> Result, bool fromCaseSensitive)
|
||||
public void FindAllInAreaList(string name, Scope[] arr, bool StopIfFind, bool NotOnlyInNetScopes, List<SymbolInfo> Result, bool caseSensitiveSearch)
|
||||
{
|
||||
if (arr == null) return;
|
||||
|
||||
|
|
@ -1002,10 +1012,10 @@ namespace SymbolTable
|
|||
else
|
||||
if (NotOnlyInNetScopes && sc != null)
|
||||
{
|
||||
var tn = sc.Symbols.Find(name, fromCaseSensitive);
|
||||
if (tn != null)
|
||||
var infos = sc.Symbols.Find(name, caseSensitiveSearch);
|
||||
if (infos != null)
|
||||
{
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
AddToSymbolInfo(infos, Result);
|
||||
if (Result.Count > add && StopIfFind)
|
||||
return;
|
||||
}
|
||||
|
|
@ -1038,7 +1048,12 @@ namespace SymbolTable
|
|||
{
|
||||
return FindAll(scope, Name, true, true, null);
|
||||
}
|
||||
|
||||
// Пока что считаем, что caseaSensitiveSearch совпадает с SymbolTableCaseSensitive EVA
|
||||
private List<SymbolInfo> FindAll(Scope scope, string Name, bool OnlyInType, bool OnlyInThisClass, Scope FromScope)
|
||||
=> FindAll(scope, Name, OnlyInType, OnlyInThisClass, FromScope, SymbolTableCaseSensitive);
|
||||
|
||||
private List<SymbolInfo> FindAll(Scope scope, string Name, bool OnlyInType, bool OnlyInThisClass, Scope FromScope, bool caseSensitiveSearch)
|
||||
{
|
||||
if (OnlyInType && !(scope is ClassScope) && !(scope is SymbolTable.DotNETScope)) return null;
|
||||
//if (!CaseSensitive) Name=Name.ToLower();
|
||||
|
|
@ -1074,7 +1089,7 @@ namespace SymbolTable
|
|||
if (scope != null)
|
||||
{
|
||||
var a = (scope as UnitInterfaceScope).TopScopeArray.Where(x => x is PascalABCCompiler.NetHelper.NetScope).ToArray();
|
||||
FindAllInAreaList(Name, a, true, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, a, true, Result, caseSensitiveSearch);
|
||||
}
|
||||
|
||||
if (Result.Count > 0)
|
||||
|
|
@ -1085,7 +1100,7 @@ namespace SymbolTable
|
|||
Scope Area = scope;
|
||||
Scope[] used_units = null;
|
||||
|
||||
HashTableNode tn = null;
|
||||
IEnumerable<SymbolInfo> infos = null;
|
||||
if (!(scope is DotNETScope))
|
||||
{
|
||||
Scope CurrentArea = Area;
|
||||
|
|
@ -1097,30 +1112,30 @@ namespace SymbolTable
|
|||
if (CurrentArea is UnitImplementationScope)
|
||||
{
|
||||
used_units = (CurrentArea as UnitImplementationScope).TopScopeArray;
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
AddToSymbolInfo(infos, Result);
|
||||
CurrentArea = CurrentArea.TopScope;
|
||||
}
|
||||
//сейча мы в InterfacePart
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
AddToSymbolInfo(infos, Result);
|
||||
//смотрим в модулях
|
||||
FindAllInAreaList(Name, used_units, true, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, (CurrentArea as UnitInterfaceScope).TopScopeArray, true, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, used_units, true, Result, caseSensitiveSearch);
|
||||
FindAllInAreaList(Name, (CurrentArea as UnitInterfaceScope).TopScopeArray, true, Result, caseSensitiveSearch);
|
||||
|
||||
return Result.Count > 0 ? Result : null;
|
||||
}
|
||||
else
|
||||
if (CurrentArea is IInterfaceScope)
|
||||
{
|
||||
FindAllInClass(Name, CurrentArea, OnlyInThisClass, Result, scope.CaseSensitive);
|
||||
FindAllInClass(Name, CurrentArea, OnlyInThisClass, Result, caseSensitiveSearch);
|
||||
|
||||
//if (Result.Count > 0) //если что-то нашли то заканчиваем
|
||||
// return Result;
|
||||
|
||||
FindAllInAreaList(Name, (CurrentArea as IInterfaceScope).TopInterfaceScopeArray, true, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, (CurrentArea as IInterfaceScope).TopInterfaceScopeArray, true, Result, caseSensitiveSearch);
|
||||
|
||||
if (Result.Count > 0 || OnlyInType) //если что-то нашли то заканчиваем
|
||||
return Result.Count > 0 ? Result : null;
|
||||
|
|
@ -1128,7 +1143,7 @@ namespace SymbolTable
|
|||
else
|
||||
if (CurrentArea is ClassScope)//мы очутились в классе
|
||||
{
|
||||
FindAllInClass(Name, CurrentArea, OnlyInThisClass, Result, scope.CaseSensitive);//надо сделать поиск по его предкам
|
||||
FindAllInClass(Name, CurrentArea, OnlyInThisClass, Result, caseSensitiveSearch);//надо сделать поиск по его предкам
|
||||
|
||||
if (Result.Count > 0 || OnlyInType) //если что-то нашли то заканчиваем
|
||||
return Result.Count > 0 ? Result : null;
|
||||
|
|
@ -1137,16 +1152,16 @@ namespace SymbolTable
|
|||
else
|
||||
if (CurrentArea is WithScope)//мы очутились в With
|
||||
{
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
AddToSymbolInfo(infos, Result);
|
||||
if (Result.Count > 0) //если что-то нашли то заканчиваем
|
||||
return Result;
|
||||
Scope[] wscopes = (CurrentArea as WithScope).WithScopes;
|
||||
if (wscopes != null)
|
||||
foreach (Scope wsc in wscopes)
|
||||
{
|
||||
FindAllInClass(Name, wsc, OnlyInThisClass, Result, scope.CaseSensitive);//надо сделать поиск по его предкам
|
||||
FindAllInClass(Name, wsc, OnlyInThisClass, Result, caseSensitiveSearch);//надо сделать поиск по его предкам
|
||||
|
||||
if (Result.Count > 0) //если что-то нашли то заканчиваем
|
||||
return Result;
|
||||
|
|
@ -1154,10 +1169,10 @@ namespace SymbolTable
|
|||
}
|
||||
else
|
||||
{
|
||||
tn = CurrentArea.Symbols.Find(Name, scope.CaseSensitive);
|
||||
if (tn != null) //что-то нашли!
|
||||
infos = CurrentArea.Symbols.Find(Name, caseSensitiveSearch);
|
||||
if (infos != null) //что-то нашли!
|
||||
{
|
||||
AddToSymbolInfo(tn.InfoList, Result);
|
||||
AddToSymbolInfo(infos, Result);
|
||||
return Result.Count > 0 ? Result : null;
|
||||
}
|
||||
if (CurrentArea is ClassMethodScope)//мы очутились в методе класса
|
||||
|
|
@ -1167,7 +1182,7 @@ namespace SymbolTable
|
|||
var currentLambdaDefScope = (CurrentArea as ClassMethodScope).CurrentLambdaDefScope;
|
||||
if (currentLambdaDefScope != null)
|
||||
{
|
||||
var defScopeRes = FindAll(currentLambdaDefScope, Name, OnlyInType, OnlyInThisClass, currentLambdaDefScope);
|
||||
var defScopeRes = FindAll(currentLambdaDefScope, Name, OnlyInType, OnlyInThisClass, currentLambdaDefScope, caseSensitiveSearch);
|
||||
|
||||
if (defScopeRes != null && defScopeRes.Count > 0)
|
||||
{
|
||||
|
|
@ -1176,7 +1191,7 @@ namespace SymbolTable
|
|||
}
|
||||
// aab 26.04.19 end
|
||||
|
||||
FindAllInClass(Name, (CurrentArea as ClassMethodScope).TopScope, OnlyInThisClass, Result, scope.CaseSensitive);//надо сделать поиск по его классу
|
||||
FindAllInClass(Name, (CurrentArea as ClassMethodScope).TopScope, OnlyInThisClass, Result, caseSensitiveSearch);//надо сделать поиск по его классу
|
||||
|
||||
|
||||
if (Result.Count > 0) //если что-то нашли то заканчиваем
|
||||
|
|
@ -1200,16 +1215,16 @@ namespace SymbolTable
|
|||
Scope NextUnitArea = null;
|
||||
//\ssyy
|
||||
Scope an;
|
||||
tn = Area.Symbols.Find(Name, scope.CaseSensitive);
|
||||
infos = Area.Symbols.Find(Name, caseSensitiveSearch);
|
||||
while (Area != null)
|
||||
{
|
||||
an = Area;
|
||||
if (an is DotNETScope)
|
||||
{
|
||||
if (tn == null)
|
||||
if (infos == null)
|
||||
AddToSymbolInfo(Result, (DotNETScope)an, Name);
|
||||
else
|
||||
FindAllInClass(Name, Area, false, Result, scope.CaseSensitive);
|
||||
FindAllInClass(Name, Area, false, Result, caseSensitiveSearch);
|
||||
}
|
||||
if (Result.Count > 0)
|
||||
return Result;
|
||||
|
|
@ -1217,18 +1232,18 @@ namespace SymbolTable
|
|||
{
|
||||
if (an is UnitImplementationScope)
|
||||
{
|
||||
FindAllInAreaList(Name, (an as UnitImplementationScope).TopScopeArray, true, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, (an as UnitImplementationScope).TopScopeArray, true, Result, caseSensitiveSearch);
|
||||
an = an.TopScope;
|
||||
}
|
||||
|
||||
FindAllInAreaList(Name, (an as UnitInterfaceScope).TopScopeArray, false, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, (an as UnitInterfaceScope).TopScopeArray, false, Result, caseSensitiveSearch);
|
||||
|
||||
if (Result.Count > 0)
|
||||
return Result;
|
||||
}
|
||||
if (an is WithScope)//мы очутились в Width
|
||||
{
|
||||
FindAllInAreaList(Name, (an as WithScope).WithScopes, true, false, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, (an as WithScope).WithScopes, true, false, Result, caseSensitiveSearch);
|
||||
|
||||
if (Result.Count > 0) //если что-то нашли то заканчиваем
|
||||
return Result;
|
||||
|
|
@ -1251,7 +1266,7 @@ namespace SymbolTable
|
|||
//В предках ничего не нашли, ищем по интерфейсам...
|
||||
if (IntScope != null)
|
||||
{
|
||||
FindAllInAreaList(Name, IntScope.TopInterfaceScopeArray, false, Result, scope.CaseSensitive);
|
||||
FindAllInAreaList(Name, IntScope.TopInterfaceScopeArray, false, Result, caseSensitiveSearch);
|
||||
if (Result.Count > 0) //если что-то нашли то заканчиваем
|
||||
return Result;
|
||||
|
||||
|
|
@ -1296,8 +1311,7 @@ namespace SymbolTable
|
|||
}
|
||||
public class TreeConverterSymbolTable:DSSymbolTable
|
||||
{
|
||||
public TreeConverterSymbolTable(bool case_sensitive):base(SymbolTableConstants.HashTable_StartSize,case_sensitive){}
|
||||
public TreeConverterSymbolTable():base(SymbolTableConstants.HashTable_StartSize,false){}
|
||||
public TreeConverterSymbolTable():base(SymbolTableConstants.HashTable_StartSize){}
|
||||
}
|
||||
public class SymbolTableController
|
||||
{
|
||||
|
|
|
|||
|
|
@ -122,6 +122,8 @@ namespace PascalABCCompiler.TreeConverter
|
|||
{
|
||||
public override string ToString() => sym_info.ToString();
|
||||
|
||||
public string Name { get; set; }
|
||||
|
||||
//private readonly name_information_type _name_information_type;
|
||||
private definition_node _sym_info;
|
||||
|
||||
|
|
@ -182,6 +184,7 @@ namespace PascalABCCompiler.TreeConverter
|
|||
public SymbolInfo copy()
|
||||
{
|
||||
SymbolInfo si = new SymbolInfo();
|
||||
si.Name = Name;
|
||||
si._access_level = this.access_level;
|
||||
si._sym_info = this._sym_info;
|
||||
si._symbol_kind = this._symbol_kind;
|
||||
|
|
|
|||
|
|
@ -159,8 +159,6 @@ namespace PascalABCCompiler.TreeConverter
|
|||
ErrorsList = initializationData.errorsList;
|
||||
WarningsList = initializationData.warningsList;
|
||||
|
||||
SymbolTable.CaseSensitive = SemanticRulesConstants.SymbolTableCaseSensitive;
|
||||
|
||||
this.debug = initializationData.debug;
|
||||
this.debugging = initializationData.debugging;
|
||||
this.for_intellisense = initializationData.forIntellisense;
|
||||
|
|
|
|||
|
|
@ -3,16 +3,16 @@
|
|||
pi = 3.14159265358979
|
||||
|
||||
def sqrt(x: float) -> float:
|
||||
return PABCSystem.sqrt(x)
|
||||
return PABCSystem.Sqrt(x)
|
||||
|
||||
def trunc(x: float) -> int:
|
||||
return PABCSystem.trunc(x)
|
||||
return PABCSystem.Trunc(x)
|
||||
|
||||
def floor(x: float) -> int:
|
||||
return PABCSystem.floor(x)
|
||||
return PABCSystem.Floor(x)
|
||||
|
||||
def ceil(x: float) -> int:
|
||||
return PABCSystem.ceil(x)
|
||||
return PABCSystem.Ceil(x)
|
||||
|
||||
def log(x: float) -> float:
|
||||
return PABCSystem.Log(x)
|
||||
|
|
@ -30,55 +30,55 @@ def log(x: float, base: int) -> float:
|
|||
return PABCSystem.LogN(base, x)
|
||||
|
||||
def exp(x: float) -> float:
|
||||
return PABCSystem.exp(x)
|
||||
return PABCSystem.Exp(x)
|
||||
|
||||
def expm1(x: float) -> float:
|
||||
return PABCSystem.exp(x - 1)
|
||||
return PABCSystem.Exp(x - 1)
|
||||
|
||||
def exp2(x: float) -> float:
|
||||
return PABCSystem.exp(log(2) * x)
|
||||
return PABCSystem.Exp(log(2) * x)
|
||||
|
||||
def sin(x: float) -> float:
|
||||
return PABCSystem.sin(x)
|
||||
return PABCSystem.Sin(x)
|
||||
|
||||
def sinh(x: float) -> float:
|
||||
return PABCSystem.sinh(x)
|
||||
return PABCSystem.Sinh(x)
|
||||
|
||||
def cos(x: float) -> float:
|
||||
return PABCSystem.cos(x)
|
||||
return PABCSystem.Cos(x)
|
||||
|
||||
def cosh(x: float) -> float:
|
||||
return PABCSystem.cosh(x)
|
||||
return PABCSystem.Cosh(x)
|
||||
|
||||
def tan(x: float) -> float:
|
||||
return PABCSystem.tan(x)
|
||||
return PABCSystem.Tan(x)
|
||||
|
||||
def tanh(x: float) -> float:
|
||||
return PABCSystem.tanh(x)
|
||||
return PABCSystem.Tanh(x)
|
||||
|
||||
def acos(x: float) -> float:
|
||||
return PABCSystem.arccos(x)
|
||||
return PABCSystem.ArcCos(x)
|
||||
|
||||
def asin(x: float) -> float:
|
||||
return PABCSystem.arcsin(x)
|
||||
return PABCSystem.ArcSin(x)
|
||||
|
||||
def atan(x: float) -> float:
|
||||
return PABCSystem.arctan(x)
|
||||
return PABCSystem.ArcTan(x)
|
||||
|
||||
def atan2(y: float, x: float) -> float:
|
||||
return PABCSystem.arctan(y / x)
|
||||
return PABCSystem.ArcTan(y / x)
|
||||
|
||||
def pow(x: float, y: int) -> float:
|
||||
return PABCSystem.power(x, y)
|
||||
return PABCSystem.Power(x, y)
|
||||
|
||||
def cbrt(x: float) -> float:
|
||||
return pow(x, 1/3)
|
||||
|
||||
def fabs(x: float) -> float:
|
||||
return PABCSystem.abs(x)
|
||||
return PABCSystem.Abs(x)
|
||||
|
||||
def pow(x: float, y: float) -> float:
|
||||
return PABCSystem.power(x, y)
|
||||
return PABCSystem.Power(x, y)
|
||||
|
||||
def isqrt(x: int) -> int:
|
||||
return floor(sqrt(x))
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
import PABCSystem
|
||||
|
||||
def random() -> float:
|
||||
return PABCSystem.random()
|
||||
return PABCSystem.Random()
|
||||
|
||||
def randint(a: int, b: int) -> int:
|
||||
return PABCSystem.random(a, b)
|
||||
return PABCSystem.Random(a, b)
|
||||
Loading…
Reference in a new issue