有没有可用于迭代for循环而无需执行迭代器的关键字?我知道可以通过使用while
循环并手动迭代而无需这样的命令来执行此操作,但是在这种情况下,如果我可以仅使用for
循环,它将大大简化操作,因为没有迭代就继续是例外,而不是规则。 (完成该操作后,将会添加更多的条件,所有这些都需要迭代)。这是我的代码(或者,到目前为止我写的):
for line in file_as_list:
response = input(line)
if response.lower() == 'help':
self.show_command_list()
response = input(line)
if response.lower() == 'loc':
self.show_location(file_as_list, location)
response = input(line)
if response.lower() == 'exit':
save_changes = input('Would you like to save the changes you have made? (Y/N) ')
while (save_changes.upper() != 'Y') & (save_changes.upper() != 'N'):
save_changes = input('That is not a valid response. Try again. ')
if save_changes.upper() == 'N':
temp = file_as_list
print('Changes were not saved.')
else:
for line in file_as_list[location:]:
temp.append(line)
print('Changes were saved.')
break
if response.lower() == 'inline':
line += ' //' + input(line + ' //')
print('Line generated: ' + line)
location += 1
temp.append(line)
答案 0 :(得分:2)
我认为您需要两个嵌套循环。尝试这样的事情:
for line in file_as_list: # outer loop
while True: # inner loop
response = input(line).lower()
if response == 'help': # these two options don't exit the inner loop
...
elif response == 'loc': # so they won't consume a line from the for loop
...
else:
break
if response == 'exit': # these other two conditions are outside the while loop
...
elif response == 'inline': # so a new line will be fetched after they run
...
如果满足前两个条件中的任何一个,则内部循环将继续运行而无需更改line
。仅当break
被命中时,内循环才会结束,其他条件也将得到测试。他们做完事情后,随着line
循环继续迭代,将为for
分配一个新值。
与您的主要问题无关,我还更改了input
行,以便在将输入保存到lower
之前立即在输入上调用response
。这意味着条件不需要继续重复调用它。您的代码并没有错,但是如果您从不关心用户的大小写,立即将其扔掉可以简化操作。
答案 1 :(得分:1)
您可以使用类似的显式迭代器
... else {
$mysqli->error; // log this and/or react to it somehow
}
,依此类推。只要确保正确处理行数不足的情况即可!
答案 2 :(得分:0)
您有两种类型的命令:一种用于推进迭代器的命令,另一种不用于执行迭代器的命令。您也可以将其称为动作vs描述性命令。从概念上讲,您最好的选择是拥有一个while
循环,该循环将继续寻找输入,直到您收到操作命令为止。此while
循环将存在于现有for
循环中。
这样做的好处是,目前无法重复使用“ help”和“ loc”之类的描述性命令,但您可能希望重复使用它们。
我建议的另一个决定是使用不同的功能来实现每个命令。通过为命令提供一致的界面,可以使代码更易于维护和理解。通过将命令注册到字典中,可以使查找更快,更灵活。
以下概念具有一堆函数,这些函数返回三态布尔值和更新。如果命令希望停留在当前行,则布尔值为True,否则为False。没有退出。行更新通常只是输入。
# in __init__
...
self.command_map = {
'help': self.help,
'loc': , self.loc,
'exit': self.exit,
'inline': self.inline,
}
self.temp = []
...
def help(self, file_as_list, location, line):
self.show_command_list()
return True, line
def loc(self, file_as_list, location, line):
self.show_location(file_as_list, location)
return True, line
def exit(self, file_as_list, location, line):
save_changes = ''
while len(save_changes) != 1 or save_changes.upper() not in 'YN':
save_changes = input('Would you like to save the changes you have made? (Y/N) ')
if save_changes.upper() == 'N':
self.temp = file_as_list
print('Changes were not saved.')
else:
self.temp.extend(file_as_list[location:])
print('Changes were saved.')
return None, line
def inline(self, file_as_list, location, line):
line += ' //' + input(line + ' //')
print('Line generated: ' + line)
return True, line
def process(self):
for location, line in enumerate(file_as_list):
stay = True
while stay:
response = input(line)
command = command_map.get(response.casefold())
if command is None:
print(f'Command "{response}" not found. Try again')
else:
stay, line = command(file_as_list, location, line)
if stay is None:
break
self.temp.append(line)
鉴于command_map
,您可以轻松完成很多事情:例如,您可以重新实现show_command_list
以使用sorted(command_map.keys())
做某事。我相信您可以看到将命令添加到列表中相对容易。您不必重复样板代码,只需小心输入和返回值即可。
如果您不喜欢嵌套循环的想法,则手动迭代此构造也容易得多:
def process(self):
stay = False
iterator = enumerate(file_as_list)
while True:
if not stay:
try:
location, line = next(iterator)
except StopIteration:
break
response = input(line)
command = command_map.get(response.casefold())
if command is None:
print(f'Command "{response}" not found. Try again')
stay = True
else:
stay, line = command(file_as_list, location, line)
if stay is None:
break
if not stay:
self.temp.append(line)
如您所见,此方法需要针对各种条件进行更多特殊处理。