Quais são as vantagens de usar operações bit a bit? [fechadas]

19

Após ler o último boletim informativo do CodeProject, deparei-me com este artigo sobre operações bit a bit . É uma leitura interessante, e certamente posso ver o benefício de verificar se um número inteiro é par ou ímpar, mas testar se o n-ésimo bit está definido? Quais podem ser as vantagens disso?

billy.bob
fonte

Respostas:

27

As operações bit a bit são absolutamente essenciais ao programar registros de hardware em sistemas embarcados. Por exemplo, todo processador que eu já usei possui um ou mais registros (geralmente um endereço de memória específico) que controlam se uma interrupção está ativada ou desativada. Para permitir que uma interrupção seja acionada, o processo usual é definir o bit de habilitação para esse tipo de interrupção e, o mais importante, não modificar nenhum dos outros bits no registro.

Quando uma interrupção é acionada, geralmente define um pouco em um registro de status, para que uma única rotina de serviço possa determinar o motivo exato da interrupção. Testar os bits individuais permite uma decodificação rápida da fonte de interrupção.

Em muitos sistemas embarcados, o total de RAM disponível pode ser de 64, 128 ou 256 BYTES (ou seja, bytes não kilobytes ou megabytes). Nesse ambiente, é comum usar um byte para armazenar vários itens de dados, sinalizadores booleanos etc. e depois usar operações de bits para definir e ler estes.

Há vários anos que trabalho com um sistema de comunicações via satélite em que a carga útil da mensagem é de 10,5 bytes. Para fazer o melhor uso desse pacote de dados, as informações devem ser compactadas no bloco de dados sem deixar nenhum bit não utilizado entre os campos. Isso significa fazer uso extensivo de operadores bit a bit e shift para pegar os valores das informações e empacotá-los na carga útil que está sendo transmitida.

uɐɪ
fonte
4
Para aqueles interessados em operações de bit mais boolean e otimizações, dê uma olhada no prazer do Hacker: amazon.com/Hackers-Delight-Henry-S-Warren/dp/0201914654
gablin
7

Basicamente, você os usa devido a considerações de tamanho e velocidade. As operações bit a bit são incrivelmente simples e, portanto, geralmente mais rápidas que as operações aritméticas. Por exemplo, para obter a parte verde de um valor rgb, a abordagem aritmética é (rgb / 256) % 256. Com operações bit a bit, você faria algo como (rgb >> 8) & 0xFF. O último é significativamente mais rápido e, quando você está acostumado, também é mais fácil. Geralmente, as operações bit a bit entram muito em jogo quando você precisa codificar / decodificar dados de maneira compacta e rápida.

back2dos
fonte
2
BYTE g1 = (rgb / 256) % 256; 00E51013...C1 E9 08...shr ecx,8 00E51016...88 0C 24...mov byte ptr [esp],cl
Rwong 24/10/10
4

Esse tipo de operação é frequentemente usado ao gravar em sistemas incorporados nos quais a memória ou a CPU são restritas.

Por exemplo, para economizar espaço, você pode armazenar várias variáveis ​​em uma única variável int de 8 bits, usando cada bit para representar um booleano. Então você precisa de uma maneira rápida de definir um bit específico ou recuperar o valor do bit.

Geralmente, ao programar em linguagens de nível superior, como C #, em um PC de mesa com Gigabytes de memória, você realmente não se importa que cada bool um ocupe um byte inteiro . Mas se você estiver programando um microcontrolador em C com 2kb de memória, cada bit é importante, portanto, a capacidade de empacotar 8 bools em um único byte pode ser crítica.

Simon P Stevens
fonte
.NET tem o [Flags]atributo que permite usar um Enumcampo como um bit. Por exemplo, Fontpossui uma Stylepropriedade que é um campo de bits contendo negrito, itálico, sublinhado e tachado.
Deltreme 22/10/10
@deltreme. Sim, eu sei que você pode usar [Flags], mas esse não é o ponto. O ponto é que, em linguagens de alto nível, você não se importa muito com o uso de alguns bytes de espaço para alguns bools. Você geralmente se preocupa mais com a manutenção e a legibilidade do código. Nos sistemas incorporados nos quais você se importa com o tamanho, não tem acesso a coisas como o atributo .net [Flags], portanto é onde você pode usar essas operações bit a bit.
Simon P Stevens
"mas testando se o n-ésimo bit está definido? Quais podem ser as vantagens disso?" esse é o ponto - mas, como nenhum idioma foi especificado, decidi inseri-lo como um comentário em uma resposta em que c # foi mencionado. Não é um comentário sobre a sua resposta, é uma adição ou é bom saber, ou o que seja.
Deltreme 25/10/10
@ Deltreme: Oh, legal.
Simon P Stevens
3

As operações bit a bit também são usadas com freqüência em codecs de vídeo e áudio, pelo mesmo motivo que em eletrônicos incorporados; ser capaz de agrupar cinco sinalizadores e um timer de onze bits em meio int é muito útil quando você deseja criar um codec de vídeo supereficiente.

De fato, o MPEG 4 ainda usa codificação Golpon exponencial para campos com tamanho de bits variável. Um valor com 17 ou 19 bits de largura no último pacote pode ter apenas três ou cinco bits de largura nesse pacote - e você descobriria tudo isso com operações bit a bit.

Tacroy
fonte
2

Os truques que combinam operações lógicas bit a bit, operações de deslocamento bit a bit e operações aritméticas podem ser entendidos por pessoas que estudaram a construção de um somador binário usando portas lógicas (e, ou, não). Fora desse círculo, é muito difícil entender sem um comentário detalhado.

É útil ao programar unidades SIMD , especialmente se a arquitetura da CPU deixar intencionalmente algumas instruções SIMD, pois elas podem ser emuladas por algumas outras.

Por exemplo, a arquitetura pode não definir instruções para obter os valores negativos de um grupo de 16 bytes, mas que podem ser emulados negando bit a bit e adicionando 1. Da mesma forma, a subtração também pode ser omitida, porque pode ser emulada usando o negativo do segundo operando. A disponibilidade da "rota alternativa" é o motivo da omissão de determinadas instruções.

Da mesma forma, o SIMD pode suportar apenas adição paralela de 8 bits, sem implementar a adição para elementos mais amplos, como 16 bits, 32 bits ou 64 bits. Para emulá-los, é necessário extrair o bit de sinal do resultado do cálculo de 8 bits e executar a operação de transporte no próximo elemento.

rwong
fonte
0

Dados de empacotamento, operações mais rápidas (multiplicação, divisão e módulo são significativamente mais rápidos se alinhadas às potências de 2), inversão de bits, etc. Aprenda-os e comece a usá-los. Você começará lentamente a ver a maioria das vantagens por conta própria.

user108496
fonte
1
Essa é uma resposta bastante ortogonal.
itsbruce