Проверьте значение наименее значимого бита (LSB) и наиболее значимого бита (MSB) в C/C++
Мне нужно проверить значение наименее значимого бита (LSB) и наиболее значимого бита (MSB) целого числа в C/C++. Как мне это сделать?
5 ответов
//int value;
int LSB = value & 1;
кроме того (который теоретически не переносится, но практически-см. комментарий Стива)
//int value;
int LSB = value % 2;
детали: Вторая формула проще. % Оператор является оператором остатка. LSB числа-1, если это нечетное число и 0 в противном случае. Поэтому мы проверяем оставшуюся часть деления на 2. Логика первой формулы такова: число 1 в двоичном формате таково:
0000...0001
если вы двоичный-и это произвольное число, все биты результата будут равны 0, кроме последнего, потому что 0 и все остальное 0. Последний бит результата будет 1, если последний бит вашего числа был 1, потому что 1 & 1 == 1
и 1 & 0 == 0
этой хороший учебник для побитовых операций.
HTH.
вы можете сделать что-то вроде этого:
#include <iostream>
int main(int argc, char **argv)
{
int a = 3;
std::cout << (a & 1) << std::endl;
return 0;
}
вот так AND
ваша переменная с LSB, потому что
3: 011
1: 001
в 3-битовое представление. Так быть AND
:
AND
-----
0 0 | 0
0 1 | 0
1 0 | 0
1 1 | 1
вы сможете узнать, является ли LSB 1 или нет.
edit: найти MSB.
прежде всего прочитайте Endianess статьи, чтобы договориться о том, что MSB
средства. В следующих строках мы предполагаем обращаться с big-endian нотация.
найти MSB
, в следующем фрагменте мы сосредоточимся на применении правого сдвига до MSB
будет AND
С 1
.
Рассмотрим следующий код:
#include <iostream>
#include <limits.h>
int main(int argc, char **argv)
{
unsigned int a = 128; // we want to find MSB of this 32-bit unsigned int
int MSB = 0; // this variable will represent the MSB we're looking for
// sizeof(unsigned int) = 4 (in Bytes)
// 1 Byte = 8 bits
// So 4 Bytes are 4 * 8 = 32 bits
// We have to perform a right shift 32 times to have the
// MSB in the LSB position.
for (int i = sizeof(unsigned int) * 8; i > 0; i--) {
MSB = (a & 1); // in the last iteration this contains the MSB value
a >>= 1; // perform the 1-bit right shift
}
// this prints out '0', because the 32-bit representation of
// unsigned int 128 is:
// 00000000000000000000000010000000
std::cout << "MSB: " << MSB << std::endl;
return 0;
}
если вы печатаете MSB
вне цикла, вы получите 0
.
Если вы измените значение a
:
unsigned int a = UINT_MAX; // found in <limits.h>
MSB
будет 1
, потому что его 32-разрядное представление:
UINT_MAX: 11111111111111111111111111111111
однако, если вы делаете то же самое с а целое число со знаком все будет по-другому.
#include <iostream>
#include <limits.h>
int main(int argc, char **argv)
{
int a = -128; // we want to find MSB of this 32-bit unsigned int
int MSB = 0; // this variable will represent the MSB we're looking for
// sizeof(int) = 4 (in Bytes)
// 1 Byte = 8 bits
// So 4 Bytes are 4 * 8 = 32 bits
// We have to perform a right shift 32 times to have the
// MSB in the LSB position.
for (int i = sizeof(int) * 8; i > 0; i--) {
MSB = (a & 1); // in the last iteration this contains the MSB value
a >>= 1; // perform the 1-bit right shift
}
// this prints out '1', because the 32-bit representation of
// int -128 is:
// 10000000000000000000000010000000
std::cout << "MSB: " << MSB << std::endl;
return 0;
}
как я сказал в комментарии ниже, то MSB
of a положительное целое число всегда 0
, а MSB
of a отрицательное целое число всегда 1
.
вы можете проверить INT_MAX 32-битное представление:
INT_MAX: 01111111111111111111111111111111
сейчас. Почему цикл использует sizeof()
?
Если вы просто делаете цикл, как я написал в комментарии: (извините за =
отсутствует в комментарии)
for (; a != 0; a >>= 1)
MSB = a & 1;
вы получаете 1
всегда, потому что C++ не будет рассматривать "биты нулевой площадки" (потому что вы указали a != 0
как заявление выхода) выше, чем самый высокий 1
. Например, для 32-разрядных целых чисел имеем:
int 7 : 00000000000000000000000000000111
^ this will be your fake MSB
without considering the full size
of the variable.
int 16: 00000000000000000000000000010000
^ fake MSB
другие уже упоминалось:
int LSB = value & 1;
для получения наименее значительного бита. Но есть способ cheatier получить ГРЩ чем уже упоминалось. Если значение уже является подписанным типом, просто сделайте:
int MSB = value < 0;
если это неподписанное количество, приведите его к знаковому типу того же размера, например, если value
был признан unsigned
, do:
int MSB = (int)value < 0;
Да, официально, не портативный, неопределенное поведение, что угодно. Но на каждой второй системе дополнения и каждый компилятор для них, о котором я знаю, работает; в конце концов, высокий бит-это бит знака, поэтому, если подписанная форма отрицательна, то MSB-1, если она неотрицательна, MSB-0. Поэтому удобно, что подписанный тест для отрицательных чисел эквивалентен извлечению MSB.
LSB легко. Просто x & 1.
MSSB немного сложнее, так как байты не могут быть 8 битами, а sizeof(int) не может быть 4, и могут быть биты заполнения справа.
кроме того, с знаковое целое число, значит знаковый разряд МС значение бита.
Если вы имеете в виду знак бит, жизнь проста. Это просто x
Если вы имеете в виду самый значительный бит значения, чтобы быть полностью переносимым.
int answer = 0;
int rack = 1;
int mask = 1;
while(rack < INT_MAX)
{
rack << = 1;
mask << = 1;
rack |= 1;
}
return x & mask;
это многословный способ сделать это. На самом деле
x & (1