在 python 中结合 yield 和 if/else 循环
combine yield with if/else loop in python
我想在法语单词列表中连接两个用星号 (*) 分隔的单词。加入这些词后,我想检查这个词是否存在于法语词典中。如果是这样,连接的单词应该保留在列表中,如果不是,则应该附加到另一个列表中。我在我的代码中使用了 yield (我是这个函数的新手)但是我的嵌套 if/else 循环有问题。任何人都可以帮助我实现我的目标吗?我不成功的代码如下:
words = ['Bien', '*', 'venue', 'pour', 'les','engage', '*', 'ment','trop', 'de', 'YIELD', 'peut','être','contre', '*', 'productif' ]
with open ('Fr-dictionary.txt') as fr:
dic = word_tokenize(fr.read().lower())
l=[ ]
def join_asterisk(ary):
i, size = 0, len(ary)
while i < size-2:
if ary[i+1] == '*':
if ary[i] + ary[i+2] in dic:
yield ary[i] + ary[i+2]
i+=2
else: yield ary[i]
i+=1
l.append(ary[i] + ary[i+2])
if i < size:
yield ary[i]
print(list(join_asterisk(words)))
好像是这几行:
i+=1
l.append(ary[i] + ary[i+2])
缩进不够,因此不涉及else
。这意味着每对中间带有 * 的单词都将附加到 l
,而不仅仅是不在 dic
.
中的单词对
你不是在找这样的东西吗:
def join_asterisk(ary):
i, size = 0, len(ary)
while i < size-2:
if ary[i+1] == '*':
if ary[i] + ary[i+2] in dic:
yield ary[i] + ary[i+2]
i+=2
else:
yield ary[i]
i+=1
l.append(ary[i] + ary[i+2])
if i < size:
yield ary[i]
'else' 块遵循相同的规则。
例如,在 'if'、'elif'、'else' 或 'while' 子句的同一行中添加表达式是可行的,但如果您想要的不仅仅是表达式associated with clause 你必须使用缩进或用';'分隔表达式像这样:
while 1:print(9,end='');print(8)
生成器非常适合此用例,您可以将生成器视为一个函数,它将一个接一个地为您提供产生的值,而不是一次全部提供(如 return 那样)。换句话说,您可以将其视为一个不在内存中的列表,只有在被要求时您才会获得下一个元素的列表。另请注意,生成器只是构建 iterators.
的一种方式
在您的情况下,这意味着您不必构建列表 l
来跟踪正确的单词,因为生成器 join_asterisk
会为您生成正确的单词。您需要做的是遍历此生成器将产生的所有值。这正是 list(generator)
会做的,它将通过遍历生成器的所有值来构建一个列表。
最终代码将如下所示:
# That look better to me (just in case you change it later)
word_separator = '*'
words = ['Bien', word_separator, 'venue', 'pour', 'les','engage', word_separator, 'ment','trop', 'de', 'YIELD', 'peut', word_separator, "tard"]
# Fake dictionary
dic = {"Bienvenue", "pour", "les", "engagement", "trop", "de", "peut", "peut-être"}
def join_asterisk(ary):
for w1, w2, w3 in zip(words, words[1:], words[2:]):
if w2 == word_separator:
word = w1 + w3
yield (word, word in dic)
elif w1 != word_separator and w1 in dic:
yield (w1, True)
correct_words = []
incorrect_words = []
for word, is_correct in join_asterisk(words):
if is_correct:
correct_words.append(word)
else:
incorrect_words.append(word)
print(correct_words)
print(incorrect_words)
这输出
['Bienvenue', 'pour', 'les', 'engagement', 'trop', 'de']
['peuttard']
另请注意,您可以使用列表理解而不是使用 for 循环来填充两个列表:
correct_words = [w for w, correct in join_asterisk(words) if correct]
incorrect_words = [w for w, correct in join_asterisk(words) if not correct]
我想在法语单词列表中连接两个用星号 (*) 分隔的单词。加入这些词后,我想检查这个词是否存在于法语词典中。如果是这样,连接的单词应该保留在列表中,如果不是,则应该附加到另一个列表中。我在我的代码中使用了 yield (我是这个函数的新手)但是我的嵌套 if/else 循环有问题。任何人都可以帮助我实现我的目标吗?我不成功的代码如下:
words = ['Bien', '*', 'venue', 'pour', 'les','engage', '*', 'ment','trop', 'de', 'YIELD', 'peut','être','contre', '*', 'productif' ]
with open ('Fr-dictionary.txt') as fr:
dic = word_tokenize(fr.read().lower())
l=[ ]
def join_asterisk(ary):
i, size = 0, len(ary)
while i < size-2:
if ary[i+1] == '*':
if ary[i] + ary[i+2] in dic:
yield ary[i] + ary[i+2]
i+=2
else: yield ary[i]
i+=1
l.append(ary[i] + ary[i+2])
if i < size:
yield ary[i]
print(list(join_asterisk(words)))
好像是这几行:
i+=1
l.append(ary[i] + ary[i+2])
缩进不够,因此不涉及else
。这意味着每对中间带有 * 的单词都将附加到 l
,而不仅仅是不在 dic
.
你不是在找这样的东西吗:
def join_asterisk(ary):
i, size = 0, len(ary)
while i < size-2:
if ary[i+1] == '*':
if ary[i] + ary[i+2] in dic:
yield ary[i] + ary[i+2]
i+=2
else:
yield ary[i]
i+=1
l.append(ary[i] + ary[i+2])
if i < size:
yield ary[i]
'else' 块遵循相同的规则。
例如,在 'if'、'elif'、'else' 或 'while' 子句的同一行中添加表达式是可行的,但如果您想要的不仅仅是表达式associated with clause 你必须使用缩进或用';'分隔表达式像这样:
while 1:print(9,end='');print(8)
生成器非常适合此用例,您可以将生成器视为一个函数,它将一个接一个地为您提供产生的值,而不是一次全部提供(如 return 那样)。换句话说,您可以将其视为一个不在内存中的列表,只有在被要求时您才会获得下一个元素的列表。另请注意,生成器只是构建 iterators.
的一种方式在您的情况下,这意味着您不必构建列表 l
来跟踪正确的单词,因为生成器 join_asterisk
会为您生成正确的单词。您需要做的是遍历此生成器将产生的所有值。这正是 list(generator)
会做的,它将通过遍历生成器的所有值来构建一个列表。
最终代码将如下所示:
# That look better to me (just in case you change it later)
word_separator = '*'
words = ['Bien', word_separator, 'venue', 'pour', 'les','engage', word_separator, 'ment','trop', 'de', 'YIELD', 'peut', word_separator, "tard"]
# Fake dictionary
dic = {"Bienvenue", "pour", "les", "engagement", "trop", "de", "peut", "peut-être"}
def join_asterisk(ary):
for w1, w2, w3 in zip(words, words[1:], words[2:]):
if w2 == word_separator:
word = w1 + w3
yield (word, word in dic)
elif w1 != word_separator and w1 in dic:
yield (w1, True)
correct_words = []
incorrect_words = []
for word, is_correct in join_asterisk(words):
if is_correct:
correct_words.append(word)
else:
incorrect_words.append(word)
print(correct_words)
print(incorrect_words)
这输出
['Bienvenue', 'pour', 'les', 'engagement', 'trop', 'de']
['peuttard']
另请注意,您可以使用列表理解而不是使用 for 循环来填充两个列表:
correct_words = [w for w, correct in join_asterisk(words) if correct]
incorrect_words = [w for w, correct in join_asterisk(words) if not correct]