Rust: Agregar soporte para literales flotantes hexadecimales

Creado en 5 ene. 2012  ·  17Comentarios  ·  Fuente: rust-lang/rust

Necesitamos poder analizar la salida de printf's% a para el soporte adecuado de constantes matemáticas sin pérdida de precisión
(es decir, sintaxis 0x1.fffffffffffffp + 1023_f64)

A-frontend E-easy

Comentario más útil

Los flotadores hexadecimales son bastante populares entre las bibliotecas matemáticas de C. Y me encantaría usarlos también en Rust.

Veo que el flotador hexadecimal se implementó en rust como una extensión, luego se movió a una caja separada y ahora está en rust-deprecated y no se compila con rust nocturno.

¿Cuál es el futuro de esta función?

Todos 17 comentarios

Jugué con este problema y llegué a la conclusión de que, lamentablemente, revive el número 1306. El lexer actual prohíbe cualquier carácter alfabético después de . debido a ello. Podemos elegir permitirlos de forma selectiva cuando se encuentra el patrón 0x<digits>. , pero parece demasiado inconsistente y puede requerir una anticipación infinita si queremos eludir una inconsistencia.

Sugiero requerir un dígito o 0x o 0b después del punto. Esto evita la colisión y (curiosamente) le permite cambiar el literal medio de radix si lo desea. Y es solo un poco más feo de lo que C99 te hace escribir.

@graydon O podemos requerir solo ceros después del punto. (por ejemplo, 0x1fffffffffffff.0p+972_f64 lugar de 0x1.fffffffffffffp+1023_f64 )

No creo que esto sea incompatible al revés, renominando.

aceptado para el hito de la función completa

visitado para triaje que data de 2013-07-15. ¿Nos hemos decidido realmente por una sintaxis aquí? Esto parece ser una tarea fácil y agradable para un nuevo colaborador _si_ podemos entregarle una especificación clara de la sintaxis; pero si la sintaxis todavía está en la fase de diseño, entonces esa afirmación es menos cierta.

Creo que aún no hemos clavado la sintaxis, pero debo señalar que sería necesario evitar chocar con sufijos (algunos de los cuales comienzan con f, un dígito hexadecimal), así que creo que si hacemos esto, solo debería funcionar para especificando la mantisa, y solo cuando se combina con un exponente completo (en decimal).

Esto aún no se ha implementado.

No 1.0

Los flotadores hexadecimales son bastante populares entre las bibliotecas matemáticas de C. Y me encantaría usarlos también en Rust.

Veo que el flotador hexadecimal se implementó en rust como una extensión, luego se movió a una caja separada y ahora está en rust-deprecated y no se compila con rust nocturno.

¿Cuál es el futuro de esta función?

También interesado en esto. Estoy buscando implementar un sistema de física reproducible para un juego, que requiere resultados consistentes en todas las computadoras. Los literales flotantes hexadecimales me permitirían escribir valores de punto flotante exactos en bits en pruebas y constantes.

Como mínimo, se agradecería una declaración de por qué esta característica está en desuso, ya que este hilo es el primer resultado que obtengo para "rust hex float literal".

La situación es un poco repugnante en este momento. Las macros de procedimiento están pasando por una renovación en este momento (# 38356), por lo que al menos sería una pérdida de tiempo mantener hexfloat actualizado mientras esto sucede. Pero no sé cuál será la historia después de eso.

Si mi entendimiento es correcto, los flotantes hexadecimales en C / C ++ están ahí porque no se garantiza que los flotantes decimales redondeen correctamente [1]. En Rust, sin embargo, después de # 27307 --- ¡sospecho que esto no es necesariamente intencional! --- casi todos los decimales flotantes (# 31407 describe casos de borde que son prácticamente irrelevantes) deben redondearse al más cercano, por lo que puede simplemente dar rustc un número apropiado (digamos, 30) de dígitos fraccionarios y obtendrá el número redondeado correctamente. Esta sería una respuesta "práctica" por ahora.

Una cosa para la que todavía creo que los flotantes hexadecimales son relevantes es una conversión de C / C ++. No querría convertir todos los flotantes hexadecimales a decimales usted mismo :) Recientemente escribí una macro de procedimiento experimental que hace exactamente esto, convirtiendo flotantes hexadecimales en flotantes decimales (que rustc puede entender), pero había sido reacio a liberar uno porque el el status quo no estaba realmente garantizado hasta ahora --- es pura suerte en mi opinión. Si hay una forma de construir un flotante con un patrón de bits exacto solo a partir de constexprs, lo adaptaré.

[1] Por ejemplo, ISO C99 solo requiere que los decimales flotantes se conviertan a un número representable dentro de ± 1,5 ulps ("el resultado es el valor representable más cercano o el valor representable más grande o más pequeño inmediatamente adyacente al valor representable más cercano" ).

@lifthrasiir , tarde o temprano me gustaría arreglar https://github.com/jameysharp/corrode/issues/73 traduciendo correctamente los flotadores hexadecimales de C a Rust, así que me gustaría entender mejor tu comentario. Todavía no he leído lo suficiente sobre cuestiones de punto flotante para comprender lo que está involucrado aquí.

¿Está diciendo que, modulo errores del compilador de Rust, cada literal hexadecimal flotante se puede convertir en un literal flotante decimal que el compilador de Rust convertirá al mismo patrón de bits? Si es así, estaría feliz de que Corrode hiciera esa conversión. ¿Puede recomendarme una referencia que debería leer para que un algoritmo haga esa conversión correctamente? (Un puntero a su macro de procedimiento sería genial, pero idealmente me gustaría tener un documento o libro para citar también).

Dicho esto, deduzco que la versión decimal exacta de un flotante hexadecimal puede tener muchos más dígitos (¿verdad?), Por lo que quizás la versión flotante hexadecimal sea más fácil de leer y comprender, al menos para las personas que se preocupan lo suficiente por la precisión numérica como para usarlos. . Si los flotadores hexadecimales son la forma preferida por los humanos para estos números, diría que Rust debería admitirlos. Entonces, en mi opinión, más comentarios de las personas que han usado flotadores hexagonales ayudarían aquí.

¿Está diciendo que, modulo errores del compilador de Rust, cada literal hexadecimal flotante se puede convertir en un literal flotante decimal que el compilador de Rust convertirá al mismo patrón de bits?

Mi creencia es que sí.

¿Puede recomendarme una referencia que debería leer para que un algoritmo haga esa conversión correctamente?

No tiene que implementar eso, porque el compilador actual de Rust y la biblioteca estándar implementan todos los algoritmos necesarios (que es más difícil :-). Si realmente necesita referencias, consulte lo siguiente:

  • La conversión de binario a decimal ("flt2dec", # 24612) es un híbrido de [Dragon4] y [Grisu3].

    • [Dragon4]: Burger, RG y Dybvig, RK 1996. Impresión de números de punto flotante de forma rápida y precisa. SIGPLAN No. 31, 5 (mayo de 1996), 108-116.
    • [Grisu3]: Florian Loitsch. 2010. Impresión de números de punto flotante de forma rápida y precisa con números enteros. SIGPLAN No. 45, 6 (junio de 2010), 233-243.
  • La conversión de decimal a binario ("dec2flt", # 27307) es un par de algoritmos descritos por [Clinger]. (No los he implementado yo mismo, por lo que mis conocimientos sobre ellos son limitados).

    • [Clinger]: William D. Clinger. 1990. Cómo leer números de coma flotante con precisión. SIGPLAN No. 25, 6 (junio de 1990), 92-101.

Para que conste, mi implementación es lifthrasiir / hexf (publicado en este momento, todavía no en crates.io). Siéntete libre de recoger.

Dicho esto, deduzco que la versión decimal exacta de un flotador hexadecimal puede tener muchos más dígitos (¿verdad?), [...] Si los flotadores hexadecimales son la forma preferida por los humanos para estos números, diría que Rust debería admitirlos. . [...]

No exactamente, por ejemplo, 0x1.999999999999bp-4 = 0.10000000000000002 . No tengo opinión sobre si Rust debería soportar flotadores hexagonales o no.

Ahora he publicado formalmente hexf en crates.io . @jameysharp , creo que probablemente puedas usar hexf-parse para tu trabajo. (La sintaxis sin guiones bajos debería ser casi idéntica a C99 hexadecimal-floating-constant non-terminal sans opcional floating-suffix .)

Editar: Aargh me perdí un caso. 0x1p1 debería ser válido pero hexf no lo reconoce; aunque probablemente sea fácil de explicar.

Caso de uso similar para mí también; Me gustaría poder generar código rust a partir de un compilador, sin pérdida de precisión para los literales flotantes.

¿Fue útil esta página
0 / 5 - 0 calificaciones