Подсчет количества установленных битов

Я хочу подсчитать количество битов в двоичном числе, которые установлены. Например, пользователь вводит число 97, которое равно 01100001 в двоичном формате. Программа должна мне выдать, что 3 бита установлены с помощью MIPS ISA.

Я могу добиться этого на C, но я не знаю, как это сделать с помощью ассемблерного кода.


person csguy11    schedule 22.09.2010    source источник


Ответы (3)


То, что вы ищете, часто называют подсчетом населения (popcount).

На Bit Twiddling Hacks есть несколько реализаций C (некоторые из которых пугающе умны). Если вы знакомы с C, каждый подход должен иметь разумный перевод на сборку MIPS после разбивки выражений.

Если ваш входной домен небольшой (например, 0-255), вы всегда можете сделать таблицу поиска и использовать ввод в качестве смещения для прямого получения количества всплывающих окон.

person Chris Schmich    schedule 22.09.2010

Поскольку это звучит как домашнее задание, я не буду приводить код MIPS, но вот алгоритм (написанный на C). Это должно быть просто для перевода в MIPS:

int bits(unsigned int number)
{
    // clear the accumulator
    int accumulator = 0;
    // loop until our number is reduced to 0
    while (number != 0)
    {
        // add the LSB (rightmost bit) to our accumulator
        accumulator += number & 1;
        // shift the number one bit to the right so that a new
        // bit is in the LSB slot
        number >>= 1;
    }
    return accumulator;
}
person Gabe    schedule 22.09.2010

Ссылка, которую дал Крис, дает несколько хороших методов подсчета битов. Я бы предложил этот метод, так как он очень быстрый и не требует не требует зацикливания, а только побитовой операции, что было бы проще сделать на ассемблере.

Другой способ получить ассемблерный код — создать код на C, скомпилировать его, а затем посмотреть на выходную сборку (большинство компиляций могут создавать выходные данные ассемблерного файла (-S для gcc, но не забудьте отключить оптимизацию с помощью -O0 для получить более легкий для понимания код), или позволить вам просмотреть дизассемблированный двоичный файл). Он должен указать вам правильное направление.

Как анекдот, я недавно провел некоторое тестирование на PowerPC (не MIPS, я знаю...) для самого быстрого способа подсчета битов в 32-битном int. Метод, который я связал, был лучшим из всех других методов, пока я не сделал таблицу поиска размером в байт и не обратился к ней 4 раза. Казалось бы, ALU медленнее, чем обращение к кешу (алгоритм обрабатывает около миллиона чисел).

person Eli Iser    schedule 22.09.2010