2015-01-31 67 views
1

我有以下問題。 我試圖從字符串中刪除所有非字母字符(即數字(string.digits),標點符號(string.punctuation),非ascii字符(如φ,χ,ψ等) 這可以是一個簡單的命令一樣輕鬆地完成。快速刪除字符串中的所有非字母字符,python

for i in str: 
    if i not in string.ascii_letters: 
     data1 = str.replace(i,"") 

,或者使用過濾器 不過,我的問題是,我的字符串的長度大約爲20.000.000(幾本書串聯在一起) 現在的情況。 3.000.000個字符,上面的命令花費了大約20分鐘,因此我不敢用20,000.000個字符來嘗試它。 能否請告訴我是否有真正快速的方法來做到這一點?

+0

你是否一次需要所有的角色?如果沒有,你可以使用'itertools.ifilter'。另外,使用'set(string.ascii_letters)'意味着更高效的成員資格測試。 – jonrsharpe 2015-01-31 20:52:08

+2

你的代碼甚至不會像你認爲的那樣工作。你正在運行'str.replace',它返回一個* new *字符串,將它賦值給'data1',然後在下一次找到另一個不在'in string.ascii_letters'中的字符時將結果扔掉。 – roippi 2015-01-31 20:54:58

回答

4

那樣的東西可能最終提高性能,因爲你沒有你的很長的字符串的副本在RAM:

data1 = (c for c in my_string if c in string.ascii_letters) 

情況因人而異,但在我的系統,它需要像6s來過濾20MB的文件,其中包含隨機的字節(含。需要"".join(...)操作要回一個字符串):

>>> data1 = (c for c in my_string if chr(ord(c)) in string.ascii_letters) 
>>> timeit.timeit('"".join(data1)', setup='from __main__ import data1') 
5.96341991424560 

正則表達式替換waaaayy花了更多的時間:

>>> timeit.timeit('re.sub("[^a-zA-Z]","",my_string)', setup='from __main__ import my_string; import re') 
... still running after 90+ minutes... 
2

我覺得正則表達式是爲這種事做......

re.sub("[^a-zA-Z]","",my_string) 
相關問題