![]() |
![]() ![]() ![]() ![]() |
|
Обсуждение документации и использования не-целочисленных значений в Delphi и PascalDelphi , Компоненты и Классы , Процедуры и функцииБулев тип в Delphi и Pascal: особенности и подводные камниВведениеБулев тип ( В этой статье мы разберём: 1. Представление булевых значений1.1. Стандартный
|
||||||||||||||||||||||||
| Тип | Размер | Ложь (False) | Истина (True) |
| Boolean | 1 байт | 0 | 1 |
| ByteBool | 1 байт | 0 | Любое ненулевое значение |
| WordBool | 2 байта | 0 | Любое ненулевое значение |
| LongBool | 4 байта | 0 | Любое ненулевое значение |
Пример:
var
A: ByteBool;
begin
A := ByteBool(42); // True, так как 42 ≠ 0
end;
Проблемы возникают, когда в Boolean попадают значения, отличные от 0 и 1. Например:
var
B: Boolean;
begin
B := Boolean(2); // Небезопасно!
if B then
WriteLn('B is True') // Может работать, но не гарантировано
else
WriteLn('B is False');
end;
Почему это опасно?
- Компилятор может генерировать код, который проверяет только нулевое/ненулевое значение (как для ByteBool).
- В некоторых случаях Boolean(2) = True может давать False (например, при сравнении).
var
B1, B2: Boolean;
begin
B1 := Boolean(1);
B2 := Boolean(2);
WriteLn(B1); // True
WriteLn(B2); // True
WriteLn(B1 and B2); // True
WriteLn(B1 = B2); // False! (в некоторых версиях FPC)
end;
Вывод:
True
True
True
False
Это происходит потому, что для сравнения (=) компилятор может сравнивать числовые значения (1 ≠ 2), а для логических операторов (and) — интерпретировать их как True.
Избегайте явного приведения к Boolean:
Вместо:
B := Boolean(X); // Плохо
Используйте:
B := (X <> 0); // Хорошо
Используйте правильный тип для API:
Для WinAPI (BOOL в C) используйте LongBool.
Для Pascal-кода придерживайтесь Boolean.
Будьте осторожны с массивами:
Если используете Boolean как индекс массива, убедитесь, что значение точно 0 или 1:
const Values: array[Boolean] of Integer = (10, 20);
var B: Boolean;
begin B := (SomeValue <> 0); // Гарантирует 0 или 1
WriteLn(Values[B]); // Безопасно end;
Если вам критично гарантировать 0/1 представление:
function SafeBool(X: Integer): Boolean;
begin
Result := (X <> 0);
end;
Или используйте тип с явным размером:
var
B: ByteBool; // Для совместимости с C/C++ bool
Boolean — это строго 0 (False) или 1 (True), но компилятор не всегда это проверяет.Boolean(X) опасны, если X не 0 или 1.ByteBool, WordBool или LongBool.X <> 0) вместо приведения типов.Соблюдение этих правил поможет избежать скрытых ошибок и неожиданного поведения в ваших программах.
Булев тип в Delphi и Pascal имеет особенности представления и приведения типов, которые могут вызывать неожиданное поведение, поэтому важно использовать его аккуратно и учитывать различия между `Boolean`, `ByteBool`, `WordBool` и `LongBool`.
Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш
Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS
:: Главная :: Процедуры и функции ::
реклама |