diff --git a/baseconvert.com/ieee-754-floating-point.html b/baseconvert.com/ieee-754-floating-point.html index cc7c24d..bae77ee 100644 --- a/baseconvert.com/ieee-754-floating-point.html +++ b/baseconvert.com/ieee-754-floating-point.html @@ -47,6 +47,7 @@

Base Convert: IEEE 754 Floating Point

+

16 bit – half

32 bit – float

64 bit – double

64 bit – double
+

16 bit – half

+ +
+ +
+ +
+ +
+ +
+ +
+

32 bit – float

diff --git a/baseconvert.com/js/converter-init-ieee-754.js b/baseconvert.com/js/converter-init-ieee-754.js index 83839c8..044a086 100644 --- a/baseconvert.com/js/converter-init-ieee-754.js +++ b/baseconvert.com/js/converter-init-ieee-754.js @@ -10,6 +10,23 @@ var initialBases = [ name: 'decimal', group: 'dec', }, + { + id: 'dec16', + name: 'decimal', + explanation: 'exact', + group: '16', + readonly: true, + }, + { + id: 'bin16', + name: 'binary', + group: '16', + }, + { + id: 'hex16', + name: 'hexadecimal', + group: '16', + }, { id: 'dec32', name: 'decimal', diff --git a/src/ieee-754.js b/src/ieee-754.js index b5b4880..14e00c7 100644 --- a/src/ieee-754.js +++ b/src/ieee-754.js @@ -28,6 +28,13 @@ function extIeee754() { return new DataView(arr.buffer); } + function numberToArr16(number) { + var arr = new Uint8Array(2); + var view = new DataView(arr.buffer); + view.setFloat16(0, +number); + return arr; + } + function numberToArr32(number) { var arr = new Uint8Array(4); var view = new DataView(arr.buffer); @@ -53,7 +60,7 @@ function extIeee754() { function getExactDec(number) { return ( - number === 0 && 1/number < 0 + number === 0 && 1 / number < 0 ? '-0' : new converter.Big( number.toString(16), @@ -64,7 +71,7 @@ function extIeee754() { function valid(base, number) { if (number === undefined) { - return base === 'dec' || /^(dec|bin|hex)(32|64)$/.test(base); + return base === 'dec' || /^(dec|bin|hex)(16|32|64)$/.test(base); } number = normalize(number); @@ -72,10 +79,14 @@ function extIeee754() { if (number) { if (base === 'dec') { return number === 'NaN' || !isNaN(+number); + } else if (base === 'bin16') { + return /^(0b)?[01]{16}$/i.test(number); } else if (base === 'bin32') { return /^(0b)?[01]{32}$/i.test(number); } else if (base === 'bin64') { return /^(0b)?[01]{64}$/i.test(number); + } else if (base === 'hex16') { + return /^(0x)?[0-9a-f]{4}$/i.test(number); } else if (base === 'hex32') { return /^(0x)?[0-9a-f]{8}$/i.test(number); } else if (base === 'hex64') { @@ -96,10 +107,14 @@ function extIeee754() { if (fromBase === 'dec') { return +number; + } else if (fromBase === 'bin16') { + return parseToView(8, 2, number).getFloat16(0); } else if (fromBase === 'bin32') { return parseToView(8, 2, number).getFloat32(0); } else if (fromBase === 'bin64') { return parseToView(8, 2, number).getFloat64(0); + } else if (fromBase === 'hex16') { + return parseToView(2, 16, number).getFloat16(0); } else if (fromBase === 'hex32') { return parseToView(2, 16, number).getFloat32(0); } else if (fromBase === 'hex64') { @@ -113,14 +128,20 @@ function extIeee754() { } else { number = +number; - if (toBase === 'dec32') { + if (toBase === 'dec16') { + return getExactDec(new DataView(numberToArr16(number).buffer).getFloat16(0)); + } else if (toBase === 'dec32') { return getExactDec(new DataView(numberToArr32(number).buffer).getFloat32(0)); } else if (toBase === 'dec64') { return getExactDec(number); + } else if (toBase === 'bin16') { + return arrToBase(2, numberToArr16(number)).replace(/^(.)(.{5})(.+)$/, '$1 $2 $3'); } else if (toBase === 'bin32') { return arrToBase(2, numberToArr32(number)).replace(/^(.)(.{8})(.+)$/, '$1 $2 $3'); } else if (toBase === 'bin64') { return arrToBase(2, numberToArr64(number)).replace(/^(.)(.{11})(.+)$/, '$1 $2 $3'); + } else if (toBase === 'hex16') { + return arrToBase(16, numberToArr16(number)); } else if (toBase === 'hex32') { return arrToBase(16, numberToArr32(number)); } else if (toBase === 'hex64') { diff --git a/test/unit/ieee-754.js b/test/unit/ieee-754.js index e371750..41e631d 100644 --- a/test/unit/ieee-754.js +++ b/test/unit/ieee-754.js @@ -9,99 +9,218 @@ Big: BigNumberIeee754, fn: function (converter) { strictEqual(converter.valid('dec'), true, 'dec'); + strictEqual(converter.valid('dec16'), true, 'dec16'); strictEqual(converter.valid('dec32'), true, 'dec32'); strictEqual(converter.valid('dec64'), true, 'dec64'); + strictEqual(converter.valid('bin16'), true, 'bin16'); strictEqual(converter.valid('bin32'), true, 'bin32'); strictEqual(converter.valid('bin64'), true, 'bin64'); + strictEqual(converter.valid('hex16'), true, 'hex16'); strictEqual(converter.valid('hex32'), true, 'hex32'); strictEqual(converter.valid('hex64'), true, 'hex64'); }, }); testConvertersOpts({ - name: 'Within 32 bits', + name: 'Within 16 bits', extensionNames: ['extIeee754'], Big: BigNumberIeee754, fn: function (converter) { var conversions = [ { dec: '0', + dec16: '0', dec32: '0', dec64: '0', + bin16: '0 00000 0000000000', bin32: '0 00000000 00000000000000000000000', bin64: '0 00000000000 0000000000000000000000000000000000000000000000000000', + hex16: '0000', hex32: '00000000', hex64: '0000000000000000', }, { dec: '-0', + dec16: '-0', dec32: '-0', dec64: '-0', + bin16: '1 00000 0000000000', bin32: '1 00000000 00000000000000000000000', bin64: '1 00000000000 0000000000000000000000000000000000000000000000000000', + hex16: '8000', hex32: '80000000', hex64: '8000000000000000', }, { - dec: '123456', - dec32: '123456', - dec64: '123456', - bin32: '0 10001111 11100010010000000000000', - bin64: '0 10000001111 1110001001000000000000000000000000000000000000000000', - hex32: '47F12000', - hex64: '40FE240000000000', + dec: '12345', + dec16: '12345', + dec32: '12345', + dec64: '12345', + bin16: '0 11100 1000000111', + bin32: '0 10001100 10000001110010000000000', + bin64: '0 10000001100 1000000111001000000000000000000000000000000000000000', + hex16: '7207', + hex32: '4640E400', + hex64: '40C81C8000000000', }, { dec: 'NaN', + dec16: 'NaN', dec32: 'NaN', dec64: 'NaN', + bin16: '0 11111 1000000000', bin32: '0 11111111 10000000000000000000000', bin64: '0 11111111111 1000000000000000000000000000000000000000000000000000', + hex16: '7E00', hex32: '7FC00000', hex64: '7FF8000000000000', }, { dec: 'Infinity', + dec16: 'Infinity', dec32: 'Infinity', dec64: 'Infinity', + bin16: '0 11111 0000000000', bin32: '0 11111111 00000000000000000000000', bin64: '0 11111111111 0000000000000000000000000000000000000000000000000000', + hex16: '7C00', hex32: '7F800000', hex64: '7FF0000000000000', }, { dec: '-Infinity', + dec16: '-Infinity', dec32: '-Infinity', dec64: '-Infinity', + bin16: '1 11111 0000000000', bin32: '1 11111111 00000000000000000000000', bin64: '1 11111111111 0000000000000000000000000000000000000000000000000000', + hex16: 'FF800000', hex32: 'FF800000', hex64: 'FFF0000000000000', }, { - dec: '0.10000000149011612', - dec32: '0.100000001490116119384765625', - dec64: '0.100000001490116119384765625', - bin32: '0 01111011 10011001100110011001101', - bin64: '0 01111111011 1001100110011001100110100000000000000000000000000000', - hex32: '3DCCCCCD', - hex64: '3FB99999A0000000', + dec: '0.0.10003662109375', + dec16: '0.0.10003662109375', + dec32: '0.0.10003662109375', + dec64: '0.0.10003662109375', + bin16: '0 01011 1001100111', + bin32: '0 01111011 10011001110000000000000', + bin64: '0 01111111011 1001100111000000000000000000000000000000000000000000', + hex16: '2E67', + hex32: '3DCCE000', + hex64: '3FB99C0000000000', + }, + { + dec: '19248', + dec16: '19248', + dec32: '19248', + dec64: '19248', + bin16: '0 11101 0010110011', + bin32: '0 10001101 00101100110000000000000', + bin64: '0 10000001101 0010110011000000000000000000000000000000000000000000', + hex16: '74B3', + hex32: '46966000', + hex64: '40D2CC0000000000', + }, + { + dec: '5.960464477539063e-8', + dec16: '0.0.000000059604644775390625', + dec32: '0.0.000000059604644775390625', + dec64: '0.0.000000059604644775390625', + bin16: '0 00000 0000000001', + bin32: '0 01100111 00000000000000000000000', + bin64: '0 01111100111 0000000000000000000000000000000000000000000000000000', + hex16: '0001', + hex32: '33800000', + hex64: '3E70000000000000', + }, + ]; + + for (var i = 0; i < conversions.length; i++) { + var c = conversions[i]; + + c.fromBin16 = c.fromBin32 = c.fromBin64 = + c.fromHex16 = c.fromHex32 = c.fromHex64 = c.dec; + + deepEqual( + { + dec: c.dec, + dec16: converter.convert('dec', 'dec16', c.dec), + dec32: converter.convert('dec', 'dec32', c.dec), + dec64: converter.convert('dec', 'dec64', c.dec), + bin16: converter.convert('dec', 'bin16', c.dec), + bin32: converter.convert('dec', 'bin32', c.dec), + bin64: converter.convert('dec', 'bin64', c.dec), + hex16: converter.convert('dec', 'hex16', c.dec), + hex32: converter.convert('dec', 'hex32', c.dec), + hex64: converter.convert('dec', 'hex64', c.dec), + + fromBin16: converter.convert('bin16', 'dec', c.bin16), + fromBin32: converter.convert('bin32', 'dec', c.bin32), + fromBin64: converter.convert('bin64', 'dec', c.bin64), + fromHex16: converter.convert('hex16', 'dec', c.hex16), + fromHex32: converter.convert('hex32', 'dec', c.hex32), + fromHex64: converter.convert('hex64', 'dec', c.hex64), + }, + c, + 'dec <-> all - ' + c.dec + ); + } + }, + }); + + testConvertersOpts({ + name: 'Between 16 bits and 32 bits', + extensionNames: ['extIeee754'], + Big: BigNumberIeee754, + fn: function (converter) { + var conversions = [ + { + dec: '123456', + dec16: 'Infinity', + dec32: '123456', + dec64: '123456', + bin16: '0 11111 0000000000', + bin32: '0 10001111 11100010010000000000000', + bin64: '0 10000001111 1110001001000000000000000000000000000000000000000000', + hex16: '7C00', + hex32: '47F12000', + hex64: '40FE240000000000', + }, + { + dec: '1.9999998807907104', + dec16: '2', + dec32: '1.99999988079071044921875', + dec64: '1.99999988079071044921875', + bin16: '0 10000 0000000000', + bin32: '0 01111111 11111111111111111111111', + bin64: '0 01111111111 1111111111111111111111100000000000000000000000000000', + hex16: '4000', + hex32: '3FFFFFFF', + hex64: '3FFFFFFFE0000000', }, { dec: '9.999999680285692e+37', + dec16: 'Infinity', dec32: '99999996802856924650656260769173209088', dec64: '99999996802856924650656260769173209088', + bin16: '0 11111 0000000000', bin32: '0 11111101 00101100111011010011001', bin64: '0 10001111101 0010110011101101001100100000000000000000000000000000', + hex16: '7C00', hex32: '7E967699', hex64: '47D2CED320000000', }, { dec: '1.401298464324817e-45', + dec16: '0', dec32: '0.00000000000000000000000000000000000000000000140129846432481707092372958328991613128026194187651577175706828388979108268586060148663818836212158203125', dec64: '0.00000000000000000000000000000000000000000000140129846432481707092372958328991613128026194187651577175706828388979108268586060148663818836212158203125', + bin16: '0 00000 0000000000', bin32: '0 00000000 00000000000000000000001', bin64: '0 01101101010 0000000000000000000000000000000000000000000000000000', + hex16: '0000', hex32: '00000001', hex64: '36A0000000000000', }, @@ -110,21 +229,26 @@ for (var i = 0; i < conversions.length; i++) { var c = conversions[i]; - c.fromBin32 = c.fromBin64 = - c.fromHex32 = c.fromHex64 = c.dec; + c.fromBin16 = c.fromBin32 = c.fromBin64 = + c.fromHex16 = c.fromHex32 = c.fromHex64 = c.dec; deepEqual( { dec: c.dec, + dec16: converter.convert('dec', 'dec16', c.dec), dec32: converter.convert('dec', 'dec32', c.dec), dec64: converter.convert('dec', 'dec64', c.dec), + bin16: converter.convert('dec', 'bin16', c.dec), bin32: converter.convert('dec', 'bin32', c.dec), bin64: converter.convert('dec', 'bin64', c.dec), + hex16: converter.convert('dec', 'hex16', c.dec), hex32: converter.convert('dec', 'hex32', c.dec), hex64: converter.convert('dec', 'hex64', c.dec), + fromBin16: converter.convert('bin16', 'dec', c.bin16), fromBin32: converter.convert('bin32', 'dec', c.bin32), fromBin64: converter.convert('bin64', 'dec', c.bin64), + fromHex16: converter.convert('hex16', 'dec', c.hex16), fromHex32: converter.convert('hex32', 'dec', c.hex32), fromHex64: converter.convert('hex64', 'dec', c.hex64), }, @@ -143,65 +267,86 @@ var conversions = [ { dec: '0.1', + dec16: '0.0999755859375', dec32: '0.100000001490116119384765625', dec64: '0.1000000000000000055511151231257827021181583404541015625', + bin16: '0 01011 1001100110', bin32: '0 01111011 10011001100110011001101', bin64: '0 01111111011 1001100110011001100110011001100110011001100110011010', + hex16: '2E66', hex32: '3DCCCCCD', hex64: '3FB999999999999A', }, { // First integer not representable in 32 bits. dec: '16777217', + dec16: 'Infinity', dec32: '16777216', dec64: '16777217', + bin16: '0 11111 0000000000', bin32: '0 10010111 00000000000000000000000', bin64: '0 10000010111 0000000000000000000000010000000000000000000000000000', + hex16: '7C00', hex32: '4B800000', hex64: '4170000010000000', }, { dec: '3.141592653589793', + dec16: '3.140625', dec32: '3.1415927410125732421875', dec64: '3.141592653589793115997963468544185161590576171875', + bin16: '0 10000 1001001000', bin32: '0 10000000 10010010000111111011011', bin64: '0 10000000000 1001001000011111101101010100010001000010110100011000', + hex16: '4248', hex32: '40490FDB', hex64: '400921FB54442D18', }, { dec: '1e+39', + dec16: 'Infinity', dec32: 'Infinity', dec64: '999999999999999939709166371603178586112', + bin16: '0 11111 0000000000', bin32: '0 11111111 00000000000000000000000', bin64: '0 10010000000 0111100000101000011111110100100111000100101000011101', + hex16: '7C00', hex32: '7F800000', hex64: '48078287F49C4A1D', }, { dec: '1e-46', + dec16: '0', dec32: '0', dec64: '0.0000000000000000000000000000000000000000000001000000000000000022999043453913216828505961640883084488789349378835264740187722591657382693176711544546107892003424942768685657057403659564442932605743408203125', + bin16: '0 00000 0000000000', bin32: '0 00000000 00000000000000000000000', bin64: '0 01101100110 0010010001001100111000100100001011000101010101100001', + hex16: '0000', hex32: '00000000', hex64: '366244CE242C5561', }, { dec: '1e+308', + dec16: 'Infinity', dec32: 'Infinity', dec64: '100000000000000001097906362944045541740492309677311846336810682903157585404911491537163328978494688899061249669721172515611590283743140088328307009198146046031271664502933027185697489699588559043338384466165001178426897626212945177628091195786707458122783970171784415105291802893207873272974885715430223118336', + bin16: '0 11111 0000000000', bin32: '0 11111111 00000000000000000000000', bin64: '0 11111111110 0001110011001111001110000101111010111100100010100000', + hex16: '7C00', hex32: '7F800000', hex64: '7FE1CCF385EBC8A0', }, { dec: '1e-323', + dec16: '0', dec32: '0', dec64: '0.00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000988131291682493088353137585736442744730119605228649528851171365001351014540417503730599672723271984759593129390891435461853313420711879592797549592021563756252601426380622809055691634335697964207377437272113997461446100012774818307129968774624946794546339230280063430770796148252477131182342053317113373536374079120621249863890543182984910658610913088802254960259419999083863978818160833126649049514295738029453560318710477223100269607052986944038758053621421498340666445368950667144166486387218476578691673612021202301233961950615668455463665849580996504946155275185449574931216955640746893939906729403594535543517025132110239826300978220290207572547633450191167477946719798732961988232841140527418055848553508913045817507736501283943653106689453125', + bin16: '0 00000 0000000000', bin32: '0 00000000 00000000000000000000000', bin64: '0 00000000000 0000000000000000000000000000000000000000000000000010', + hex16: '0000', hex32: '00000000', hex64: '0000000000000002', }, @@ -210,21 +355,26 @@ for (var i = 0; i < conversions.length; i++) { var c = conversions[i]; - c.fromBin32 = c.fromHex32 = +c.dec32 + ''; - c.fromBin64 = c.fromHex64 = c.dec; + c.fromBin16 = c.fromBin32 = c.fromBin64 = + c.fromHex16 = c.fromHex32 = c.fromHex64 = c.dec; deepEqual( { dec: c.dec, + dec16: converter.convert('dec', 'dec16', c.dec), dec32: converter.convert('dec', 'dec32', c.dec), dec64: converter.convert('dec', 'dec64', c.dec), + bin16: converter.convert('dec', 'bin16', c.dec), bin32: converter.convert('dec', 'bin32', c.dec), bin64: converter.convert('dec', 'bin64', c.dec), + hex16: converter.convert('dec', 'hex16', c.dec), hex32: converter.convert('dec', 'hex32', c.dec), hex64: converter.convert('dec', 'hex64', c.dec), + fromBin16: converter.convert('bin16', 'dec', c.bin16), fromBin32: converter.convert('bin32', 'dec', c.bin32), fromBin64: converter.convert('bin64', 'dec', c.bin64), + fromHex16: converter.convert('hex16', 'dec', c.hex16), fromHex32: converter.convert('hex32', 'dec', c.hex32), fromHex64: converter.convert('hex64', 'dec', c.hex64), },