简体   繁体   中英

Floating-point number representation difference between PostgreSQL and Java

I use PostgreSQL 9.4.1 (32-bit, Windows) and have a table with a real column - quantity. When I execute the following query on pgAdmin:

SELECT quantity || ' pcs' FROM table

I get the following results:

123.234 psc 123 psc 12 psc 12.3 psc

Surprisingly, the same query through Java driver postgresql-9.4-1201.jdbc4 (and postgresql-9.2-1002.jdbc3 ) is different:

123.2341 psc 123 psc 12 psc 12.3000002 psc

As quantity is not returned by the query directly (but a string containing it), I don't expect such differences in the results. Can anyone suggest a solution so that Java result is the same as the one from pgAdmin.

It looks like pgAdmin is set to display only 3 trailing digits.

You can use a DecimalFormat object in your code to display the data in the same manner.

double numberOne = 123.2341;
double numberTwo = 123;
double numberThree = 12;
double numberFour = 12.30000002;

DecimalFormat formatter = new DecimalFormat();
formatter.setMaximumFractionDigits(3);

System.out.println(formatter.format(numberOne));   // 123.234
System.out.println(formatter.format(numberTwo));   // 123
System.out.println(formatter.format(numberThree)); // 12
System.out.println(formatter.format(numberFour));  // 12.3

PostgreSQL says that the real data type is an inexact, variable-precision numeric types , and that [o]n most platforms, the real type has a range of at least 1E-37 to 1E+37 with a precision of at least 6 decimal digits , because they use an IEE754 single precision representation with only 24 bits for the mantissa.

That means that in the database , 123.234 and 123.2341 are represented by the same value. I assume that you are using double datatype in Java, with a precision of about 15 decimal digits. The differences are normal.

If you want the values to be the same, you can try to use simple precision floats in Java, but you will still depend on the display modes between Java and pgAdmin.

The only foolproof way to maintain accuracy on decimal values is to use NUMERIC(precision, scale) in PostgreSQL, and BigDecimal in Java.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM