Announcement Announcement Module
Collapse
No announcement yet.
BigDecimal representation problem Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • BigDecimal representation problem

    Hello guys

    i work with BigDecimal object for hibernate property that represents of course decimals numbers like 0.5 or other ugly numbers

    my problem is how represent this number to format string how 1/2 ?

    0.33 = 1/3 ?
    0.25 = 1/4 ?
    i saw the api but nothing to help me,

    thanks in advanced

  • #2
    1/2 = actually 1 divided by 2 which is 0.5. So I think the only way is to parse the string and do the math, so to speak.

    Comment


    • #3
      From what I understand it's the other way around. Showing 0.5 as 1/2, so finding a fraction for every decimal number. I wonder if that's possible at all but I'm not a mathematician

      Joerg

      Comment


      • #4
        Oeps. Misreading on my side, you are right Jörg. Hmm, not sure if that is possible. You could do 1 divide it by the number you have 0.5, the result will be 2 then display 1/[result]. However that might create some ackward situation if the number isn't a full number I guess..

        Code:
        import java.math.BigDecimal;
        
        
        public class FractionTest {
        
        	/**
        	 * @param args
        	 */
        	public static void main(String[] args) {
        		BigDecimal dec1 = new BigDecimal("0.5");
        		BigDecimal dec2 = new BigDecimal("0.33");
        		BigDecimal dec3 = new BigDecimal("0.25");
        		BigDecimal dec4 = new BigDecimal("0.125");
        		
        		System.out.println("1/" + result(dec1));
        		System.out.println("1/" + result(dec2));
        		System.out.println("1/" + result(dec3));
        		System.out.println("1/" + result(dec4));
        		
        	}
        	
        	static int result(BigDecimal number) {
        		return new Double(1/number.doubleValue()).intValue();
        	}
        
        }
        The above code prints

        1/2
        1/3
        1/4
        1/8

        So Converting it to something usuable shouldn't be that hard.
        Last edited by Marten Deinum; Jan 16th, 2008, 01:22 AM.

        Comment


        • #5
          I suggest to add some rounding logic to get around precision issues. But anyway, I guess you are bound to a specific type of fraction like 1/x.

          Regards,
          Andreas

          Comment


          • #6
            After a quick googling, I found a couple of articles on representing decimal numbers as fractions. I havent found a complete ready to use algorithm, but you can find some ideas by looking at the following articles :

            http://mathforum.org/dr.math/faq/faq...s.html#decfrac
            http://mathforum.org/library/drmath/view/51886.html

            Comment


            • #7
              Or even better (why didnt I think of that before) : the Jakarta Commons Math. Have a look at http://commons.apache.org/math/apido...e-summary.html

              Comment


              • #8
                thanks so much for your replies friends, i really appreciate

                well by parts

                Jörg Heinicke
                I wonder if that's possible at all but I'm not a mathematician
                me too, and i am wondered, by doesnt exists a default mehtod for this in Java

                mdeinum
                Oeps. Misreading on my side, you are right Jörg.
                my english in my first post is very bad? :-(

                you code looks pretty cool and simple thanks so much

                Andreas Senft
                I suggest to add some rounding logic to get around precision issues.
                i found a hard problem

                under some circumstances this value 0.3333333.... is converted to 0.34
                with a simple division
                Code:
                a.setPrecioUnitarioVenta(
                      a.getTotalValorizado().divide(
                              b.getStockactual(),2 ) );
                where
                a= 14.00
                b=6.00
                where with a simple calculator c = 2.33333333.....
                and c should be i think 2.33
                but
                c is shown how 2.34

                some help about this

                gehel
                your links are valid but i dont know if this can resolve my problem of the 0.33333


                dont take this like some offense but
                i would like all you to read this
                http://forum.java.sun.com/thread.jsp...694&tstart=165

                thanks so much in advanced

                Comment


                • #9
                  I havent actually tried it, but this constructor seems to be able to round the result to a reasonable approximation. If you manage to make it work, I'll be interested in your results !

                  Comment


                  • #10
                    Hi gehel

                    thanks for the reply

                    wondered why recieve double like paremters instead of BigDecimal
                    i hope that BigDecimal (and must exists) offer a represetnation to double

                    thanks for your time

                    Comment


                    • #11
                      Worst case, you can always extract the needed code from commons-math and adapt it for BigDecimal. It doesnt seem to be too hard to understand and should not be too hard to adapt.

                      Comment


                      • #12
                        Hello gehel

                        about of formating string x/y thats done

                        the problem is for 14/6 = 2.333.....
                        or
                        14.00/6.00
                        see that this constructor recieve the number, i think already divided
                        for my bad luck 2.34
                        Code:
                        public Fraction(double value,
                                        double epsilon,
                                        int maxIterations)
                                 throws FractionConversionException
                        i need a method that recieve 2 bigdecimals or 2 doubles to resolve
                        the problem about 14 and 6

                        Code:
                                        BigDecimal a = new BigDecimal("14.1515");
                        		Double da = new Double(a.toString());
                        		System.out.println("a: "+a+" da: "+da);
                        		BigDecimal b = new BigDecimal("6.18");
                        		Double db = b.doubleValue();		
                        		System.out.println("b: "+b+" db: "+db);
                        show
                        Code:
                        a: 14.1515 da: 14.1515
                        b: 6.18 db: 6.18
                        c: 2.2899 dc: 2.2899
                        so i can play with BigDecimals or doubles

                        thanks in advanced

                        Comment


                        • #13
                          just after to try my last option like playing

                          Code:
                                         BigDecimal a = new BigDecimal("14.00");
                          		Double da = new Double(a.toString());
                          		System.out.println("a: "+a+" da: "+da);
                          		BigDecimal b = new BigDecimal("6.00");
                          		Double db = b.doubleValue();		
                          		System.out.println("b: "+b+" db: "+db);
                          
                          		BigDecimal c = a.divide(b,3); //<--------------- 3 instead of 2
                          		Double dc = c.doubleValue();
                          		System.out.println("c: "+c+" dc: "+dc);
                          show
                          Code:
                          a: 14.00 da: 14.0
                          b: 6.00 db: 6.0
                          c: 2.33 dc: 2.33  <---------- the desired value
                          so why 14/6 = 2.33333333....
                          for
                          Code:
                          BigDecimal c = a.divide(b,2);
                          is 2.34
                          and for
                          Code:
                          BigDecimal c = a.divide(b,3);
                          2.33

                          it should be the same?

                          regards

                          Comment


                          • #14
                            The int argument of divide() is the rounding-mode which is used to round to the given scale (in your case the scale is 2).
                            Rounding mode 2 stands for ROUND_CEILING and 3 for ROUND_FLOOR. So that makes the difference.

                            Try out this:
                            Code:
                            BigDecimal bd = new BigDecimal(2.333d);
                            System.out.println(bd.scale(2, RoundingMode.CEILING));
                            System.out.println(bd.scale(2, RoundingMode.FLOOR));
                            It yields 2.34 and 2.33.

                            Regards,
                            Andreas

                            Comment


                            • #15
                              Hi Andreas

                              BigDecimal bd = new BigDecimal(2.333d);
                              System.out.println(bd.setScale(2, RoundingMode.CEILING));
                              System.out.println(bd.setScale(2, RoundingMode.FLOOR));
                              show
                              Code:
                              2.34
                              2.33
                              thats right

                              but in the sun forums, i recieved the same suggestion,

                              about RoundingMode.CEILING

                              in
                              http://java.sun.com/j2se/1.5.0/docs/...e.html#CEILING

                              Code:
                              CEILING
                               
                              public static final RoundingMode CEILING
                               
                                  Rounding mode to round towards positive infinity. If the result is positive, behaves as for RoundingMode.UP; if negative, behaves as for RoundingMode.DOWN. Note that this rounding mode never decreases the calculated value.
                               
                                  Example:
                                  Input Number 	Input rounded to one digit
                                  with CEILING rounding
                                  5.5 	6
                                  2.5 	3
                                  1.6 	2
                                  1.1 	2
                                  1.0 	1
                                  -1.0 	-1
                                  -1.1 	-1
                                  -1.6 	-1
                                  -2.5 	-2
                                  -5.5 	-5
                              according to this (no tested yet) 0.33..... would become 1

                              ant i can remember that this behaviour happens, thats the reason i avoid it, coz all my control of historial of prices gone wrong with this behaviour

                              now i am really wondered and confused why in your case it works

                              regards

                              Comment

                              Working...
                              X