DoubleBits.js 1.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. export default function DoubleBits() { }
  2. DoubleBits.exponent = function(d) {
  3. return CVTFWD(64, d) - 1023
  4. }
  5. DoubleBits.powerOf2 = function(exp) {
  6. return Math.pow(2, exp)
  7. }
  8. /**
  9. * Calculates the exponent of the bit-pattern for a number. Uses code from:
  10. * http://www.merlyn.demon.co.uk/js-exact.htm
  11. *
  12. * @param {Number}
  13. * NumW 32 or 64 to denote the number of bits.
  14. * @param {Number}
  15. * Qty the number to calculate the bit pattern for.
  16. * @return {Number} The integer value of the exponent.
  17. * @private
  18. */
  19. function CVTFWD(NumW, Qty) {
  20. let Sign
  21. let Expo
  22. let Mant
  23. let Bin
  24. const Inf = {
  25. 32: {
  26. d: 0x7F,
  27. c: 0x80,
  28. b: 0,
  29. a: 0
  30. },
  31. 64: {
  32. d: 0x7FF0,
  33. c: 0,
  34. b: 0,
  35. a: 0
  36. }
  37. }
  38. const ExW = {
  39. 32: 8,
  40. 64: 11
  41. }[NumW]
  42. if (!Bin) {
  43. Sign = Qty < 0 || 1 / Qty < 0 // OK for +-0
  44. if (!isFinite(Qty)) {
  45. Bin = Inf[NumW]
  46. if (Sign) Bin.d += 1 << (NumW / 4 - 1)
  47. Expo = Math.pow(2, ExW) - 1
  48. Mant = 0
  49. }
  50. }
  51. if (!Bin) {
  52. Expo = {
  53. 32: 127,
  54. 64: 1023
  55. }[NumW]
  56. Mant = Math.abs(Qty)
  57. while (Mant >= 2) {
  58. Expo++
  59. Mant /= 2
  60. }
  61. while (Mant < 1 && Expo > 0) {
  62. Expo--
  63. Mant *= 2
  64. }
  65. if (Expo <= 0) Mant /= 2
  66. if (NumW === 32 && Expo > 254) {
  67. Bin = {
  68. d: Sign ? 0xFF : 0x7F,
  69. c: 0x80,
  70. b: 0,
  71. a: 0
  72. }
  73. Expo = Math.pow(2, ExW) - 1
  74. Mant = 0
  75. }
  76. }
  77. return Expo
  78. }