Ir ao conteúdo

C Imprecisão com ponto flutuante


Ir à solução Resolvido por Midori,

Posts recomendados

Postado
#include <stdio.h>
#include <stdlib.h>

int main() {
    float f = 1.559f;
    float g = f * 100.0f;
    printf("%f %f", f, g);
    return 0;
}

Alguém saberia dizer o motivo de ser este o resultado?

1.559000 155.899994

E não

1.559000 155.900000

Talvez seja a imprecisão na representação do número, mas não sei dizer o real motivo.

Postado

Float é armazenados em 4 bytes (32 bits), então tem 6~7 dígitos de precisão. Se usar double em vez de float, dá pra aproximar o resultado com um pouco mais de precisão.

  • Obrigado 1
  • Solução
Postado

@Luccas Fernando Nem todo número decimal pode ser representado exatamente em binário (lembre-se que os computadores processam cálculos no sistema binário, só 0 e 1), um exemplo é 0,1. Veja o resultado deste comando,

 

printf("%.15f\n", 0.1f);

 

Com a precisão simples e representação de 15 casas será: 0.100000001490116. Para entender o motivo converta 0.1 para binário,

 

0.1 * 2 = 0.2 | 0

0.2 * 2 = 0.4 | 0

0,4 * 2 = 0,8 | 0

-----------------------

0,8 * 2 = 1,6 | 1

0,6 * 2 = 1,2 | 1

0,2 * 2 = 0,4 | 0

0,4 * 2 = 0,8 | 0

-----------------------

0,8 * 2 = 1,6 | 1

0,6 * 2 = 1,2 | 1

0,2 * 2 = 0,4 | 0

.....

 

0.1 (dec) = 1100110...  (Normalizado fica 1.1001 1001 1001...)

 

Veja que após 1,2 o cálculo se repete infinitamente. Se quiser saber mais procure pelo padrão IEEE 754 para representação de números decimais. Ele tem 32 bits para armazenamento de precisão simples (float) onde: 1 bit é para o sinal, 8 bits para o expoente e 23 bits para a mantissa.

 

A conversão do número 155.9 do seu exemplo para esse padrão fica: Convertendo 155 para binário = 10011011. E 0,9 para binário,

 

0,9 * 2 = 1,8 | 1

0,8 * 2 = 1,6 | 1

0,6 * 2 = 1,2 | 1

0,2 * 2 = 0,4 | 0

0,4 * 2 = 0,8 | 0

---------------------

0,8 * 2 = 1,6 | 1

0,6 * 2 = 1,2 | 1

0,2 * 2 = 0,4 | 0

0,4 * 2 = 0,8 | 0

---------------------

0,8 * 2 = 1,6 | 1

...

 

No primeiro passo temos 155.9 = 10011011.1110011001...

 

O próximo passo é normalizar o número deslocando a vírgula para a esquerda: 1.00110111110011001...

 

Foram 7 casas então os bits do expoente será 134 (10000110) já que 127 + 7 (127 é excesso) do IEEE 754 para precisão simples, logo o binário para 155,9 é: 01000011000110111110011001100110. E como vimos o 0,9 não tem representação exata então o valor mostrado não será exatamente 155.900000, mas 155.899994.

  • Curtir 1
  • Amei 1

Crie uma conta ou entre para comentar

Você precisa ser um usuário para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar agora

Sobre o Clube do Hardware

No ar desde 1996, o Clube do Hardware é uma das maiores, mais antigas e mais respeitadas comunidades sobre tecnologia do Brasil. Leia mais

Direitos autorais

Não permitimos a cópia ou reprodução do conteúdo do nosso site, fórum, newsletters e redes sociais, mesmo citando-se a fonte. Leia mais

×
×
  • Criar novo...

LANÇAMENTO!

eletronica2025-popup.jpg


CLIQUE AQUI E BAIXE AGORA MESMO!