tomee
2021-04-07 21:48:15

equal

It's a question that's likely to be asked in an interview , After online access to a variety of information 、 Articles, etc , There are descriptions of this problem . But the details and some key points need to be carefully studied and pondered to understand . In the process of figuring out this problem, we have experienced a lot of ideological struggles , So it's still necessary to record and share your insights .

First , Be clear about all the calculations in the program , Going to the bottom of the computer is binary Computing , and , Binary computation has no concept of subtraction , The subtraction will be calculated by adding a negative number .

One more thing to note ,0.1+0.2 It's not equal to 0.3 It's not just about JavaScript in , Follow in other areas IEEE 754 This problem also exists in standard programming languages .JavaScript There is only one type for all numbers, including integers and decimals — Number. Its implementation follows IEEE 754 standard , Use 64 Bit fixed length , That's standard double Double precision floating point （ There's more to it float 32 Bit single precision ）.

The whole calculation process goes through the following steps ：

- Decimal to binary .
- Binary to scientific notation .
- Memory is used to analyze the data represented by scientific notation 、 Storage .
- Operations on orders .
- Binary addition .
- Rounding operation .
- Binary to decimal .

Back to the question itself , Let's start with how to put 0.1 Convert it to the underlying storage of the computer ,0.2 The idea of the transformation is clear . How to convert decimal to binary , Reference resources Novice tutorial that will do , No more details here .0.1 The conversion to binary is like this ：

Go back and you'll find , This process is an infinite loop state . Never mind that , Write it down first ：

0.00011(0011)…

Next, should we deal with infinite loops ？ Not at all , We know , In everyday decimal operations , We want to represent as much data as possible , Will use scientific notation . The same goes for the bottom layer of the computer , As we mentioned earlier ,JavaScript In order to double precision storage Number type , Therefore, if the data is converted to binary and stored directly , So the maximum number it can store is 2^{63}（ The first bit is the sign bit ）, In today's data age , This computable range is quite limited . therefore , Binary data should also be converted into scientific notation , Then the scientific notation is stored in parts ：

1.1(0011)… * 2

^{-4}（ Move the decimal point to the right 4 position , The base of binary is 2）

OK, The next question is , The computer 64 How do bits store scientific notation ？

This icon shows 64 Bit binary different parts of the stored data label . First , The highest bit is the sign bit , So it can't participate in the task of storing data , The subsequent 11 position （ Index part ） Binary number used to store the index in scientific notation , remainder 52 position （ Mantissa part ） It is used to store the decimal point of mantissa in scientific notation 52 position . The sign bits and mantissa of these three parts are very clear , Sign bit 0 It means a positive number ,1 A negative number ; The mantissa part of science is just the mantissa part 52 position ; The determination of the index part is a little more complicated .

Memory gives 11 Bit binary gives exponent , therefore ,11 If bit binary is converted to decimal , The range of data that can be stored is ：[0, 2^{11}], namely `[0, 2048]`

. But there's a problem , The index can also be negative ！ How do negative numbers mean ？ Don't 11 The bit has to give up another bit to represent the sign bit ？ Not at all , In this part of the processing ,IEEE754 The standard index is 0 The cardinal number of is 1023（ With 1023 As the dividing line between positive and negative numbers ）, It's equivalent to being able to store `[-1023, 1024]`

The number of this range . therefore , With 0.1 Take the index converted to scientific notation as an example , Index -4 Will be converted into `1023 - 4 = 1019`

, And then convert it to binary ：

1019 It's converted to binary ：1111111011. therefore ,0.1 Before the final binary 12 Position as ：

001111111011

Next , The mantissa is reserved for 52 position , What about infinite loops ？ It's time to Rounding operation , follow 0 House 1 The principle of entry （ It is similar to the meaning of rounding in decimal system ）,** This is also the key point of this issue , Rounding makes the data lose some precision .**

You may wonder , A simple calculation can lead to the deviation of the calculation results , So is the result of a slightly more complex operation reliable ？ Of course it's reliable . firstly , It's rare to see an infinite loop in such a transformation , Even if there is , The double precision storage provided by the computer can also ensure that the data operation is within the allowable error range ; second , The bottom layer of the computer has a processing mechanism for precision error calculation , Calculation will not be allowed to go further and further on the road of deviation .

0.1 The final binary form is like this ：

0 01111111011 1001100110011001100110011001100110011001100110011010

0.2 The binary storage of is ：

0 01111111100 1001100110011001100110011001100110011001100110011010

The next step is to do the addition , Binary addition is not difficult , It's like the decimal system . But it's not easy , Before we will 0.1 and 0.2 When it comes to scientific notation , We found that 0.1 My index is -4,0.2 My index is -3. If you want to express the results of their operations in a scientific way , We have to unify the exponents and then extract the common factor for calculation . Here's a question Operations on orders , To minimize the loss of accuracy , We need to follow the small order to the large order （ That is, to convert a smaller index into a larger one ） Principles . In this case , We need to unify the index into -3. therefore ,0.1 After the operation of the order of the binary , That's true ：

0 01111111100 (0.)1100110011001100110011001100110011001100110011001101.

The mantissa needs to be shifted one bit to the right , Move the excess right to round . The integer part omitted by default 1 It's moved to the decimal part , So the integral part becomes 0.

Next, when you do the addition , To complete the integer part omitted before the mantissa , Because when there is carry , The integral part can change , This is also to facilitate the subsequent adjustment of the calculation results .

The result of adding mantissa is ：

10.0110011001100110011001100110011001100110011001100111

There are two problems with this result ：

- It doesn't conform to the rules of scientific notation .
- The mantissa part exceeds the number of digits .

So adjust the results , First, change the result to “1.” At the beginning , The decimal point is shifted one place to the left , become ：

1.00110011001100110011001100110011001100110011001100111

meanwhile , Add the index to 1： become ：

01111111101

Last , Still based on 0 House 1 The principle of entry , Put the mantissa part beyond 52 The part outside the bit is rounded , The result is ：

1.0011001100110011001100110011001100110011001100110100

therefore , The complete result is ：

0 11111111101 (1.)0011001100110011001100110011001100110011001100110100

Converting to decimal is ：

0.30000000000000004

thus , All the steps and detailed analysis of this problem have come to an end .

- JavaScript Decimals are at the bottom of the computer with double precision （ namely 64 position ） How to store .
- There are many precision losses in the whole process ： Operations on orders 、 Addition operation .
- The loss of precision is essentially the result of rounding operations , When it comes to rounding operations, we have to follow 0 House 1 The principle of entry .

- Element tree control: invalid to modify current node key
- linux下安装apache（httpd-2.4.3版本）各种坑
- How to install Apache (httpd-2.4.3) under Linux
- 程序员业余时间写的代码也算公司的？Nginx之父被捕引发争议
- Nacos serialize for class [com.alibaba.nacos.common.http.HttpRestResult] failed.
- Do programmers write code in their spare time? Controversy over the arrest of nginx's father
- Nacos serialize for class [ com.alibaba.nacos . common.http.HttpRestResult ] failed.
- Seamless management of API documents using eolink and gitlab
- vue 的基础应用（上）
- 28岁开始零基础学前端，这些血的教训你一定要避免
- Basic application of Vue
- Starting at the age of 28, you must avoid these bloody lessons
- Ubuntu 16.04 can not connect to the wireless solution and QQ installation
- Industry security experts talk about the rapid development of digital economy, how to guarantee the security of data elements?
- 利用Vue实现一个简单的购物车功能
- Behind the "tireless classroom" and teacher training, can byte education really "work wonders"?
- Using Vue to realize a simple shopping cart function
- 【css】伪类和伪类元素的区别
- 【css效果】实现简单的下拉菜单
- 【vue】父子组件传值
- The difference between pseudo class and pseudo class elements
- [CSS effect] simple drop-down menu
- [Vue] value transfer by parent-child component
- 【css】设置table表格边框样式
- 【css】修改input，textarea中的placeholder样式
- vue-router的两种模式（hash和history）及区别
- CSS3的滤镜filter属性
- [CSS] set table border style
- [CSS] modify the placeholder style in input and textarea
- Two modes of Vue router (hash and History) and their differences
- Filter property of CSS3
- 全局安装gulp 报错问题解决
- Solution of error report in global installation of gulp
- 18个好用的自定义react hook
- 你应该知道的常用服务器HTTP状态码？
- 18 user defined react hooks
- What HTTP status codes should you know about common servers?
- 手把手教你打造属于自己团队的前端小报系统
- Hand in hand to teach you to build your own front-end tabloid system
- In 2021, enterprise SEO actual operation, how to less update, batch ranking regional words?
- vue cli4.0 快速搭建项目详解
- Vue cli4.0 quick build project
- vue-cli脚手架安装
- Installation of Vue cli scaffold
- [JS knowledge] method of getting elements from DOM
- 【jQuery效果】文字滚动
- [jQuery effect] text scrolling
- [front end] live broadcast of user experience optimization series, real-life sharing of front-line celebrities
- React native introduces third party Android SDK
- Using html2canvas to generate shared images, CDN images do not show the problem
- Using hooks to write react components
- Explain the module hot replacement function of webpack in detail
- An incomplete guide to writing a simple native wechat applet
- How JavaScript calculates 1 + 1 - Part 1 creates a source string
- Jsonp method to solve cross domain problems
- Canvas animation demo (from zero to one)
- El dialog of elementui component encapsulation
- Transition group of Vue source code
- When encountering bracket validity, next larger element, specific minimum value, try stack
- Vue3 virtual DOM