[Mono-bugs] [Bug 34640][Wis] New - Decimal.ToString() fails for some numbers
bugzilla-daemon@rocky.ximian.com
bugzilla-daemon@rocky.ximian.com
26 Nov 2002 19:56:15 -0000
Please do not reply to this email- if you want to comment on the bug, go to the
URL shown below and enter your comments there.
Changed by kend0@earthlink.net.
http://bugzilla.ximian.com/show_bug.cgi?id=34640
--- shadow/34640 Tue Nov 26 14:56:15 2002
+++ shadow/34640.tmp.3840 Tue Nov 26 14:56:15 2002
@@ -0,0 +1,283 @@
+Bug#: 34640
+Product: Mono/Class Libraries
+Version: unspecified
+OS: Red Hat 7.2
+OS Details:
+Status: NEW
+Resolution:
+Severity:
+Priority: Wishlist
+Component: System
+AssignedTo: mono-bugs@ximian.com
+ReportedBy: kend0@earthlink.net
+QAContact: mono-bugs@ximian.com
+TargetMilestone: ---
+URL:
+Cc:
+Summary: Decimal.ToString() fails for some numbers
+
+version: Mono/mcs 0.13
+
+Description of Problem:
+
+ ToString() fails for some Decimal numbers. (see Actual, below).
+
+ The salient traceback is: VVVVV
+Unhandled Exception: System.ArgumentException: length
+in <0x00210> 00 System.Array:Copy (System.Array,int,System.Array,int,int)
+in <0x000a5> 00 System.Text.StringBuilder:Remove (int,int)
+in <0x000be> 00 System.DecimalFormatter:FormatGeneral (System.Globalization.NumberFormatInfo,System.Text.StringBuilder,int,int,int,char)
+in <0x003e9> 00 System.DecimalFormatter:NumberToString (string,System.Globalization.NumberFormatInfo,System.Decimal)
+in <0x0005c> 00 System.Decimal:ToString (string,System.IFormatProvider)
+in <0x00475> 00 LFT.RunMe:Main (string[])
+ ^^^^^
+
+
+Steps to reproduce the problem:
+1. compile and run the following program
+VVVVVVVVVVVVVVVVVVVVVVVVVV
+// FILE "lft.cs"
+// IMPLEMENTS Linear Fractional Transform (Mobius Transform) real numbers
+// AUTHOR Ken Dickey
+// DATE 2002 November 26
+// Copyright (C) 2002 by Kenneth Alan Dickey. All rights reserved.
+
+using System ;
+using System.IO ;
+using System.Math ;
+using System.Collections ;
+
+namespace LFT {
+ public class LFTMat {
+ Int64 a = 0, b = 0, c = 0, d = 1 ;
+ // | a c |
+ // | b d |
+ public LFTMat( Int64 a, Int64 b, Int64 c, Int64 d ) {
+ this.a = a ;
+ this.b = b ;
+ this.c = c ;
+ this.d = d ;
+ // return( this ) ;
+ }
+ public override String ToString() {
+ return "<LFT: a=" + this.a.ToString()
+ + ", b=" + this.b.ToString()
+ + ", c=" + this.c.ToString()
+ + ", d=" + this.d.ToString()
+ + ">";
+ }
+ public Decimal mash( Decimal x ) {
+ // | a c |
+ // | b d | => ( ax+c / bx+d )
+ return ( (this.a * x + this.c) / (this.b * x + this.d) ) ;
+ }
+ public Boolean isAffine() {
+ return ( (this.b == 0) && (this.d != 0) ) ;
+ }
+ public Int64 determinant() {
+ // (ad - bc)
+ return ((this.a * this.d) - (this.b * this.c)) ;
+ }
+ public Boolean isSingular() {
+ return (this.determinant() != 0) ;
+ }
+ public LFTMat inverse() {
+ if (this.isSingular())
+ throw new Exception("LFTMat.inverse: is singular" + this.ToString()) ;
+ else
+ return( new LFTMat( d, -b, -c, a ) ) ;
+ }
+ public static LFTMat operator+( LFTMat x, LFTMat y ) {
+ return( new
+ LFTMat( x.a + y.a ,
+ x.b + y.b ,
+ x.c + y.c ,
+ x.d + y.d ) ) ;
+ }
+ public static LFTMat operator-( LFTMat x, LFTMat y ) {
+ return( new
+ LFTMat( x.a - y.a ,
+ x.b - y.b ,
+ x.c - y.c ,
+ x.d - y.d ) ) ;
+ }
+ public static LFTMat operator*( LFTMat x, LFTMat y ) {
+ // product:
+ // | a1 c1 | | a2 c2 | | (a1a2 + c1b2) (a1c2 + c1d2) |
+ // | b1 d1 | * | b2 d2 | = | (b1a2 + d1b2) (b1c2 + d1d2) |
+ return( new
+ LFTMat( x.a * y.a + x.c * y.b ,
+ x.b * y.a + x.d * y.b ,
+ x.a * y.c + x.c * y.d ,
+ x.b * y.c + x.d * y.d ) ) ;
+ }
+ public Boolean isRefining() {
+ return( this.isAffine() &&
+ ( (Math.Abs(this.a) + Math.Abs(this.c)) <= Math.Abs(this.d) )
+ ) ;
+ }
+ public Decimal contractivity() {
+ if (this.isAffine())
+ return( Math.Abs(this.a / this.b) ) ;
+ else
+ throw new Exception("LFTMat.contractivity: is NOT affine"
+ + this.ToString()) ;
+ }
+ } // end LFTMat
+
+ public class LFT {
+ public static Boolean debugMe = true ;
+ LFTMat sign;
+ LFTMat[] digits;
+ public LFT( LFTMat sign, LFTMat[] digits ) {
+ this.sign = sign ;
+ this.digits = digits ;
+ // return( this ) ;
+ }
+ } // end LFT
+ public class E_LFT {
+ Int64 x ;
+ public E_LFT( Int64 x ) {
+ this.x = x ;
+ // return( this ) ;
+ }
+ // e^x = | x x+1 | ------oo | x x |
+ // | 0 1 | | |n=1 | 0 n+1 |
+ public Decimal mash( Int64 whatever ) {
+ // mash( sign * digit1 * ... * digitN )
+ Int64 x = this.x ;
+ LFTMat sign = new LFTMat( x, 0, (x+1), 1 ) ;
+ LFTMat tmp = sign ;
+ for (int n = 1; n <= whatever; n++)
+ tmp = tmp * (new LFTMat( x, 0, x, (n + 1) )) ;
+ if (LFT.debugMe) {
+ Console.WriteLine( "E-LFT for n={0} is {1}", whatever, tmp ) ;
+ Decimal result = tmp.mash( x ) ;
+ //Console.WriteLine( "E-LFT result is {0}", (Double)result ) ;
+ return( result ) ;
+ }
+ else
+ return( tmp.mash( x ) ) ;
+ }
+
+ } // end E_LFT
+
+ public class RunMe {
+ static void Main(string[] args)
+ {
+ LFTMat a = new LFTMat( 1, 0, 2, 1 ) ;
+ LFTMat b = new LFTMat( 1, 1, 0, 2 ) ;
+ Console.WriteLine("**VVV Starting Linear Transform Code VVV**") ;
+ Console.WriteLine("A is {0}", a.ToString() ) ;
+ Console.WriteLine("B is {0}", b.ToString() ) ;
+ Console.WriteLine("A + B is {0}", (a+b).ToString() ) ;
+ Console.WriteLine("A - B is {0}", (a-b).ToString() ) ;
+ Console.WriteLine("A * B is {0}", (a*b).ToString() ) ;
+ Console.WriteLine("A.mash(3) is {0}", a.mash(3).ToString() ) ;
+ E_LFT e = new E_LFT( 1 ) ; // e^1 is e
+ Console.WriteLine("Math.E is {0}", Math.E.ToString() ) ;
+ Decimal approx = 3 ;
+ Decimal bigE = (Decimal)Math.E ;
+ Decimal delta = (Decimal)0.00000000000001 ;
+ Int64 n = 1 ;
+ while ( (Math.Abs(approx - bigE) > delta) ) {
+ approx = e.mash(n) ;
+ Console.WriteLine( "eLFT.mash({0}) is {1}",
+ n.ToString(),
+ approx.ToString() //((Double)approx).ToString()
+ ) ;
+ n = (n + 1) ;
+ }
+ Console.WriteLine("Math.E is {0}", Math.E.ToString() ) ;
+ Console.WriteLine("**^^^ Ending Linear Transform Code ^^^**") ;
+ }
+ } // end RunMe
+}
+
+
+/* --- E O F --- */
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+Actual Results:
+
+kend@bandicoot:/usr/local/src/Mono/Test>> mcs lft.cs
+lft.cs(123) warning CS0162: Unreachable code detected
+Compilation succeeded - 1 warning(s)
+kend@bandicoot:/usr/local/src/Mono/Test>> mono lft.exe
+**VVV Starting Linear Transform Code VVV**
+A is <LFT: a=1, b=0, c=2, d=1>
+B is <LFT: a=1, b=1, c=0, d=2>
+A + B is <LFT: a=2, b=1, c=2, d=3>
+A - B is <LFT: a=0, b=-1, c=2, d=-1>
+A * B is <LFT: a=3, b=1, c=4, d=2>
+A.mash(3) is 5
+Math.E is 2.71828182845905
+E-LFT for n=1 is <LFT: a=1, b=0, c=5, d=2>
+eLFT.mash(1) is 3
+E-LFT for n=2 is <LFT: a=1, b=0, c=16, d=6>
+eLFT.mash(2) is 2.8333333333333333333333333333
+E-LFT for n=3 is <LFT: a=1, b=0, c=65, d=24>
+eLFT.mash(3) is 2.75
+E-LFT for n=4 is <LFT: a=1, b=0, c=326, d=120>
+
+Unhandled Exception: System.ArgumentException: length
+in <0x00210> 00 System.Array:Copy (System.Array,int,System.Array,int,int)
+in <0x000a5> 00 System.Text.StringBuilder:Remove (int,int)
+in <0x000be> 00 System.DecimalFormatter:FormatGeneral (System.Globalization.NumberFormatInfo,System.Text.StringBuilder,int,int,int,char)
+in <0x003e9> 00 System.DecimalFormatter:NumberToString (string,System.Globalization.NumberFormatInfo,System.Decimal)
+in <0x0005c> 00 System.Decimal:ToString (string,System.IFormatProvider)
+in <0x00475> 00 LFT.RunMe:Main (string[])
+
+kend@bandicoot:/usr/local/src/Mono/Test>>
+
+Expected Results:
+
+[obtained by casting result to Double before output]
+**VVV Starting Linear Transform Code VVV**
+A is <LFT: a=1, b=0, c=2, d=1>
+B is <LFT: a=1, b=1, c=0, d=2>
+A + B is <LFT: a=2, b=1, c=2, d=3>
+A - B is <LFT: a=0, b=-1, c=2, d=-1>
+A * B is <LFT: a=3, b=1, c=4, d=2>
+A.mash(3) is 5
+Math.E is 2.71828182845905
+E-LFT for n=1 is <LFT: a=1, b=0, c=5, d=2>
+eLFT.mash(1) is 3
+E-LFT for n=2 is <LFT: a=1, b=0, c=16, d=6>
+eLFT.mash(2) is 2.83333333333333
+E-LFT for n=3 is <LFT: a=1, b=0, c=65, d=24>
+eLFT.mash(3) is 2.75
+E-LFT for n=4 is <LFT: a=1, b=0, c=326, d=120>
+eLFT.mash(4) is 2.725
+E-LFT for n=5 is <LFT: a=1, b=0, c=1957, d=720>
+eLFT.mash(5) is 2.71944444444444
+E-LFT for n=6 is <LFT: a=1, b=0, c=13700, d=5040>
+eLFT.mash(6) is 2.71845238095238
+E-LFT for n=7 is <LFT: a=1, b=0, c=109601, d=40320>
+eLFT.mash(7) is 2.71830357142857
+E-LFT for n=8 is <LFT: a=1, b=0, c=986410, d=362880>
+eLFT.mash(8) is 2.71828428130511
+E-LFT for n=9 is <LFT: a=1, b=0, c=9864101, d=3628800>
+eLFT.mash(9) is 2.71828207671958
+E-LFT for n=10 is <LFT: a=1, b=0, c=108505112, d=39916800>
+eLFT.mash(10) is 2.7182818512506
+E-LFT for n=11 is <LFT: a=1, b=0, c=1302061345, d=479001600>
+eLFT.mash(11) is 2.71828183037384
+E-LFT for n=12 is <LFT: a=1, b=0, c=16926797486, d=6227020800>
+eLFT.mash(12) is 2.71828182860735
+E-LFT for n=13 is <LFT: a=1, b=0, c=236975164805, d=87178291200>
+eLFT.mash(13) is 2.7182818284697
+E-LFT for n=14 is <LFT: a=1, b=0, c=3554627472076, d=1307674368000>
+eLFT.mash(14) is 2.71828182845976
+E-LFT for n=15 is <LFT: a=1, b=0, c=56874039553217, d=20922789888000>
+eLFT.mash(15) is 2.71828182845909
+E-LFT for n=16 is <LFT: a=1, b=0, c=966858672404690, d=355687428096000>
+eLFT.mash(16) is 2.71828182845905
+Math.E is 2.71828182845905
+**^^^ Ending Linear Transform Code ^^^**
+
+
+How often does this happen?
+
+
+Additional Information: