2011-01-05 4 views
8

짧은 문장의 일부 발췌가 영어인지 아닌지를 간단하게 검색 할 수있는 방법을 찾고 있습니다. 이 문제는 임의의 언어를 탐지하는 것보다 훨씬 쉽습니다. 거기에 어떤 소프트웨어 가이 일을 할 수 있습니까? 나는 파이썬으로 글을 쓰고 있는데, 파이썬 라이브러리를 선호하지만 뭔가 다른 것도 괜찮을 것이다. 나는 구글을 시도했지만 TOS가 자동화 된 쿼리를 허용하지 않는다는 것을 깨달았다.텍스트가 영어인지 여부를 감지 (일괄)

+1

[파이썬 - 유니 코드 문자열 언어 코드를 감지 할 수 있습니까?] (http://stackoverflow.com/questions/4545977/python-can-i-detect-unicode-string-language-code) – ismail

+2

' 그들이 임의의 언어를 구하는 그 실과는 대조적으로, 여기서만 영어를 묻습니다. – user449511

+0

그냥 영어로 잘 작동합니다. – ismail

답변

10

나는 3 선형

http://en.wikipedia.org/wiki/Trigram

당신은 텍스트 위로 이동 한 다음에 가장 많이 사용되는 괘를 감지하는 시도 할 수 있습니다를 사용하여 Enlgish langauge를 감지하는 방법을 읽어 말. 가장 많이 사용되는 것들은 대부분 영어 단어 중 사용과 일치 할 경우, 텍스트는이 루비 프로젝트에보고하려고

영어

에 기록 될 수 있습니다 :

https://github.com/feedbackmine/language_detector

+0

+1 용 Trigams - 매우 멋지다. –

+0

감사!이것은 구현하기 쉬운 생각입니다. 얼마나 효과가 있는지 알아야하는 작은 테스트 텍스트 세트로이 테스트를 신속하게 수행 할 수 있습니다! – user449511

+0

큰 샘플 텍스트가 필요할 것입니다. OP가 그것에 액세스 할 수 없습니다. – marcog

4

편집 : OP는 Google의 서비스 약관에 위배되는 대량으로 텍스트를 처리하기 때문에이 경우에는 작동하지 않습니다.

Google 번역 language detect API을 사용하십시오. 워드 프로세서에서 파이썬 예 :

url = ('https://ajax.googleapis.com/ajax/services/language/detect?' + 
     'v=1.0&q=Hola,%20mi%20amigo!&key=INSERT-YOUR-KEY&userip=INSERT-USER-IP') 
request = urllib2.Request(url, None, {'Referer': /* Enter the URL of your site here */}) 
response = urllib2.urlopen(request) 
results = simplejson.load(response) 
if results['responseData']['language'] == 'en': 
    print 'English detected' 
+0

"Google 언어 감지 API는 사용자 생성 언어 감지에 사용되어야하며 모든 종류의 자동 또는 일괄 검색어는 엄격히 금지됩니다." 질문자가 그가 보았던 서비스 약관을 언급하고있는 이유는 그가 사용자 입력없이 언어를 감지하기를 원한다고 생각합니다. –

+0

@tomlog 아마도 맞을 것입니다. 나는 그가 GT 페이지를 긁어 모으는 것을 언급하고 있다고 생각했다. @user, 사용자가 생성 한 문자열을 처리하는지 여부를 확인할 수 있습니까? – marcog

+0

나는 내 텍스트로 API를 쿼리하여 액세스를 거부하고 내 문제를 깨달았다. 나는 사용자 생성 문자열을 사용하지 않는다. 감사! – user449511

1

입력해도 Google이 아닌 자신만큼 좋은, 자체 사전 트리밍 된 ngram 모델과 함께 제공되는 Apache Nutch LanguageIdentifier를 사용하여 좋은 결과를 얻었습니다. 나는 여러 언어로 된 실제 데이터의 큰 (50GB pdf, text-mostly) 코퍼스에서 꽤 좋은 결과를 얻었다.

그것은 Java이지만, 파이썬에서 다시 구현하려면 ngram 프로파일을 다시 읽을 수 있어야합니다.

1

Google 번역 API v2 allows automated queries하지만 자유롭게 사용할 수있는 API 키를 사용해야합니다 (Google APIs console).

텍스트 당신이 질문 Python - can I detect unicode string language code?에 내 대답에서 detect_language_v2() 기능 (즉,이 API를 사용하여) 사용할 수있는 영어입니다 여부를 감지하려면

if all(lang == 'en' for lang in detect_language_v2(['some text', 'more text'])): 
    # all text fragments are in English 
0

는 최근 이에 대한 해결책을 썼다. 내 솔루션은 어리석은 증거가 아니며 많은 양의 텍스트에 대해 계산적으로 실행 가능할 것이라고 생각하지 않지만 작은 문장에서는 잘 작동하는 것으로 보입니다.

  1. "UNGHSYINDJFHAKJSNFNDKUAJUD"
목표는 다음 2. 아니지만 1. 아마 영어는 것을 확인하는 것입니다

을 "LETMEBEGINBYSAYINGTHANKS"

은 두 텍스트 문자열이 있다고 가정 . 직관적으로, 내 마음이 결정하는 방식은 문장 (LET, ME, BEGIN 등)에서 영어 단어의 경계를 찾는 것입니다. 그러나 중복되는 단어 (BE, GIN, BEGIN, SAY, SAYING, THANK, THANKS 등)가 있기 때문에 이것은 계산적으로 간단하지 않습니다.

  1. { known English words }{ all substrings of the text of all lengths }의 교회법을 가지고 :

    내 방법은 다음을 수행합니다.

  2. 단어의 끝 뒤의 문자의 시작 위치로 향하는 모서리가있는 문장의 단어 시작 위치가 위치하는 정점 그래프를 구성합니다. 예를 들어 (0)L이므로 "LET"은 (0) -> (3)으로 표시 할 수 있습니다. 여기에서 (3)M이므로 "내게 맡기십시오".
  3. 0에서 사이의 가장 큰 정수 n을 찾고 인덱스 0에서 인덱스 n까지 단순한 직접 경로가 존재하는지 확인하십시오.
  4. 해당 숫자를 으로 나누어 텍스트의 몇 퍼센트가 연속 영어 단어로 보는지 대략적인 아이디어를 얻으십시오.

내 코드는 단어 사이에 공백이 없다고 가정하지만, 공간을 상당히 쉽게 고려할 수 있다고 생각합니다. 내 코드가 작동하려면 영어 단어 목록 파일이 필요합니다. 나는 here에서 하나를 얻었지만 그러한 파일을 사용할 수 있습니다.이 방법으로이 기술을 다른 언어로 확장 할 수 있다고 상상합니다. 여기

코드입니다 :

from collections import defaultdict 

# This function tests what percent of the string seems to me to be maybe 
# English-language 
# We use an English words list from here: 
# https://github.com/first20hours/google-10000-english 
def englishness(maybeplaintext): 
    maybeplaintext = maybeplaintext.lower() 
    f = open('words.txt', 'r') 
    words = f.read() 
    f.close() 
    words = words.lower().split("\n") 
    letters = [c for c in maybeplaintext] 
    # Now let's iterate over letters and look for some English! 
    wordGraph = defaultdict(list) 
    lt = len(maybeplaintext) 
    for start in range(0, lt): 
     st = lt - start 
     if st > 1: 
      for length in range(2, st): 
       end = start + length 
       possibleWord = maybeplaintext[start:end] 
       if possibleWord in words: 
        if not start in wordGraph: 
         wordGraph[start] = [] 
        wordGraph[start].append(end) 
    # Ok, now we have a big graph of words. 
    # What is the shortest path from the first letter to the last letter, 
    # moving exclusively through the English language? 
    # Does any such path exist? 
    englishness = 0 
    values = set([a for sublist in list(wordGraph.values()) for a in sublist]) 
    numberVertices = len(set(wordGraph.keys()).union(values)) 
    for i in range(2, lt): 
     if isReachable(numberVertices, wordGraph, i): 
      englishness = i 
    return englishness/lt 

# Here I use my modified version of the technique from: 
# https://www.geeksforgeeks.org/ 
# find-if-there-is-a-path-between-two-vertices-in-a-given-graph/ 
def isReachable(numberVertices, wordGraph, end): 
    visited = [0] 
    queue = [0] 
    while queue: 
     n = queue.pop(0) 
     if n == end or n > end: 
      return True 
     for i in wordGraph[n]: 
      if not i in visited: 
       queue.append(i) 
       visited.append(i) 
    return False 

그리고 여기 처음 내가 준 예제 I/O입니다 :

In [5]: englishness('LETMEBEGINBYSAYINGTHANKS') 
Out[5]: 0.9583333333333334 

In [6]: englishness('UNGHSYINDJFHAKJSNFNDKUAJUD') 
Out[6]: 0.07692307692307693 

그럼 약 말해서, 나는 LETMEBEGINBYSAYINGTHANKS 영어 96 % 확실하고 있다고하고, 8 %는 UNGHSYINDJFHAKJSNFNDKUAJUD이 영어임을 확신합니다. 어느 것이 옳은 소리!

텍스트를 훨씬 더 큰 부분으로 확장하려면 짧은 부분 문자열을 서브 샘플링하고 "영어"를 확인하는 것이 좋습니다. 희망이 도움이!

+0

나의 교수는 내 기술이 그래프를 통해 앞으로 나아가 기보다는 뒤로 나아감으로써 개선 될 수 있다는 것을 관찰했다. 또한 불필요한 검사를 없애기 위해 bisect 검색 방법을 약간 개선 할 수 있다고 생각합니다. 날씨가 좋든 그렇지 않든 입력의 영어 길이의 빈도 분포에 따라 가능성이 높아집니다. –

관련 문제