From 34234f4f646c3d61d59f61424739bed8f41edba0 Mon Sep 17 00:00:00 2001 From: Mikhalkovich Stanislav Date: Sat, 18 Oct 2025 22:50:19 +0300 Subject: [PATCH] =?UTF-8?q?print=5Fprocedure(x:9:2)=20-=D1=82=D0=B5=D0=BF?= =?UTF-8?q?=D0=B5=D1=80=D1=8C=20=D0=B8=20=D0=B2=20Print=20=D0=BC=D0=BE?= =?UTF-8?q?=D0=B6=D0=BD=D0=BE=20=D0=BF=D0=B8=D1=81=D0=B0=D1=82=D1=8C=20?= =?UTF-8?q?=D0=B0=D1=82=D1=80=D0=B8=D0=B1=D1=83=D1=82=D1=8B=20=D1=84=D0=BE?= =?UTF-8?q?=D1=80=D0=BC=D0=B0=D1=82=D0=B8=D1=80=D0=BE=D0=B2=D0=B0=D0=BD?= =?UTF-8?q?=D0=B8=D1=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Windowed как более традиционный синоним NWise --- Configuration/GlobalAssemblyInfo.cs | 2 +- Configuration/Version.defs | 4 +- .../WhatsNew/3_11_1/FormatInPrint.pas | 3 + InstallerSamples/WhatsNew/3_11_1/L_Swap.pas | 9 + InstallerSamples/WhatsNew/3_11_1/None.pas | 6 + Release/pabcversion.txt | 2 +- ReleaseGenerators/PascalABCNET_version.nsh | 2 +- StringConstants/StringConstants.cs | 2 + TestSuite/CompilationSamples/PABCSystem.pas | 240 ++++++++++-------- .../SystemLib/SystemLibInitializer.cs | 2 + .../TreeConversion/syntax_tree_visitor.cs | 11 +- bin/Lib/PABCSystem.pas | 86 +++++-- bin/Lng/Eng/SemanticErrors_ib.dat | 2 +- bin/Lng/Rus/SemanticErrors_ib.dat | 2 +- 14 files changed, 239 insertions(+), 134 deletions(-) create mode 100644 InstallerSamples/WhatsNew/3_11_1/FormatInPrint.pas create mode 100644 InstallerSamples/WhatsNew/3_11_1/L_Swap.pas create mode 100644 InstallerSamples/WhatsNew/3_11_1/None.pas diff --git a/Configuration/GlobalAssemblyInfo.cs b/Configuration/GlobalAssemblyInfo.cs index 7f92ef348..b676a2f76 100644 --- a/Configuration/GlobalAssemblyInfo.cs +++ b/Configuration/GlobalAssemblyInfo.cs @@ -15,7 +15,7 @@ internal static class RevisionClass public const string Major = "3"; public const string Minor = "11"; public const string Build = "0"; - public const string Revision = "3671"; + public const string Revision = "3672"; public const string MainVersion = Major + "." + Minor; public const string FullVersion = Major + "." + Minor + "." + Build + "." + Revision; diff --git a/Configuration/Version.defs b/Configuration/Version.defs index 75827d39e..5f09bd398 100644 --- a/Configuration/Version.defs +++ b/Configuration/Version.defs @@ -1,4 +1,4 @@ -%MINOR%=11 -%REVISION%=3671 %COREVERSION%=0 +%REVISION%=3672 +%MINOR%=11 %MAJOR%=3 diff --git a/InstallerSamples/WhatsNew/3_11_1/FormatInPrint.pas b/InstallerSamples/WhatsNew/3_11_1/FormatInPrint.pas new file mode 100644 index 000000000..e0e8f70df --- /dev/null +++ b/InstallerSamples/WhatsNew/3_11_1/FormatInPrint.pas @@ -0,0 +1,3 @@ +begin + Print(Pi:0:4) +end. \ No newline at end of file diff --git a/InstallerSamples/WhatsNew/3_11_1/L_Swap.pas b/InstallerSamples/WhatsNew/3_11_1/L_Swap.pas new file mode 100644 index 000000000..035f97b04 --- /dev/null +++ b/InstallerSamples/WhatsNew/3_11_1/L_Swap.pas @@ -0,0 +1,9 @@ +begin + var L := Lst(1..10); + // Меняет местами элементы списка + L.Swap(0,9).Swap(1,8).Println; + + var a := Arr(1..10); + // Меняет местами элементы массива + a.Swap(0,9).Swap(1,8).Print; +end. \ No newline at end of file diff --git a/InstallerSamples/WhatsNew/3_11_1/None.pas b/InstallerSamples/WhatsNew/3_11_1/None.pas new file mode 100644 index 000000000..6ebd57ce9 --- /dev/null +++ b/InstallerSamples/WhatsNew/3_11_1/None.pas @@ -0,0 +1,6 @@ +// None - ни один из элементов не удовлетворяет условию + +begin + var a := Arr(1,2,3,4); + a.None(x -> x > 5).Print +end. \ No newline at end of file diff --git a/Release/pabcversion.txt b/Release/pabcversion.txt index 219093cc9..509ecdfab 100644 --- a/Release/pabcversion.txt +++ b/Release/pabcversion.txt @@ -1 +1 @@ -3.11.0.3671 +3.11.0.3672 diff --git a/ReleaseGenerators/PascalABCNET_version.nsh b/ReleaseGenerators/PascalABCNET_version.nsh index c41b7feae..720c08d5d 100644 --- a/ReleaseGenerators/PascalABCNET_version.nsh +++ b/ReleaseGenerators/PascalABCNET_version.nsh @@ -1 +1 @@ -!define VERSION '3.11.0.3671' +!define VERSION '3.11.0.3672' diff --git a/StringConstants/StringConstants.cs b/StringConstants/StringConstants.cs index 294fa7d51..5b53c9219 100644 --- a/StringConstants/StringConstants.cs +++ b/StringConstants/StringConstants.cs @@ -219,6 +219,8 @@ namespace PascalABCCompiler public static string read_procedure_name = "read"; public static string write_procedure_name = "write"; public static string writeln_procedure_name = "writeln"; + public static string print_procedure_name = "print"; + public static string println_procedure_name = "println"; public static string readln_procedure_name = "readln"; public static string text_file_name_type_name = "Text"; public static string TextFileInitProcedureName = "TextFileInit"; diff --git a/TestSuite/CompilationSamples/PABCSystem.pas b/TestSuite/CompilationSamples/PABCSystem.pas index dfee62427..95872fa60 100644 --- a/TestSuite/CompilationSamples/PABCSystem.pas +++ b/TestSuite/CompilationSamples/PABCSystem.pas @@ -1896,6 +1896,11 @@ function DegToRad(x: real): real; function Atan2(y, x: real): real; /// Возвращает гипотенузу треугольника с катетами x,y function Hypot(x, y: real): real; +/// Возвращает значение на отрезке [a, b] в позиции t ∈ [0, 1] +///При t=0 — a, при t=1 — b, при t=0.5 — середина между ними +function Lerp(a, b, t: real): real; +/// Преобразует x из диапазона [a1,b1] в диапазон [a2,b2] с сохранением относительной позиции +function Remap(x, a1, b1, a2, b2: real): real; /// Инициализирует датчик псевдослучайных чисел procedure Randomize; @@ -1911,7 +1916,7 @@ function Random(maxValue: real): real; function Random(a, b: integer): integer; /// Возвращает случайное вещественное в диапазоне [a,b) function Random(a, b: real): real; -/// Возвращает случайное вещественное в диапазоне [a,b] c количеством значащих цифр после точки, равным digits +/// Возвращает случайное вещественное в диапазоне [a,b], округленное до digits знаков после десятичной точки function RandomReal(a, b: real; digits: integer := 2): real; /// Возвращает случайный символ в диапазоне от a до b function Random(a, b: char): char; @@ -2066,8 +2071,6 @@ function Sqrt(c: Complex): Complex; function Abs(c: Complex): real; /// Возвращает комплексно сопряженное число function Conjugate(c: Complex): Complex; -/// Возвращает косинус комплексного числа -function Cos(c: Complex): Complex; /// Возвращает экспоненту комплексного числа function Exp(c: Complex): Complex; /// Возвращает натуральный логарифм комплексного числа @@ -2080,6 +2083,8 @@ function Log10(c: Complex): Complex; function Power(c, power: Complex): Complex; /// Возвращает синус комплексного числа function Sin(c: Complex): Complex; +/// Возвращает косинус комплексного числа +function Cos(c: Complex): Complex; // ----------------------------------------------------- //>> Подпрограммы для работы со стандартными множествами # Subroutines for set of T @@ -2402,10 +2407,11 @@ function Pred(x: boolean): boolean; function InRange(val, a, b: T): boolean; where T: IComparable; /// Возвращает True, если значение val находится между a и b независимо от порядка a и b function Between(val, a, b: T; inclusive: boolean := true): boolean; where T: IComparable; -/// Возвращает значение, ограниченное диапазоном от bottom до top включительно +/// Ограничивает значение x диапазоном [bottom, top] function Clamp(x,bottom,top: T): T; where T: IComparable; -/// Меняет местами значения двух переменных +/// Обменивает местами значения двух переменных procedure Swap(var a, b: T); + /// Возвращает True, если достигнут конец строки function Eoln: boolean; /// Возвращает True, если достигнут конец потока ввода @@ -2414,7 +2420,7 @@ function Eof: boolean; function SeekEof: boolean; /// Пропускает пробельные символы, после чего возвращает True, если достигнут конец строки function SeekEoln: boolean; -/// Возвращает аргумены командой строки, с которыми была запущена программа +/// Возвращает список аргументов командой строки, с которыми была запущена программа function CommandLineArgs: array of string; /// Преобразует объект в строковое представление @@ -2427,35 +2433,35 @@ function ObjectToString(obj: object): string; /// Возвращает 0 function Low(i: System.Array): integer; ///- function High(a: array of T): integer; -/// Возвращает верхнюю границу динамического массива +/// Возвращает верхнюю границу массива function High(i: System.Array): integer; ///- function Length(a: array of T): integer; -/// Возвращает длину динамического массива +/// Возвращает длину массива function Length(a: System.Array): integer; ///- function Length(a: array of T; dim: integer): integer; -/// Возвращает длину динамического массива по размерности dim +/// Возвращает длину массива по размерности dim function Length(a: System.Array; dim: integer): integer; ///- procedure SetLength(var a: array of T; n: integer); -/// Устанавливает длину одномерного динамического массива. Старое содержимое сохраняется +/// Устанавливает длину одномерного массива. Старое содержимое сохраняется //procedure SetLength(var a: array of T; n: integer); ///- procedure SetLength(var a: array [,...,] of T; n1,n2,...: integer); -/// Устанавливает размеры n-мерного динамического массива. Старое содержимое сохраняется +/// Устанавливает размеры n-мерного массива. Старое содержимое сохраняется //procedure SetLength(var a: array[,...,] of T; n: integer); ///- function Copy(a: array of T): array of T; -/// Создаёт копию динамического массива +/// Создаёт копию массива function Copy(a: System.Array): System.Array; -/// Сортирует динамический массив по возрастанию +/// Сортирует массив по возрастанию procedure Sort(a: array of T); -/// Сортирует динамический массив по возрастанию +/// Сортирует массив по возрастанию procedure Sort(a: array of string); -/// Сортирует динамический массив по критерию сортировки, задаваемому функцией сравнения cmp +/// Сортирует массив по критерию сортировки, задаваемому функцией сравнения cmp procedure Sort(a: array of T; cmp: (T,T)->integer); -/// Сортирует динамический массив по критерию сортировки, задаваемому функцией сравнения less +/// Сортирует массив по критерию сортировки, задаваемому функцией сравнения less procedure Sort(a: array of T; less: (T,T)->boolean); -/// Сортирует динамический массив по ключу +/// Сортирует массив по ключу procedure Sort(a: array of T; keySelector: T->TKey); -/// Сортирует динамический массив по ключу +/// Сортирует массив по ключу procedure Sort(a: array of T; keySelector: T->string); /// Сортирует список по возрастанию @@ -2471,13 +2477,13 @@ procedure Sort(var l: List; keySelector: T->T1); /// Сортирует список по возрастанию по ключу procedure Sort(var l: List; keySelector: T->string); -/// Сортирует динамический массив по убыванию +/// Сортирует массив по убыванию procedure SortDescending(a: array of T); -/// Сортирует динамический массив по убыванию +/// Сортирует массив по убыванию procedure SortDescending(a: array of string); -/// Сортирует динамический массив по убыванию по ключу +/// Сортирует массив по убыванию по ключу procedure SortDescending(var a: array of T; keySelector: T->T1); -/// Сортирует динамический массив по убыванию по ключу +/// Сортирует массив по убыванию по ключу procedure SortDescending(var a: array of T; keySelector: T->string); /// Сортирует список по убыванию procedure SortDescending(l: List); @@ -2487,9 +2493,9 @@ procedure SortDescending(var l: List); procedure SortDescending(var l: List; keySelector: T->T1); /// Сортирует список по убыванию по ключу procedure SortDescending(var l: List; keySelector: T->string); -/// Изменяет порядок элементов в динамическом массиве на противоположный +/// Изменяет порядок элементов в массиве на противоположный procedure Reverse(a: array of T); -/// Изменяет порядок элементов на противоположный в диапазоне динамического массива длины count, начиная с индекса index +/// Изменяет порядок элементов на противоположный в диапазоне массива длины count, начиная с индекса index procedure Reverse(a: array of T; index, count: integer); /// Изменяет порядок элементов в списке на противоположный procedure Reverse(a: List); @@ -2499,17 +2505,18 @@ procedure Reverse(a: List; index, count: integer); procedure Reverse(var s: string); /// Изменяет порядок символов в части строки длины count на противоположный, начиная с индекса index procedure Reverse(var s: string; index, count: integer); -/// Перемешивает динамический массив случайным образом +/// Случайно перемешивает элементы массива procedure Shuffle(a: array of T); -/// Возвращает, совпадают ли массивы -function ArrEqual(a, b: array of T): boolean; - -/// Сравнивает матрицы на равенство -function MatrEqual(a, b: array [,] of T): boolean; -/// Перемешивает список случайным образом +/// Случайно перемешивает элементы списка procedure Shuffle(l: List); -/// Возвращает следующую перестановку в массиве +/// Проверяет равенство двух массивов +function ArrEqual(a, b: array of T): boolean; +/// Проверяет равенство двух матриц +function MatrEqual(a, b: array [,] of T): boolean; + + +/// Возвращает следующую перестановку в массиве; возвращает False, если это последняя function NextPermutation(a: array of integer): boolean; @@ -2532,7 +2539,9 @@ function Range(c1, c2: char; step: integer): sequence of char; function Range(a, b, step: real): sequence of real; /// Возвращает последовательность вещественных в точках разбиения отрезка [a,b] на n равных частей function PartitionPoints(a, b: real; n: integer): sequence of real; -/// Возвращает последовательность указанных элементов +/// Возвращает n равномерно распределённых точек между a и b включительно (аналог numpy.linspace) +function Linspace(a, b: real; n: integer): sequence of real; +/// Возвращает последовательность из указанных элементов function Seq(params a: array of T): sequence of T; /// Возвращает последовательность из n случайных целых элементов function SeqRandom(n: integer := 10; a: integer := 0; b: integer := 100): sequence of integer; @@ -2576,21 +2585,21 @@ function Zip(a: sequence of T; b: sequence of T1; c: sequen /// Применяет указанную функцию к соответствующим элементам кортежей, возвращает последовательность результатов function Zip(a: sequence of T; b: sequence of T1; c: sequence of T2; d: sequence of T3; e: sequence of T4; fun: (T,T1,T2,T3,T4) -> TRes): sequence of TRes; -/// Возвращает декартово произведение последовательностей, проектируя каждую пару на значение +/// Возвращает все комбинации элементов двух последовательностей, проектируя каждую пару на значение function Cartesian(a: sequence of T; b: sequence of T1; func: (T,T1)->TRes): sequence of TRes; -/// Возвращает декартово произведение последовательностей, проектируя каждую тройку на значение +/// Возвращает все комбинации элементов последовательностей, проектируя каждую тройку на значение function Cartesian(a: sequence of T; b: sequence of T1; c: sequence of T2; func: (T,T1,T2)->TRes): sequence of TRes; -/// Возвращает декартово произведение последовательностей, проектируя каждую четвёрку на значение +/// Возвращает все комбинации элементов последовательностей, проектируя каждую четвёрку на значение function Cartesian(a: sequence of T; b: sequence of T1; c: sequence of T2; d: sequence of T3; func: (T,T1,T2,T3)->TRes): sequence of TRes; -/// Возвращает декартово произведение последовательностей, проектируя каждую пятёрку на значение +/// Возвращает все комбинации элементов последовательностей, проектируя каждую пятёрку на значение function Cartesian(a: sequence of T; b: sequence of T1; c: sequence of T2; d: sequence of T3; e: sequence of T4; func: (T,T1,T2,T3,T4)->TRes): sequence of TRes; -/// Возвращает декартово произведение последовательностей в виде последовательности пар +/// Возвращает все комбинации элементов последовательностей в виде последовательности пар function Cartesian(a: sequence of T; b: sequence of T1): sequence of (T, T1); -/// Возвращает декартово произведение последовательностей в виде последовательности троек +/// Возвращает все комбинации элементов последовательностей в виде последовательности троек function Cartesian(a: sequence of T; b: sequence of T1; c: sequence of T2): sequence of (T, T1, T2); -/// Возвращает декартово произведение последовательностей в виде последовательности четвёрок +/// Возвращает все комбинации элементов последовательностей в виде последовательности четвёрок function Cartesian(a: sequence of T; b: sequence of T1; c: sequence of T2; d: sequence of T3): sequence of (T, T1, T2, T3); -/// Возвращает декартово произведение последовательностей в виде последовательности пятёрок +/// Возвращает все комбинации элементов последовательностей в виде последовательности пятёрок function Cartesian(a: sequence of T; b: sequence of T1; c: sequence of T2; d: sequence of T3; e: sequence of T4): sequence of (T, T1, T2, T3, T4); @@ -2623,11 +2632,11 @@ function ReadSeqRealWhile(prompt: string; cond: real->boolean): sequence of real function ReadSeqStringWhile(prompt: string; cond: string->boolean): sequence of string; // ----------------------------------------------------- -//>> Подпрограммы для создания динамических массивов # Subroutines for array of T generation +//>> Подпрограммы для создания одномерных массивов # Subroutines for array of T generation // ----------------------------------------------------- /// Возвращает массив, заполненный указанными значениями function Arr(params a: array of T): array of T; -/// Возвращает массив, заполненный значениями из последовательнсти +/// Возвращает массив, заполненный значениями из последовательности function Arr(a: sequence of T): array of T; /// Возвращает массив, заполненный диапазоном значений function Arr(a: IntRange): array of integer; @@ -2687,7 +2696,7 @@ function ReadArrString(prompt: string; n: integer): array of string; // ----------------------------------------------------- -//>> Подпрограммы для создания двумерных динамических массивов # Subroutines for matrixes +//>> Подпрограммы для создания двумерных массивов # Subroutines for matrixes // ----------------------------------------------------- /// Возвращает двумерный массив размера m x n, заполненный указанными значениями по строкам function Matr(m,n: integer; params data: array of T): array [,] of T; @@ -2712,9 +2721,9 @@ function MatrByCol(a: sequence of sequence of T): array [,] of T; /// Генерирует двумерный массив по столбцам из последовательности function MatrByCol(m,n: integer; a: sequence of T): array [,] of T; -/// Возвращает матрицу m на n целых, введенных с клавиатуры +/// Возвращает двумерный массив размера m x n из целых, введенных с клавиатуры function ReadMatrInteger(m, n: integer): array [,] of integer; -/// Возвращает матрицу m на n вещественных, введенных с клавиатуры +/// Возвращает двумерный массив размера m x n из вещественных, введенных с клавиатуры function ReadMatrReal(m, n: integer): array [,] of real; /// Возвращает двумерный массив размера m x n, заполненный случайными целыми значениями function MatrRandom(m: integer := 5; n: integer := 5; a: integer := 0; b: integer := 100): array [,] of integer; @@ -2796,25 +2805,25 @@ function SSetInt(params a: array of integer): SortedSet; function SSetStr(params a: array of string): SortedSet; -/// Возвращает словарь пар элементов (ключ, значение) +/// Возвращает словарь из набора пар элементов (ключ, значение) function Dict(params pairs: array of KeyValuePair): Dictionary; -/// Возвращает словарь пар элементов (ключ, значение) +/// Возвращает словарь из набора пар элементов (ключ, значение), заданных как кортежи function Dict(params pairs: array of (TKey, TVal)): Dictionary; -/// Возвращает словарь пар элементов (ключ, значение), построенный по последовательности пар +/// Возвращает словарь из последовательности пар элементов (ключ, значение) function Dict(pairs: sequence of KeyValuePair): Dictionary; -/// Возвращает словарь пар элементов (ключ, значение), построенный по последовательности пар +/// Возвращает словарь из последовательности пар элементов (ключ, значение), заданных как кортежи function Dict(pairs: sequence of (TKey, TVal)): Dictionary; -/// Возвращает словарь пар элементов (ключ, значение), построенный по последовательностям ключей и значений +/// Возвращает словарь словарь из двух последовательностей — ключей и значений function Dict(keys: sequence of TKey; values: sequence of TVal): Dictionary; /// Возвращает пару элементов (ключ, значение) function KV(key: TKey; value: TVal): KeyValuePair; /// Возвращает пару элементов (ключ, значение) function Pair(key: TKey; value: TVal): KeyValuePair; -/// Возвращает словарь пар элементов (строка, строка) +/// Возвращает словарь из набора пар элементов (строка, строка) function DictStr(params pairs: array of (string, string)): Dictionary; -/// Возвращает словарь пар элементов (строка, целое) +/// Возвращает словарь из набора пар элементов (строка, целое) function DictStrInt(params pairs: array of (string, integer)): Dictionary; -/// Возвращает словарь пар элементов (целое, целое) +/// Возвращает словарь из набора пар элементов (целое, целое) function DictInt(params pairs: array of (integer, integer)): Dictionary; @@ -3268,10 +3277,10 @@ const COUNT_PARAMS_MINFUN_MUSTBE_GREATER0 = 'Количество параметров функции Min должно быть > 1!!Min function must have more than one parameter'; Format_InvalidString = 'Входная строка имела неверный формат!!Input string was not in a valid format'; Overflow_Int32 = 'Целочисленное переполнение!!Integer overflow'; - FOR_STEP_CANNOT_BE_EQUAL0 = 'Шаг цикла for не может быт равен 0!!The step of a for loop cannot be 0'; + FOR_STEP_CANNOT_BE_EQUAL0 = 'Шаг цикла for не может быть равен 0!!The step of a for loop cannot be 0'; SEQUENCE_CANNOT_BE_EMPTY = 'Последовательность не может быть пустой!!Sequence cannot be empty'; ARRAY_CANNOT_BE_EMPTY = 'Массив не может быть пустым!!Array cannot be empty'; - MIN_CANNOT_BE_GREATER_THAN_MAX = 'CLamp: min не может быть больше чем max!!CLamp: min cannot be greater than max'; + MIN_CANNOT_BE_GREATER_THAN_MAX = 'Clamp: min не может быть больше чем max!!Clamp: min cannot be greater than max'; // ----------------------------------------------------- // WINAPI // ----------------------------------------------------- @@ -3854,17 +3863,6 @@ begin Result := ts; end; -///-- -{class function TypedSet.operator implicit(s: array of T): TypedSet; -begin - var ts := new TypedSet(); - foreach key: T in s do - begin - ts.ht[key] := key; - end; - Result := ts; -end;} - ///-- function TypedSet.ToString: string; var @@ -3922,13 +3920,6 @@ begin result := '[' + result + ']'; end; -{class function TypedSet.operator implicit(hset: HashSet): TypedSet; -begin - Result := new TypedSet(); - foreach var x in hset do - Result.ht[x] := x; -end;} - ///-- function TypedSet.CompareEquals(s: TypedSet): boolean; begin @@ -4121,15 +4112,7 @@ end; [System.Diagnostics.DebuggerStepThrough] function InSet(obj: object; s: TypedSet): boolean; begin - {if obj.GetType().IsEnum then - Result := s.ht[obj] <> nil - else} Result := (obj <> nil) and s.Contains(obj); - {Result := (obj <> nil) and (s.ht[obj] <> nil); - if not Result and (obj is TypedSet) then - Result := s.Contains(obj as TypedSet);} - //if Result = true then - // Result := s.IsInDiapason(obj); end; [System.Diagnostics.DebuggerStepThrough] @@ -5525,6 +5508,9 @@ begin end; end; +function Linspace(a, b: real; n: integer): sequence of real := PartitionPoints(a, b, n - 1); + + function Range(c1, c2: char): sequence of char; begin Result := Range(integer(c1), integer(c2)).Select(x -> Chr(x)); @@ -9535,6 +9521,10 @@ begin else Result := 0; end; +function Lerp(a, b, t: real): real := a + (b - a) * t; + +function Remap(x, a1, b1, a2, b2: real): real := a2 + (x - a1) * (b2 - a2) / (b1 - a1); + procedure Randomize; begin @@ -11142,12 +11132,16 @@ function Flatten(Self: sequence of sequence of T): sequence of T; extensionme function JoinToString(Self: sequence of T; delim: string): string; extensionmethod; begin var g := Self.GetEnumerator(); - var sb := new System.Text.StringBuilder(''); + var sb := new System.Text.StringBuilder(); if g.MoveNext() then begin - sb.Append(g.Current.ToString()); - while g.MoveNext() do - sb.Append(delim + g.Current.ToString()); + sb.Append(System.Convert.ToString(g.Current)); + while g.MoveNext() do + begin + if delim<>'' then + sb.Append(delim); + sb.Append(System.Convert.ToString(g.Current)); + end end; Result := sb.ToString; end; @@ -11614,7 +11608,9 @@ begin Result := maxElement; end; -{function TakeLast(Self: sequence of T; count: integer): sequence of T; extensionmethod; +{ +// Не помню, почему закомментировал +function TakeLast(Self: sequence of T; count: integer): sequence of T; extensionmethod; begin if count < 0 then raise new System.ArgumentOutOfRangeException('count', count, GetTranslation(PARAMETER_MUST_BE_GREATER_EQUAL_0)); @@ -11864,7 +11860,7 @@ begin end; /// Табулирует функцию последовательностью -function Tabulate(Self: sequence of T; F: T->T1): sequence of (T, T1); extensionmethod; +function Tabulate(Self: sequence of T; f: T->T1): sequence of (T, T1); extensionmethod; begin Result := Self.Select(x -> (x, f(x))); end; @@ -11887,20 +11883,27 @@ begin end; /// Превращает последовательность в последовательность массивов, содержащих n соседних элементов -function Nwise(Self: sequence of T; n: integer): sequence of array of T; extensionmethod; +function Windowed(Self: sequence of T; n: integer): sequence of array of T; extensionmethod; begin - var chunk := new Queue(n); + if n <= 0 then + raise new System.ArgumentException(GetTranslation(PARAMETER_MUST_BE_GREATER_0)); + + var q := new Queue(n); foreach var x in Self do begin - chunk.Enqueue(x); - if chunk.Count = n then + q.Enqueue(x); + if q.Count = n then begin - yield chunk.ToArray; - chunk.Dequeue; + yield q.ToArray; + q.Dequeue; // step = 1 end; end; end; +/// Превращает последовательность в последовательность массивов, содержащих n соседних элементов +function Nwise(Self: sequence of T; n: integer): sequence of array of T; extensionmethod := Self.Windowed(n); + + /// Превращает последовательность в последовательность пар соседних элементов, применяет func к каждой паре полученных элементов и получает новую последовательность function Pairwise(Self: sequence of T; func: (T,T)->Res): sequence of Res; extensionmethod; begin @@ -12171,6 +12174,10 @@ end; /// Возвращает элементы последовательности, ключи для которых отличаются, используя компоратор по-умолчанию function DistinctBy(Self: sequence of T; by: T->TKey); extensionmethod := Self.DistinctBy(by, nil); +/// Возвращает True, если ни один элемент не удовлетворяет условию +function None(Self: sequence of T; pred: T->boolean): boolean; extensionmethod := + not Self.Any(pred); + // ----------------------------------------------------- //>> Методы расширения списков # Extension methods for List T // ----------------------------------------------------- @@ -12393,42 +12400,45 @@ begin Result := maxIndex; end; - -/// Заменяет в массиве все вхождения одного значения на другое /// Заменяет в списке все вхождения одного значения на другое -procedure Replace(Self: List; oldValue, newValue: T); extensionmethod; +function Replace(Self: List; oldValue, newValue: T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do if Self[i] = oldValue then Self[i] := newValue; + Result := Self; end; /// Преобразует элементы массива или списка по заданному правилу -procedure Transform(Self: List; f: T->T); extensionmethod; +function Transform(Self: List; f: T->T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := f(Self[i]); + Result := Self; end; /// Преобразует элементы массива или списка по заданному правилу -procedure Transform(Self: List; f: (T,integer)->T); extensionmethod; +function Transform(Self: List; f: (T,integer)->T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := f(Self[i],i); + Result := Self; end; /// Заполняет элементы списка указанным значением -procedure Fill(Self: List; x: T); extensionmethod; +function Fill(Self: List; x: T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := x; + Result := Self; end; /// Заполняет элементы списка значениями, вычисляемыми по некоторому правилу -procedure Fill(Self: List; f: integer->T); extensionmethod; +function Fill(Self: List; f: integer->T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := f(i); + Result := Self; end; ///-- @@ -12488,6 +12498,15 @@ begin Result := Self; end; +/// Меняет местами элементы списка с индексами i и j +function Swap(Self: List; i, j: integer): List; extensionmethod; +begin + var tmp := Self[i]; + Self[i] := Self[j]; + Self[j] := tmp; + Result := Self; +end; + procedure CorrectFromTo(situation: integer; Len: integer; var from, &to: integer; step: integer); begin if situation=0 then exit; @@ -13358,6 +13377,15 @@ begin Result := Self; end; +/// Меняет местами элементы массива с индексами i и j +function Swap(Self: array of T; i, j: integer): array of T; extensionmethod; +begin + var tmp := Self[i]; + Self[i] := Self[j]; + Self[j] := tmp; + Result := Self; +end; + {/// Находит первую пару подряд идущих одинаковых элементов и возвращает индекс первого элемента пары. Если не найден, возвращается -1 function AdjacentFind(Self: array of T; start: integer := 0): integer; extensionmethod; begin @@ -13514,25 +13542,29 @@ begin Self[i] := f(i); end; -procedure Replace(Self: array of T; oldValue, newValue: T); extensionmethod; +/// Заменяет в массиве все вхождения одного значения на другое +function Replace(Self: array of T; oldValue, newValue: T): array of T; extensionmethod; begin for var i := 0 to Self.Length - 1 do if Self[i] = oldValue then Self[i] := newValue; + Result := Self; end; /// Преобразует элементы массива по заданному правилу -procedure Transform(Self: array of T; f: T->T); extensionmethod; +function Transform(Self: array of T; f: T->T): array of T; extensionmethod; begin for var i := 0 to Self.Length - 1 do Self[i] := f(Self[i]); + Result := Self; end; /// Преобразует элементы массива по заданному правилу -procedure Transform(Self: array of T; f: (T,integer)->T); extensionmethod; +function Transform(Self: array of T; f: (T,integer)->T): array of T; extensionmethod; begin for var i := 0 to Self.Length - 1 do Self[i] := f(Self[i],i); + Result := Self; end; /// Выполняет бинарный поиск в отсортированном массиве diff --git a/TreeConverter/SystemLib/SystemLibInitializer.cs b/TreeConverter/SystemLib/SystemLibInitializer.cs index 8e04ae611..22607b71f 100644 --- a/TreeConverter/SystemLib/SystemLibInitializer.cs +++ b/TreeConverter/SystemLib/SystemLibInitializer.cs @@ -235,6 +235,8 @@ namespace PascalABCCompiler.SystemLibrary public static UnitDefinitionItem read_procedure; public static UnitDefinitionItem write_procedure; public static UnitDefinitionItem writeln_procedure; + public static UnitDefinitionItem print_procedure; + public static UnitDefinitionItem println_procedure; public static UnitDefinitionItem readln_procedure; public static UnitDefinitionItem readln_from_file_procedure; public static UnitDefinitionItem read_short_string_procedure; diff --git a/TreeConverter/TreeConversion/syntax_tree_visitor.cs b/TreeConverter/TreeConversion/syntax_tree_visitor.cs index 101a0e59e..a00685446 100644 --- a/TreeConverter/TreeConversion/syntax_tree_visitor.cs +++ b/TreeConverter/TreeConversion/syntax_tree_visitor.cs @@ -398,6 +398,8 @@ namespace PascalABCCompiler.TreeConverter SystemLibrary.SystemLibInitializer.read_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.read_procedure_name); SystemLibrary.SystemLibInitializer.write_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.write_procedure_name); SystemLibrary.SystemLibInitializer.writeln_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.writeln_procedure_name); + SystemLibrary.SystemLibInitializer.print_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.print_procedure_name); + SystemLibrary.SystemLibInitializer.println_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.println_procedure_name); SystemLibrary.SystemLibInitializer.readln_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.readln_procedure_name); SystemLibrary.SystemLibInitializer.TextFileType = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.text_file_name_type_name); SystemLibrary.SystemLibInitializer.TextFileInitProcedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.TextFileInitProcedureName); @@ -492,6 +494,8 @@ namespace PascalABCCompiler.TreeConverter SystemLibrary.SystemLibInitializer.read_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.read_procedure_name); SystemLibrary.SystemLibInitializer.write_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.write_procedure_name); SystemLibrary.SystemLibInitializer.writeln_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.writeln_procedure_name); + SystemLibrary.SystemLibInitializer.print_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.print_procedure_name); + SystemLibrary.SystemLibInitializer.println_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.println_procedure_name); SystemLibrary.SystemLibInitializer.readln_procedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.readln_procedure_name); SystemLibrary.SystemLibInitializer.TextFileType = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.text_file_name_type_name); SystemLibrary.SystemLibInitializer.TextFileInitProcedure = new SystemLibrary.UnitDefinitionItem(psystem_unit, StringConstants.TextFileInitProcedureName); @@ -6987,7 +6991,12 @@ namespace PascalABCCompiler.TreeConverter return; } - else if (SystemLibrary.SystemLibInitializer.write_procedure.Equal(sil) || SystemLibrary.SystemLibInitializer.writeln_procedure.Equal(sil) || SystemLibrary.SystemLibInitializer.StrProcedure.Equal(sil)) + else if (SystemLibrary.SystemLibInitializer.write_procedure.Equal(sil) + || SystemLibrary.SystemLibInitializer.writeln_procedure.Equal(sil) + || SystemLibrary.SystemLibInitializer.print_procedure.Equal(sil) + || SystemLibrary.SystemLibInitializer.println_procedure.Equal(sil) + || SystemLibrary.SystemLibInitializer.StrProcedure.Equal(sil) + ) { is_format_allowed = true; } diff --git a/bin/Lib/PABCSystem.pas b/bin/Lib/PABCSystem.pas index c5797d916..95872fa60 100644 --- a/bin/Lib/PABCSystem.pas +++ b/bin/Lib/PABCSystem.pas @@ -11132,12 +11132,16 @@ function Flatten(Self: sequence of sequence of T): sequence of T; extensionme function JoinToString(Self: sequence of T; delim: string): string; extensionmethod; begin var g := Self.GetEnumerator(); - var sb := new System.Text.StringBuilder(''); + var sb := new System.Text.StringBuilder(); if g.MoveNext() then begin - sb.Append(g.Current.ToString()); - while g.MoveNext() do - sb.Append(delim + g.Current.ToString()); + sb.Append(System.Convert.ToString(g.Current)); + while g.MoveNext() do + begin + if delim<>'' then + sb.Append(delim); + sb.Append(System.Convert.ToString(g.Current)); + end end; Result := sb.ToString; end; @@ -11604,7 +11608,9 @@ begin Result := maxElement; end; -{function TakeLast(Self: sequence of T; count: integer): sequence of T; extensionmethod; +{ +// Не помню, почему закомментировал +function TakeLast(Self: sequence of T; count: integer): sequence of T; extensionmethod; begin if count < 0 then raise new System.ArgumentOutOfRangeException('count', count, GetTranslation(PARAMETER_MUST_BE_GREATER_EQUAL_0)); @@ -11854,7 +11860,7 @@ begin end; /// Табулирует функцию последовательностью -function Tabulate(Self: sequence of T; F: T->T1): sequence of (T, T1); extensionmethod; +function Tabulate(Self: sequence of T; f: T->T1): sequence of (T, T1); extensionmethod; begin Result := Self.Select(x -> (x, f(x))); end; @@ -11877,20 +11883,27 @@ begin end; /// Превращает последовательность в последовательность массивов, содержащих n соседних элементов -function Nwise(Self: sequence of T; n: integer): sequence of array of T; extensionmethod; +function Windowed(Self: sequence of T; n: integer): sequence of array of T; extensionmethod; begin - var chunk := new Queue(n); + if n <= 0 then + raise new System.ArgumentException(GetTranslation(PARAMETER_MUST_BE_GREATER_0)); + + var q := new Queue(n); foreach var x in Self do begin - chunk.Enqueue(x); - if chunk.Count = n then + q.Enqueue(x); + if q.Count = n then begin - yield chunk.ToArray; - chunk.Dequeue; + yield q.ToArray; + q.Dequeue; // step = 1 end; end; end; +/// Превращает последовательность в последовательность массивов, содержащих n соседних элементов +function Nwise(Self: sequence of T; n: integer): sequence of array of T; extensionmethod := Self.Windowed(n); + + /// Превращает последовательность в последовательность пар соседних элементов, применяет func к каждой паре полученных элементов и получает новую последовательность function Pairwise(Self: sequence of T; func: (T,T)->Res): sequence of Res; extensionmethod; begin @@ -12161,6 +12174,10 @@ end; /// Возвращает элементы последовательности, ключи для которых отличаются, используя компоратор по-умолчанию function DistinctBy(Self: sequence of T; by: T->TKey); extensionmethod := Self.DistinctBy(by, nil); +/// Возвращает True, если ни один элемент не удовлетворяет условию +function None(Self: sequence of T; pred: T->boolean): boolean; extensionmethod := + not Self.Any(pred); + // ----------------------------------------------------- //>> Методы расширения списков # Extension methods for List T // ----------------------------------------------------- @@ -12383,42 +12400,45 @@ begin Result := maxIndex; end; - -/// Заменяет в массиве все вхождения одного значения на другое /// Заменяет в списке все вхождения одного значения на другое -procedure Replace(Self: List; oldValue, newValue: T); extensionmethod; +function Replace(Self: List; oldValue, newValue: T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do if Self[i] = oldValue then Self[i] := newValue; + Result := Self; end; /// Преобразует элементы массива или списка по заданному правилу -procedure Transform(Self: List; f: T->T); extensionmethod; +function Transform(Self: List; f: T->T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := f(Self[i]); + Result := Self; end; /// Преобразует элементы массива или списка по заданному правилу -procedure Transform(Self: List; f: (T,integer)->T); extensionmethod; +function Transform(Self: List; f: (T,integer)->T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := f(Self[i],i); + Result := Self; end; /// Заполняет элементы списка указанным значением -procedure Fill(Self: List; x: T); extensionmethod; +function Fill(Self: List; x: T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := x; + Result := Self; end; /// Заполняет элементы списка значениями, вычисляемыми по некоторому правилу -procedure Fill(Self: List; f: integer->T); extensionmethod; +function Fill(Self: List; f: integer->T): List; extensionmethod; begin for var i := 0 to Self.Count - 1 do Self[i] := f(i); + Result := Self; end; ///-- @@ -12478,6 +12498,15 @@ begin Result := Self; end; +/// Меняет местами элементы списка с индексами i и j +function Swap(Self: List; i, j: integer): List; extensionmethod; +begin + var tmp := Self[i]; + Self[i] := Self[j]; + Self[j] := tmp; + Result := Self; +end; + procedure CorrectFromTo(situation: integer; Len: integer; var from, &to: integer; step: integer); begin if situation=0 then exit; @@ -13348,6 +13377,15 @@ begin Result := Self; end; +/// Меняет местами элементы массива с индексами i и j +function Swap(Self: array of T; i, j: integer): array of T; extensionmethod; +begin + var tmp := Self[i]; + Self[i] := Self[j]; + Self[j] := tmp; + Result := Self; +end; + {/// Находит первую пару подряд идущих одинаковых элементов и возвращает индекс первого элемента пары. Если не найден, возвращается -1 function AdjacentFind(Self: array of T; start: integer := 0): integer; extensionmethod; begin @@ -13504,25 +13542,29 @@ begin Self[i] := f(i); end; -procedure Replace(Self: array of T; oldValue, newValue: T); extensionmethod; +/// Заменяет в массиве все вхождения одного значения на другое +function Replace(Self: array of T; oldValue, newValue: T): array of T; extensionmethod; begin for var i := 0 to Self.Length - 1 do if Self[i] = oldValue then Self[i] := newValue; + Result := Self; end; /// Преобразует элементы массива по заданному правилу -procedure Transform(Self: array of T; f: T->T); extensionmethod; +function Transform(Self: array of T; f: T->T): array of T; extensionmethod; begin for var i := 0 to Self.Length - 1 do Self[i] := f(Self[i]); + Result := Self; end; /// Преобразует элементы массива по заданному правилу -procedure Transform(Self: array of T; f: (T,integer)->T); extensionmethod; +function Transform(Self: array of T; f: (T,integer)->T): array of T; extensionmethod; begin for var i := 0 to Self.Length - 1 do Self[i] := f(Self[i],i); + Result := Self; end; /// Выполняет бинарный поиск в отсортированном массиве diff --git a/bin/Lng/Eng/SemanticErrors_ib.dat b/bin/Lng/Eng/SemanticErrors_ib.dat index e410e010a..3a9c1084e 100644 --- a/bin/Lng/Eng/SemanticErrors_ib.dat +++ b/bin/Lng/Eng/SemanticErrors_ib.dat @@ -18,7 +18,7 @@ CANNOT_ASSIGN_TO_READONLY_PROPERTY=A readonly property cannot be assigned to DESTRUCTOR_CANNOT_HAVE_PARAMETERS=Destructor cannot have parameters USING_MODIFIERS{0}_{1}_TOGETHER_NOT_ALLOWED=Modifier '{0}' has conflicts with modifier '{1}' CONST_PARAMETERS_CANNOT_HAVE_DEFAULT_VALUE=const-parameters cannot have default value -FORMAT_EXPRESSION_CAN_USE_ONLY_IN_THESE_PROCEDURES=Format expression can be used only in calls of write, writeln и str +FORMAT_EXPRESSION_CAN_USE_ONLY_IN_THESE_PROCEDURES=Format expression can be used only in calls of Write, Writeln, Print, Println and Str BAD_CONSTRUCTED_FORMAT_EXPRESSION=Badly constructed format expression NIL_IN_SET_CONSTRUCTOR_NOT_ALLOWED=nil cannot be used in a set constructor POINTERS_IN_SETS_NOT_ALLOWED=Set cannot contain pointers diff --git a/bin/Lng/Rus/SemanticErrors_ib.dat b/bin/Lng/Rus/SemanticErrors_ib.dat index 472d9d8a2..27595ff7d 100644 --- a/bin/Lng/Rus/SemanticErrors_ib.dat +++ b/bin/Lng/Rus/SemanticErrors_ib.dat @@ -18,7 +18,7 @@ CANNOT_ASSIGN_TO_READONLY_PROPERTY=Нельзя присвоить свойст DESTRUCTOR_CANNOT_HAVE_PARAMETERS=Деструктор не может иметь параметры USING_MODIFIERS{0}_{1}_TOGETHER_NOT_ALLOWED=Совместное использование модификаторов {0} и {1} недопустимо CONST_PARAMETERS_CANNOT_HAVE_DEFAULT_VALUE=const-параметры не могут иметь значение по умолчанию -FORMAT_EXPRESSION_CAN_USE_ONLY_IN_THESE_PROCEDURES=Форматное выражение может использоваться только внутри write, writeln и str +FORMAT_EXPRESSION_CAN_USE_ONLY_IN_THESE_PROCEDURES=Форматное выражение может использоваться только внутри Write, Writeln, Print, Println и Str BAD_CONSTRUCTED_FORMAT_EXPRESSION=Неверно сконструированное форматное выражение NIL_IN_SET_CONSTRUCTOR_NOT_ALLOWED=Нельзя использовать nil в конструкторе множества POINTERS_IN_SETS_NOT_ALLOWED=Множество не может содержать указатели