I was going to write a little Python program to try it out. Basically, we are creating two fibonacci sequences, one starting with 12, 18 and the other starting with 5, 5. At first I thought there will be nothing new here. Then I remembered that I was looking for a good example with which to demonstrate generator functions and I figured out that this would be a perfect example. Basically, we are looking for a function that each time we call it will generate the next fibonacci number in a sequence.
There is an example of such a Fibonacci function in an earlier post which I will repeat here:
def fibonacci(): parent, baby = 1, 0 while baby < 1000: print baby parent, baby = (parent + baby, parent)In this case, we don't want to print the fibonacci number, but want to return the next number in the series. We can do this with a generator function. A generator function is one that has the keyword yield. yield is like a return statement, except that the function remembers where we are and then the next time we call that function, we start from where we left off (or, in other words, directly after yield). Here is our fibonacci generator:
def fibonacci(t1, t2): while True: yield t1 t1, t2 = t2, t1 + t2 fib = fibonacci(0, 1) for i in range(10): print fib.next()Running this we get:
0 1 1 2 3 5 8 13 21 34Now comes the interesting part - we can create as many generators as we want, so here is our final program:
def fibonacci(t1, t2): while True: yield t1 t1, t2 = t2, t1 + t2 lhs = fibonacci(12, 18) rhs = fibonacci(5, 5) for i in range(30): l = lhs.next() r = rhs.next() print '%10d %10d %8.7f' % (l, r, float(l) / r)So, when I run it, I get the following results:
12 5 2.4000000 18 5 3.6000000 30 10 3.0000000 48 15 3.2000000 78 25 3.1200000 126 40 3.1500000 204 65 3.1384615 330 105 3.1428571 534 170 3.1411765 864 275 3.1418182This looks promising and it seems to converge really quickly. So, lets run it for 20 iterations.
12 5 2.4000000 18 5 3.6000000 30 10 3.0000000 48 15 3.2000000 78 25 3.1200000 126 40 3.1500000 204 65 3.1384615 330 105 3.1428571 534 170 3.1411765 864 275 3.1418182 1398 445 3.1415730 2262 720 3.1416667 3660 1165 3.1416309 5922 1885 3.1416446 9582 3050 3.1416393 15504 4935 3.1416413 25086 7985 3.1416406 40590 12920 3.1416409 65676 20905 3.1416408 106266 33825 3.1416408Well, that's weird. It got really close to Pi (which, as far as I can remember is something like 3.1415927), but then it seems to wander off again. Well, maybe it oscillates for a while before settling down. So, let's try 30 iterations (I will just record the last few lines of output).
728358 231840 3.1416408 1178508 375125 3.1416408 1906866 606965 3.1416408 3085374 982090 3.1416408 4992240 1589055 3.1416408 8077614 2571145 3.1416408 13069854 4160200 3.1416408
Well, it seems that we're not converging on Pi, but something very close to Pi.
Maybe I should have just stopped after 10 iterations. I marvelled at how the ratio between two fibonacci sequences would converge on Pi. Now I am a bit wiser, but also a bit sadder.
What you've done is programmed some Lucas sequences. Since the ratio of successive terms of the Fibonacci sequence converges to phi = (1 + sqrt(5))/2, the ratio you have is
ReplyDelete6/5 * phi^2
which is not pi, although not far from it.
cheers,
Alasdair
Thanks for that, Alasdair. I had seen an explanation, but unfortunately did not bookmark it. Now to go and check out Lucas Sequences...
ReplyDelete