user146068
user146068

Reputation: 21

Recursive Python Function Factorial

Write a recursive Python function called odd_factorial(x) that for input x (x >= 5) calculates 3 × 5 × 7 × . . . × x, if x is odd; or 3 × 5 × . . . × (x − 1) if x is even.

I have the recursion but I am not quite sure how to ensure x >= 5 for the first loop:

def odd_factorial(x):
    if x%2 == 1:
        if x == 3:
            return 3
        else:
            return x*odd_factorial(x-2)
    else:
        x -= 1
        if x == 3:
            return 3
        else:
            return x*odd_factorial(x-2)

Upvotes: 0

Views: 791

Answers (6)

Steffi Keran Rani J
Steffi Keran Rani J

Reputation: 4093

Here is a very simple recursive factorial program using just the odd numbers

#Factorial using Recursion
n = int(input("Enter the n value for Factorial:"))
def factorial(n):
if n<=1:
    return 1
else:
    return n*factorial(n-2)

print(factorial(n))

Upvotes: 0

itzMEonTV
itzMEonTV

Reputation: 20339

Simply complicated :)

def odd_factorial(x, signal=None):
    if x < 5 and signal==None:
        return "number should be greater than 5"
    else:
        if x%2 == 1:
            if x == 3:
                return 3
            else:
                return x*odd_factorial(x-2, signal="r")
        else:
            x -= 1
            if x == 3:
                return 3
            else:
                return x*odd_factorial(x-2, signal="r")

Upvotes: 0

Padraic Cunningham
Padraic Cunningham

Reputation: 180391

add an extra check setting a flag so you catch values entered < 5 if it is the first call of the function, you can also remove the else from your code as you can only return any one line at a time:

def odd_factorial(x, flag=True):
    if x < 5 and  flag:
        return "Only numbers >= 5"
    if x % 2: # or if x & 1
        return x * odd_factorial(x - 2, False) if x != 3 else 3
    x -= 1
    return x * odd_factorial(x - 2, False)

In [32]: odd_factorial(5)
Out[32]: 15

In [33]: odd_factorial(3)
Out[33]: 'Only numbers >= 5'

In [34]: odd_factorial(7)
Out[34]: 105

Upvotes: 0

J_mie6
J_mie6

Reputation: 720

Why not simply change the way it is calculated:

def odd_factorial(x):
    if x%2 == 0:
        x -= 1
    if x == 5:
        return 3*5
    elif x < 5:
        raise ValueError("Input should not be < 5")
    else:
        return x*odd_factorial(x-2)

This is good because you don't repeat yourself as you did before (with the even/odd check) and you still follow the specification!

Upvotes: 0

This will be speedier and cleaner as it does not do conditioning in the actual recursion. It is still a function, albeit with another nested in.

def odd_factorial(x):
    def do_fact(x):
        if x == 3:
            return 3

        return x * do_fact(x - 2)

    if x < 5:
        raise ValueError("X must be at least 5")

    if not x % 2:
        x -= 1

    return do_fact(x)

Running:

>>> odd_factorial(5)
15
>>> odd_factorial(6)
15
>>> odd_factorial(7)
105
>>> odd_factorial(4)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "test.py", line 9, in odd_factorial
    raise ValueError("X must be at least 5")
ValueError: X must be at least 5
>>> odd_factorial(3)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "test.py", line 9, in odd_factorial
    raise ValueError("X must be at least 5")
ValueError: X must be at least 5

Another way is to return 15 for odd_factorial(5) and odd_factorial(6) directly:

def odd_factorial(x):
    if x < 5:
        raise ValueError("x must be at least 5")
    if x % 2 == 0:
        x -= 1     
    if x == 5:
        return 15
    return x * odd_factorial(x - 2)

Upvotes: 1

Ofiris
Ofiris

Reputation: 6141

Use an inner function, saves you an extra parameter:

>>> def odd_factorial(input):
     def odd_factorial_inner(x):
         if x%2 == 1:
             if x == 3:
                 return 3
             else:
                 return x*odd_factorial_inner(x-2)
         else:
             x -= 1
             if x == 3:
                 return 3
             else:
                 return x*odd_factorial_inner(x-2)
     if (input >= 5):
         return odd_factorial_inner(input)
     else:
         print "input is smaller than 5"

>>> odd_factorial(9)
945
>>> odd_factorial(4)
Input is smaller than 5.

Upvotes: 0

Related Questions