【100个python算法超详细讲解】@谷哥技术

1.问题描述
警察审问4名窃贼嫌疑犯。现在已知,这4人当中仅有一名是窃
贼,还知道这4个人中的每个人要么是诚实的,要么总是说谎。
下面是这4个人给警察的回答。
·?说:“乙没有偷,是丁偷的。”
·乙说:“我没有偷,是丙偷的。”
·丙说:“?没有偷,是乙偷的。”
·丁说:“我没有偷。”
请根据这4个人的回答判断谁是窃贼。
2.问题分析
显然该题是一个逻辑推断问题。已知4个人中的每个人要么是诚实
的,要么总是说谎,那么如何来判断他们到底谁是窃贼呢?
由问题描述可知,?、乙、丙、丁4人中仅有一名窃贼,且这4个
人中每个人要么是诚实的,要么总是说谎。分析?、乙、丙3人所说的
话可以发现,他们每人都说了两句话,即“X没有偷,X偷的”,因此,
不论这三人是否说谎,他们所提到的这两个人中必有一个是窃贼。而
丁只说了他自己没有偷,故无法判断其真假。
假设用变量A、B、C、D分别代表4个人,变量的值为1代表该人是
窃贼,则根据4个人的说法可列出下面的4个条件:
·?说:“乙没有偷,是丁偷的。”——B+D=1 ①
·乙说:“我没有偷,是丙偷的。”——B+C=1 ②
·丙说:“?没有偷,是乙偷的。”——A+B=1 ③
·丁说:“我没有偷。”——A+B+C+D=1 ?
由于?、乙、丙3人的话中都提到了两个人,其中必有一人是小
偷,故在根据他们的话列出条件表达式时,可以不关心谁说的是真
话,谁说的是假话。
由于丁的话无法判断真假,故根据丁的话列出的表达式只反映了4
人中仅有一名是窃贼的条件。
3.算法设计
该问题的关键是使用Python中的逻辑表达式将问题分析中得到的4
个条件表达出来,逻辑表达式如下:
B+D==1 and B+C==1 and A+B==1 ?
条件④表示A、B、C、D中必有一个为1。
在程序中可依次假定?、乙、丙、丁分别为窃贼,代入⑤进行测
试,满足条件⑤的那个人为窃贼,具体如下:
1)先假定?为窃贼,即A=1、B=0、C=0、D=0,代入条件⑤测试
是否成立,若成立则不再对乙、丙、丁进行测试。
2)若不成立,则再假定乙为窃贼,即A=0、B=1、C=0、D=0,代
入条件⑤测试是否成立,若成立则可确定乙为窃贼,不再对丙、丁进行
测试。
3)若不成立,再假定丙为窃贼,即A=0、B=0、C=1、D=0,代入
条件⑤测试是否成立,若成立则可确定丙为窃贼,不再对丁进行测试。
4)若不成立,再假定丁为窃贼,即A=0、B=0、C=0、D=1,代入
条件⑤测试是否成立,若成立则确定丁为窃贼。
4.确定程序框架
程序的流程图如图6.7所示。

Python 小偷钻石问题 找出小偷python_python

5.完整的程序
根据上面的分析,编写程序如下:

#!/usr/bin/python3
# -*- coding: ?TF-8 -*-
#author: liuhefei
#desc: 谁是窃贼
if __name__ == "__main__":
#?、乙、丙、丁分别用A、B、C、D代表。A、B、C、D的值要么为1,要么为0
# 为1表示是窃贼,为0表示不是
# 满足4个条件:B+D=1,B+C=1,A+B=1,A+B+C+D=1
A, B, C, D = 1, 0, 0, 0
for i in range(1, 4+1): #i=1,2,3,4
if B+D == 1 and B+C == 1 and A+B == 1:
break
else:
if i == 1:
A=0
B=1
if i == 2:
B=0
C=1
if i == 3:
C=0
D=1
print("判断结果:")
if i == 1:
print("?是窃贼\n")
if i == 2:
print("乙是窃贼\n")
if i == 3:
print("丙是窃贼\n")
if i == 4:
print("丁是窃贼\n")

 程序说明如下:
·使用变量i控制循环次数,因为要分别对?、乙、丙、丁进行测
试,故循环次数为4。
·输出时根据i的取值来确定输出结果。
6.运行结果
在PyCharm下运行程序,结果如图6.8所示。由运行结果可知,乙
是窃贼。

Python 小偷钻石问题 找出小偷python_网络协议_02