operations on continued fractions
- Subject: operations on continued fractions
- From: Robert Dodier
- Date: Tue, 14 Nov 2006 22:59:23 -0700
Hello,
I've reworked the continued fractions code (cf and friends)
so that a continued fraction is represented by an expression
like cf(1, 1, 2, 3, 1). The new code mostly just arranges
things to make the existing code happy and then it punts.
There are a couple of new features. One is that arithmetic
operations on cf expressions are recognized. This is
accomplished via tellsimpafter. The other new feature
is that cf expressions evaluate to numeric values when
the numer flag is true.
One other feature that seems useful would be to make
rat(cf(...)) return the value of cf(...) as a rational number.
(Hmm, come to think of it, float(cf(...)) should likewise
convert cf(...) to a float.)
The current implementation of this stuff is a mix of Lisp
and Maxima code. The tellsimpafter stuff noticeably increases
the time to execute the test suite (because it is executed
for every * + ^ expression), so I'll probably try to code
everything in Lisp.
FWIW
Robert
PS. Here are some examples which, I hope, show the
existing functionality still works, and also shows the
new features.
(%i1) cf (1);
(%o1) cf(1)
(%i2) cf (17/29);
(%o2) cf(0, 1, 1, 2, 2, 2)
(%i3) cfdisrep (%);
1
(%o3) -----------------
1
1 + -------------
1
1 + ---------
1
2 + -----
1
2 + -
2
(%i4) ?resimplify (%);
17
(%o4) --
29
(%i5) cf (2.718281828459045);
(%o5) cf(2, 1, 2, 1, 1, 4, 1, 1, 6, 1, 1, 8)
(%i6) ''%, numer;
(%o6) 2.718281835205993
(%i7) cf (sqrt (10));
(%o7) cf(3, 6, 6)
(%i8) cfdisrep (%);
1
(%o8) 3 + -----
1
6 + -
6
(%i9) cf ((1 + sqrt(5))/2);
(%o9) cf(1, 1, 1, 1, 1, 1, 1, 2)
(%i10) ''%, numer;
(%o10) 1.617647058823529
(%i11) cf (sqrt (55)) - cf (sqrt (54));
By *rule1 , -cf(7,2,1,6,1,2,14,2,1,6,1,2,14) -->
cf(-8,1,1,1,6,1,2,14,2,1,6,1,2,14)
By +rule1 , cf(7,2,2,2,14,2,2,2,14)+cf(-8,1,1,1,6,1,2,14,2,1,6,1,2,14) -->
cf(0,14,1,3,4,90,1,1,1,4,1,1,1,526,1,1,3)
(%o11) cf(0, 14, 1, 3, 4, 90, 1, 1, 1, 4, 1, 1, 1, 526, 1, 1, 3)
(%i12) ''%, numer;
(%o12) .06772925831991705
(%i13) sqrt (55) - sqrt (54), numer;
(%o13) .06772925874612845
(%i14) 17/29 + 19/31 - 23/37;
19209
(%o14) -----
33263
(%i15) cf (17/29 + 19/31 - 23/37);
(%o15) cf(0, 1, 1, 2, 1, 2, 1, 1, 1, 7, 1, 2, 1, 2, 1, 3)
(%i16) cf (17/29) + cf (19/31) - cf (23/37);
By *rule1 , -cf(0,1,1,1,1,1,4) --> cf(-1,2,1,1,1,4)
By +rule1 , cf(0,1,1,2,2,2)+cf(0,1,1,1,1,2,2)+cf(-1,2,1,1,1,4) -->
cf(0,1,1,2,1,2,1,1,1,7,1,2,1,2,1,3)
(%o16) cf(0, 1, 1, 2, 1, 2, 1, 1, 1, 7, 1, 2, 1, 2, 1, 3)
(%i17) ?resimplify (cfdisrep (%));
19209
(%o17) -----
33263
(%i18) 17/29 * 19/31 / (23/37);
11951
(%o18) -----
20677
(%i19) cf (17/29 * 19/31 / (23/37));
(%o19) cf(0, 1, 1, 2, 1, 2, 2, 1, 1, 23, 8)
(%i20) cf (17/29) * cf (19/31) / cf (23/37);
By *rule1 , cf(0,1,1,1,1,2,2)*cf(0,1,1,2,2,2) --> cf(0,2,1,3,1,1,1,1,2,5)
By ^rule1 , 1/cf(0,1,1,1,1,1,4) --> cf(1,1,1,1,1,4)
By *rule1 , cf(0,2,1,3,1,1,1,1,2,5)*cf(1,1,1,1,1,4) -->
cf(0,1,1,2,1,2,2,1,1,23,8)
(%o20) cf(0, 1, 1, 2, 1, 2, 2, 1, 1, 23, 8)
(%i21) ?resimplify (cfdisrep (%));
11951
(%o21) -----
20677
(%i22) (17/29) ^ 5;
1419857
(%o22) --------
20511149
(%i23) cf ((17/29) ^ 5);
(%o23) cf(0, 14, 2, 4, 8, 8, 1, 64, 1, 5, 2, 2)
(%i24) cf (17/29) ^ 5;
By ^rule1 , cf(0,1,1,2,2,2)^5 --> cf(0,14,2,4,8,8,1,64,1,5,2,2)
(%o24) cf(0, 14, 2, 4, 8, 8, 1, 64, 1, 5, 2, 2)
(%i25) ?resimplify (cfdisrep (%));
1419857
(%o25) --------
20511149
(%i26) cflength : 2;
(%o26) 2
(%i27) cf ((1 + sqrt(5))/2);
(%o27) cf(1, 1, 1, 1, 1, 1, 1, 2)
(%i28) ''%, numer;
(%o28) 1.617647058823529
(%i29) cf (2.718281828459045);
(%o29) cf(2, 1, 2, 1, 1, 4, 1, 1, 6, 1, 1, 8)
(%i30) cfexpand (%);
[ 23225 2721 ]
(%o30) [ ]
[ 8544 1001 ]
(%i31) %[1,1] / %[2,1];
23225
(%o31) -----
8544
(%i32) ''%, numer;
(%o32) 2.718281835205993