는 1000 개 문구가있는 경우, 당신은 문자열있는 그 문구 어떤 찾기 위해 입력 문자열을 검색하는, 당신은 아마 당신은 큰 정규 표현식을 사용에서 얻는 성능에 행복하지 않을거야. trie 구현하기 위해 조금 더 많은 작업이지만, 훨씬 더 효율적입니다 : a|b|c|d|e
주어진 입력 문자열의 각 문자에 5 개 테스트를 수행하는 정규 표현식하는 트라이 하나만 않지만. Plex과 같은 DFA를 생성하는 렉서 (lexer)를 사용할 수도 있습니다.
편집 :
는 오늘 아침을 미루는 것으로 나타났습니다. 이 시도 :
class Trie(object):
def __init__(self):
self.children = {}
self.item = None
def add(self, item, remainder=None):
"""Add an item to the trie."""
if remainder == None:
remainder = item
if remainder == "":
self.item = item
else:
ch = remainder[0]
if not self.children.has_key(ch):
self.children[ch] = Trie()
self.children[ch].add(item, remainder[1:])
def find(self, word):
"""Return True if word is an item in the trie."""
if not word:
return True
ch = word[0]
if not self.children.has_key(ch):
return False
return self.children[ch].find(word[1:])
def find_words(self, word, results=None):
"""Find all items in the trie that word begins with."""
if results == None:
results = []
if self.item:
results.append(self.item)
if not word:
return results
ch = word[0]
if not self.children.has_key(ch):
return results
return self.children[ch].find_words(word[1:], results)
빠른 테스트 (words.txt
이 매우 편리한 것은 주위가하는 BSD 워드 파일 - 그것은 약 240,000 단어 포함) :
>>> t = Trie()
>>> with open(r'c:\temp\words.txt', 'r') as f:
for word in f:
t.add(word.strip())
에 약 15 초 정도 걸립니다 내 기계. 그러나 이것은 거의 순간적 :
>>> s = "I played video games in a drunken haze."
>>> r = []
>>> for i in range(len(s)):
r.extend(t.find_words(s[i:]))
>>> r
['I', 'p', 'play', 'l', 'la', 'lay', 'a', 'ay', 'aye', 'y', 'ye', 'yed', 'e', 'd', 'v', 'video', 'i', 'id', 'ide', 'd', 'de', 'e', 'o', 'g', 'ga', 'gam', 'game', 'a', 'am', 'ame', 'm', 'me', 'e', 'es', 's', 'i', 'in', 'n', 'a', 'd', 'drunk', 'drunken', 'r', 'run', 'u', 'un', 'unken', 'n', 'k', 'ken', 'e', 'en', 'n', 'h', 'ha', 'haze', 'a', 'z', 'e']
예, unken
이 words.txt입니다. 나는 이유를 모른다.
아, 그리고 정규 표현식과 비교하려고 않았다 ...이 작업
>>> import re
>>> with open(r'c:\temp\words.txt', 'r') as f:
p = "|".join([l.strip() for l in f])
>>> p = re.compile(p)
Traceback (most recent call last):
File "<pyshell#250>", line 1, in <module>
p = re.compile(p)
File "C:\Python26\lib\re.py", line 188, in compile
return _compile(pattern, flags)
File "C:\Python26\lib\re.py", line 241, in _compile
p = sre_compile.compile(pattern, flags)
File "C:\Python26\lib\sre_compile.py", line 529, in compile
groupindex, indexgroup
OverflowError: regular expression code size limit exceeded
잘 - 종류. 나는 그 블록 내에서 내가 찾고있는 텍스트와 구획 블록을 가지고있다. 저는 현재 다음과 같은 정규 표현식을 사용하고 있습니다 : >>> text_input = "이것은 첫 번째 구 및 첫 번째 구가" "일 수 있습니다. >>> regex ="첫 번째 구 | 두 번째 구 | 세 번째 구 " > >> p = re.compile (정규식, re.I) >>> p.findall (TEXT_INPUT) [ '제 구문', '제 문구'] –
FWIW는 문법 세트 이해 파이썬 3.0 이상이다. – hughdbrown
@hughdbrown : 나는 새로운 스타일 세트 리터럴 http://docs.python.org/3.1/whatsnew/3.0.html#new-syntax 여기에 모든 것이 평 2에서 수행 될 수를 사용하고, 세트 이해를 사용하지 않았다. x를 사용하여'set (lst)' – SilentGhost