/*|| sil.Count() == 1*/ в s_t_v.cs 5889

Устранил некоторые ошибки с именованными аргументами
This commit is contained in:
Mikhalkovich Stanislav 2023-05-13 13:46:53 +03:00
parent 9ffbea0c95
commit bc9e7d85d4
9 changed files with 47 additions and 24 deletions

View file

@ -15,7 +15,7 @@ internal static class RevisionClass
public const string Major = "3";
public const string Minor = "9";
public const string Build = "0";
public const string Revision = "3278";
public const string Revision = "3280";
public const string MainVersion = Major + "." + Minor;
public const string FullVersion = Major + "." + Minor + "." + Build + "." + Revision;

View file

@ -1,4 +1,4 @@
%COREVERSION%=0
%REVISION%=3278
%REVISION%=3280
%MINOR%=9
%MAJOR%=3

View file

@ -2,7 +2,6 @@
<param name="Keyword" value="AdjacentFind">
<param name="Keyword" value="ArrEqual">
<param name="Keyword" value="BinarySearch">
<param name="Keyword" value="Cartesian">
<param name="Keyword" value="CartesianPower">
<param name="Keyword" value="Combinations">
<param name="Keyword" value="ConvertAll">
@ -36,18 +35,20 @@
</HEAD><body><H1>Ìåòîäû ðàñøèðåíèÿ îäíîìåðíûõ äèíàìè÷åñêèõ ìàññèâîâ</H1>
<table border=0 cellpadding=5><tr><td><code>(ðàñøèðåíèå <b>sequence </b> <b>of</b> T) <b>function</b> Cartesian&lt;T, T1&gt;(b: <b>sequence </b> <b>of</b> T1): <b>sequence </b> <b>of</b> (T, T1);</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò äåêàðòîâî ïðîèçâåäåíèå ïîñëåäîâàòåëüíîñòåé â âèäå ïîñëåäîâàòåëüíîñòè ïàð</td></tr>
<tr><td><code>(ðàñøèðåíèå <b>sequence </b> <b>of</b> T) <b>function</b> Cartesian&lt;T, T1&gt;(b: <b>sequence </b> <b>of</b> T1): <b>sequence </b> <b>of</b> (T, T1);</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò n-òóþ äåêàðòîâó ñòåïåíü ìíîæåñòâà ñèìâîëîâ, çàäàííîãî ñòðîêîé</td></tr>
<tr><td><code><b>function</b> AdjacentFind&lt;T&gt;(Self: <b>array</b> <b>of</b> T; eq: (T,T)-&gt;boolean; start: integer := 0): integer;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Íàõîäèò ïåðâóþ ïàðó ïîäðÿä èäóùèõ îäèíàêîâûõ ýëåìåíòîâ, èñïîëüçóÿ ôóíêöèþ ñðàâíåíèÿ eq, è âîçâðàùàåò èíäåêñ ïåðâîãî ýëåìåíòà ïàðû. Åñëè íå íàéäåí, âîçâðàùàåòñÿ -1</td></tr>
<tr><td><code><b>function</b> ArrEqual&lt;T&gt;(Self,b: <b>array</b> <b>of</b> T): boolean;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò, ñîâïàäàþò ëè ìàññèâû</td></tr>
<tr><td><code><b>function</b> BinarySearch&lt;T&gt;(Self: <b>array</b> <b>of</b> T; x: T): integer;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âûïîëíÿåò áèíàðíûé ïîèñê â îòñîðòèðîâàííîì ìàññèâå</td></tr>
<tr><td><code><b>function</b> Cartesian(Self: string; n: integer): <b>sequence </b> <b>of</b> string;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò n-òóþ äåêàðòîâó ñòåïåíü ìíîæåñòâà ñèìâîëîâ, çàäàííîãî ñòðîêîé</td></tr>
<tr><td><code><b>function</b> CartesianPower&lt;T&gt;(Self: <b>array</b> <b>of</b> T; n: integer): <b>sequence </b> <b>of</b> <b>array</b> <b>of</b> T;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò n-òóþ äåêàðòîâó ñòåïåíü ìíîæåñòâà ýëåìåíòîâ, çàäàííîãî ìàññèâîì</td></tr>
<tr><td><code><b>function</b> CartesianPower&lt;T&gt;(Self: <b>sequence </b> <b>of</b> T; n: integer): <b>sequence </b> <b>of</b> <b>array</b> <b>of</b> T;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò n-òóþ äåêàðòîâó ñòåïåíü ìíîæåñòâà ýëåìåíòîâ, çàäàííîãî ïîñëåäîâàòåëüíîñòüþ</td></tr>
<tr><td><code><b>function</b> CartesianPower(Self: string; n: integer): <b>sequence </b> <b>of</b> string;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò n-òóþ äåêàðòîâó ñòåïåíü ìíîæåñòâà ñèìâîëîâ, çàäàííîãî ñòðîêîé</td></tr>
<tr><td><code><b>function</b> Combinations&lt;T&gt;(Self: <b>array</b> <b>of</b> T; m: integer): <b>sequence </b> <b>of</b> <b>array</b> <b>of</b> T;</code>
<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Âîçâðàùàåò âñå ñî÷åòàíèÿ ïî m ýëåìåíòîâ</td></tr>
<tr><td><code><b>function</b> Combinations&lt;T&gt;(Self: <b>sequence </b> <b>of</b> T; m: integer): <b>sequence </b> <b>of</b> <b>array</b> <b>of</b> T;</code>

View file

@ -18,6 +18,7 @@ dfn {
}
code {
font-family: Consolas, monospace;
color: #000080;
font-size: 12pt;
}

View file

@ -1 +1 @@
3.9.0.3278
3.9.0.3280

View file

@ -1 +1 @@
!define VERSION '3.9.0.3278'
!define VERSION '3.9.0.3280'

View file

@ -2892,11 +2892,17 @@ namespace PascalABCCompiler.TreeConverter
}
//Первый параметр - выходной. Он содержит выражения с необходимыми преобразованиями типов.
public function_node select_function(expressions_list parameters, List<SymbolInfo> functions, location loc, List<SyntaxTree.expression> syntax_nodes_parameters = null, bool only_from_not_extensions = false)
public function_node select_function(expressions_list parameters, List<SymbolInfo> functions, location loc,
List<SyntaxTree.expression> syntax_nodes_parameters = null, bool only_from_not_extensions = false, int params_inc = 0)
{
// only_from_not_extensions = false - не вырезается первый параметр (Включая методы расширения)
// only_from_not_extensions = true - вырезается первый параметр (Исключая методы расширения)
string FunctionName = "";
// а вот в func[i].parameters - только если это метод расширения. Для методов не надо !!!
if (functions != null && functions.Count > 0)
{
FunctionName = (functions[0].sym_info as function_node).name;
}
// с какого номера начинаются именованные параметры
var indexOfFirstNamedArgument = -1;
if (syntax_nodes_parameters != null)
@ -2912,6 +2918,8 @@ namespace PascalABCCompiler.TreeConverter
}
else
{
var indexOfFirstNamedArgumentSem = indexOfFirstNamedArgument + params_inc;
// Вначале ищем среди оставшихся параметров именованные
// Создадим список имен ident именованных аргументов.
List<SyntaxTree.ident> NamesInNamedArguments = syntax_nodes_parameters.Skip(indexOfFirstNamedArgument)
@ -2922,7 +2930,8 @@ namespace PascalABCCompiler.TreeConverter
var found = false;
foreach (var ff in functions)
{
var names = (ff.sym_info as function_node).parameters.Skip(indexOfFirstNamedArgument).Select(par => par.name);
var is_ext1 = (ff.sym_info as function_node).is_extension_method;
var names = (ff.sym_info as function_node).parameters.Skip(indexOfFirstNamedArgument + (is_ext1 ? 1 : 0)).Select(par => par.name);
var fo = names.Contains(name.name, StringComparer.OrdinalIgnoreCase);
if (fo)
{
@ -2937,7 +2946,8 @@ namespace PascalABCCompiler.TreeConverter
var foundUnnamed = false;
foreach (var ff in functions)
{
var names = (ff.sym_info as function_node).parameters.Take(indexOfFirstNamedArgument).Select(par => par.name);
var is_ext1 = (ff.sym_info as function_node).is_extension_method;
var names = (ff.sym_info as function_node).parameters.Take(indexOfFirstNamedArgument + (is_ext1 ? 1 : 0)).Select(par => par.name);
var fo = names.Contains(name.name, StringComparer.OrdinalIgnoreCase);
if (fo)
{
@ -2954,11 +2964,12 @@ namespace PascalABCCompiler.TreeConverter
// сделаем копию parameters без именованных аргументов
var parameters_helper = new expressions_list();
for (int i = 0; i < indexOfFirstNamedArgument; i++)
for (int i = 0; i < indexOfFirstNamedArgumentSem; i++)
parameters_helper.AddElement(parameters[i]);
Errors.Error err_out;
var list = select_function_helper(parameters_helper, functions, loc, syntax_nodes_parameters, only_from_not_extensions, out err_out);
var syntax_nodes_parameters1 = syntax_nodes_parameters.Take(indexOfFirstNamedArgument).ToList();
var list = select_function_helper(parameters_helper, functions, loc, syntax_nodes_parameters1, only_from_not_extensions, out err_out);
if (list.Count == 0 && err_out != null) // С именованными уже точно ничего не получится
return AddError<function_node>(new NoFunctionWithSameArguments(FunctionName, loc, functions.Count == 1));
@ -2977,7 +2988,8 @@ namespace PascalABCCompiler.TreeConverter
// Удалим из list все неподходящие, где нет таких имен параметров в оставшейся части
list.RemoveAll(ff =>
{
var names = ff.parameters.Skip(indexOfFirstNamedArgument).Select(par => par.name);
var is_ext1 = ff.is_extension_method;
var names = ff.parameters.Skip(indexOfFirstNamedArgument + (is_ext1 ? 1 : 0)).Select(par => par.name);
var hsnames = new HashSet<string>(names, StringComparer.OrdinalIgnoreCase);
return !hs.IsSubsetOf(hsnames);
// то есть все имена в именованных аргументах должны находиться среди оставшихся параметров по умолчанию
@ -2997,14 +3009,16 @@ namespace PascalABCCompiler.TreeConverter
for (int i = indexOfFirstNamedArgument; i < syntax_nodes_parameters.Count; i++)
{
var nae = syntax_nodes_parameters[i] as SyntaxTree.name_assign_expr;
dict[nae.name.name] = parameters[i]; // parameters и syntax_nodes_parameters д.б.одной длины
//dict[nae.name.name] = parameters[i + (NeedIncrementIndexFNA ? 1 : 0)]; // parameters и syntax_nodes_parameters д.б.одной длины
dict[nae.name.name] = parameters[i + params_inc];
}
// Вот теперь как-то хвост в parameters надо менять на параметры по умолчанию или на те, что хранятся в dict
// Я бы очистил хвост parameters и добавлял бы в него как раньше параметры по умолчанию
parameters.remove_range(indexOfFirstNamedArgument, parameters.Count - indexOfFirstNamedArgument); // удалить хвост
var fun1 = functions[0].sym_info as function_node;
for (int i = indexOfFirstNamedArgument; i < fun1.parameters.Count; i++) // сверить это с другим кодом
parameters.remove_range(indexOfFirstNamedArgumentSem, parameters.Count - indexOfFirstNamedArgumentSem); // удалить хвост
var fun1 = functions[0].sym_info as function_node; // это - единственная функция
var is_ext = fun1.is_extension_method;
for (int i = indexOfFirstNamedArgument + (is_ext ? 1 : 0); i < fun1.parameters.Count; i++) // сверить это с другим кодом
{
var par = fun1.parameters[i];
var paramexpr = par.default_value;

View file

@ -5896,16 +5896,21 @@ namespace PascalABCCompiler.TreeConverter
#endregion
function_node fn = null;
if (!skip_first_parameter || sil.Count() == 1)
if (!skip_first_parameter /*|| sil.Count() == 1*/)
{
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters);
// exprs.Count = 2; s_n_p = 2; false - не удаляем 1 параметр
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters, false);
}
else
else // skip_first_parameter = true
{
try
{
ThrowCompilationError = false;
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters);
// Включая методы расширения
// Семантическая разница между exprs.Count и s_n_p.Count равна 1 !!! Только здесь! И вот ее и передавать!
// exprs.Count = 3; s_n_p = 2; false - не удаляем 1 параметр
// Добавил последний параметр = 1 - это единственное место где длина exprs на 1 больше
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters, false, 1);
if (fn == null && skip_first_parameter)
{
if (sil.Count() == 1)
@ -5917,7 +5922,8 @@ namespace PascalABCCompiler.TreeConverter
skip_first_parameter = false;
sil = tmp_sil;
exprs.remove_at(0);
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters,true);
// exprs.Count = 2; s_n_p = 2; true - удаляем 1 параметр, пропускаем расширения
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters,true);
if (fn == null)
{
ThrowCompilationError = true;
@ -5942,7 +5948,8 @@ namespace PascalABCCompiler.TreeConverter
function_node tmp_fn = fn;
exprs.remove_at(0);
sil = tmp_sil;
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters,true);
// Только для методов, исключая методы расширения
fn = convertion_data_and_alghoritms.select_function(exprs, sil, subloc, syntax_nodes_parameters,true); // true - удаляем 1 параметр, пропускаем расширения
if (fn == null)
{
fn = tmp_fn;

Binary file not shown.