我需要用JavaScript编写一段硬件模拟器。它具有自己的浮点格式,因此我在JS数字和该格式之间进行了大量转换,这很慢。我有使用JavaScript TypedArray float32的想法,因为我可以直接访问形成float32浮点值的字节,该值与所需的格式相距不远,因此这种转换将更快(仅使用Uint8进行一些移位等) Float32视图)。

但是,我不确定该解决方案的便携性。有关TypedArray主题的各种文档都指出,float32类似于“该硬件上的本机C格式”等。但是我可以期望float32的确切二进制格式在运行某些浏览器/ JS的所有平台上都相同吗?我猜想端基可能是一个问题,但是如果至少没有其他区别,我可以解决。据我所知,所使用的格式似乎是IEE754,但是在某些(嗯,至少不是那么奇特的……)平台上,是否可以使用其他格式在JS中实现float32?

我至少可以测试x86和Apple A7 CPU,看来它们是完全相同的,这很好,但也很奇怪,因为我认为这些CPU的字节顺序不同(也许至少不是浮动格式?)。但是,仅检查两个平台/ OSes /浏览器/任何东西都远不是全球性的真理。

最佳答案

Float32Array将在内部表示基于主机系统的字节序的值,通常为小字节序。

是的,格式为IEEE 754(自从FPU出现之前就存在了,格式的变化涉及更大的宽度,即64位,80位等)。 JavaScript中的所有数字(Number)在内部都表示为64位IEEE754。对于类型化数组,当然可以使用32位和64位IEEE 754。

PowerPC和68k CPU使用big-endian(应该是这种方式!:))。所谓的网络顺序也是big-endian,并且许多与平台无关的文件格式都以big-endian字节顺序存储(尤其是音频和图形)。大多数主流计算机都使用x86之类的低端CPU。因此,如果将这些组合在一起,则很可能必须处理不同的字节顺序。

为了处理字节序,您可以使用DataView而不是Float32Array。

例如:

var buffer = new ArrayBuffer(10240);    // some raw byte buffer
var view = new DataView(buffer);        // flexible view supporting endianness


现在,您可以牢记字节顺序来读取和写入缓冲区中的任何位置(DataView还允许从未对齐的位置读取/写入数据,即,如果需要,可以将Float32值写入位置3。您不能使用Float32 / Uint32 / Int16等执行此操作)。

浏览器将在内部转换为正确的顺序-您只需按原样提供值即可:

view.setFloat32(pos, 0.5);              // big-endian
view.setFloat32(pos, 0.5, false)        // big-endian
view.setFloat32(pos, 0.5, true);        // little-endian


同样,在阅读时:

var n = view.getFloat32(pos);           // big-endian
var n = view.getFloat32(pos, false)     // big-endian
var n = view.getFloat32(pos, true);     // little-endian


提示:您可以在内部使用本机Float32Array,以后可以使用字节序对其进行读/写。这往往会更快一些,但是如果最终缓冲区的字节序不同于主机系统,则需要在最后使用DataView进行转换:

var f32 = new Float32Array(buffer);     // or use a size
f32[0] = 0.5;


然后确保您具有big-endian表示形式:

var view = new DataView(f32.buffer);
var msbVal = view.getFloat32(0):        // returns 32-bit repres. in big-endian


希望能给一些意见!如果您想让我详细说明一下,请向我提问。

关于javascript - 关于JavaScript TypedArray float32的二进制格式,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/26025215/

10-13 02:28