Чудо Второе (Absolute Miracle).
Положите на главную форму созданного ранее проекта новую кнопку и напишите в его обработчике события OnClick такой код:
procedure TfrmAllMiracles.btnAbsMrclClick (Sender: TObject); var i1: int64; begin i1:= abs(low(integer)); ShowMessage(IntToStr(i1)); end; Figure 2. |
Прежде чем нажать
F9, проанализируем написаное.
Low от
integer - значение известное всем, записанное даже в Help'е и равное
-2147483648, т.е. число отрицательное.
Help не говорит о функции
Abs ничего нового: Abs returns the absolute value of the argument X. X is an integer-type or real-type expression.
Переменная i1 описана как int64, и это правильно, потому что 2147483648 - уже выходит за границы типа integer. Это значение (2147483648) мы и ожидаем увидеть на экране, не так ли? А вот и нет. Проверьте. На экране вновь -2147483648. Как абсолютное значение может быть отрицательным?
Давайте еще раз, повнимательнее рассмотрим выражение abs(low(integer)). Что можно еще сказать про него? Не смотря на наличее в нем функций, это - константа
Читаем Help по теме
"Constant expressions":
...Constant expressions cannot include variables, pointers, or function calls, except calls to the following predefined functions: Abs...Low...
попробуем описать константу со значением равным этому выражению:
... const ci = abs(low(integer)); ... Figure 3. |
Код компилируется. Значит мы - правы, а это значит, что результат выражения определяется еще на стадии компиляции. Далее,
low(integer)) имеет целый тип.
Abs от
integer - тоже целое, а нам нужно
int64. Поробуем переписать код следующим образом:
procedure TfrmAllMiracles.btnAbsMrclClick (Sender: TObject); const ci = abs(low(integer)); var i1: int64; begin // i1:= abs((low(integer)));
i1:= abs(int64(low(integer))); ShowMessage(IntToStr(i1)); end; Figure 4. |
Теперь - заработало. Секрет "Абсолютного чуда" раскрыт! Кстати,
abs(int64(low(integer))) - тоже константа.
Следующее чудо - пример того, как вполне правильный код отказывается компилироваться.
Содержание раздела