Получение левого бита - PullRequest
2 голосов
/ 24 мая 2010

У меня есть 5-битное целое число, с которым я работаю.Есть ли в Objective-C встроенная функция, которая позволит мне узнать, какой бит самый левый?

Ответы [ 9 ]

7 голосов
/ 24 мая 2010

Вы можете построить справочную таблицу из 32 элементов: 0, 1, 2, 2, 3 и т. Д.

6 голосов
/ 24 мая 2010

Это фактически та же самая операция, что и подсчет числа ведущих нулей. Некоторые процессоры имеют инструкции для этого, в противном случае вы можете использовать приемы, подобные тем, которые можно найти в Восторг хакера .

Это также эквивалентно округлению до ближайшей степени 2, и снова вы можете найти эффективные методы для этого в Восторг Хакера , например,

uint8_t flp2(uint8_t x)
{
    x = x | (x >> 1);
    x = x | (x >> 2);
    x = x | (x >> 4);
    return x - (x >> 1);
}

См. Также: Предыдущая сила 2

4 голосов
/ 24 мая 2010
NSInteger value = 9;
NSInteger shift = 1;
for(NSInteger bit = value; bit > 1; bit = value >> ++shift);
NSInteger leftmostbit = 1 << shift;

Работает для каждого количества бит.

2 голосов
/ 24 мая 2010

Если вы не хотите использовать поиск по таблице, я бы использовал 31 - __builtin_clz(yourNumber).

__builtin_clz( ) - встроенная функция компилятора, поддерживаемая gcc, llvm-gcc и clang (и, возможно, другими компиляторами) Возвращает количество начальных нулевых битов в целочисленном аргументе. Вычитая это из 31, вы получите позицию установочного бита самого высокого порядка. Он должен генерировать достаточно быстрый код на любой целевой архитектуре.

0 голосов
/ 05 августа 2010

С помощью VC ++ взгляните на _BitScanReverse / (64) в

0 голосов
/ 24 мая 2010

Чтобы очистить все биты ниже старшего значащего бита:

while ( x & (x-1) ) x &= x - 1;
// 01001 => 01000

Чтобы очистить все биты выше младшего значащего бита:

x &= -x;
// 01001 => 00001

Чтобы получить позицию только установленного битав байте:

position = ((0x56374210>>(((((x)&-(x))*0x17)>>3)&0x1C))&0x07);
// 01000 => 3

В libkern.h определена функция clz для подсчета лидирующих нулей в 32-битном int.Это ближе всего к нативной функции Objective-C.Чтобы получить позицию старшего значащего бита в int:

position = 31 - clz( x );
// 01001 => 3
0 голосов
/ 24 мая 2010

Я не знаю цель C, но именно так я бы это сделал в C.

pow (2, int (log2 (Number))

Это должно дать вам левуюсамое большее 1 битное значение.

ПОЖАЛУЙСТА, ВИДИТЕ КОММЕНТАРИЙ Стивена Кэнона, НИЖЕ ПЕРЕД ИСПОЛЬЗОВАНИЕМ ЭТОГО РЕШЕНИЯ.

0 голосов
/ 24 мая 2010

Если вы имеете в виду значение любого бита, находящегося в пятой позиции справа (самое левое из пятибитного значения), то:

    int value = 17;
    int bit = (value >> 4) & 1; // bit is 1

Если вы имеете в виду позицию крайнего левого бита, равную 1:

    int value = 2;
    int position;
    for (position = 0; position < 5; position++) {
            int bit = (value >> position) & 1;
            if (bit == 1)
                    break;
    }
    // position is 1

Позиция будет 0 для самого дальнего справа бита, 4 для самого левого бита вашего пятибитного значения или 5, если все биты равны нулю.

Примечание: это не самое эффективное решение в тактовых циклах. Надеюсь, это достаточно ясный и образовательный. :)

0 голосов
/ 24 мая 2010

Stanford Bit Twiddling Hacks есть много примеров того, как этого добиться.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...