Html Agility Packでノードを選択する際の問題


質問

私は現在のHTMLレイアウトを持っています

<table> //table[1]
</table>
<table> //table[2]
<tbody>
   <tr>
      <td>
         <p>
            &nbsp;
         </p>
      </td>
   </tr>
   <tr>
      <td>
         <table> //table[1]//table[1]
            <tbody>
               <tr>
                  <td>
                     <p>
                        INFO 1
                     </p>
                  </td>
                  <td>
                     <p>
                        INFO 2
                     </p>
                  </td>
                  <td>
                     <p>
                        INFO 3
                     </p>
                  </td>
                  <td>
                     <p>
                        INFO 4
                     </p>
                  </td>
               </tr>
            </tbody>
         </table>
      </td>
   </tr>
   <tr>
      <td>
         <table> //table[1]//table[2]
            <tbody>
               <tr>
                  <td>
                     <p><strong>Name</strong></p>
                  </td>
                  <td>
                     <p><strong>Quantity</strong></p>
                  </td>
               </tr>
               <tr>
                  <td>
                     <p>Apples </p>
                  </td>
                  <td>10</td>
               </tr>
            </tbody>
         </table>
      </td>
   </tr>
   <tr>
      <td>
         <table>  //table[1]//table[3]
         </table>
      </td>
   </tr>
</tbody>
</table>

私は//table[1]//table[2]内のデータを取得しようとしていますが、次のものについてはnull HtmlNode( System.NullReferenceException )が続きます。

は動作しません: doc.DocumentNode.SelectSingleNode("//table[2]//tbody//tr//td//table[2]//tbody//tr");

なぜ私は//table[1]//table[1]データを取得しようとすると、この構文でうまく動作するのかわかりません

動作します: doc.DocumentNode.SelectSingleNode("//table[2]//tbody//tr//td//table[1]//tbody//tr");

Html Agility Packのインデックス作成の仕組みを誤解していますか?

受け入れられた回答

//table[2]は、XPathで同じ親の 2番目の<table>要素を返し<table>

[] )は、( //および/ )よりも高い優先順位(優先順位)を持ちます。 [ 参考のために ]

あなたのケースでは、各<td><table>が1つしかないため、Xpath式は何も返しませんでした。可能な解決策の1つは、括弧を入れて優先順位を変更することです。

(//table[2]//tbody//tr//td//table)[2]//tbody//tr

Xpathの上に、内側のXPath //table[2]//tbody//tr//td//tableから返されたすべての<table>から2番目の<table>要素を取得し//table[2]//tbody//tr//td//table 。その後、その<table>から子孫//tbody//tr要素を引き続き返します。


人気のある回答

なぜ私の他の方法がうまくいかなかったのか分からないtrの根拠に基づいていることに終わりましたが、この方法でうまくいきます。

私は基本的に私のテーブルの上の次のレベルにインデックスを移動しました。だから最初のtbody各テーブルはtr / tdステートメントの中にあり、私は単純にtrのインデックスを作成するためにHtmlNodeを構築しました。選択プロセスを広げると、Agility Packがうまく機能するのでしょうか? IDK。

いずれかの方法...

table[2]//table[1]では私が使った:

HtmlNode table = doc.DocumentNode.SelectSingleNode("//table[2]//tbody//tr[2]//table");
foreach (var cell in table.SelectNodes(".//tr//td/p"))
...

あなたが上記の例のHTMLを書き留めておけば、ブランクスペースの前にtr / tdを持っていたので、tr [2]を選択しました

table[2]//table[2]では私は使用しました

HtmlNode table = doc.DocumentNode.SelectSingleNode("//table[2]//tbody//tr[2]//table");
foreach (var cell in table.SelectNodes(".//tr//td/p"))
...

誰かが問題を抱えている場合は、特定のタグをより広範なものにプッシュすることで、より広範な選択肢に検索を移動してみてください。





ライセンスを受けた: CC-BY-SA
所属していない Stack Overflow
このKBは合法ですか? はい、理由を学ぶ