2013-04-26 71 views
-7

我在python中編寫csv文件,並且有四個級別的嵌套對象。像如何在Python中爲循環創建高效?

我需要顯示CSV這樣

StudentNameStudentClassSubjectNameSubjectDateSubjectBookNAmeSubjectBookpage

我使用的循環一樣

Just example not actual code

for s in students: 
    for subject in s.subjects: 
     for book in subject.books : 
      writer.writerow(s.name, s.class, subject.name, book.name) 

這工作正常如果我有所有的孩子對象。

但是,當我沒有書或科目,然後循環不起作用。

我不想使用許多if else有沒有什麼辦法來efficently寫這些循環,如果有在for循環的系統沒有行工作

+2

什麼不行?發佈您的實際代碼。 – Blender 2013-04-26 06:58:12

+1

如果沒有科目或書籍,它應該如何工作? – 2013-04-26 06:58:47

+2

它*很難保留一些最低標準的文本格式? – 2013-04-26 07:00:02

回答

4

假設s.subjectsNone或其他一些False值時,有沒有對象,同樣的書籍

for s in students: 
    for subject in s.subjects or []: 
     for book in subject.books or []: 
      writer.writerow(s.name, s.class, subject.name, book.name) 

更一般地,你可以寫

for s in students: 
    for subject in s.subjects if <condition> else []: 
     for book in subject.books if <condition> else []: 
      writer.writerow(s.name, s.class, subject.name, book.name) 

哪裏<condition>是什麼表情有道理

+0

我想這個'm,n在izip_longest(l1,l2,fillvalue = defaultdict())或[]'並且它不工作,其中l1,l2是列表。所以我希望即使兩者都是空的,即使那麼循環應該運行一次 – user2294401 2013-04-26 07:14:00

+2

@ user2294401,所以你的問題確實與你的問題沒有關係。 izip_longest總是返回一個生成器,所以它永遠不會是'False'。另外,使用'fillvalue = defaultdict()'將爲所有fillvalues使用相同的defaultdict,這可能不是您想要的! – 2013-04-26 07:18:11

+0

@ user2294401,所以你希望循環運行一次,即使列表是空的?在這種情況下應該寫出什麼? – 2013-04-26 07:19:38

0

你應該初始化s.subjectssubject.books以空列表。這樣,當您嘗試在代碼中的這些地方或其他地方迭代它們時,您不會遇到錯誤。

+0

如果我這樣做,那麼會發生什麼,如果我有空列表 – user2294401 2013-04-26 06:58:33

+0

@ user2294401什麼都不會發生,循環將不會進入...嘗試它。 – Kai 2013-04-26 07:00:42

+0

有什麼辦法,即使列表是空的,循環只運行一次。我想要的是,如果沒有子元素,那麼循環應該表現得像它不存在和執行下面的其他代碼 – user2294401 2013-04-26 07:29:57

0

用[]初始化您的student.subjects和subject.books,然後它會工作。就像@ user714965所說的那樣。

,或者使用列表理解:

for s in [stu if stu.has_key(subjects) for stu in students]: 
    for subject in [subj if subj.has_key(books) for subj in s.subjects]: 
     lists= [(s.name, s.class, subject.name, book.name) for book in subject.books] 
       print r'\n'.join(r','join(lists)) 

如果你的循環不是很深,嘗試這樣的事情:

fn= s.has_key('subjects') and (lambda s: /do sth. with s/) or (lambda s: /do sth. else with s/) 
在循環

,使用fn像這樣,

[fn(s) for s in students ]