Storage representation of type A. Double

Java floating-point types represent full compliance with the IEEE754 Standard (standards of IEEE 754 floating point numbers) and are interested in being able to go to the IEEE Standard Web site (www.ieee.org) Check it out. The content of the standard basically describes the storage format of floating-point types (Storage Layout), which I summarize in a few paragraphs to summarize the standard, please refer to the standard text for more information.

1. What is a floating-point number.

There are two ways to express real numbers on a computer: fixed-point representation (fixed-point) and floating-point representation (floating-point). Fixed-point notation is a fixed decimal point somewhere in the middle of an existing number, and the representation of the integer and fractional parts is no different from the representation of a normal integer. For example , the length of our numbers is 4, the decimal point is in the middle, so you can say 10.28, or 00.01, a fixed-point representation similar to the nature of this method and the form of a fraction. fixed-window form of fixed-point number so that he could neither represent very large numbers nor represent very small numbers. And when division happens, , a lot of precision is lost.

Floating-point numbers represent real numbers in the form of scientific notation. For example, 123.456 can be expressed as a 1.23456x102. The limit of a fixed window with a fixed-point number, which uses a floating window (sliding window), So you can represent a real number in a larger range of precision.

2. Storage layout (Storage Layout)

The so-called storage layout is how a floating-point number is represented in memory. We know that floating-point numbers have float and double, which is 4 bytes, 32 bits, and 8 bytes is 64 bits. The layout is:

Symbol exponent Decimal Part offset append (bias)

Single-precision 1[31] 8[30-23] 23[22-00] 127

Double precision 1[63] 11[62-52] 52[51-00] 1023

The number range of bits within the brackets, and the number of bits occupied by that part. Offset appends content that is not part of a bit representation, is a constant, and is explained later.

The symbol has only one digit: 0-Indicates positive number 1-represents the negative number

Exponent: The value of the exponent (8-bit/11-bit, unsigned) minus the offset attaches to the actual exponent of the number for example, the value is 200, and the actual exponent is 73=200-127. Constant bias=1023 for double doubles

Mantissa: What is the mantissa? For a scientific notation, a form like this l.mxbe, then this l.m is called the mantissa (Mantisa). It consists of a starting bit and a fractional part. For example, 5 can be expressed in different forms by scientific notation:

5*100

0.5*101

50*10-1

Then we introduce a concept, canonical form (normalized form), and non-standard form (denormalized forms). We define the canonical form as a normalized form after the decimal point is the first number that is not 0. So the first form of the above is canonical form, the other is nonstandard form, floating point representation in Java exactly according to this standard, only two forms of normalization form: 1.f and nonstandard form 0.f.

So, for our bit layout, with a base of 2, only one number is Non-zero, and that's 1. So our implied starting numbers can be no more than a bit, because in addition to 0 can only be 1, the specific implied rules, later shown.

3. The meaning of expression.

Corresponds to the table above, the meaning of the floating-point number represented by the range of values for each region:

The meaning expressed by the sign bit s-digit e decimal place F

0 00..00 00..00 +0

0 00..00 00..01

:

11..11 positive non-canonical real numbers, computational methods V=0.FX2 (-B+1)

0 00..01

:

11..10 XX. XX positive normalized real number, computational method V=1.FX2 (E-b)

0 11..11 00..00 Positive Infinity

0 11..11 00..01

:

01..11 insignificant non-digital Snan

0 11..11 10..00

:

11..11 insignificant non-digital Qnan

where b=127 (float)/b=1023 (double), Snan represents the result of an invalid operation, Qnan represents an indeterminate result of the operation, is meaningless.

If you change the symbol bit s to 1, then it's all negative and the other meaning is the same.

In addition, we see that for meaningless numbers the exponent is all 1 o'clock, which means that there are many combinations that are meaningless non-numeric, and in our Java it is quite simple to judge whether a number is Nan

Static public boolean isNaN (double v) {

Return (v!= v);

}

As can be seen from here, the virtual machine for the double type of data comparisons, it is certainly the first to do the exponent value of the decision, found that not all 1 o'clock to do the memory of the bitwise comparison. Of course it's my guess, it's like I don't know if it's true.

And again, we ' are very clear now, the minimum value that a double type can represent is the distance between its values, which is what we mean by precision, when the number is added to the integer "1-step", just can't exactly match the 1, in other words, 1 is not the minimum (precision/distance) Integer times. So if you set the variable double d = 0.1 and the result is not 0.1, because 0.1 is not represented;

Two. How do I see a double type storage structure?

We know that the Java double type provides a function called the Doubletolongbits function, which is actually very simple, and we realize that the long and double types are 64-bit, and they have the same size of memory, The function is to copy the memory structure of the double to the memory structure of the same size long variable. Returns this Long value. Because Java does not support bitwise operations on double types, therefore:

1. This function cannot be done in the Java language, so he is a JNI implementation

2. We use a long type of bitwise operation to print out the memory structure for viewing.

/**

* Test

*/

public static void Main (string[] args) {

MyTest t = new myTest ();

Double d = 0.1d;

Long L = double.doubletolongbits (d);

System.out.println (T.getlongbits (l));

}

/**

* Get the bit bit representation string of the constant integer

* @param a

* @return

*/

Public String getlongbits (long a) {

8 byte array of bytes, read it out

Byte[] B = new Byte[8];

for (int i=7;i>=0;i--) {

B[i] = (byte) (A&0X000000FF);

A = a>>8;

}

return This.byte2hex (b); Call one of the following functions

}

/**

* byte array converted to string

* @param b

* @return

*/

public static String Byte2hex (byte[] b) {

StringBuffer sb=new StringBuffer ();

String stmp= "";

for (int n=0;nstmp= (integer.tohexstring (B[n]&0xff));

if (Stmp.length () ==1) {

At the end of less than two digits, fill 0

Sb.append ("0" +stmp);

} else{

Sb.append (STMP);

}

if (n//":" As a separator

Sb.append (":");

}

}

Return sb.tostring (). toUpperCase ();

}

0.1 the printed memory results are:

3f:b9:99:99:99:99:99:9a

Let's get back to the first section of the meaning comparison table:

0 01111111011 1001.....1010

If you're interested, you can do that. The science calculator calculates its value according to the rules of the first section, oh, that's exactly what we printed through System.out.println (d).