0

私が思ったそれぞれの結果は同じ行にあるはずです。ただし、class = "title"ごとに、BRが検出されるたびに結果が別の配列行に分割されます。結果はすべて同じ行にあるはずです。

[html]

<td class="title">
<a href="http://boguslink">bogus title</a>....<br>
here is some text
</td>

[php]

$dom = new DOMDocument();
$dom->loadHTML($html);
$xpath = new DOMXPath($dom);

$result = $xpath->query('//td[@class="title"]/text()');

foreach ($result as $result_row) 
{       
         echo $i.":".$result_row->nodeValue."<br />";
         $i++;
}

[出力]

 0: ....
 1: here is some text

出力が必要な場合

[出力]

 0: ....here is some text

これはバグですか?そうでない場合は、class = "title"の結果が別々の行に分割されないようにし、同時に上記のようにコードを高速に保つにはどうすればよいですか?

編集:

/ text()のバグや動作ではありません。xpath式から/text()を削除するだけで、そのクラスのすべての内部テキストを取得できます。この時点でリンクテキストを除外する方法を理解しようとしているだけなので、「....ここにいくつかのテキストがあります」しか表示されません。

したがって、リンクテキストを除外する式が必要です。最初に失敗した試行はです。

//td[@class="title"][not(a)] 
//td[@class="title"][not(self::a)] 
//td[@class="title"][not(@href)]
4

2 に答える 2

2

いいえ、バグではありません。text()関数はテキスト ノードを取得します。テキストの間に 1 つまたは別のタグがある場合は<br />、必然的に複数のノードを作成しています。それがDOMの仕組みです。

さて、text() は思ったように動作しません (すべての innerhtml が連続しています)。/text() を削除しましたが、適切な xpath を見つけ出すだけでよいので、リンク テキストを取得できません。どうも

ええ、単一のクエリでそれができるとは思いません。基本的に のテキスト コンテンツをtd1 つの文字列として取得するには、 の が必要nodeValueですtd。ただし、これには常に のテキスト ノードも含まaれます。XPath はノードに基づいて選択するだけです。それがどのように機能するかです。したがってtd、 をノードとして取得し、すべてのコンテンツを文字列として取得するか、 の子をフィルタリングしてtd必要なノードのみを取得します (これらはすべて直接textNodeの でした)。ただし、それらを文字列として再構築する必要があります。

したがって、3 つのオプションがあります。

  1. テキストaを処理して使用する$theTd->nodeValue
  2. a実行する前にDOMからタグを削除してください$theTd->nodeValue
  3. テキスト ノードのみを取得し、それらを完全な文字列に再構築します

個人的には #3 が最良の選択肢だと思います。コードを作り直す必要があるだけです...

$tdNodes = $xpath->query('//td[@class="title"]');

foreach ($tdNodes as $i => $td) 
{       
         $text = $xpath->query('./text()', $td);
         $textStr = '';

         foreach($text as $str) 
         {
            $textStr .= $str->nodeValue;
         }

         echo $i.":".$textStr."<br />";
}
于 2012-06-15T15:38:40.307 に答える
0

これはばかげた解決策ですが、うまくいくかもしれません...テキストの切れ目を処理したくない場合は、DOMを実行する前に、HTML文字列の区切りをスペースまたは何も置き換えないでください。

于 2012-06-15T15:43:48.280 に答える