• 締切済み

preg_match_all、余計な文字を消したい

$source = "(・・・数千文字あるので省略します)" $data = '/<td class="c">\s*.*\s*<\/td>|<td>.*<\/td>/'; preg_match_all($data, $source, $data_matches); var_dump($data_matches); 上記、var_dumpの出力内容は(何故か二次元配列になってしまうんですが)、 array(1) { [0]=> array(80) { [0]=> string(72) "<td class="c"> hogehoge </td>" [1]=> string(21) "<td class="c">hogehoge</td>" [2]=> string(27) "<td>hogehoge</td>" [3]=> string(9) "<td>hogehoge</td>" [4]=> string(21) "<td class="c">hogehoge</td>" [5]=> string(9) "<td>hogehoge</td>" 上記の様に、欲しかったhogehogeの情報は取れているんですが、 <td class="c"></td>、<td></td>が邪魔です。。。 '/<td class="c">\s*.*\s*<\/td>|<td>.*<\/td>/'; 上記の正規表現は、hogehogeの場所を突き止めるのに必要だと思うんですが、 hogehogeのみ抽出したくて・・・。 $re = str_replace('<td class="c">', "", $data_matches); var_dump($re); 例えば上記の様にしても、<td class="c">が消えてくれません。。。 質問 1、何故、二次元配列になってしまうんでしょうか?問題ないのでしょうか?出来れば普通の配列にしたいんですが・・・。 2、どうすればhogehogeの場所を突き止め、そしてさらにhogehogeのみの情報を抽出出来るでしょうか?

みんなの回答

  • shimix
  • ベストアンサー率54% (865/1590)
回答No.3

うーん・・。すでに適切な回答が付いているような気もします(汗 マニュアルをちゃんと読んで書いていけば到達出来ると思うんですけどねぇ・・・ <?php $source =<<<EOD <tr> <td class="c"> <IMG border='0' src='../common/img/noimage.gif'> </td> <td class="c">hoge</td> <td>hoge</td> <td></td> <td class="c">hoge</td> <td></td> <td class="c"></td> <td class="c"><A hoge</a></td> </tr> <tr> <td class="c"> <IMG border='0' src='hoge'> </td> <td class="c">hoge</td> <td>hoge</td> <td>hoge</td> <td class="c">hoge</td> <td>hoge</td> <td class="c">hoge</td> <td class="c">hoge</td> </tr> <tr> <td class="c"> <IMG border='0' src='hoge'> </td> <td class="c">hoge</td> <td>hoge</td> <td>hogehoge</td> <td class="c">hoge</td> <td>hoge</td> <td class="c">hoge</td> <td class="c"><A target="_blank" href="hoge"><img src="../common/img/to_site.jpg" width="42" height="30"></a></td> </tr> <tr> EOD; $data = '/<td class="c">(.*)<\/td>|<td>(.*)<\/td>/'; preg_match_all($data, $source, $data_matches, PREG_PATTERN_ORDER + PREG_OFFSET_CAPTURE); $arr = $data_matches[1]; foreach ($arr as $key=>$val) { if ($val[0] === '') { continue; } print htmlspecialchars($val[0]) . '&nbsp;&nbsp;pos:' . $val[1] . '<br />' . PHP_EOL; }

全文を見る
すると、全ての回答が全文表示されます。
回答No.2

> 1、何故、二次元配列になってしまうんでしょうか?問題ないのでしょうか?出来れば普通の配列にしたいんですが・・・。 それは、preg_match_allの期待された動作だと思います。 http://php.net/manual/ja/function.preg-match-all.php flagsの項目を読むと、こういうことが書いてありませんか? | PREG_PATTERN_ORDER | $matches[0] はパターン全体にマッチした文字列の配列、 | $matches[1] は第 1 のキャプチャ用サブパターンにマッチした文字列の配列、 | といった順番となります。 書いておられるプログラム中ではサブパターンを使用していないので、なぜ二次元配列か理解できないかもしれません。例えば、パターンが例えば'/<td class="c">\s*(.*)\s*<\/td>/'と()を使ってみるとサブパターンのところだけを取り出した配列ができるのでこれの必然性というのが少しは理解できると思います。 サブパターンとは?: http://php.net/manual/ja/regexp.reference.subpatterns.php 2次元配列から欲しい方の1次元配列を取り出せば良いと思います。 > 2、どうすればhogehogeの場所を突き止め、そしてさらにhogehogeのみの情報を抽出出来るでしょうか? 自分は質問文の次の文が何を主張しているのかよくわからなかったのですが、次のどちらかでしょうか。 > <td class="c"></td>、<td></td>が邪魔です a. <td></td>で囲っているのが邪魔。<td>foo</td>ではなく、fooと表示してほしい。 b. <td></td>と中身が入っていないものがマッチするのが邪魔。中身が無いものは消してほしい。 a.の場合はこんなパターンを書くと良いでしょう。 '/<td class="c">\s*(.*)\s*<\/td>|<td>(.*)<\/td>/' そして、できた2次元配列からそこだけ取り出します。 $pattern = '/<td class="c">\s*(.*)\s*<\/td>|<td>(.*)<\/td>/'; preg_match_all($pattern, $source, $matches, PREG_PATTERN_ORDER); $extracted = $matches[1]; var_dump($extracted); b.だとすると、パターンを改良することをおすすめします。 '/<td class="c">\s*.+\s*<\/td>|<td>.+<\/td>/' *だと0文字でもマッチするので、+にして1文字以上のときにマッチするようにしましょう。 aとbの両方の場合はこんな感じでしょうか。 $pattern = '/<td\s*(|class="c")>\s*(.+)\s*<\/td>/'; preg_match_all($pattern, $source, $matches, PREG_PATTERN_ORDER); $extracted = $matches[2]; var_dump($extracted); 正規表現のパターンで同じ事を二度書くのは嫌ですし、サブパターンを書く所でミスってしまいそうなのでちょっと整理しました。

全文を見る
すると、全ての回答が全文表示されます。
  • agunuz
  • ベストアンサー率65% (288/438)
回答No.1

#知恵袋の続きですね(汗 http://detail.chiebukuro.yahoo.co.jp/qa/question_detail/q14103000684 結局、私が提示した(Uを付加した) $data = '/<td class="c">\s*.*\s*<\/td>|<td>.*<\/td>/U'; と変えてもダメだったのでしょうか? >$source = "(・・・数千文字あるので省略します)" 数千文字を転記しろというのは無理だとわかりますが「現象が再現できる」文字列を提示できませんか?こちらで再現できないものは調べようがありません。 >1、何故、二次元配列になってしまうんでしょうか? については、同じ回答しかしません。必ず一読してください。これを読まずに質問されても困りますので。 RTFM. http://php.net/manual/ja/function.preg-match-all.php >どうすればhogehogeの場所を突き止め、 RTFM. http://php.net/manual/ja/function.preg-match-all.php ヒント)PREG_OFFSET_CAPTURE

htryhjykjkyu
質問者

補足

>>$data = '/<td class="c">\s*.*\s*<\/td>|<td>.*<\/td>/U'; 結果のソースも見ましたが変わりませんでした。 >>数千文字を転記しろというのは無理だとわかりますが「現象が再現できる」文字列を提示できませんか?こちらで再現できないものは調べようがありません。 <tr> <td class="c"> <IMG border='0' src='../common/img/noimage.gif'> </td> <td class="c">hoge</td> <td>hoge</td> <td></td> <td class="c">hoge</td> <td></td> <td class="c"></td> <td class="c"><A hoge</a></td> </tr> <tr> <td class="c"> <IMG border='0' src='hoge'> </td> <td class="c">hoge</td> <td>hoge</td> <td>hoge</td> <td class="c">hoge</td> <td>hoge</td> <td class="c">hoge</td> <td class="c">hoge</td> </tr> <tr> <td class="c"> <IMG border='0' src='hoge'> </td> <td class="c">hoge</td> <td>hoge</td> <td>hogehoge</td> <td class="c">hoge</td> <td>hoge</td> <td class="c">hoge</td> <td class="c"><A target="_blank" href="hoge"><img src="../common/img/to_site.jpg" width="42" height="30"></a></td> </tr> <tr> .... ... .. .

全文を見る
すると、全ての回答が全文表示されます。

関連するQ&A

  • 多次元配列のカウント+1の仕方

    多次元配列のカウント+1の仕方 下記のような多次元配列(ちなみに、これって二次元配列ですか?)があるとき、 常に、「2列目の0がある数+1」を返すようにしたいのですが、 どうすればよいのでしょうか? $data[0][1]とか$data[1][1]とか$data[2][1]とかの意味です。 下記の例でいくと、2列目に0が3つあるので、数値の4を返したいのですが…、 ■$data 1,0,A1,B1,C1 2,0,A2,B2,C2 3,0,A3,B3,C3 4,2,A4,B4,C4 ■var_dump($data); array(4) { [0]=> array(5) { [0]=> string(1) "1" [1]=> string(1) "0" [2]=> string(2) "A1" [3]=> string(2) "B1" [4]=> string(2) "C1" } [1]=> array(5) { [0]=> string(1) "2" [1]=> string(1) "0" [2]=> string(2) "A2" [3]=> string(2) "B2" [4]=> string(2) "C2" } [2]=> array(5) { [0]=> string(1) "3" [1]=> string(1) "0" [2]=> string(2) "A3" [3]=> string(2) "B3" [4]=> string(2) "C3" } [3]=> array(5) { [0]=> string(1) "4" [1]=> string(1) "2" [2]=> string(2) "A4" [3]=> string(2) "B4" [4]=> string(2) "C4" } }

    • ベストアンサー
    • PHP
  • PHP 配列 変換

    失礼します現在配列をvar_dumpすると array(3) { [0]=> string(32) "hogehoge" [1]=> string(32) "pipyup4646" [2]=> string(9) "1000%" } array(3) { [0]=> string(32) "testtest" [1]=> string(32) "kodsaf45454” [2]=> string(9) "500%" } array(3) { [0]=> string(32) "ldkfaofpjdsa" [1]=> string(32) "fasdfasdfaf4546" [2]=> string(9) "50000%" } となっておりこれを[0][1] = [2] のように[英語][英数字] = 値のようにしたいです。 ご教授いただけると助かります。 宜しくお願い致します。

    • ベストアンサー
    • PHP
  • [PHP]ループ内の配列取得、表示について

    質問させていただきます。 データをDBから取得しwhileで全てのデータを配列として出力しているとします。 (whileの中で出力し、3つのデータがあるため3回ループされている) 結果 array(1) { [0]=> string(5) "17:10" } array(2) { [0]=> string(5) "17:10" [1]=> string(5) "17:25" } array(3) { [0]=> string(5) "17:10" [1]=> string(5) "17:25" [2]=> string(5) "11:15" } 現在の出力内容は、 var_dump[$hoge[0]] 出力結果 string(5) "17:10" string(5) "17:10" string(5) "17:10" var_dump[$hoge[1]] 出力結果 NULL string(5) "17:25" string(5) "17:25" var_dump[$hoge[2]] 出力結果 NULL NULL string(5) "11:15" という出力になっていますが、最後のarray(3)の部分だけを抜き出したいです。 その場合はどのようにすればよいのでしょうか? -理想の結果- 利用したいのはarray(3)の部分だけ。 var_dump[$hoge[0]] "17:10" var_dump[$hoge[1]] "17:25" var_dump[$hoge[2]] "11:15" 説明不足かもしれませんが、よろしくお願いいたしますm(_ _)m

    • ベストアンサー
    • PHP
  • PHP 配列

    多重の質問申し訳ございません。現在配列をvar_dumpすると array(3) { [0]=> string(32) "hogehoge" [1]=> string(32) "pipyup4646" [2]=> string(9) "1000%" } array(3) { [0]=> string(32) "testtest" [1]=> string(32) "kodsaf45454” [2]=> string(9) "500%" } prinfをしましたら出力結果が array(英語,英数字,値); という形になっているみたいです。 これを[英語][英数字] = 値というのは可能でしょうか? 宜しくお願い致します。

    • ベストアンサー
    • PHP
  • PHPの配列の扱い方

    配列を勉強中なのですが、 よく判らなくなってしまったので教えてください。 print var_dump($aa); を実行すると array(5) { [0]=> string(2) "AE" [2]=> string(1) "C" [4]=> string(1) "F" [5]=> string(1) "N" [6]=> string(1) "Y" } とか array(2) { [27]=> string(2) "BA" [41]=> string(2) "BP" } とかかえってくる配列$aaがあるのですが、 この"AE"や"C"や"BP"など文字情報だけを見たい場合はどのように表記すればいいのでしょうか?

    • ベストアンサー
    • PHP
  • 配列から指定した値を取得する関数

    $itemから["a"]の値だけを取り出した配列を呼び出す関数を作成したいのですが、この様な配列の場合はどうしたら良いのでしょうか? $item var_dump( $item ); array(1) { [0]=> object(data)#1 (5) { ["a"]=> int(1) ["b"]=> string(1) "2" ["c"]=> string(7) "string1" ["d"]=> string(7) "string2" ["e"]=> string(8) "keyword1" } [1]=> object(data)#2 (5) { ["a"]=> int(3) ["b"]=> string(1) "4" ["c"]=> string(7) "string3" ["d"]=> string(7) "string4" ["e"]=> string(8) "keyword2" } }

    • ベストアンサー
    • PHP
  • ある文字を含む文字列のみ配列にする方法

    var_dump($text); を行うと array(1) { [0]=> string(XX) "あいさつ" } array(1) { [0]=> string(XX) "いい日旅立ち" } array(1) { [0]=> string(XX) "りんご、うまい" } array(1) { [0]=> string(XX) "メロン好き" } …… となるような変数 $text があり、そこから $key = array("ばなな","りんご","メロン"); の配列内にある文字列を含むものだけを新たに格納したいです。 自分では foreach($text as $value){ if(in_array($value, $key)){ $key_text[] = $value; } } と書いて試したのですが、NULLと返ってきてしまいます。 どうやって書けばいいか教えて下さい。 よろしくお願いします。

    • ベストアンサー
    • PHP
  • 多次元配列のソートがうまくいかない

    多次元配列のソートがうまくいかない 質問失礼します. 以下のような,String型,int型,double型の混在した多次元配列([3][3]の配列)をソートするプログラムを作成しました. このプログラムでは3番目の項目でソートを行っています. 問題点なのですが, 3番目の項目がdouble型の一桁(例えばarray[1][2]が2.0)ならばうまくソートできるのですが, 一つを2桁(例えばarray[1][2]を10.0)にすると何故か先頭の数(10.0の場合1)を基準にソートされてしまっているようです・・・ 配列へのデータの入れ方が間違っているのでしょうか? 原因がはっきりわからず困っているのですが, わかる方いましたらよろしくお願いします. public class Sort_test { /** * @param args */ public static void main(String[] args) { // TODO 自動生成されたメソッド・スタブ String[][] array = new String[3][3]; array[ 0 ][ 0 ] = "A"; array[ 0 ][ 1 ] = 2001+""; array[ 0 ][ 2 ] = 9.0+""; array[ 1 ][ 0 ] = "B"; array[ 1 ][ 1 ] = 1001+""; array[ 1 ][ 2 ] = 2.0+""; array[ 2 ][ 0 ] = "C"; array[ 2 ][ 1 ] = 3001+""; array[ 2 ][ 2 ] = 6.0+""; TheComparator comparator = new TheComparator(); // 3番目の項目でソートするように設定 comparator.setIndex( 2 ); // ソート実施 Arrays.sort( array, comparator ); dump(array); } public static void dump( String[][] array ) { for ( int i = 0;i < array.length;i++ ) { for ( int j = 0; j < array[ i ].length;j++ ) { System.out.print( "\t" + array[ i ][ j ] ); } System.out.println(); } } } //多次元配列ソート用クラス class TheComparator implements Comparator { /** ソート対象のカラムの位置 */ private int index = 0; /** ソートするためのカラム位置をセット */ public void setIndex( int index ) { this.index = index; } public int compare( Object a, Object b ) { String[] strA = ( String[] ) a; String[] strB = ( String[] ) b; return ( strA[ index ].compareTo( strB[ index ] ) ); } }

    • ベストアンサー
    • Java
  • PHPで正規表現を使った対象データを全て取り出した

    PHPで正規表現を使った対象データを全て取り出したいのですが、 echo ($matches); にしても「Array」しかでないし、、 var_dump($matches); で確認しても意図するものが取れておりません。。 正規表現で取りだしたい箇所は hrefの「100065」と「100066」です。 これはテスト用に作っているので2個ですが、本来は 30個程度対象箇所があります。 何か正規表現の記述が間違っていると思いますが、ご指摘願います。。 ・プログラム preg_match_all( "(/abcNo=(.*?)&ckFlg/)", $_getHTML, $matches); var_dump($matches); ・var_dumpしたブラウザの表示内容 array(2) { [0]=> array(0) { } [1]=> array(0) { } } 補足: $_getHTML は既にダミーで用意したHTMLを読み込んだものです。 $_getHTML で読み込んでいるファイルの中身です。 <html> <body> <a href="abcNo=100065&ckFlg=1"></a> <a href="abcNo=100066&ckFlg=1"></a> </body> </html>

    • ベストアンサー
    • PHP
  • 連想配列からテーブルを作成する関数

    連想配列からテーブルを作成する関数を作ろうと思っています。 関数をどのように書けばHTMLのソースのようになるでしょうか? //----- 関数 ----- function table($v) { } //----- 配列 ----- $s[0] = array( 'あ行' , 'い行' , 'う行' , 'え行' , 'お行' ); $s[1] = array( 'か' , 'き' , 'く' , 'け' , 'こ' ); $s[2] = array( 'さ' , 'し' , 'す' , 'せ' , 'そ' ); table($s); //----- 生成されるhtml ----- <table> <tr><td>あ行</td><td>い行</td><td>う行</td><td>え行</td><td>お行</td></tr> <tr><td>か</td><td>き</td><td>く</td><td>け</td><td>こ</td></tr> <tr><td>さ</td><td>し</td><td>す</td><td>せ</td><td>そ</td></tr> </table> //----- print_r ----- array(3) {  [0]=>  array(5) {   [0]=>   string(4) "あ行"   [1]=>   string(4) "い行"   [2]=>   string(4) "う行"   [3]=>   string(4) "え行"   [4]=>   string(4) "お行"  }  [1]=>  array(5) {   [0]=>   string(2) "か"   [1]=>   string(2) "き"   [2]=>   string(2) "く"   [3]=>   string(2) "け"   [4]=>   string(2) "こ"  }  [2]=>  array(5) {   [0]=>   string(2) "さ"   [1]=>   string(2) "し"   [2]=>   string(2) "す"   [3]=>   string(2) "せ"   [4]=>   string(2) "そ"  } }

    • ベストアンサー
    • PHP
ゲームパッドの不具合
このQ&Aのポイント
  • JC-U4013SBKを使用してXboxをプレイしていたところ、ゲームボタン配置がバラバラになり、一部のゲームが動かなくなりました。
  • 10月10日以前は正常に作動していたため、アップデート関係の問題と考えられます。
  • 現在のバージョンはWindows10 21H1で、ゲームパッドアシストでは動作確認できており、ボタン割り当ても試しましたがうまくいきません。何か解決策をご存知の方がいらっしゃれば教えてください。
回答を見る

専門家に質問してみよう