2014-02-14 4 views
0

for 루프는 실행 시간에 있어서는 상당히 비쌉니다. 나는 교정 알고리즘을 만들고 피터 노르 비그의 철자 교정 코드를 사용했습니다. 나는 그것을 약간 수정했고 수천 개의 단어에 대한 최적화를 실행하는데 너무 오래 걸린다는 것을 깨달았습니다.실행 속도 향상, 파이썬

알고리즘은 1 및 2 편집 거리를 확인하고 수정합니다. 나는 그것을 만들었다 3. 그래서 시간이 늘어날 수 있습니다 (확실하지 않습니다). 여기에 가장 높은 발생 단어를 기준으로 사용되는 말의 일부입니다

def correct(word): 
    candidates = (known([word]).union(known(edits1(word)))).union(known_edits2(word).union(known_edits3(word)) or [word]) # this is where the problem is 

    candidate_new = [] 
    for candidate in candidates: #this statement isnt the problem 
     if soundex(candidate) == soundex(word): 
      candidate_new.append(candidate) 
    return max(candidate_new, key=(NWORDS.get)) 

그리고 for candidate in candidates는 실행 시간을 증가 문처럼 보인다. peter norvig의 코드를 쉽게 볼 수 있습니다. here을 클릭하십시오.
문제를 파악했습니다. 그것은 실행 시간이 3 배 증가 edits3 내부 루프 (3)이 있다는 것을

def known_edits3(word): 
    return set(e3 for e1 in edits1(word) for e2 in edits1(e1) 
             for e3 in edits1(e2) if e3 in NWORDS) 

그것은 볼 수있다, 문

candidates = (known([word]).union(known(edits1(word))) 
      ).union(known_edits2(word).union(known_edits3(word)) or [word]) 

에 있습니다. edits2에는 for 루프가 2 개 있습니다. 그래서 이것은 범인입니다.

어떻게 표현을 최소화합니까? itertools.repeat이 도움이 될 수 있습니까 ??

+0

* 무엇보다 * 실행 시간이 증가합니까? –

+1

후보 목록을 먼저 해보고 그 점이 개선되는지 봅니다 :'candidate_new = [soundex (후보자) == soundex (단어)]이면 후보자 후보' – Evert

+0

@Evert 나는 궁금하지만, 왜 목록 이해력 측정 가능한 영향은 있습니까? –

답변

2

여기에 성능을 향상하는 방법 몇 :

  • 이 코드가 줄일 각 반복
  • 에서 같은 일을 계산하지 마십시오

    1. 사용 지능형리스트 (또는 발전기) :

      def correct(word): 
          candidates = (known([word]).union(known(edits1(word)))).union(known_edits2(word).union(known_edits3(word)) or [word]) 
      
          # Compute soundex outside the loop 
          soundex_word = soundex(word) 
      
          # List compre 
          candidate_new = [candidate for candidate in candidates if soundex(candidate) == soundex_word] 
      
          # Or Generator. This will save memory 
          candidate_new = (candidate for candidate in candidates if soundex(candidate) == soundex_word) 
      
          return max(candidate_new, key=(NWORDS.get)) 
      

      또 다른 개선점은 e MAX 후보

      def correct(word): 
          candidates = (known([word]).union(known(edits1(word)))).union(known_edits2(word).union(known_edits3(word)) or [word]) 
      
          soundex_word = soundex(word) 
          max_candidate = None 
          max_nword = 0 
          for candidate in candidates: 
           if soundex(candidate) == soundex_word and NWORDS.get(candidate) > max_nword: 
            max_candidate = candidate 
          return max_candidate 
      
    +0

    안녕하세요, 감사합니다. 그러나 내가 자세히 보았을 때 나는 그 문제가 다른 것임을 깨달았다. 내 질문을 확인, 나는 그것을 편집했습니다. –