Reputation: 81
First of all, what I am trying to do is NOT the greatest COMMON divisor. I am trying to find the greatest divisor. For example, for the number 12, my greatest divisor will be 6. For the number 15 it'll be 5 and for 17 it'll be 1.
What I did was this with an iteration :
def greatest_divisor(n):
for d in range(n-1,0,-1):
if n % d == 0:
return d
break
greatest_divisor(12)
>6
which runs properly. What I need is the recursive form of this function. If you could come up with something working I appreciate it!
Upvotes: 0
Views: 41
Reputation: 350300
In general you would need fewer iterations if you would find the least divisor (greater than 1) first, and then divide n by that divisor to get the greatest. In that case you don't have to iterate more than up to the square root of n. When there is none found, then return 1.
Here is the iterative solution for that:
def greatest_divisor(n):
for low in range(2, int(n**0.5)+1):
if n % low == 0:
return n // low
return 1
There is really no gain in making this recursive, as that will be just a case of tail recursion:
def greatest_divisor(n, low=2):
if n % low == 0:
return n // low
if low*low > n:
return 1
return greatest_divisor(n, low+1)
Upvotes: 2
Reputation: 148965
First I would start with a mathematical remark: finding the greatest divisor is the same thing as finding the smallest divisor (but 1), and that smallest divisor will be prime. That property could lead to more efficient algorithms if you wanted to search for a great number of values.
Next any iterative method can be rewritten as a recursive one by defining a starting point and a stop condition. It is generally avoided because recursive methods have in impact of the stack and break if you recurse too deeply while iterative methods can only require constant resources.
So here a direct transformation of your own code is:
def r_greatest_divisor(n, cur=None):
if cur is None:
cur = n - 1
if cur <= 1:
return 1
if n % cur == 0:
return cur
return r_greatest_divisor(n, cur - 1)
Upvotes: 1