質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.61%

  • Python 3.x

    5943questions

    Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

tf-idfを用いて、重要度の低い単語をデータ内から削除したい

受付中

回答 1

投稿 編集

  • 評価
  • クリップ 1
  • VIEW 242

James1201

score 7

tf-idfを用いて、重要度の低い単語*をリスト内から削除したいのですが、そのままだとおそらくTfidfVectorizerにリスト型を放り込めないらしくエラーが出てしまいます。
以下が問題のコードになります。

*リスト内には複数の文書があり、全体の中で頻出していることから重要度が低いと判断できる単語を削除したいという狙いです。

import janome
from gensim.models.doc2vec import Doc2Vec
from gensim.models.doc2vec import TaggedDocument
from collections import OrderedDict
from janome.tokenizer import Tokenizer
import re
import time
from tqdm import tqdm
import glob
import collections
import pandas as pd
import MeCab
import math
import pandas as pd
import codecs 

with codecs.open("タイトルと冒頭一覧.csv", "r", "Shift-JIS", "ignore") as file:
    df = pd.read_table(file, delimiter=",")

#文章から単語を抽出する関数
def words(text):
    """
        文章から単語を抽出
    """
    out_words = []

    tagger = MeCab.Tagger('-d /usr/local/lib/mecab/dic/mecab-ipadic-neologd/')
    tagger.parse('')
    node = tagger.parseToNode(text)

    while node:
        word_type = node.feature.split(",")[0]
        if word_type in ["動詞","形容詞","名詞"]:
            out_words.append(node.surface)
        node = node.next
    return out_words

#学習に使うタイトル
training_docs = []
for i,dd in tqdm(df.iterrows()):
    #print(dd["ID"],dd["title"])
    training_docs.append(TaggedDocument(words=words(dd["titlebeginning"]), tags=[dd["ID"]]))


#エラーが出てしまう問題箇所
import numpy as np
from sklearn.feature_extraction.text import TfidfVectorizer

for i in range(0,len(df)):
    vectorizer = TfidfVectorizer(use_idf=True, token_pattern=u'(?u)\\b\\w+\\b')
    tf_idfs = vectorizer.fit_transform(training_docs)
    print(tf_idfs)

以上の処理を行い、最終的には、以下のコードにtf-idf処理を施して重要度の低い単語を除いたtraining_docsを代入したいのですが、どのようにしたら良いのでしょうか。
何卒よろしくお願い致します。

# min_count=1:最低1回出現した単語を学習に使用
# dm=0: 学習モデル=DBOW
model = Doc2Vec(documents=training_docs, min_count=1, dm=0)
model.docvecs.similarity(0,1551)

エラー内容

AttributeError                            Traceback (most recent call last)
<ipython-input-32-a49b5702c1c0> in <module>()
      4 for i in range(0,len(df)):
      5     vectorizer = TfidfVectorizer(use_idf=True, token_pattern=u'(?u)\\b\\w+\\b')
----> 6     tf_idfs = vectorizer.fit_transform(training_docs)
      7     print(tf_idfs)

~/anaconda3/envs/kenkyuu/lib/python3.6/site-packages/sklearn/feature_extraction/text.py in fit_transform(self, raw_documents, y)
   1379             Tf-idf-weighted document-term matrix.
   1380         """
-> 1381         X = super(TfidfVectorizer, self).fit_transform(raw_documents)
   1382         self._tfidf.fit(X)
   1383         # X is already a transformed view of raw_documents so

~/anaconda3/envs/kenkyuu/lib/python3.6/site-packages/sklearn/feature_extraction/text.py in fit_transform(self, raw_documents, y)
    867 
    868         vocabulary, X = self._count_vocab(raw_documents,
--> 869                                           self.fixed_vocabulary_)
    870 
    871         if self.binary:

~/anaconda3/envs/kenkyuu/lib/python3.6/site-packages/sklearn/feature_extraction/text.py in _count_vocab(self, raw_documents, fixed_vocab)
    790         for doc in raw_documents:
    791             feature_counter = {}
--> 792             for feature in analyze(doc):
    793                 try:
    794                     feature_idx = vocabulary[feature]

~/anaconda3/envs/kenkyuu/lib/python3.6/site-packages/sklearn/feature_extraction/text.py in <lambda>(doc)
    264 
    265             return lambda doc: self._word_ngrams(
--> 266                 tokenize(preprocess(self.decode(doc))), stop_words)
    267 
    268         else:

~/anaconda3/envs/kenkyuu/lib/python3.6/site-packages/sklearn/feature_extraction/text.py in <lambda>(x)
    230 
    231         if self.lowercase:
--> 232             return lambda x: strip_accents(x.lower())
    233         else:
    234             return strip_accents

AttributeError: 'TaggedDocument' object has no attribute 'lower'

こちらが問題のファイルになります

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • hayataka2049

    2018/06/09 18:13

    エラーの内容を追記してください

    キャンセル

  • James1201

    2018/06/09 18:16 編集

    すみません。最終行の表記に訂正がありました。 エラー内容とともに修正させていただきます...!

    キャンセル

回答 1

+1

TfidfVectorizer.fit_transformの引数は文字列のリストにすれば良いです。

sklearn.feature_extraction.text.TfidfVectorizer — scikit-learn 0.19.1 documentation

ただし、デフォルトのanalyzerが英語用なので、日本語用のanalyzerをanalyzer引数に指定してやる必要があります。これは文字列を受け取って単語のリストを返すような関数にしてやる必要がありますが、幸いwords関数がそんな機能なので、そのまま使えると思います。

doc2vec用のTaggedDocumentの生成でも同じ処理をしているので計算が無駄だと思うなら、analyzerにはlambda x:xのようなものを渡して実質的に機能を殺してやり、fit_transformには

[doc.words for doc in training_docs]

を渡してやれば良いはずです。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/06/09 19:25

    回答ありがとうございます。
    無事、fit_transformに渡してtfidf値を出せたのですが、これをもとにtraining_docsに質問文のようなフィルター処理を行うにはどのようにすれば良いのでしょうか...

    キャンセル

  • 2018/06/09 19:40 編集

    各文書のtfidfベクトルから、下位n件を捨てる、しきい値th以下を捨てるみたいな感じでやればよいかと。そんな方針で、np.argsortとか使って、TfidfVectorizerのvocabulary_属性と突き合わせれば使うべき単語のリストを作れるので、あとはそれを使ってフィルタ
    そうするとtfidf計算をループさせている意味がまったくないのと、TaggedDocumentにする処理もフィルタかけてから作れば良いので下でやることになって、プログラムは全面的に書き換えることになりますね…

    キャンセル

  • 2018/06/09 19:45

    あと、TfidfVectorizerのmin_dfを適当に指定しないと、「その文書にだけやたら出現する」みたいな単語ばっかり拾っちゃうとか、いろいろ考えるべきことはあります

    キャンセル

  • 2018/06/10 19:33

    ありがとうございます。
    すみません、もう少し回答を集めさせてください・・・!

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 90.61%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

  • 受付中

    形態素解析の結果の一部のみを抽出したい

    前提・実現したいこと csvファイルにある文章をPythonを経由してMeCabで形態素解析をしています。  結果を出力する際、特定の品詞(名詞、形容詞、接続詞)と原形だけ

  • 受付中

    形態素解析の結果の際pydotplus、graphvizの結果が白紙出力

    いつもお世話になっております。質問です。 実現したいこと 以下のコードの実行結果がgraph().jpgで出力されるが、真っ白で出力。 しかし画像サイズはそれぞれ別々のサイズで

  • 解決済

    pythonでMecabを利用した語彙解析がうまくできない。

    ●環境 ・Windows Edition:Windows 7 Professional  Service Pack 1 ・pythonバージョン:Python 3.6.2 (v3.

  • 解決済

    Pythonのpipでのパッケージインストール

    前提・実現したいこと Pythonを使ってBitcoinのBotを作ろうと思っていましたのでAPIを取得しようと思っていました。 発生している問題・エラーメッセージ Zaifと

  • 解決済

    mecab 品詞 選択

    やりたいこと 選択したテキストファイル内の文章をmecabを用いて形態素解析し、 品詞(名詞、動詞など)を絞り込みたいと考えています。 現在、テキストファイルの文章を形態素解析する

  • 解決済

    jedi-vim と anaconda の連携について

    いい方法あれば教えてください。  仮想環境にマッチする site-packages をセットする方法 conda activate hogehoge hogehoge

  • 解決済

    指定した言葉を排除したい

    やりたいこと テキストファイルからトピックモデルを作成するプログラムを実装中なのですが、コーパスを生成するのに用いる辞書に指示語(あれ、ここ、そちら)や、それ自体に重要な意味を持た

  • 受付中

    1つのファイルのトピックを調べたい(LDAモデル)

    質問 LDAモデルに詳しい方に質問です。 また、以下に記すプログラムで 複数の小説のテキストファイルからLDAモデルを作成したとき、その中に含まれる 1つの文書のトピックを参照

同じタグがついた質問を見る

  • Python 3.x

    5943questions

    Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。