Как объявить беззнаковое 32-битное целое?

Есть ли способ объявить 32-битное целое число без знака в PowerShell?

Я пытаюсь добавить беззнаковое (начинается с 0xf), то есть 0xff000000 + 0xAA, но получилось отрицательное число, а я хочу, чтобы оно было 0xff0000AA.


person Patrick    schedule 16.05.2012    source источник


Ответы (4)


0xff00000AA слишком велик для 32-битного целого числа без знака, используйте uint64

PS> [uint64]0xff00000AA
68451041450
person Shay Levy    schedule 16.05.2012
comment
Это не отвечает на фактически заданный вопрос, т. е. как объявить беззнаковое 32-битное целое число с оставшейся частью текста, подразумевающей, что установлен старший бит. Ответ, предоставленный Пенчо, действительно предоставляет средства для этого. Учитывая заданный вопрос, кажется разумным предположить, что в приведенном примере просто больше шестнадцатеричных цифр, чем предполагалось, и нет, что он слишком велик для 32-битного целого числа (знакового или иного). - person Bob Reynolds; 01.03.2013
comment
0xff000000 + 0xAA = 0xff0000AA, а не 0xff00000AA. Все они подходят для uint32. - person phuclv; 20.04.2020

Код из принятого в настоящее время ответа вызывает следующую ошибку в моей системе:

сообщение об ошибке

Это связано с тем, что PowerShell всегда пытается сначала преобразовать шестнадцатеричные значения в int, поэтому даже если вы приведете к uint64, среда будет жаловаться, если число имеет отрицательное значение int. Вы можете увидеть это из следующего примера:

PS C:\> [uint64] (-1)
Cannot convert value "-1" to type "System.UInt64". Error: "Value was either too large or too small for a UInt64."
At line:1 char:26
+ Invoke-Expression $ENUS; [uint64] (-1)
+                          ~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [], RuntimeException
    + FullyQualifiedErrorId : InvalidCastIConvertible

Вам нужно преобразовать строковое представление числа в uint64, чтобы избежать этого:

[uint64]"0xff000000" + [uint64]"0xAA"
person Pencho Ilchev    schedule 16.05.2012
comment
Я не получаю описанную вами ошибку, и ответ, который дал @Shay, отлично работает для меня. Использование 64-битной версии PSv2. Тем не менее, просто ввод 0xff00000AA автоматически конвертирует в 68451041450 без необходимости приведения. - person SpellingD; 17.05.2012
comment
@SpellingD: разница в том, что Пенчо использовал 0xFF0000AA (четыре нуля) для получения отрицательного значения Int32 со знаком (которое не может быть преобразовано в значение без знака), где в вопросе используется 0xFF00000AA (пять нулей) для получения положительного значения Int64 со знаком (которое преобразует успешно). - person Emperor XLII; 15.07.2012
comment
Не используйте изображения для публикации кода или ошибок. Скопируйте их в ответ. - person jpmc26; 12.08.2016

Я предполагаю, что вы имели в виду 0xff0000AA, поскольку, как уже упоминалось, 0xff00000AA является переполнением.

Самый простой способ сделать это — преобразовать значение из строки. Вы можете использовать System.Convert:

[System.Convert]::ToUInt32('0xff0000AA',16)
[System.Convert]::ToUInt32('ff0000AA',16)

Или просто попробуйте привести строку, но в этом случае вам нужно добавить 0x:

[uint32]'0xff0000AA'

Если, с другой стороны, вы действительно действительно хотите узнать 32-битную целочисленную часть 64-битного числа `0xff00000aa' без знака, то вы можете сделать это:

[System.Convert]::ToUInt32([System.Convert]::ToString(0xff00000AA -band ([uint32]::MaxValue),16),16)
person Bacon Bits    schedule 22.02.2016

Самый простой способ — привести к [uint32] из литерала long (с суффиксом L). Вам не нужно делать математику в [uint64] или приводить из строки

[uint32]0xff000000L + 0xAA

В PowerShell 6.2 a добавлен ряд новых суффиксов, включая суффикс u для uint32, так что это можно сделать еще проще

0xff000000u + 0xAA
person phuclv    schedule 20.04.2020