from Dictionary - Floating point issue
부동 소수점 관련 문제
class FloatingPoint {
@Test
public void fpFailure() {
Assertions.assertEquals(1.2 , 1.1 + 0.1);
//결과는? false
//부동소수점 문제 때문에 그렇다. (특히 이 주변은 다 괜찮은데 얘만 그렇다.)
/**
* Expected :1.2
* Actual :1.2000000000000002
*/
//위와 같은 결과로 나온다.
}
@Test
public void fpSuccess() {
Assertions.assertEquals(BigDecimal.valueOf(1.2), BigDecimal.valueOf(1.1).add(BigDecimal.valueOf(0.1)));
//이러면 성공한다.
}
}
Java _ BigDecimal 관련 사용 시 유의점
연산
- ’+’ :
BigDecimal.valueOf(x).add(BigDecimal.valueOf(y)); - ’-‘ :
BigDecimal.valueOf(x).substract(BigDecimal.valueOf(y)); - ‘*’ :
BigDecimal.valueOf(x).multiply(BigDecimal.valueOf(y)); - ’/’ :
BigDecimal.valueOf(x).divide(BigDecimal.valueOf(y)); - ’%’ :
BigDecimal.valueOf(x).remainder(BigDecimal.valueOf(y)); - 절대값 :
BigDecimal.valueOf(x).abs();
소수점
RoundingMode
UP(BigDecimal.ROUND_UP),: 양수일 때 올림, 음수일 때 내림DOWN(BigDecimal.ROUND_DOWN),: ROUND_UP과 반대CEILING(BigDecimal.ROUND_CEILING),: 올림FLOOR(BigDecimal.ROUND_FLOOR),: 내림HALF_UP(BigDecimal.ROUND_HALF_UP),: 반올림 (5이상 올림 5미만 버림)HALF_DOWN(BigDecimal.ROUND_HALF_DOWN),: 반올림 ( 6이상 올림, 6미만 버림)HALF_EVEN(BigDecimal.ROUND_HALF_EVEN),: 반올림 값이 짝수면 HALF_DOWN, 홀수면 HALF_UPUNNECESSARY(BigDecimal.ROUND_UNNECESSARY);: 딱 떨어지는 값이 아니면 ArithmeticException
사용법
BigDecimal("0.9999").setScale(0, RoundingMode.CEILING);
MathContext
UNLIMITED = new MathContext(0, RoundingMode.HALF_UP);: unlimit (무제한 정밀 산술)DECIMAL32 = new MathContext(7, RoundingMode.HALF_EVEN);: matching the precision of the IEEE 754-2019 decimal32 format, 7 digits ( 7자리 정밀도 및 HALF_EVENT의 반올림 모드)DECIMAL64 = new MathContext(16, RoundingMode.HALF_EVEN);: matching the precision of the IEEE 754-2019 decimal64 format, 16 digits ( 16자리 정밀도 및 HALF_EVENT의 반올림 모드)DECIMAL128 = new MathContext(34, RoundingMode.HALF_EVEN);: matching the precision of the IEEE 754-2019 decimal128 format, 34 digits ( 32자리 정밀도 및 HALF_EVENT의 반올림 모드)
Methods
BigInteger
class IntroduceBigInteger {
public void bit () {
BigInteger i = new BigInteger("1018"); // 2진수로 표현하면 : 1111111010(2)
int bitCount = i.bitCount(); // 1의 갯수 : 8
int bitLength = i.bitLength(); // 비트 수 : 10
int getLowestSetBit = i.getLowestSetBit(); // 1
boolean testBit3 = i.testBit(3); // true
BigInteger setBit12 = i.setBit(12); // 우측에서 13번째 비트를 1로 변경 → 1001111111010(2) → 5114
BigInteger flipBit0 = i.flipBit(0); // 1111111011(2) → 1019
BigInteger clearBit3 = i.clearBit(3); // 1111110010(2) → 1010
}
public void bitOperate () {
BigInteger i = new BigInteger("17"); // 2진수 : 10001(2)
BigInteger j = new BigInteger("7"); // 2진수 : 111(2)
BigInteger and = i.and(j); // 10001(2) & 111(2) = 00001(2) → 1(10)
BigInteger or = i.or(j); // 23
BigInteger not = j.not(); // -8
BigInteger xor = i.xor(j); // 22
BigInteger andNot = i.andNot(j); // 16
BigInteger shiftLeft = i.shiftLeft(1); // 34
BigInteger shiftRight = i.shiftRight(1); // 8
}
}
JsonSerializer
BigDecimal to JsonValue
class BigDecimalScale6WithBankersRoundingSerializer implements JsonSerializer<BigDecimal> {
public static Integer SCALE_SIX = 6;
public static RoundingMode BANKERS_ROUNDING_MODE = RoundingMode.HALF_EVEN;
@Override
public Object serialize( BigDecimal value, JsonGenerator gen, SerializerProvider serializers ) {
return gen.writeString(value.setScale(SCALE_SIX, BANKERS_ROUNDING_MODE).toString());
}
}