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

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

新規登録して質問してみよう
ただいま回答率
85.48%
Python 3.x

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

自然言語処理

自然言語処理は、日常的に使用される自然言語をコンピューターに処理させる技術やソフトウェアの総称です。

Q&A

解決済

1回答

6489閲覧

テキスト分類のValueError: dimension mismatchの対処で困っています。。

Ya.Tatsuro

総合スコア10

Python 3.x

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

自然言語処理

自然言語処理は、日常的に使用される自然言語をコンピューターに処理させる技術やソフトウェアの総称です。

0グッド

0クリップ

投稿2017/07/21 13:09

編集2017/07/23 12:21

#実現したいこと
テキストデータ(仕事内容(20文字程度))をjanomeで形態素解析し、CountVectorizerで配列化し、sklearn.naive_bayes(MultinomialNB)で学習させ、仕事内容から仕事分類を予測したいです。
※説明変数は仕事内容、目的変数は仕事分類、環境はpython3.6

#困っていること
学習及び検証までは実施できましたが、この学習済みモデルに未知データ(学習、検証以外のデータ)を与えて、検証でやった正答率が正しいかを確認したいと思っていますが、以下エラーになり対処が分かりません。。(p_-)皆さんに教えていただければ幸いです。どうぞよろしくお願いします。m(__)m

#コード

import

1from janome.tokenizer import Tokenizer 2 3documents = [] # 形態素用の配列を用意 4t = Tokenizer() 5y = [] # クラスラベル用の配列を用意 6with open('./test.csv') as f: 7 reader = csv.reader(f) 8 next(reader) 9 for columns in reader: 10 y.append(columns[1]) # 仕事分類をクラスラベルとしてまとめる 11 document = [] # 1行分の仮の配列を用意 12 for token in t.tokenize(columns[0]): 13 document.append(token.surface) # 仮の配列に形態素を追加 14 documents.append(' '.join(document)) 15 16import numpy as np 17from sklearn.feature_extraction.text $import CountVectorizer 18 19CountVect = CountVectorizer(min_df=1) 20X = CountVect.fit_transform(documents) 21 22from sklearn.externals import joblib 23clf2 = joblib.load('clf.pkl') 24clf2.predict(X) 25print(clf2.score(X, y))

#エラー内容

ValueError Traceback (most recent call last) <ipython-input-38-8c6bc2aa9621> in <module>() 4 5 #■学習済みモデルから、未知データを予測する ----> 6 clf2.predict(X) 7 print(clf2.score(X, y)) 8 C:\Users\XXXX\AppData\Local\Continuum\Anaconda3\lib\site-packages\sklearn\naive_bayes.py in predict(self, X) 63 Predicted target values for X 64 """ ---> 65 jll = self._joint_log_likelihood(X) 66 return self.classes_[np.argmax(jll, axis=1)] 67 C:\Users\XXXX\AppData\Local\Continuum\Anaconda3\lib\site-packages\sklearn\naive_bayes.py in _joint_log_likelihood(self, X) 705 706 X = check_array(X, accept_sparse='csr') --> 707 return (safe_sparse_dot(X, self.feature_log_prob_.T) + 708 self.class_log_prior_) 709 C:\Users\XXXX\AppData\Local\Continuum\Anaconda3\lib\site-packages\sklearn\utils\extmath.py in safe_sparse_dot(a, b, dense_output) 182 """ 183 if issparse(a) or issparse(b): --> 184 ret = a * b 185 if dense_output and hasattr(ret, "toarray"): 186 ret = ret.toarray() C:\Users\XXXX\AppData\Local\Continuum\Anaconda3\lib\site-packages\scipy\sparse\base.py in __mul__(self, other) 403 404 if other.shape[0] != self.shape[1]: --> 405 raise ValueError('dimension mismatch') 406 407 result = self._mul_multivector(np.asarray(other)) ValueError: dimension mismatch

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

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Ya.Tatsuro

2017/07/22 04:33 編集

見ていただきありがとうございます‼ すみませんでした、スペース入れても変わらなかったので、$を入れて分かるようにしてみました。どうぞ、よろしいお願いしますm(_ _)m
shimizukawa

2017/07/22 05:52

いやそうじゃない。リンク先読みました? "teratailではソースコードをシンタックスハイライトすることができます。" の部分です
Ya.Tatsuro

2017/07/23 12:22

誤っており、また遅くなり大変すみませんでした。再度ご確認頂けましたらと思います。
guest

回答1

0

ベストアンサー

学習済みモデルと与えてる未知データのベクトル行列の次元数が違うからValueErrorになってるんじゃないですかね
学習済みモデルをoutputして他で適用するのは自分は試していないので正しいかどうかはなんとも言えませんが

python3

1print(X.shape)

上記のようなコードで次元数の確認を行うことをオススメします
学習済みモデルを作成した際の次元数はどんなものだったか確認して、その次元数に合うようにすれば、エラーは消えると思いますが

あと蛇足ですがコード大変読みにくいので他の方にいただいたアドバイスはしっかり目を通すべきかと


追記

回答したあとで見つけましたが、こちらの質問が今回の本当に知りたい回答に近いと思いました。
機械学習の勉強を初めてまだ2ヶ月程度の自分はまだ当たっていませんが、私自身もいずれ当たる課題だと思います。

投稿2017/07/23 07:16

編集2017/07/23 07:46
swallowataill

総合スコア36

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Ya.Tatsuro

2017/07/23 12:41

回答ありがとうございます!! またリンクも参考になりました。 shapeで調べてみたところ、ご指摘の通り、学習済みモデルの次元数と未次データのベクトル配列の次元数が異なっていました。今回のやりたいことの想定としては、一度学習したモデルで実装させ、定期的にくる未知データに対して分類させたかったのです。次元数が異なることまでは分かったのですが、未知データに対し、学習時の次元数にどのように合わせたら良いのかが分かりません。自分でも調べるとともに、もし追加で参考になりそうな情報がありましたら教えて頂けましたらと思います。よろしくお願い申し上げます。
swallowataill

2017/07/23 16:05

回答内容がある程度あっていたようで何よりでした。 ベクトルの次元数だけ合わせるなら、次元削減によって元データの次元数と同じ次元数にしてあげれば解決だけはします。ベクトルの次元削減については、PCAやSVDなどscikit-learn内に関数が用意されているので、そこらへんを使えばさほど苦労はしないかと思います。しかし、それが果たして本当に正しいデータや解析になるのかと言えば違うという風にも感じます。 自分もテキストのベクトル化を行う際に、今回と同じように次元数の問題に当たりました。その時は一旦未知データも含めて辞書がわりに.fit_transformさせ、その後学習用データと与える未知データのベクトル化を.transformで行いました。ただこれは、与えるデータが一応手元にあるからこそできることになります。実運用ではできないでしょうね。リンクした質問にあったような辞書を作るというのとは少し違いますが、ニュアンスとしてはほぼほぼ同じになると思います。 実際に未知データを与えた時にどうするかは、一旦上記したように次元数だけ合わせて判定を行い、その後判定が間違ってしたら正解ラベルデータを与えて再学習という風な形が取れればいいのかなぁという風にも感じています。一旦outputしたモデルを用いて追加データ分を再学習ということがはたしてできるかどうかはちょっと試してみないとわからないかなという感じです。 リンクした質問先にもありましたが単語の正規化ということに関しては[こちら](http://qiita.com/Hironsan/items/2466fe0f344115aff177)が参考になると考えています。リンク先はテキストの前処理についてですが、個人的に参考になった記事なので。 単語の正規化を行うことによってかなり単語数は限られてくるとは思いますが、こちらにも辞書のようなものが結局必要になるのかなあと考えています。精度を上げるために、単語の正規化を行うことは今絶賛お試し中なので、私自身もあんまり突っ込んだことは言い切れません。私が行なっているのは、tweetの分類なので表記揺れがとても多くてなかなか苦労する部分はあります。 ちょっと長々してしまってしっかり答えられたか怪しいですが一応こんな感じですかね。私よりもっとよくわかってる方々がここには多いので、もっと具体的な回答をできる人がいると思うので、こういう回答でいいのか不安ではありますが参考までに
Ya.Tatsuro

2017/07/26 22:37

遅くなりましたが、回答ありがとうございます。確かに未知データ含めて学習させて次元を合わせて、その後切り出してやるやり方もありますね。単語の正規化も役に立ちそうなんですね。してみます。ありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問