2012-11-30 32 views
3

我有一个函数可以在列表项目过去(小于当前日期)的情况下过滤列表项目。当列表为空时列表理解抛出异常

meetings = [] 
def clean_old(): 
    meetings = [meeting for meeting in meetings if time.mktime(meeting) >= time.localtime()] 

当列表为空时,此代码崩溃。

它为什么会崩溃?它说for meeting in meetings,如果会议是空的,那么一切应该没问题。

我该如何解决这个问题,以及对这种情况的解释是什么?

+3

当初始地被定义会议?它是空的还是未定义的?抛出什么异常? – FogleBird

+0

@FogleBird说什么。 –

+1

[48]:会议= [在会议会议会议用于如果time.mktime(会议)> = time.localtime()] 在[49]:会议 缺货[49]:[] – Tengis

回答

7

我假设你看到这个异常:

UnboundLocalError: local variable 'meetings' referenced before assignment 

什么您遇到这里实际上并没有什么关系列表理解。发生此错误是因为您最初在函数外部定义了meetings,但您正尝试在函数内为其分配一个新值。

当Python看到一个变量被分配了一个函数内的值时,它将它视为一个新变量,特定于该函数。这可以防止函数访问具有相同名称的函数外部的任何变量。

内部,Python是做一些排序的是这样的:

meetings_outside = [] 

def clean_old(): 
    meetings_inside = [meeting for meeting in meetings_inside if time.mktime(meeting) >= time.localtime()] 

你可以理解为什么会失败:meetings_inside是本身来界定。当Python尝试查找meetings_inside的值以开始遍历其内容时,它会失败,因为它尚未分配值。

如何处理这个取决于哪个版本的Python您使用,还有的meetings初始值的定义。

在Python 3,你可以简单地添加nonlocal meetings到您的函数的顶部。这将告诉它你指的是一个名为meetings的现有变量,而不是创建另一个变量。

但是你可能使用Python 2,不具备nonlocal关键字。它确实具有global关键字,它做同样的事情,但只有当meetings在一个模块的顶部级别定义:外的任何其他功能或类。

例如,这将在Python 2的工作,如果你在你的文件没有别的事情:

进口时间

meetings = [] 

def clean_old(): 
    global meetings 
    meetings = [meeting for meeting in meetings if time.mktime(meeting) >= time.localtime()] 

clean_old() 
print meetings 
[] 

但是这不会,因为meetings是一个内部定义功能:

import time 

def main(): 
    meetings = [] 

    def clean_old(): 
     global meetings 
     meetings = [meeting for meeting in meetings if time.mktime(meeting) >= time.localtime()] 

    clean_old() 
    print meetings 

main() 
NameError: global name 'meetings' is not defined 

您将需要解决的问题。最简单的方法是修改分配为:

meetings[:] = [meeting for meeting in meetings if time.mktime(meeting) >= time.localtime()] 

这告诉Python要更换所有的meetings内的值,但不创建一个新的list对象。 (该:语法被称为“切片”和被部分地描述in the Python tutorial。)

+0

我认为这是一个非常优秀的答案。 –

+0

非常感谢! – Lior

相关问题