我正在优化数值/统计库的排序函数,基于这样的假设:在过滤掉任何NaN并进行一些微调之后,可以将浮点数作为32位整数进行比较而不改变结果,并且可以将双精度数据进行比较64位整数.
这似乎加速了这些数组的排序大约40%,并且只要浮点数的位级表示是IEEE 754,我的假设就成立.是否存在人们实际使用的真实CPU(不包括在嵌入式设备中,这个库没有针对哪个)使用其他可能会破坏这种假设的表示?
float
在使用IEEE754的系统中)double
在使用IEEE754的系统中)在任何地方都可以使用Java库来执行IEEE 754半精度数字的计算或将它们转换为双精度数据吗?
这些方法中的任何一种都是合适的:
编辑:转换需要100%准确 - 输入文件中有很多NaN,无穷大和次正规.
相关问题,但对于JavaScript:在Javascript中解压缩半精度浮点数
我的方法如下
def myMethod(myDouble: Double): Double = myDouble match {
case Double.NaN => ...
case _ => ...
}
Run Code Online (Sandbox Code Playgroud)
IntelliJ调试器显示NaN但在我的模式匹配中没有获取.有可能我省略的情况
我想另一种表达这个问题的方法是你可以使用float
只有0到1之间的小数位数吗?
我试着通过查看MSDN来解决这个问题.其中精度为7位数.我认为这意味着它只能追踪变化0.0000001
.
但是,如果我这样做:
float test = 0.00000000000000000000000000000000000000000001f;
Console.WriteLine(test);
Run Code Online (Sandbox Code Playgroud)
它写出来了 9.949219E-44
如果我再添加零,它将输出0
.
我很确定我在这里遗漏了一些东西,因为这种准确度似乎非常错误.主要是浮动的大小为32位,在该精度级别仅为0-1,包含1e + 44个可能的数字......
我有一个double[]
LINQ操作正在执行:
MD = MD.Select(n => n * 100 / MD.Sum()).ToArray();
Run Code Online (Sandbox Code Playgroud)
在某些情况下,所有元素MD
都是0然后Sum
也是零.然后0 * 100 = 0 / 0
,它没有给出除零例外或任何例外.为什么会这样?
C99添加了一个宏__STDC_IEC_559__
,可用于测试编译器和标准库是否符合ISO/IEC/IEEE 60559(或IEEE 754)标准.
根据这个问题的答案,
如何检查-ieee-754-单精度-32位浮点表示,大多数C编译器不设置预处理器宏__STDC_IEC_559__
.
根据海湾合作委员会的文件,它没有定义__STDC_IEC_559__
.
我用GCC 4.9.2和Clang 3.6.0测试了这两个,使用glibc
2.21使用以下代码.
//test.c
//#include <features.h>
int main(void) {
#if defined ( __STDC_IEC_559__ )
//#if defined ( __GCC_IEC_559__ )
return 1;
#else
return 0;
#endif
}
Run Code Online (Sandbox Code Playgroud)
然后
echo $?
Run Code Online (Sandbox Code Playgroud)
这表明此代码__STDC_IEC_559__
是使用GCC定义的,而不是使用Clang定义的.然后我做了gcc -E
,它显示该文件stdc-predef.h
包含在内.这个文件定义__STDC_IEC_559__
.
/* glibc's intent is to support the IEC 559 math functionality, real
and complex. If the GCC (4.9 and later) predefined macros
specifying compiler intent …
Run Code Online (Sandbox Code Playgroud) 这个主题在StackOverflow上出现了很多次,但我相信这是一个新的看法.是的,我已经阅读了布鲁斯道森的文章和每个计算机科学家应该知道的关于浮点算术的内容和这个很好的答案.
据我了解,在一个典型的系统上,比较浮点数是否相等有四个基本问题:
a-b
是"小"取决于规模a
和b
a-b
为"小"取决于类型a
和b
(例如浮动,双,长双)这个答案 - 又名."Google方法" - 似乎很受欢迎.它确实处理了所有棘手的案件.并且它确实非常精确地缩放比较,检查两个值是否在彼此的固定数量的ULP内.因此,例如,非常大的数字将"几乎相等"与无穷大相比较.
然而:
我想要类似的东西,但使用标准的C++并处理长双打.如果可能的话,我指的是C++ 03,如果需要,我指的是C++ 11.
这是我的尝试.
#include <cmath>
#include <limits>
#include <algorithm>
namespace {
// Local version of frexp() that handles infinities specially.
template<typename T>
T my_frexp(const T num, int *exp)
{
typedef std::numeric_limits<T> limits;
// Treat +-infinity as +-(2^max_exponent).
if (std::abs(num) > limits::max())
{
*exp …
Run Code Online (Sandbox Code Playgroud) 作为单元测试的一部分,我需要测试一些边界条件.一种方法接受一个System.Double
参数.
有没有办法获得下一个最小的双值?(即将尾数减1个单位值)?
我考虑使用,Double.Epsilon
但这是不可靠的,因为它只是从零开始的最小增量,因此不适用于较大的值(即9999999999 - Double.Epsilon == 9999999999
).
那么所需的算法或代码是什么:
NextSmallest(Double d) < d
Run Code Online (Sandbox Code Playgroud)
......总是如此.
浮点是在C中定义的实现.因此没有任何保证.
我们的代码需要是可移植的,我们正在讨论在我们的协议中使用IEEE754浮点数是否可以接受.出于性能原因,如果我们不必在发送或接收数据时在固定点格式之间来回转换,那将是很好的.
虽然我知道平台和架构之间可能存在关于long
或的大小的差异wchar_t
.但我似乎无法找到任何具体的float
和double
.
到目前为止我发现字节顺序可能在大端平台上被反转.虽然有不带浮动包含代码,其中点支撑平台float
和double
甚至无法链接.否则平台似乎坚持IEEE754单精度和双精度.
那么可以假设浮点数在IEEE754可用时安全吗?
编辑:回应评论:
你对"安全"的定义是什么?
安全我的意思是,一个系统上的位模式在另一个系统上意味着相同(在字节旋转之后处理字节序).