Python:言語を決定する方法は?


89

私はこれを手に入れたい:

Input text: "ру́сский язы́к"
Output text: "Russian" 

Input text: "中文"
Output text: "Chinese" 

Input text: "にほんご"
Output text: "Japanese" 

Input text: "العَرَبِيَّة"
Output text: "Arabic"

Pythonでどうすればいいですか?ありがとう。


4
何を試しましたか?
Raskayu 2016


うまくここに要約stackoverflow.com/a/48436520/2063605
SNA

回答:


57

langdetectを見たことがありますか?

from langdetect import detect

lang = detect("Ein, zwei, drei, vier")

print lang
#output: de

28
あまり正確ではありません-テキストの言語「解剖学的構造」をro(ルーマニア語)として検出します。このような場合には、複数の言語の出力が必要です。polyglotのパフォーマンスははるかに優れています。
YuriyPetrovskiy18年

2
興味深いことに、同じ例でlangdetect異なる言語を判別できます:-)
Denis Kuzin 2018年

1
何らかの理由で、langdetectがエラーを与えられて、私は、Python 3.6を使用しています
ほのめかし

アインのことは聞いたことがない!!!
ティモ

200
  1. TextBlob。NLTKパッケージが必要で、Googleを使用します。

    from textblob import TextBlob
    b = TextBlob("bonjour")
    b.detect_language()
    

    pip install textblob

  2. ポリグロット。numpyといくつかの難解なライブラリが必要ですが、Windowsで動作する可能性は低いです。(Windowsの場合、適切なバージョンの取得PyICUMorfessorPyCLD2をからここだけで、その後、pip install downloaded_wheel.whl。)混合言語でテキストを検出することができ。

    from polyglot.detect import Detector
    
    mixed_text = u"""
    China (simplified Chinese: 中国; traditional Chinese: 中國),
    officially the People's Republic of China (PRC), is a sovereign state
    located in East Asia.
    """
    for language in Detector(mixed_text).languages:
            print(language)
    
    # name: English     code: en       confidence:  87.0 read bytes:  1154
    # name: Chinese     code: zh_Hant  confidence:   5.0 read bytes:  1755
    # name: un          code: un       confidence:   0.0 read bytes:     0
    

    pip install polyglot

    依存関係をインストールするには、次を実行します。 sudo apt-get install python-numpy libicu-dev

  3. chardetには、範囲(127〜255]に文字バイトがある場合に言語を検出する機能もあります。

    >>> chardet.detect("Я люблю вкусные пампушки".encode('cp1251'))
    {'encoding': 'windows-1251', 'confidence': 0.9637267119204621, 'language': 'Russian'}
    

    pip install chardet

  4. langdetectテキストの大部分が必要です。内部では非決定論的アプローチを使用します。つまり、同じテキストサンプルに対して異なる結果が得られます。ドキュメントによると、決定するには次のコードを使用する必要があります。

    from langdetect import detect, DetectorFactory
    DetectorFactory.seed = 0
    detect('今一はお前さん')
    

    pip install langdetect

  5. guess_languageこのスペルチェッカーを辞書とともに使用することにより、非常に短いサンプルを検出できます。

    pip install guess_language-spirit

  6. langidは両方のモジュールを提供します

    import langid
    langid.classify("This is a test")
    # ('en', -54.41310358047485)
    

    およびコマンドラインツール:

    $ langid < README.md
    

    pip install langid

  7. FastTextはテキスト分類子であり、言語分類の適切なモデルを使用して176の言語を認識するために使用できます。このモデルをダウンロードしから:

    import fasttext
    model = fasttext.load_model('lid.176.ftz')
    print(model.predict('الشمس تشرق', k=2))  # top 2 matching languages
    
    (('__label__ar', '__label__fa'), array([0.98124713, 0.01265871]))
    

    pip install fasttext

  8. pyCLD3は、言語識別のためのニューラルネットワークモデルです。このパッケージには、推論コードとトレーニング済みモデルが含まれています。

    import cld3
    cld3.get_language("影響包含對氣候的變化以及自然資源的枯竭程度")
    
    LanguagePrediction(language='zh', probability=0.999969482421875, is_reliable=True, proportion=1.0)
    

    pip install pycld3


2
detectlangよりもTextblob
はるかに

7
@AnwarvicTextBlobはGoogleAPI(github.com/sloria/TextBlob/blob/dev/textblob/translate.py#L33)を使用しています!それが遅い理由です。
トーマスデコー

4
polyglot最終的に、私のユースケースで最もパフォーマンスが高くなりました。langid第二に来た
jamescampbell

3
言語検出だけが必要な場合は、実際にはPolyglotパッケージ全体を処理する必要はありません。ドキュメントに記載された、検出がで行われpyCLD2非常にシンプルで、ライブラリを使用することは簡単です。
Jeyekomon

1
pyCLD3あります。
tttthomasssss

7

langdetect並列化に使用されているときに問題が発生し、失敗します。しかし、それspacy_langdetectはそのラッパーであり、その目的に使用できます。次のスニペットも使用できます。

import spacy
from spacy_langdetect import LanguageDetector

nlp = spacy.load("en")
nlp.add_pipe(LanguageDetector(), name="language_detector", last=True)
text = "This is English text Er lebt mit seinen Eltern und seiner Schwester in Berlin. Yo me divierto todos los días en el parque. Je m'appelle Angélica Summer, j'ai 12 ans et je suis canadienne."
doc = nlp(text)
# document level language detection. Think of it like average language of document!
print(doc._.language['language'])
# sentence level language detection
for i, sent in enumerate(doc.sents):
    print(sent, sent._.language)

私はあなたの答えに従いましたが、私はまだと同じ速度を得ていると思いますlangdetect。テキストを含むDF列があり、をcolumn.apply()実行する関数で使用していscipy_langdetectます。助言がありますか?
RishabhSahrawat20年

のような関数の並列化を利用できるようにするには、並列ライブラリを使用する必要がありますdask。そうしないと、違いはありません。
HabibKarbasian20年

3

あなたが探している場合は、長い文章を高速であり、ライブラリpolyglotそしてfastextここで最高の仕事をしています。

ダーティでランダムなHTMLのコレクションから10000のドキュメントをサンプリングしましたが、結果は次のとおりです。

+------------+----------+
| Library    | Time     |
+------------+----------+
| polyglot   | 3.67 s   |
+------------+----------+
| fasttext   | 6.41     |
+------------+----------+
| cld3       | 14 s     |
+------------+----------+
| langid     | 1min 8s  |
+------------+----------+
| langdetect | 2min 53s |
+------------+----------+
| chardet    | 4min 36s |
+------------+----------+

おそらく解決するのが難しい問題のために、多くの方法が短いテキストに焦点を合わせていることに気づきました。テキストがたくさんある場合、言語を検出するのは本当に簡単です(たとえば、辞書を使用するだけです!)。ただし、これにより、長いテキストに簡単で適切な方法を見つけることが困難になります。


polyglot言語検出はに基づいていますがpycld2、全体としてそれほど高速ではありません。または、それを使用して一種のバッチモードで言語を識別する方法はありますか?私は文ごとに処理しようとしただけです。
Wiktor第Stribiżew

長いテキストは同じ言語だと思います。私は10000のドキュメントを読み、それらをメモリに保存します。fastextccの場合、\n文字を削除する必要がありますが、polyglotの場合は削除しません(cdl2の結果はほとんど同じで、テストも行いました)。多言語が遅いと思う理由がわかりません。最速でした。あなたは、私が削除されているべきだと思いますか\nだけでなく、そして私の結果は、ちょうど(最初の前すなわち、最初の文を反映していること\n
toto_tico

つまり、すべて1行の文字列である何百万もの個別のドキュメントの言語をチェックします。それはpycld2では遅いです。
Wiktor第Stribiżew

なるほど、そうする方法はないと思います。あなたはそれを一つずつしなければなりません。ドキュメントが保存されている場所によっては、マルチプロセッシング機能を使用できる場合があります。また、アジア言語のエンコーディングで問題が発生したため、fasttextccの使用を終了しました。
toto_tico

私の場合、ほとんどのドキュメントは長く、ベンチマークは短い文では非常に異なって見えるかもしれません。
toto_tico

3

Python用の無料で無制限のGoogle翻訳APIであるGoogletrans(非公式)を使用できます。

あなたは好きなだけリクエストをすることができます、制限はありません

インストール:

$ pip install googletrans

言語検出:

>>> from googletrans import Translator
>>> t = Translator().detect("hello world!")
>>> t.lang
'en'
>>> t.confidence
0.8225234

2

場合によっては、次のいずれかの方法を使用することをお勧めします。

方法0:APIまたはライブラリを使用する

通常、これらのライブラリにはいくつかの問題があります。これは、一部のライブラリが小さなテキストに対して正確ではない、一部の言語が欠落している、遅い、インターネット接続が必要、無料ではないなどの理由からです。しかし、一般的に言えば、ほとんどのニーズに適合します。 。

方法1:言語モデル

言語モデルは、一連の単語の確率を示します。これは、テキストに他の言語の単語が含まれている場合でも、テキストの言語を確実に検出できるため重要です(例:「「Hola」はスペイン語で「hello」を意味します))。

N言語モデル(言語ごとに1つ)を使用して、テキストにスコアを付けることができます。検出された言語は、最高のスコアを与えたモデルの言語になります。

このための単純な言語モデルを構築したい場合は、1グラムを選択します。これを行うには、大きなテキスト(たとえば、「X」言語のWikipediaコーパス)の各単語が出現した回数を数えるだけで済みます。

次に、単語の確率は、その頻度を分析された単語の総数(すべての頻度の合計)で割ったものになります。

the 23135851162
of  13151942776
and 12997637966
to  12136980858
a   9081174698
in  8469404971
for 5933321709
...

=> P("'Hola' means 'hello' in spanish") = P("hola") * P("means") * P("hello") * P("in") * P("spanish")

検出するテキストが非常に大きい場合は、N個のランダムな単語をサンプリングしてから、浮動小数点の精度の問題を回避するために、乗算ではなく対数の合計を使用することをお勧めします。

P(s) = 0.03 * 0.01 * 0.014 = 0.0000042
P(s) = log10(0.03) + log10(0.01) + log10(0.014) = -5.376

方法2:交差するセット

さらに簡単なアプローチは、上位M個の最も頻繁な単語を含むNセット(言語ごとに1つ)を準備することです。次に、テキストを各セットと交差させます。交差の数が最も多いセットが、検出された言語になります。

spanish_set = {"de", "hola", "la", "casa",...}
english_set = {"of", "hello", "the", "house",...}
czech_set = {"z", "ahoj", "závěrky", "dům",...}
...

text_set = {"hola", "means", "hello", "in", "spanish"}

spanish_votes = text_set.intersection(spanish_set)  # 1
english_votes = text_set.intersection(english_set)  # 4
czech_votes = text_set.intersection(czech_set)  # 0
...

方法3:Zip圧縮

これは他の何よりも好奇心が強いですが、ここにあります...テキスト(LZ77など)を圧縮してから、参照圧縮テキスト(ターゲット言語)に関するzip距離を測定できます。個人的には、他の方法よりも遅く、正確で、説明が少ないため、私はそれが好きではありませんでした。それにもかかわらず、この方法には興味深いアプリケーションがあるかもしれません。続きを読む:言語ツリーと圧縮


1

事前にトレーニングされた高速テキストモデルは、私の同様のニーズに最適に機能しました

私は非常によく似たニーズであなたの質問にたどり着きました。私の特定のニーズに対するRabashの回答から最も助けが得られました。

テキストファイルが60,000以上のテキストファイルで英語であることを確認するという彼の推奨事項の中で最も効果的なものを見つけるために実験した後、fasttextがそのようなタスクに優れたツールであることがわかりました。

少しの作業で、多くのファイルに対して非常に高速に動作するツールができました。ただし、fasttextは行のリストに対して簡単に機能するため、ケースのように簡単に変更できます。

コメント付きの私のコードは、この投稿の回答の1つです。あなたや他の人は、他の特定のニーズに合わせてこのコードを簡単に変更できると思います。


0

入力文字列内の文字のUnicodeグループを判別して、言語のタイプ(たとえば、ロシア語のキリル文字)を示してから、テキスト内の言語固有の記号を検索してみてください。


0

私はそこにあるすべてのライブラリを試しましたが、pycld2が最も高速で正確なライブラリであると結論付けました。

次のようにインストールできます。

python -m pip install -U pycld2

あなたはそれをこのように使うことができます:

isReliable, textBytesFound, details = cld2.detect(your_sentence)

print(isReliable, details[0][1]) # reliablity(bool),lang abbrev.(en/es/de...)   
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.