【问题标题】:Am I passing the string correctly to the python library?我是否将字符串正确传递给 python 库?
【发布时间】:2010-01-29 20:23:12
【问题描述】:

我正在使用一个名为 Guess Language 的 Python 库: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))

【问题讨论】:

    标签: python unicode encoding nlp


    【解决方案1】:

    查看主页,它显示“”“检测 60 多种语言;希腊语 (el)、韩语 (ko)、日语 (ja)、中文 (zh) 以及 trigrams 目录中列出的所有语言。” "

    这 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"
    

    对于像片假名或平假名这样的脚本名称出现在scripts 中,此类字符必须占输入文本的 40% 或更多(在删除非字母字符等的规范化之后)。某些日文文本可能需要低于 40% 的阈值。但是,如果这是您的文本的问题,我希望它有超过 40% 的汉字(CJK 统一表意文字),因此应该返回“zh”(中文)。

    更新经过一些实验,包括插入打印语句以显示检测到的脚本块的百分比:

    朝日报纸网站上的一条典型新闻:

     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
    

    Basic Latin 的高比例当然是由于加价。我还没有调查是什么让它选择“ca”(加泰罗尼亚语)而不是任何其他使用基本拉丁语的语言,包括英语。但是,您打印的 gobbledegook 没有显示任何包含标记的迹象。

    更新结束

    更新 2

    这是一个示例(2 个标题和接下来的 4 个段落来自 this link),其中大约 83% 的字符是东亚人,其余是基本拉丁语,但结果是 en(英语)。

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

    基本拉丁字符是由文本中使用组织等英文名称引起的。日本的规则失败了,因为片假名和平假名都没有得分 40%(他们一起得分 48.1%)。中国规则失败了,因为中日韩统一表意文字得分低于 40%。所以83.1%的东亚字符被忽略了,结果由16.9%的少数人决定。这些“rotten borough”规则需要一些改革。一般来说,可以这样表达:

    如果(仅语言 X 使用的脚本块总数)>= X 特定阈值,则选择语言 X。

    如上所述,平假名 + 片假名 >= 40% 可能会为日语解决问题。韩语可能需要类似的规则。

    您的 gobbledegook 实际上确实包含了一些标记字符(我没有向右滚动足够远来查看它),但肯定不足以将所有东亚分数压低到 40% 以下。因此,我们仍在等待看看您的实际输入是什么以及您是如何从哪里获得的。

    更新结束2

    为了帮助诊断您的问题,请不要打印 gobbledegook;使用

    print repr(justwords)
    

    这样,任何对实际进行调试感兴趣的人都可以进行一些工作。如果您提供网页的 URL,并显示用于获取 unicode justwords 的 Python 代码,将会有所帮助。请编辑您的答案以显示这 3 条信息。

    更新 3 感谢您提供网址。目视检查表明该语言绝大多数是中文。是什么让你觉得它是日本的?

    感谢您提供部分代码。为避免您的通讯员为您工作,并避免因猜测而造成误解,您应该始终提供(不被询问)一个独立的脚本来重现您的问题。请注意,如果您没有执行 .encode('utf8'),您会说您收到“ASCII 错误”(没有确切的错误消息!没有回溯!)——我的代码(见下文)没有这个问题。

    不,感谢您不提供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
    

    统计数据是通过摆弄guess_language.py 的第 361 行获得的,因此它显示为:

    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 内容(参见前面的示例);通过查看通过取消注释 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
    

    您需要对标记做一些事情。步骤: 在 XML 浏览器中查看原始的“htmlSource”。 XML 不兼容吗?如何避免未翻译的< 等?哪些元素仅因为它是 URL 或类似内容而具有“英语”的文本内容? Beautiful[Stone]Soup 有问题吗?您是否应该使用 Beautiful[Stone]Soup 的其他功能?你应该改用 lxml 吗?

    我建议进行一些研究,然后提出一个新的 SO 问题。

    更新 3 结束

    【讨论】:

    • 感谢您的帮助。我更新了我的帖子以显示我想要确定的 URL。
    • 嗨,John Machin——您是如何获得分数和百分比的?你能粘贴你的代码吗?谢谢。
    【解决方案2】:

    看起来您应该能够按原样传递您的 unicode。 guessLanguagestr 的输入解码为 utf-8。所以你的.encode('utf-8') 是安全的,但没有必要。

    我浏览了源代码并假设它完全依赖其“trigrams”目录中的数据进行语言检测,并且它不会处理日语,因为那里没有“ja”子目录。正如 John Machin 所指出的那样,这是不正确的。所以我必须假设您的输入不是您认为的那样(这很难调试,因为它没有在您的问题中正确显示)。

    【讨论】:

    • +1 指出 encode 是不必要的。 -1 表示“需要为日语添加一些三元组”备注。
    【解决方案3】:

    谷歌说你的例子是中文的。他们有一个(更高级的)webservice 来翻译文本并猜测语言。

    他们有一个APIcode examples for Python

    【讨论】:

    • 我无法使用 Google 的 API,因为我会经常使用它。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-04-27
    • 2014-01-21
    • 2011-04-12
    • 1970-01-01
    • 1970-01-01
    • 2016-12-19
    • 2017-12-08
    相关资源
    最近更新 更多