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

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

新規登録して質問してみよう
ただいま回答率
85.50%
PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Eclipse

Eclipseは、IBM社で開発された統合開発環境のひとつです。2001年11月にオープンソース化されました。 たくさんのプラグインがあり自由に機能を追加をすることができるため、開発ツールにおける共通プラットフォームとして位置づけられています。 Eclipse自体は、Javaで実装されています。

Mecab

Mecabは、オープンソースの形態素解析エンジンです。 言語、辞書、コーパスに依存しない汎用的な設計を基本方針としています。 Mecabの由来は、開発者の好物である和布蕪(めかぶ)から名づけられました。

Q&A

解決済

1回答

625閲覧

phpでmecabを使い、特定の品詞の単語を抽出したい

agep31

総合スコア29

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Eclipse

Eclipseは、IBM社で開発された統合開発環境のひとつです。2001年11月にオープンソース化されました。 たくさんのプラグインがあり自由に機能を追加をすることができるため、開発ツールにおける共通プラットフォームとして位置づけられています。 Eclipse自体は、Javaで実装されています。

Mecab

Mecabは、オープンソースの形態素解析エンジンです。 言語、辞書、コーパスに依存しない汎用的な設計を基本方針としています。 Mecabの由来は、開発者の好物である和布蕪(めかぶ)から名づけられました。

0グッド

0クリップ

投稿2018/06/13 05:12

編集2018/06/13 10:40

前提・実現したいこと

windows環境でphpを使い特定のurlから<title>タグを取得し、その<title>タグの中のテキストに対して形態素解析を行っています。
形態素解析にはmecabを使っているのですが、特定の品詞のみを抽出する方法がわかりません。
preg_match関数を使い正規表現で「地域」と判断された単語を抽出したいです。

<var_dumpでの出力結果>
array(31) {
[0]=>
string(41) "#★< 名詞,サ変接続,,,,,*
"
[1]=>
string(73) "成田 名詞,固有名詞,地域,一般,,,成田,ナリタ,ナリタ
"
[2]=>
string(63) "午前 名詞,副詞可能,,,,,午前,ゴゼン,ゴゼン
"
[3]=>
string(50) "発 名詞,接尾,一般,,,,発,ハツ,ハツ
"
[4]=>
string(33) "/ 名詞,サ変接続,
,,,,
"
[5]=>
string(79) "香港 名詞,固有名詞,地域,一般,,,香港,ホンコン,ホンコン
"
[6]=>
string(57) "午後 名詞,副詞可能,,,,,午後,ゴゴ,ゴゴ
"
[7]=>
string(50) "発 名詞,接尾,一般,,,,発,ハツ,ハツ
"
[8]=>
string(42) "> 記号,括弧閉,
,,,,>,>,>
"
[9]=>
string(59) "デラックスクラスホテル 名詞,一般,
,,,,
"
[10]=>
string(47) "に 助詞,格助詞,一般,,,,に,ニ,ニ
"
[11]=>
string(42) "3 名詞,数,
,,,,3,サン,サン
"
[12]=>
string(53) "連 名詞,接尾,助数詞,
,,,連,レン,レン
"
[13]=>
string(51) "泊 名詞,サ変接続,,,,,泊,ハク,ハク
"
[14]=>
string(35) "♪ 名詞,サ変接続,,,,,*
"
[15]=>
string(79) "香港 名詞,固有名詞,地域,一般,,,香港,ホンコン,ホンコン
"
[16]=>
string(79) "マカオ 名詞,固有名詞,地域,一般,,,マカオ,マカオ,マカオ
"
[17]=>
string(63) "黄金 名詞,一般,,,,,黄金,オウゴン,オーゴン
"
[18]=>
string(63) "海岸 名詞,一般,,,,,海岸,カイガン,カイガン
"
[19]=>
string(69) "物語 名詞,一般,,,,,物語,モノガタリ,モノガタリ
"
[20]=>
string(28) "II 名詞,一般,,,,,*
"
[21]=>
string(24) "4 名詞,数,,,,,*
"
[22]=>
string(71) "日間 名詞,接尾,助数詞,,,,日間,ニチカン,ニチカン
"
[23]=>
string(33) "( 名詞,サ変接続,
,,,,
"
[24]=>
string(28) "NT 名詞,一般,,,,,*
"
[25]=>
string(27) "2531 名詞,数,,,,,*
"
[26]=>
string(27) "A 名詞,一般,,,,,*
"
[27]=>
string(36) ")| 名詞,サ変接続,,,,,*
"
[28]=>
string(134) "阪急交通社 名詞,固有名詞,組織,,,*,阪急交通社,ハンキュウコウツウシャ,ハンキューコーツーシャ
"
[29]=>
string(5) "EOS
"
[30]=>
bool(false)
}

該当のソースコード

<?php $html = file_get_contents('http://www.hankyu-travel.com/tour/detail_i.php?p_course_id=NT2531A&p_hei=10'); // htmlをXMLに変換 $dom = new DOMDocument; @$dom->loadHTML( mb_convert_encoding($html, 'HTML-ENTITIES', 'ASCII,JIS,UTF-8,eucJP-win,SJIS-win'), LIBXML_HTML_NOIMPLIED | LIBXML_HTML_NODEFDTD ); /*------------タイトルの取得------------------*/ $xpath = new DOMXPath($dom); $title = $xpath->query('//head/title[1]')->item(0)->nodeValue; echo "タイトル:", $title, "<br>"; /*------------行先の取得mecab------------------*/ $path = '"C:\Program Files\MeCab\bin\mecab.exe"'; $input = $title; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w") ); $process = proc_open($path, $descriptorspec, $pipes); if(is_resource($process)) { fwrite($pipes[0], $input); fclose($pipes[0]); while(!feof($pipes[1])){ $output[] = fgets($pipes[1]); } fclose($pipes[1]); proc_close($process); } echo "<pre>"; print_r($output);//形態素解析の結果の出力 echo "</pre>"; ?>

補足情報(FW/ツールのバージョンなど)

php 5.6.34

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

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

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

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

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

guest

回答1

0

ベストアンサー

単純に配列から特定のキーワードでフィルタしたいということであればこう?

PHP

1<?PHP 2$keyword="地域"; 3$a=[ 4 "#★< 名詞,サ変接続,*,*,*,*,*", 5 "成田 名詞,固有名詞,地域,一般,*,*,成田,ナリタ,ナリタ", 6 "午前 名詞,副詞可能,*,*,*,*,午前,ゴゼン,ゴゼン", 7 "発 名詞,接尾,一般,*,*,*,発,ハツ,ハツ", 8 " 名詞,サ変接続,*,*,*,*,*", 9 "香港 名詞,固有名詞,地域,一般,*,*,香港,ホンコン,ホンコン", 10 "午後 名詞,副詞可能,*,*,*,*,午後,ゴゴ,ゴゴ", 11 "発 名詞,接尾,一般,*,*,*,発,ハツ,ハツ", 12 "> 記号,括弧閉,*,*,*,*,>,>,>", 13 "デラックスクラスホテル 名詞,一般,*,*,*,*,*", 14 "に 助詞,格助詞,一般,*,*,*,に,ニ,ニ", 15 "3 名詞,数,*,*,*,*,3,サン,サン", 16 "連 名詞,接尾,助数詞,*,*,*,連,レン,レン", 17 "泊 名詞,サ変接続,*,*,*,*,泊,ハク,ハク", 18 "♪ 名詞,サ変接続,*,*,*,*,*", 19 "香港 名詞,固有名詞,地域,一般,*,*,香港,ホンコン,ホンコン", 20 "マカオ 名詞,固有名詞,地域,一般,*,*,マカオ,マカオ,マカオ", 21 "黄金 名詞,一般,*,*,*,*,黄金,オウゴン,オーゴン", 22 "海岸 名詞,一般,*,*,*,*,海岸,カイガン,カイガン", 23 "物語 名詞,一般,*,*,*,*,物語,モノガタリ,モノガタリ", 24 "II 名詞,一般,*,*,*,*,*", 25 "4 名詞,数,*,*,*,*,*", 26 "日間 名詞,接尾,助数詞,*,*,*,日間,ニチカン,ニチカン", 27 "( 名詞,サ変接続,*,*,*,*,*", 28 "NT 名詞,一般,*,*,*,*,*", 29 "2531 名詞,数,*,*,*,*,*", 30 "A 名詞,一般,*,*,*,*,*", 31 ")| 名詞,サ変接続,*,*,*,*,*", 32 "阪急交通社 名詞,固有名詞,組織,*,*,*,阪急交通社,ハンキュウコウツウシャ,ハンキューコーツーシャ", 33 "EOS", 34 ]; 35$a=array_filter($a,function($x) use($keyword){ 36 return preg_match("/".preg_quote($keyword,"/")."/",$x); 37}); 38print_r($a);

修正

  • とりだしたあと、先頭の文字だけ抜き出す
  • キーワードは工夫が必要
  • $outputという変数を受けて処理する

もろもろ調整しました

PHP

1$keyword="名詞,固有名詞,地域"; 2$a=array_map(function($x){ 3 return preg_match("/^(.+?)(?=\s)/",$x,$match)?$match[1]:""; 4},array_filter($output,function($x) use($keyword){ 5 return preg_match("/".preg_quote($keyword,"/")."/",$x); 6})); 7print_r($a);

投稿2018/06/13 05:23

編集2018/06/13 10:48
yambejp

総合スコア114572

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

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

agep31

2018/06/13 05:31

ご回答ありがとうございます。ご提示されたプログラムを動かしてみたのですが、「地域」と判断された要素は取り出せたのですが、「成田」「香港」「マカオ」などの単語を取り出したいです。
yambejp

2018/06/13 09:19

失礼しました。地名を抜き出すんですね。 追記しておきましたので確認ください
hayataka2049

2018/06/13 09:38

$keyword="地域";とするとそのままの「地域」(名詞)や「地域経済」のような単語も(辞書に登録されていれば)マッチしてしまうので、少し都合が悪いようです。 正攻法で処理するなら、まずスペースで切り、後ろ半分をcsvとして処理していくことになりますが、面倒ですから $keyword="名詞,固有名詞,地域"; で良いんじゃないでしょうか。 参考 https://hayashibe.jp/tr/mecab/dictionary/ipadic http://www.unixuser.org/~euske/doc/postag/
agep31

2018/06/13 09:38

ご回答ありがとうございます。とても理想の形に近づいたのですが、最初の$a = [・・・];のところを、形態素解析した結果の出力である$outputにしたいのですが、どのようのすればよいのでしょうか?
agep31

2018/06/13 09:41

hayataka様 ご指摘ありがとうございます。修正しました。
yambejp

2018/06/13 09:46

ご指摘いただいた箇所を考慮して修正してみました。 うまくいかないようなら再度ご指摘ください
agep31

2018/06/13 09:49

ご指摘ありがとうございます。コードを修正してみたのですが、うまく取り出せません。
yambejp

2018/06/13 09:57

ちょっと状況がわからないのですが print_r($output)すると例示のようなarrayが表示されるのですよね? であれば、array_mapとarray_filterで普通に処理できると思いますが たとえば文字エンコードがちがうとかそういうレベルの間違いはありませんか?
agep31

2018/06/13 10:02

$outputの中身は例示の通りです。回答にあるプログラムの通り、$a[]の中に直接形態素解析の結果を書くときちんと取り出せるのですが、$outputを使うと取り出せなくなります。
agep31

2018/06/13 10:04

Array ( [1] => 成田 名詞,固有名詞,地域,一般,*,*,成田,ナリタ,ナリタ    [5] => 香港 名詞,固有名詞,地域,一般,*,*,香港,ホンコン,ホンコン    [15] => 香港 名詞,固有名詞,地域,一般,*,*,香港,ホンコン,ホンコン [16] => マカオ 名詞,固有名詞,地域,一般,*,*,マカオ,マカオ,マカオ ) ここまでは取り出せています。
yambejp

2018/06/13 10:09

フィルタはされているけど、地域名だけが抜き出せないのですね? 地域名の後ろの空白文字はスペースかタブだと睨んでいるのですがなにか 特殊文字が出力されているのかもしれませんね /^(.+)(?=\s)/ は先頭から後ろに空白文字(半角スペースやタブ、改行マークなど)がくるまでという意味なので もし特殊文字が出力されているならそれに合わせないといけないと思います
agep31

2018/06/13 10:12

地域名の後ろに来るのは半角スペースです。
yambejp

2018/06/13 10:17

たとえば「\s」を「 」(半角スペース)に変えて試してみてください
agep31

2018/06/13 10:23

回答にあるプログラムだと以下のように取り出されるので、正規表現については問題のではないかと思います。 Array ( [1] => 成田 [5] => 香港 [15] => 香港 [16] => マカオ )
agep31

2018/06/13 10:26

ただ、入力の部分を直接書き込むのではなく、$outputを使って書きたいです。
yambejp

2018/06/13 10:27

環境によって円マークが悪さをする可能性も否定出来ないので chr(92)を使って明示的にするとか・・・あまり効果はないかもです
yambejp

2018/06/13 10:29

> $outputを使って書きたい 追記部分がそうなっていますが、認識が異なるのでしょうか?
agep31

2018/06/13 10:31

追記部分のコードでは取り出せませんでした。やはり以下のような出力になってしまいます。 Array ( [1] => 成田 名詞,固有名詞,地域,一般,*,*,成田,ナリタ,ナリタ [5] => 香港 名詞,固有名詞,地域,一般,*,*,香港,ホンコン,ホンコン [15] => 香港 名詞,固有名詞,地域,一般,*,*,香港,ホンコン,ホンコン [16] => マカオ 名詞,固有名詞,地域,一般,*,*,マカオ,マカオ,マカオ )
yambejp

2018/06/13 10:37

なんでしょうね・・print_rではなくvar_dumpした結果もはれますか?
agep31

2018/06/13 10:41

var_dumpでの出力結果を「前提・実現したいこと」のところに載せました。
yambejp

2018/06/13 10:49

申し訳ない。完全にケアレスミスでした 単純に最短マッチがぬけていました。 修正版のとおり/^(.+?)(?=\s)/で行けるはずです
agep31

2018/06/13 10:52

うまく取り出せました。ありがとうございます。まだ理由がわかっていないのですが、教えていただけませんか?
yambejp

2018/06/13 10:57

/^(.+?)(?=\s)/ と /^(.+)(?=\s)/の違いは、 前者が最初に出てくる空白文字まで(つまり最短マッチ) 後者が最後に出てくる空白文字まで という意味になります 抽出したデータは文字列の最後に改行マークがついており 改行マークも空白文字の一種なので文字列全体がマッチしていました
agep31

2018/06/13 11:03

なるほど。最後に出てくる改行マークを認識してしまたのですね。とても助かりました。どうもありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.50%

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

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

質問する

関連した質問