Python 递归检查奇数或偶数

Python 递归检查奇数或偶数,python,recursion,Python,Recursion,在此代码中: def is_even(x): if x == 0: return True else: return is_odd(x-1) def is_odd(x): return not is_even(x) print(is_even(2)) print(is_odd(2)) 我脑子里一直在想这个,不知道它是怎么工作的。在我看来,中的x最终是偶数(x)每次都会返回True。但是,当我运行代码时,它工作得非常好,并相应地返回True和False。有人能解释

在此代码中:

def is_even(x):
  if x == 0:
    return True
  else:
    return is_odd(x-1)

def is_odd(x):
  return not is_even(x)

print(is_even(2))
print(is_odd(2))
我脑子里一直在想这个,不知道它是怎么工作的。在我看来,
中的
x
最终是偶数(x)
每次都会返回
True
。但是,当我运行代码时,它工作得非常好,并相应地返回
True
False
。有人能解释一下这是怎么发生的吗

我理解递归的基本概念,并且完全理解著名的阶乘示例是如何工作的。然而,这件事让我很难理解


现在感觉自己无能…

像在大多数情况下一样,在执行之后简单地包含
print
s可能会有所帮助:

def is_even(x):
    print('check if {} is even'.format(x))
    if x == 0:
        return True
    else:
        return is_odd(x-1)

def is_odd(x):
    print('check if {} is odd'.format(x))
    return not is_even(x)
那么在你的情况下:

>>> print(is_even(2))
check if 2 is even
check if 1 is odd
check if 1 is even
check if 0 is odd
check if 0 is even
True

>>> print(is_odd(2))
check if 2 is odd
check if 2 is even
check if 1 is odd
check if 1 is even
check if 0 is odd
check if 0 is even
False

所以基本上它会递减这个数字,直到
0
。关键是在
奇数
调用中累积了多少
not
s。如果是偶数的
not
s,那么结果将是
True
,否则
False

这是真的;递归应该在
is\u偶数
内结束

当这种情况发生时,您将知道您拥有的数字是
0

现在让我们回顾一下。此最终状态将通过两种情况实现-直接调用
为偶数(0)
或从
调用为奇数(0)
。在第一种情况下,结果都很好。在第二种情况下-结果将返回到
is_odd
函数,并被否定,因此将为falsy-给出正确的结果

现在,缺少的部分来了-递归:为了达到这种状态,我们需要每次减少参数,通过相反的函数传递它-这正是我们通过
return is_odd(x-1)
得到的结果


注意:这个递归最终会导致
返回的值
True
的一系列否定。此链的长度为
x
,其中
x
是您的号码,因此在通信中为奇数或偶数

因此,以下代码也会这样做(缺少
是很奇怪的
很好的副作用):


在找到基本情况之前,分解递归关系总是有帮助的

is_even(2) => return is_odd(1) 
           => return not is_even(1) 
           => return not is_odd(0)
           => return not not is_even(0)
           => return not not True
           => return True            ---- (1)

一般来说,从递归函数中,很容易观察到
是偶数(n)
将返回
[不是…n次]真值
,而
是奇数(n)
将返回
[不是…n-1次]真值
。因此,
not
s的数量以及最终表达式取决于
n
(aha!)。嗯,这当然是一种迂回的方式来询问

n % 2 == 0

我认为所有其他答案都很好,但理解这个问题最简单的方法可能是答案被“not”ed的次数。每次它通过is_odd函数时,not将被添加到最终答案中。True将始终返回,但对于偶数,总是有偶数个Not相互抵消,但是对于奇数,它们总是有奇数个Not,因此返回false。

添加两个
print
语句,您将看到它在做什么:

from __future__ import print_function

def is_even(x):
    if x == 0:
        print('True')
        return True
    else:
        return is_odd(x-1)

def is_odd(x):
    print('not', end=' ')
    return not is_even(x)

>>> is_even(5)
not not not not not True
False
>>> is_odd(5)
not not not not not not True
True

但不要在负数上尝试这些方法……:)尝试在一张纸上写入输出如果调用
是偶数(3)
,最终执行的递归调用之一将是
是偶数(0)
,但尽管该递归调用将返回True,但这不是
是偶数(3)
将返回的结果。@MSeifert只需将
x
更改为
abs(x)
到处都可以,OP也可以。为什么你认为
是偶数
总是会返回
真值
?如果你连自己的想法都没有弄清楚,还没有把它写下来,那么我们就不可能解释出哪里出了问题。这让我们不禁要问,你是否真的想清楚了。作为软件开发人员,我们必须有能力批评我们自己的思维(有时是我们思维的缺失)。恐怕我必须投反对票,不这样做。此外,问题没有标记为python-3.x,因此最好在顶部包含一个来自未来的导入打印函数的
n % 2 == 0
from __future__ import print_function

def is_even(x):
    if x == 0:
        print('True')
        return True
    else:
        return is_odd(x-1)

def is_odd(x):
    print('not', end=' ')
    return not is_even(x)

>>> is_even(5)
not not not not not True
False
>>> is_odd(5)
not not not not not not True
True