2015-04-06 76 views
0

我有一個我想要過濾掉csv的東西的列表,我試圖找出一個pythonic的方式來做到這一點。 EG,這是我在做什麼:在字符串列表中沒有任何項目Python

with open('output.csv', 'wb') as outf: 
    with open('input.csv', 'rbU') as inf: 
     read = csv.reader(inf) 
     outwriter = csv.writer(outf) 
     notstrings = ['and', 'or', '&', 'is', 'a', 'the'] 
     for row in read: 
      (if none of notstrings in row[3]) 
       outwriter(row) 

我不知道要放什麼東西在括號(或者,如果有去這個更好的整體方式)。

+0

你是說如果第4列包含任何這些詞,你想排除一行? –

+0

'row [3]'中有什麼樣的值?這是一句話嗎?是否有標點符號?應該只有整個單詞匹配? –

+0

不,只是第3列。此外,第3行是*假設*是一個名稱,但我正在慢慢地創建一個過濾器列表,以避免非名稱(更好太熱心,而不是熱心)。但是,我更多地使用這個來學習最好的方法,而不是特定於這個應用程序。 – Xodarap777

回答

2

可以使用any() function來測試每個單詞在列表中對列:

if not any(w in row[3] for w in notstrings): 
    # none of the strings are found, write the row 

如果這些字符串沒有出現在row[3]這會成真。它將匹配子串,但是,例如,false-positive將與'a' in 'false-positive匹配。

投入方面:

with open('output.csv', 'wb') as outf: 
    with open('input.csv', 'rbU') as inf: 
     read = csv.reader(inf) 
     outwriter = csv.writer(outf) 
     notstrings = ['and', 'or', '&', 'is', 'a', 'the'] 
     for row in read: 
      if not any(w in row[3] for w in notstrings): 
       outwriter(row) 

如果需要兌現字邊界則正則表達式將是一個更好的主意在這裏:

notstrings = re.compile(r'(?:\b(?:and|or|is|a|the)\b)|(?:\B&\B)') 
if not notstrings.search(row[3]): 
    # none of the words are found, write the row 

我創建了一個Regex101 demo的表達演示它是如何工作的。它有兩個分支:

  • \b(?:and|or|is|a|the)\b - 匹配提供的列表中的話他們在起點,終點,或者非單詞字符(標點符號,空格等)\B&\B之間
  • - 比賽&字符,如果在開始,結束或非單詞字符之間。您不能在這裏使用\b,因爲&本身不是一個單詞字符。
+0

如何使用\ ba \ b來避免誤報? r'\ ba \ b'足夠嗎? – Xodarap777

+0

@ Xodarap777:這對'&'不起作用,因爲它不是一個單詞字符。剩下的就足夠了。你可以用一個正則表達式來執行沒有'any()'的測試,一步:'r'\ b(和|或| is | a | the)\ b''。我會在'&'裏看看混音。 –

1

您可以使用集合。在這段代碼中,我將你的列表轉換成一個集合。我將你的row[3]轉換成一組單詞,然後檢查兩組之間的交集。如果沒有交集,那意味着沒有任何字符串在row[3]

使用集合,您確保只匹配單詞而不匹配單詞的部分。

with open('output.csv', 'wb') as outf: 
    with open('input.csv', 'rbU') as inf: 
     read = csv.reader(inf) 
     outwriter = csv.writer(outf) 
     notstrings = set(['and', 'or', '&', 'is', 'a', 'the']) 
     for row in read: 
      if not notstrings.intersection(set(row[3].split(' '))): 
       outwriter(row) 
+0

這種方法避免了任何()的誤報嗎? – Xodarap777

+0

它應該,是的。 –

+0

這就要求'row [3]'中只有空格和單詞;如果涉及標點符號,它將不起作用。 –

相關問題