Преобразование Boolean в Integer в VB.NET
Возьмите следующий код:
Sub Main()
Dim i As Integer
Dim b As Boolean
i = 1
b = i
i = b
Console.WriteLine(i)
i = Convert.ToInt32(b)
Console.WriteLine(i)
End Sub
Отпечатано следующее:
-1
1
Почему это?
(Просто шутка:) Вы тоже можете получить 0...
Int32.TryParse("True", i)
Console.WriteLine(i)
Ответы
Ответ 1
То, что вы видите, - это немного устаревший код, показывающий его голову.
В основе дела лежит тип VT_BOOL. Visual Basic 6.0 использовал тип VT_BOOL (AKA VARIANT_BOOL) для своих логических значений. True для VARIANT_BOOL представлен значением VARIANT_TRUE, которое имеет целочисленное значение -1. Во время перехода на .NET было решено, что при использовании подпрограмм преобразования Visual Basic для преобразования логического значения в значение Integer семантика Visual Basic 6.0 будет поддерживаться на возвращаемом значении; это будет -1.
Первое неявное преобразование происходит с помощью строки b = i. Под капотом это делает неявное преобразование от целого к логическому. Любое ненулевое значение считается истинным, поэтому полученное значение истинно.
Однако следующая строка кода выполняет неявное преобразование в целочисленный тип.
i = b
Под капотом используется одна из процедур преобразования Visual Basic (CType или CInt), чтобы преобразовать значение в целое число. Поскольку такая семантика Visual Basic находится в игре, а возвращаемое значение равно -1.
Следующая интересная строка - это строка Convert.ToInt32()
. Это использует процедуру преобразования .NET, которая не использует семантику Visual Basic. Вместо этого он возвращает базовое выражение BCL для истинного булевского значения, которое равно 1.
Ответ 2
Некоторые языки считают логическое значение true равным -1, а не 1. Я должен был бы провести исследование, чтобы понять, почему, как я не помню.
В VB6 константа True
имеет значение -1
.
Однако Convert.ToInt32(Boolean)
documented в качестве возвращаемого значения "Число 1, если значение истинно, в противном случае - 0." Таким образом, это то же самое независимо от того, какой язык рамки вы используете.
Изменить: см. вопрос boolean true - положительный 1 или отрицательный 1
Ответ 3
Что касается того, почему -1 используется для True, я считаю, что это потому, что это буквально (NOT 0).
Начните с нуля, переверните все биты, а затем прочитайте его как два дополнения - получится отрицательный.
Итак, поскольку все, что не является False, является True, а False равно 0, (NOT False) представляется -1.
Это может быть просто совпадение, хотя....
Ответ 4
Из документации MSDN Visual Basic:
Преобразования типов
Когда Visual Basic преобразует числовые значения типа данных в Boolean, 0 становится Ложные и все другие значения становятся Правда. Когда Visual Basic конвертирует Логические значения для числовых типов, False становится равным 0, а True - -1.
И для Convert.ToInt32 (значение):
возвращает число 1, если значение истинно; в противном случае 0.
Итак, для вашего кода:
i = 1
b = i // b becomes true
i = b // true = -1
Console.WriteLine(i) // i is -1
i = Convert.ToInt32(b) // Convert.ToInt32(true) = 1
Console.WriteLine(i) // i is 1
Ответ 5
"True" - это отрицание от значения 0 числового типа данных!
Не (0) для не подписанных типов возвращает 1.
Не (0) для подписанных типов возвращает -1.
Я не знаю вашего кода, возможно, ваш код выполняет внутреннее преобразование данных во второй раз.
Ответ 6
Это потому, что в VB.NET значения Boolean равны -1 для true и 0 для false по умолчанию. Я не уверен, почему он печатает как 1 второй раз, хотя...
Ответ 7
Все числовые типы данных могут использоваться как Boolean! Результат зависит от используемого типа данных.
Примеры:
Dim i As Byte ' Byte is non-signed!
Dim b As Boolean = True
i = b ' Set first (lowest) bit of i (non-signed byte)
' i is now binary 0000 0001 = 1!
Dim i As SByte ' SByte is signed!
Dim b As Boolean = True
i = b ' Set all bits of i (signed byte)
' i is now FF (binary 1111 1111 = -1 !
Целое число подписано, True - целое → -1.
UInteger не подписан, True - UInt → 1.
И так далее...
Фальсифицированное значение очищает старший бит в числовых знаках, и самый низкий в неписанных числах.
Поэтому False - 0 во всех числовых типах данных.
Ответ 8
Это изворотливый ответ, но:
Dim b As Boolean
b = False
Dim i As Integer
i = IIf(b, 1, 0)