Не знаю, как правильно написать, в цикле по словарю при автовыводе переменной типа KeyValuePair не хочет показывать свойств Key и Value, а если указать этот тип, то показывает. И вообще, разные подсказки.
С автовыводом типа
С указанием типа
Вроде была тема по ошибкам Intellisense, или не было?
Наведите мышку на x в первом случае - видно проблему. Анализатор кода считает что у него тип integer. Это #894, 1 из древних ошибок которые почему то никак не хотят исправлять.
Анализатор кода это часть IDE, поэтому вы правильно сюда кинули. Тема была, но администраниция решила что лучше их не плодить.
Program2.pas(15) : Нельзя преобразовать тип array of procedure() к array of procedure()
type
TAProc = array of procedure;
procedure test(prc:TAProc);
begin
prc[0];
end;
procedure test2();
begin
writeln('TEST');
end;
BEGIN
test(arr(test2))
END.
Это баг или действительно нельзя передавать массив процедур в качестве параметра?
type
TProcedure = procedure; // Или вместо определения своего типа используем Action0, что также есть System.Action.
T = array of TProcedure;
procedure WithArray(a: T);
begin
end;
procedure P();
begin
end;
begin
WithArray(Arr&<TProcedure>(P)); // Обязательно указываем в угловых скобках тип элементов массива.
end.
Такого ограничения нет в языке. Я думаю, что это баг (моё скромное мнение).
По подобным вопросам я Вам бы советовал обращаться к постоянным пользователям языка (например, @Sun_Serega, @RAlex). Ибо у меня иная специализация (в статусе посмотрите).
Кстати, почему Вы написали в данную тему? Это же баг (если баг) не самой IDE, а компилятора.
begin
var p1: procedure := ()->writeln(1);
var p2: procedure := ()->writeln(2);
writeln(p1.GetType=p2.GetType); // False
end.
Но, при объявлении:
TProcedure = procedure;
Вы создаёте единый тип делегата, в данном случае без параметра и возвращаемого значения. Теперь если написать:
type
TProc = procedure;
procedure test(prc: array of TProc);
begin
prc[0];
end;
procedure test2();
begin
writeln('TEST');
end;
begin
test(Arr(TProc(test2)));
end.
И в параметре test, и в выражении Arr(...) - используется одинаковый тип делегата.
Использовать стандартные типы аля Action0, Action, Action2, Action3. (а для функций - Func0, Func, …)
Они и есть точно такие же типы делегатов, как TProc в коде выше. Только их не надо руками объявлять, раз они есть.
Если вам не хватает 3 параметров - можно ещё писать System.Action<*список типов через запятую*>
и System.Func<*список типов через запятую*>
они, вроде, до 16 параметров включительно поддерживают.
Вместо приведения каждого параметра (TProc(*имя процедуры*)) - можно явно указать тип элементов массива, который создаётся, с помощью &<>.
Или, ещё лучше, использовать создание массива с помощью new, оно, обычно, раза в 2 быстрее чем arr, но не может авто определять тип элементов. А раз нам как раз нужно без авто определения - так лучше:
procedure test(prc: array of Action0);
begin
prc[0];
end;
procedure test2();
begin
writeln('TEST');
end;
begin
test(new Action0[](test2));
end.
Сначала решил посмотреть код стандартного модуля и заметил интересную особенность:
В функции Abs(x) не было замечено принятия параметра в типе данных byte (0..255), размер 1 байт.
Ниже код:
///-function Abs(x: число): число;
/// Возвращает модуль числа x
function Abs(x: integer): integer;
///--
function Abs(x: shortint): shortint;
///--
function Abs(x: smallint): smallint;
///--
function Abs(x: BigInteger): BigInteger;
///--
function Abs(x: longword): longword;
///--
function Abs(x: int64): int64;
///--
function Abs(x: uint64): uint64;
///--
function Abs(x: real): real;
///--
function Abs(x: single): single;
------------------------------------------------
Далее решено было создать тестовую программу на использование этой функции:
begin
var a:byte;
a:=255;
a:=abs(a);
write(a);//FIXME: выводит неправильное значение модуля 255, в подпрограмме нет функции для byte.
end.
На вывод (при успешной компиляции) программа дает:
1
Если переменной a присвоить значение 254 то выводит: 2; 253: 3 и т. д.
При шаге со входом в подпрограмму вычисление происходит в функции
function Abs(x: shortint): shortint;
begin
Result := Math.Abs(x);
end;
Но shortint (-128..127)
При a:byte:= 128 выводит ошибку: "Ошибка времени выполнения: Инвертировать минимальное значение двоичного дополнения невозможно."
Вопрос: В чём причина данной ошибки? Проблема в стандартном модуле или моём тестировании?
Что нужно сделать, чтобы модуль числа возвращался правильно, не меняя при этом типа данных (byte) ?
на что, при наведении на функцию inc(), был выведен комментарий:
хотя у нас a имеет тип данных word, а в описании у нас символьный тип данных. Такое же сообщение есть и для longword, uint64, shortint, smallint, int64.
Для integer описание верное:
и для char:
Для byte в описании применен перечислимый тип данных:
Для biginteger нет перегруженной подпрограммы и описание неверное:
unit biginc;
interface
uses PABCSystem;
function Inc(a:biginteger):biginteger;
implementation
function Inc(a:biginteger):biginteger;
begin
result:=a+1;
end;
end.
после чего запустил код
uses biginc;
begin
var a:biginteger:=10;
write(Inc(a));
end.
Программа вывела верное значение 11 (в данном случае). Также работает и на других значениях.
1.Обеспечить правильный вывод описания над вышеописанными типами данных
2.Осуществить работу инкремента над BigInteger.
Благодарю за чтение сообщения до конца!
Информация для разработчиков:
PascalABCCompiler.Core v3.5.0.2167 (01.07.2019), debug version
Runtime version: 4.0.30319.42000
OS version: Microsoft Windows NT 6.1.7601 Service Pack 1
Processor count: 4
WorkingSet: 200452 kb
Кстати, это весьма интересная проблема. Ведь Ord(x: перечислимы тип) в PABCSystem нет. Это функция с внутренней реализацией. Собственно, бесполезная, ведь между перечислимым типом и целым число можно использовать просто явное приведение.