CS3343/3341 Analysis of Algorithms Spring 2012 Weird Topic 
Fibonacci Search

The Fibonacci Numbers consist of the sequence of integers: F_{0} = 0, F_{1} = 1, F_{2} = 1, F_{3} = 2, F_{4} = 3, F_{5} = 5, F_{6} = 8, F_{7} = 13, F_{8} = 21, F_{9} = 34, F_{10} = 55, ... . These are defined recursively by the following formula:
This is a strange algorithm similar to binary search, with almost the same performance. [Fibonacci search was invented in 1960 by D.E. Ferguson. No normal human being would ever think of a search like this.]
For motivation in getting to Fibonacci search, let's review binary search. Also, to fit with the later search better, we'll assume our binary search starts with 1. So search an ordered array with elements A[1], ..., A[N] inclusive for y. We want an integer x, 0 < x < N+1 such that y == A[x] or else determine that no such x exists. At each stage of binary search, we have an interval [low, high]. (At the end we may have low == high.) We need to divide [low, high] into two parts: [low, mid], and [mid, high], and of course mid is midway between low and high (or as close as we can get). In case y == A[mid], we're done, and otherwise we know that y must be found using either [low, mid) or (mid, high], where a parenthesis means we are excluding the end value. Toward the end we may have mid == low or mid == high. In case we have low > high, we know the element isn't in the array.
With Fibonacci search, we start with the same ordered array A, except that N+1 must be a Fibonacci number, say, F[m+1]. We still want an integer x, 0 < x < N+1 = F[m+1]. Instead of the midpoint, we use the next Fibonacci number down: F[m].
Specific numbers will make this clearer: Take N = 54, so that N+1 = 55 = F[10]. We will be searching the sorted array: A[1], ..., A[54], inclusive. The array indexes are strictly between the two Fibonacci number: 0 < 55. Instead of the midpoint, this search uses the next Fibonacci number down from F[10] = 55, namely F[9] = 34. Instead of dividing the search interval in two, 50% on either side, we divide roughly by the golden ratio, roughly 62% to the left and 38% to the right. If y == A[34], then we've found it. Otherwise we have two smaller intervals to search: 0 to 34 and 34 to 55, not including the endpoints. If you have two successive Fibonacci numbers, it's easy to march backwards using subtraction, so that above, the next number back from 34 is 55  34 = 21. We would break up 0 to 34 with a 21 in the middle. The range from 34 to 55 is broken using the next Fibonacci number down: 34  21 = 13. The whole interval [34, 55] has length 21, and we go 13 past the start, to 34 + 13 = 47. Notice that this is not a Fibonacci number  it's the lengths of all the intervals that are.
The table below shows possibilities for successive places to break up the range from 0 to 55. Every search of this array will either make its way into one of these ranges, and a few more steps beyond, or it will find the item along the way.
0 < 55   one range of size 55 0 < 34 < 55   two: 34, 21 0 < 21 < 34 < 47 < 55   four: 21, 13, 13, 8 0 < 13 < 21 < 29 < 34 < 42 < 47 < 52 < 55   eight: 13,8,8,5,8,5,5,3 0< 8<13<18<21<26<29<32<34<39<42<45<47<50<52<54<55   sixteen: 8,5,5,3,5,3,3,2,5,3,3,2,3,2,2,1 
Here is sample data from a run of the program Fibonacci search program. In red above are the particular dividing integers that occur in the run below which made two more dividing steps.
Let y = A[x]. Want to find x. N = 55. mid:34, p:21,q:13  0 < 34 < 55, y > A[34], so 0 < x < 34 mid:21, p:13,q: 8  0 < 21 < 34, y > A[34], so 21 < x < 34 mid:29, p: 5,q: 3  21 < 29 < 34, y > A[29], so 29 < x < 34 mid:32, p: 2,q: 1  29 < 32 < 34, y < A[32], so 29 < x < 32 mid:31, p: 1,q: 1  29 < 31 < 32, y < A[31], so 29 < x < 31 mid:30, p: 1,q: 0  29 < 30 < 31, y == A[30], x == 30 Found: 30 
Here is the algorithm itself. Notice that this search does have a mid variable, and it has variables corresponding to low and high, namely the variables p and q, which are always Fibonacci numbers. However, unlike low and high, p and q are offsets from mid, and the search range is implicit rather than explicit.
Fibonacci Algorithm 

// Fibonacci search, search A[1],A[2],...,A[N] // Here N+1 must be a Fibonacci number, F[m+1] int fibSearch(int y) { // y = A[x], 0 < x < F[m+1] int mid = F[m]; // F[m] is partway from 0 to F[m+1] int p = F[m1] = F[m]  F[m1] int q = F[m2] = 2*F[m1}  F[m] for (;;) { System.out.println("mid:" + mid + ", p:" + p + ",q:" + q); if (y == A[mid) return mid; else if (y < A[mid) { if (q == 0) return (mid  1); mid = mid  q; int temp = p; p = q; q = temp  q; } else if (y > A[mid]) { if (p == 1) return mid; mid = mid + q; p = p  q; q = q  p; } } } 