Pergunta

O que é o maior "no-flutuante" inteiro que pode ser armazenado em um tipo de dupla IEEE 754 sem perder precisão?

Foi útil?

Solução

A maior maior inteiro / que podem ser armazenadas em um duplo sem perder precisão é o mesmo que o maior valor possível de um duplo. Ou seja, DBL_MAX ou cerca de 1,8 × 10 308 (se o casal é um IEEE 754 de 64 bits duplo). É um inteiro. É representado exatamente. O que mais você quer?

Vá em frente, me perguntam o que o maior inteiro é, tal que e todos os inteiros menores pode ser armazenado em IEEE duplos de 64 bits sem perder precisão. Um IEEE 64-bit dupla tem 52 bits de mantissa, então eu acho que é 2 53 :

  • 2 53 + 1 não pode ser armazenada, porque a 1 no início eo 1 no final tem muitos zeros no meio.
  • Qualquer coisa menos do que 2 53 pode ser armazenada, com 52 bits armazenados explicitamente no mantissa, e então o expoente em vigor dando-lhe outro.
  • 2 53 , obviamente, pode ser armazenado, já que é uma pequena potência de 2.

Ou uma outra maneira de olhar para ele: uma vez o viés foi retirado o expoente, e ignorando o bit de sinal como irrelevantes para a questão, o valor armazenado por um duplo é uma potência de 2, além de um número inteiro de 52-bit multiplicado por 2 expoente - 52 . Assim, com expoente 52 você pode armazenar todos os valores de 2 52 até 2 53 - 1. Depois, com expoente 53, o próximo número que você pode armazenar depois de 2 53 é 2 53 + 1 × 2 53-52 . Então perda de precisão ocorre primeiro com 2 53 + 1.

Outras dicas

9007199254740992 (que é 9,007,199,254,740,992) sem garantias:)

Programa

#include <math.h>
#include <stdio.h>

int main(void) {
  double dbl = 0; /* I started with 9007199254000000, a little less than 2^53 */
  while (dbl + 1 != dbl) dbl++;
  printf("%.0f\n", dbl - 1);
  printf("%.0f\n", dbl);
  printf("%.0f\n", dbl + 1);
  return 0;
}

Resultado

9007199254740991
9007199254740992
9007199254740992

Wikipedia tem a dizer no mesmo contexto com um link para IEEE 754 :

Em um sistema de computador típico, um 'precisão dupla' (64-bit) binário número de ponto flutuante tem um coeficiente de 53 bits (um dos quais está implícito), um expoente de 11 bits e um bit de sinal.

2 ^ 53 é pouco mais de 9 * 10 ^ 15.

A maior inteiro que pode ser representado em 754 IEEE dupla (64 bits) é o mesmo que o valor maior que o tipo pode representar, desde que o valor é em si um número inteiro.

Este é representado como 0x7FEFFFFFFFFFFFFF, que é composta de:

  • O signo bit 0 (positivo) em vez de 1 (negativo)
  • A 0x7FE máximo expoente (2,046 que representa 1.023 depois de a distorção ser subtraída) em vez de 0x7FF (2,047 o que indica uma NaN ou infinito).
  • A 0xFFFFFFFFFFFFF mantissa máximo que é de 52 bits de tudo um.

No sistema binário, o valor é o implícito 1 seguido por mais 52 os da mantissa, em seguida, 971 zeros (1023 - 52 = 971). Do expoente

O valor decimal exata é:

179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858368

Este é de aproximadamente 1,8 x 10 308 .

Você precisa olhar para o tamanho da mantissa. IEEE 754 de 64 bits número de ponto flutuante (que tem 52 bits, além de um implícita) pode representar exactamente números inteiros com um valor absoluto de menos do que ou igual a 2 ^ 53.

DECIMAL_DIG de <float.h> deve dar pelo menos uma aproximação razoável do que isso. Desde que lida com dígitos decimais, e é realmente armazenados em binário, você provavelmente pode armazenar algo um pouco maior sem perder precisão, mas exatamente quanto é difícil dizer. Eu suponho que você deve ser capaz de descobrir isso a partir FLT_RADIX e DBL_MANT_DIG, mas eu não estou certo que eu confio completamente o resultado.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top