Правильно ли я передаю строку в библиотеку python? - PullRequest
0 голосов
/ 29 января 2010

Я использую библиотеку Python под названием Guess Language: http://pypi.python.org/pypi/guess-language/0.1

"justwords" - это строка с текстом Unicode. Я вставляю его в пакет, но он всегда возвращает английский, хотя веб-страница на японском языке. Кто-нибудь знает почему? Я правильно не кодирую?

§ç©ºéå
¶ä»æ¡å°±æ²æéç¨®å¾                                é¤ï¼æ以ä¾é裡ç¶ç
éäºï¼åæ­¤ç°å¢æ°£æ°¹³åèµ·ä¾åªè½ç®âå¾å¥½âé常好âåå                 ¶æ¯è¦é»é¤ï¼é¨ä¾¿é»çé»ã飲æãä¸ææ²»ç­åä¸å                                     便å®ï¼æ¯æ´è¥ç   äºï¼æ³æ³é裡以å°é»ãæ¯è§ä¾èªªä¹è©²æpremiumï¼åªæ±é¤é»å¥½å就好äºã<br /><br />é¦åç¾ï¼æ以就é»åå®æ´ç         æ­£è¦åä¸ä¸å
ä¸ç                           å¥é¤å§ï¼å



justwords = justwords.encode('utf-8')
true_lang =  str(guess_language.guessLanguage(justwords))
print true_lang

Редактировать: Спасибо, ребята, за вашу помощь. Это обновление проблемы.

Я пытаюсь «угадать» язык этого: http://feeds.feedburner.com/nchild

По сути, в Python я получаю htmlSource. Затем я удаляю теги с помощью BeautifulSoup. Затем я передаю его в библиотеку, чтобы получить язык. Если я не буду кодировать (utf-8), то возникнут ASCII-ошибки. Итак, это обязательно.

soup = BeautifulStoneSoup(htmlSource)
justwords = ''.join(soup.findAll(text=True))
justwords = justwords.encode('utf-8')
true_lang =  str(guess_language.guessLanguage(justwords))

Ответы [ 3 ]

7 голосов
/ 30 января 2010

Глядя на главную страницу, он говорит "" "Обнаруживает более 60 языков: греческий (el), корейский (ko), японский (ja), китайский (zh) и все языки, перечисленные в каталоге триграмм." " «

Он не использует триграммы для этих 4 языков; он зависит от того, какие блоки скриптов присутствуют во входном тексте. Глядя на исходный код:

if "Katakana" in scripts or "Hiragana" in scripts or "Katakana Phonetic Extensions" in scripts:
    return "ja"

if "CJK Unified Ideographs" in scripts or "Bopomofo" in scripts \
        or "Bopomofo Extended" in scripts or "KangXi Radicals" in scripts:
    return "zh"

Чтобы имя сценария, такое как Katakana или Hiragana, отображалось в scripts, такие символы должны составлять 40% или более входного текста (после нормализации, которая удаляет не алфавитные символы и т. Д.). Вполне возможно, что для некоторых текстов на японском языке пороговое значение составляет менее 40%. ОДНАКО, если бы это была проблема с вашим текстом, я ожидал бы, что он будет иметь более 40% кандзи (унифицированных идеографов CJK) и, следовательно, должен возвращать "zh" (китайский).

Обновление после некоторых экспериментов, включая вставку оператора печати, чтобы показать, какие блоки сценария были обнаружены с каким процентом:

Предположительно типичная новость с сайта газеты Asahi:

 49.3 Hiragana
  8.7 Katakana
 42.0 CJK Unified Ideographs
result ja

Предположительно, нетипичное то же самое:

 35.9 Hiragana
 49.2 CJK Unified Ideographs
 13.3 Katakana
  1.6 Halfwidth and Fullwidth Forms
result zh

(Похоже, было бы неплохо основывать тест на общем содержании (хирагана + катакана))

Результат проталкивания необработанной первой страницы (XML, HTML, всего) через механизм:

  2.4 Hiragana
  6.1 CJK Unified Ideographs
  0.1 Halfwidth and Fullwidth Forms
  3.7 Katakana
 87.7 Basic Latin
result ca

Высокий процент базовой латиницы, конечно же, связан с разметкой. Я не исследовал то, что заставило его выбрать «ca» (каталанский) по сравнению с любым другим языком, который использует Basic Latin, включая английский. Однако напечатанный тобой гоббл не содержит никаких признаков, включая разметку.

Конец обновления

Обновление 2

Вот пример (2 заголовка и следующие 4 абзаца из этой ссылки ), где около 83% символов - восточноазиатские, а остальные - базовая латиница, но в результате получается en (на английском языке).

 29.6 Hiragana
 18.5 Katakana
 34.9 CJK Unified Ideographs
 16.9 Basic Latin
result en

Основные латинские символы вызваны использованием в тексте английских названий организаций и т. Д. Японское правило не выполняется, потому что ни Катакана, ни Хирагана не набирают 40% (вместе они набирают 48,1%). Китайское правило не выполняется, потому что CJK Unified Ideographs набирает менее 40%. Таким образом, символы восточной Азии на 83,1% игнорируются, и результат определяется меньшинством на 16,9%. Эти "1041 * гнилые города " требуют некоторой реформы. В целом это можно выразить так:

Если (общее количество блоков сценария, используемых только языком X)> = пороговое значение, характерное для X, выберите язык X.

Как указывалось выше, Хирагана + Катакана> = 40%, вероятно, добьются цели для японцев. Подобное правило вполне может потребоваться для корейского языка.

Ваш гоблдегук действительно содержал несколько символов разметки (я не прокручивал достаточно далеко вправо, чтобы увидеть его), но, конечно, недостаточно, чтобы снизить все баллы по Восточной Азии ниже 40%. Так что мы все еще ждем, чтобы узнать, каков ваш фактический вклад и как вы его получили.

Конец обновления2

Чтобы помочь в диагностике вашей проблемы, не печатайте gobbledegook; использовать

print repr(justwords)

Таким образом, у любого, кто заинтересован в том, чтобы на самом деле делать отладку, есть над чем работать. Было бы полезно, если бы вы указали URL-адрес веб-страницы и показали код Python, который вы использовали для получения юникода justwords. Пожалуйста, измените свой ответ, чтобы показать эти 3 части информации.

Обновление 3 Спасибо за URL. Визуальный осмотр показывает, что язык в основном китайский. Что создало у вас впечатление, что это японец?

Полутанки за предоставление части вашего кода. Чтобы ваши корреспонденты не выполняли вашу работу за вас, а также чтобы избежать недоразумений из-за догадок, вы должны всегда предоставлять (без запроса) автономный сценарий, который воспроизведет вашу проблему. Обратите внимание, что вы говорите, что получили «ошибки ASCII» (нет точного сообщения об ошибке! Нет трассировки!), Если вы не сделали .encode ('utf8') - мой код (см. Ниже) не имеет этой проблемы.

Нет, спасибо, что не предоставили результат print repr(justwords) (даже после запроса). Проверка того, какие промежуточные данные были созданы, является очень элементарной и очень эффективной техникой отладки. Это то, что вы всегда должны делать, прежде чем задать вопрос. Вооружившись этими знаниями, вы можете задать лучший вопрос.

Используя этот код:

# coding: ascii
import sys
sys.path.append(r"C:\junk\wotlang\guess-language\guess_language")
import guess_language
URL = "http://feeds.feedburner.com/nchild"
from BeautifulSoup import BeautifulStoneSoup
from pprint import pprint as pp
import urllib2
htmlSource = urllib2.urlopen(URL).read()
soup = BeautifulStoneSoup(htmlSource)
fall = soup.findAll(text=True)
# pp(fall)
justwords = ''.join(fall)
# justwords = justwords.encode('utf-8')
result = guess_language.guessLanguage(justwords)
print "result", result

Я получил эти результаты:

 29.0 CJK Unified Ideographs
  0.0 Extended Latin
  0.1 Katakana
 70.9 Basic Latin
result en

Обратите внимание, что содержимое URL не является статическим; примерно через час я получил:

 27.9 CJK Unified Ideographs
  0.0 Extended Latin
  0.1 Katakana
 72.0 Basic Latin

Статистические данные были получены путем перебора строки 361 из guess_language.py, так что она гласит:

for key, value in run_types.items():
    pct = (value*100.0) / totalCount # line changed so that pct is a float
    print "%5.1f %s" % (pct, key) # line inserted
    if pct >=40:
        relevant_runs.append(key)

Статистика симптоматична для китайцев с большим количеством HTML / XML / Javascript (см. Предыдущий пример); это подтверждается просмотром вывода pretty-print, полученного без комментариев pp(fall) - таких вещей как:

<img style="float:left; margin:0 10px 0px 10px;cursor:pointer; cursor:hand
;" width="60px" src="http://2.bp.blogspot.com/_LBJ4udkQZag/Rm6sTn1b7NI/AAAAAAAAA
FA/bYkSJZ3i2bg/s400/hepinge169.gif" border="0" alt=""id="BLOGGER_PHOTO_ID_507518
3283203730642" alt="\u548c\u5e73\u6771\u8def\u4e00\u6bb5169\u865f" title="\u548c
\u5e73\u6771\u8def\u4e00\u6bb5169\u865f"/>\u4eca\u5929\u4e2d\u5348\u8d70\u523
0\u516c\u53f8\u5c0d\u9762\u76847-11\u8cb7\u98f2\u6599\uff0c\u7a81\u7136\u770b\u5
230\u9019\u500b7-11\u602a\u7269\uff01\u770b\u8d77\u4f86\u6bd4\u6a19\u6e96\u62db\
u724c\u6709\u4f5c\u7528\u7684\u53ea\u6709\u4e2d\u9593\u7684\u6307\u793a\u71c8\u8
00c\u5df2\uff0c\u53ef\u537b\u6709\u8d85\u7d1a\u5927\u7684footprint\uff01<br /
><br /><a href="http://4.bp.blogspot.com/_LBJ4udkQZag/Rm6wHH1b7QI/AA

Вам нужно что-то сделать с разметкой. Шаги: Посмотрите на ваш сырой "htmlSource" в браузере XML. Является ли XML несовместимым? Как можно избежать непереведенного < и т. Д.? Какие элементы имеют текстовое содержимое, которое является «английским» только благодаря тому, что оно является URL-адресом или аналогичным? Есть ли проблема в Beautiful [Stone] Soup? Вы должны использовать некоторые другие функции Beautiful [Stone] Soup? Стоит ли использовать вместо этого lxml?

Я бы предложил провести некоторое исследование с последующим новым вопросом SO.

конец обновления 3

0 голосов
/ 01 февраля 2010

Google говорит, что ваш пример на китайском языке. У них есть (гораздо более продвинутый) веб-сервис для перевода текста и угадывания языка.

У них есть API и примеры кода для Python .

0 голосов
/ 30 января 2010

Похоже, вы должны быть в состоянии передать свой юникод как есть. guessLanguage декодирует вход str как utf-8. Так что ваш .encode('utf-8') безопасен, но не нужен.

Я просмотрел исходный код и предположил, что он полагается исключительно на данные в каталоге «trigrams» для определения языка, и он не будет обрабатывать японский, потому что там нет подкаталога «ja». Это не правильно, как указал Джон Мачин. Поэтому я должен предположить, что ваш вклад не соответствует вашим ожиданиям (что трудно отладить, поскольку он не отображается правильно в вашем вопросе).

...