Aritmética Binária
- Conteúdo: Complemento de um/ Complemento de dois/ Ponto fixo/ Soma binária/
 
Podemos utilizar números binários para codificar qualquer tipo de dado, como vimos na teoria de dados digitais. Mas ainda não sabemos como utilizar números binários para representar: números inteiros que possam ser negativos e números reais fracionados (exemplo: -15;  1,032; -0,0001; 10001231231).
Essa teoria irá tratar desses temas e também da parte referente a operações com números binários (soma e subtração).
Soma binária
A soma binária é realizada de maneira similar a soma de decimais, só que precisamos reforçar que 1+1 em binário (esse + é de soma não de OR), resulta em 10, o 1 do estouro e que passa para a próxima casa é chamado de carry. Esse carry é similar ao vai um em uma soma decimal, por exemplo: quando somamos em decimal 9 + 3 o resultado é 12 (10 + 2).
Exemplos a seguir consideram
- Palavras binárias com 8 bits
 - Números inteiros positivos
 
Tip 1
01+01=1001+01+01=1110+10=100
- 0xAA + 0x55 = 0xFF
 
                          : Carry
     1 0 1 0 1 0 1 0      : A 
     0 1 0 1 0 1 0 1 +    : B
     ---------------  
     1 1 1 1 1 1 1 1      : Resultado (A+B)
- 0xAA + 0x55 = 0xFF
 
                          : Carry
     1 0 1 0 1 0 1 0      : A 
     0 1 0 1 0 1 0 1 +    : B
     ---------------  
     1 1 1 1 1 1 1 1      : Resultado (A+B)
- 0x2B + 0x57 = 0xFF
 
     1 1 1 1 1 1 1        : Carry
     0 0 1 0 1 0 1 1      : A 
     0 1 0 1 0 1 1 1 +    : B
     ---------------  
     1 0 0 0 0 0 1 0      : Resultado (A+B)
Precisamos entender que cada bit deve ser armazenado em hardware! Um sistema com 8 bits não consegue armazenar 9 bits, e se houver um estouro no último bit essa informação será perdida.
Note
Os bits são armazenados na memória, as memórias armazenam vetores de bits. Computadores reais não possuem memória infinita e nem largura de bits infinita.
- 0x80 + 0x80 = 0x100, mas resulta em 0x00 por conta do somador ser 8 bits:
 
carry é perdido
   x
    \
     1 0 0 0 0 0 0 0 
     1 0 0 0 0 0 0 0 +
     ---------------
     0 0 0 0 0 0 0 0
- 0x03 + 0x81 = 0x84
 
               1 1        : carry (vai um)
                  \       
     0 0 0 0 0 0 1 1 
     1 0 0 0 0 0 0 1 +
     ---------------
     1 0 0 0 0 1 0 0    
Complemento de um
Warning
Forma errada/ não usual de armazenar números sinalizados (+, -)
Exemplos a seguir consideram
- Palavras binárias com 8 bits
 - Números inteiros positivos
 
No complemento de um, utilizamos a casa/bit mais significativa de um vetor de bits para representar se o número é positivo (0) ou negativo (1). Exemplo (utilizando 8 bits):
- Valor +1 em binário, com complemento de 1
 
    00000001
    ^
    | indica que o valor é positivo
- Valor -1 em binário, com complemento de 1
 
    10000001 
    ^
    | indica que o valor é negativo
O problema do complemento de 1 é que:
- Possuímos duas representações para o valor 0: 
00000000e10000000 - 
Operações de soma não funcionam corretamente entre os dois números codificados em complemento de um.
 - 
Exemplo: 1 - 1 = -2 e não 0
 
                 1        : carry (vai um)
                  \       
     0 0 0 0 0 0 0 1      : +1
     1 0 0 0 0 0 0 1 +    : -1
     ---------------
     1 0 0 0 0 0 1 0      : -2 e não 0 
Tabela com 3 bits
| Decimal | Binário em complemento de 1 | 
|---|---|
| 3 | 011 | 
| 2 | 010 | 
| 1 | 001 | 
| 0 | 000 / 100 | 
| -1 | 101 | 
| -2 | 110 | 
| -3 | 111 | 
Complemento de 2
O complemento de dois é uma outra maneira de representar números sinalizados com bits, essa técnica possui alguams vantagens:
- Uma única representação para o valor 0: 
0000 - A operação de soma/ subtração funciona corretamente!
 - O bit mais significativo indica se a palavra é positiva (
0) ou negativa (1). 
Para obter um número positivo ↔ negativo nessa notação é necessário seguir os seguintes passos:
- Escreva o valor em binário (positivo)
 - Inverter todos os bits (not bit a bit) da palavra original
 - 
Somar o valor
1a palavra invertida. - 
Exemplo:
-3=11111101 
     0 0 0 0 0 0 1 1      : 3
    -----------------------
     1 1 1 1 1 1 0 0      : not bit a bit da palavra original
     0 0 0 0     + 1      : Soma um a palavra invertida
    -----------------------
     1 1 1 1 1 1 0 1  <-- -3 em complemento de 2       
- Exemplo: 
-5=111111011 
    0 0 0 0 0 1 0 1      : 5
    -----------------------
    1 1 1 1 1 0 1 0      : not bit a bit da palavra original
    0 0 0 0 0 0 0 1 +    : Soma um a palavra invertida
    -----------------------
    1 1 1 1 1 0 1 1  <-- -5 em complemento de 2
- Exemplo (com 4 bits para simplificar): -9 (não funciona porque não cabe)
 
(exemplo com 4 bits!)
     1 0 0 1      : 9
     0 1 1 0      : not bit a bit da palavra original
         + 1      : Soma um a palavra invertida
     0 1 1 1    <-- 7 !! (não funcionou)
     ^
     | não funcionou =(
O exemplo anterior não funciona pois faltam bits para representar o valor -9, para isso seria necessário 5 bits e não 4 como no exemplo.
Tabela com 3 bits
| Decimal | Binário em complemento de dois | 
|---|---|
| 3 | 011 | 
| 2 | 010 | 
| 1 | 001 | 
| 0 | 000 | 
| -1 | 111 | 
| -2 | 110 | 
| -3 | 101 | 
| -4 | 100 | 
Multiplicação/ Divisão por múltiplo de 2
Assumindo
- Um número positivo
 
Em binário, para multiplicar uma palavra (positiva) por 2 basta rotacionar todos os bits uma casa para esquerda. Para dividir por 2 basta rotacionar todos os bits uma vez para direita (sempre colocando 0 no bit que entra e desaparecendo com o bit que sai).
Exemplos a seguir:
- 2 x 1 (
00000001) = 200000010 
      <-- 1x 
    00000001 => 00000010
- 2 x 4 (
00000100) = 800001000 
      <-- 1x 
    00000100 => 00001000
- 9 (
00001001) / 2 = 400000100 
1x --> 
    00001001 => 00000100
Note
A divisão de 9/2 retorna um número inteiro. Isso se dá devido a técnica só funcionar com números inteiros.
Essa técnica de rotacionar vale para múltiplos de 2, se deseja multiplicar/dividir por M, onde M é um múltiplo de 2 (M=Nx2), é necessário rotacionar o vetor de bits N vezes: 
- exemplo: 4 x 1 (
00000001) =00000100 
      <-- 2x 
    00000001 => 00000100
Ponto fixo
Ponto fixo é uma das técnicas de representação de números fracionados em binário, nessa notação fixasse quantos bits serão utilizados para a parte inteira e quantos serão utilizados para a fração. É aplicado o mesmo conceito dos números decimais, as casas a direita do ponto possuem peso na ordem 2^-n.
Vamos pegar como exemplo o valor 26.5, e assumindo que estamos trabalhando com uma palavra de 8 bits onde o ponto está localizado no bit 3: XXXXX.YYY.
Nesse caso, cada casa binária possui o peso a seguir:
| 2^5 | 2^4 | 2^3 | 2^2 | 2^1 | 2^0 | 2^-1 | 2^-2 | 2^-3 | 
|---|---|---|---|---|---|---|---|---|
| 32 | 16 | 8 | 4 | 2 | 1 | 0.5 | 0.25 | 0.125 | 
Para construirmos o valor 26.5 basta selecionarmos os bits que somados dão esse valor:
011010100 : 0*32 + 1*16 + 1*8 + 0*4 + 1*2 + 0*1 + 1*0.5 + 0*0.025 + 0*0.125 = 26.5
A questão dessa notação é que uma vez escolhido onde o ponto vai estar localizado (projeto de hardware) não da para mudar depois, se o número a ser armazenado é apenas fração, perdemos muitos bits sem uso com a parte inteira, o que faz possuirmos menor resolução.
A solução para isso é a notação de ponto flutuante - IEEE 754 vocês vão ver isso na disciplina de Sistemas Hardware Software do 5s).
Ponto flutuante
Ponto flutuante é uma outra notação na qual é possível representar números racionais digitalmente (binário), nessa técnica a vírgula não é fixa, e a notação pode se adequar para armazenar números muito trandes ou muito pequenos. No entanto, existe um custo computacional mais elevado envolvido nisso.
Processadores modernos possuem um hardware (ULA) dedicada a realizar operações em ponto flutuante, normalmente usando o padrão IEEE 754.