给定两个字符串作为参数返回true iff第一个单词可以通过改变一个字母从第二个单词形成。我接近这个的方式是:
def differ(word_one, word_two):
'''(str, str) -> bool
Returns true iff word_two can be formed from word_one by changing
exactly one letter.
>>> differ('cat', 'bat')
True
>>> differ('word', 'sword')
False
'''
temp_list = []
# If the length of the first string is equal to the length of the
# second string, iterate over the letters in the first string and
# if the letter in the first string does not equal to the letter
# in the second string append the letter to temp_list
if len(word_one) == len(word_two):
for char in word_one:
if char != word_two[word_one.index(char)]:
temp_list.append(char)
if len(temp_list) == 1:
return True
else:
return False
根据描述,我的代码似乎工作得很好但是有更简化的方法吗?
答案 0 :(得分:5)
看起来像一个简单的zip
(加上一些长度检查),没有?
sum(a != b for a, b in zip(word1, word2)) == 1
这确实依赖于在算术上下文中有些模糊的事实,True == 1
和False == 0
。例如True + True + True + False == 3
示例:
>>> def differ(word1, word2):
... return ((len(word1) == len(word2)) and
... (sum(a != b for a, b in zip(word1, word2)) == 1))
...
>>> differ('cat', 'bat')
True
>>> differ('cat', 'hat')
True
>>> differ('cat', 'can')
True
>>> differ('cat', 'car')
True
>>> differ('cat', 'bar')
False
答案 1 :(得分:3)
if len(word_one) == len(word_two):
return sum(c!=d for c,d in zip(word_one, word_two)) == 1
return False # optional - often None will do instead
使用地图的另一种方式。
import operator
def differ(w1, w2):
return len(w1) == len(w2) and sum(map(operator.ne, w1, w2)) == 1
使用sum
的版本的问题在于,即使在开始时已经存在一些差异,它们也会迭代整个字符串。所以有一个短路版本
import operator, itertools
def differ(w1, w2):
it = itertools.imap(operator.ne, w1, w2)
return len(w1) == len(w2) and any(it) and not any(it)