閉じられていないHTMLタグがある場合、HtmlAgilityPackの問題を修正することは可能ですか?

c# html-agility-pack xpath

質問

よく私は次の問題があります。
私が持っているhtmlは不正形式であり、この場合、html agility packを使ってノードを選択する際に問題があります。
コードは次のとおりです。

string strHtml = @"
<html>
  <div>
    <p><strong>Elem_A</strong>String_A1_2 String_A1_2</p>
    <p><strong>Elem_B</strong>String_B1_2 String_B1_2</p>
  </div>
  <div>
    <p><strong>Elem_A</strong>String_A2_2 <String_A2_2> asdas</p>
    <p><strong>Elem_B</strong>String_B2_2 String_B2_2</p>
  </div>
</html>";
HtmlAgilityPack.HtmlDocument objHtmlDocument = new HtmlAgilityPack.HtmlDocument();
objHtmlDocument.LoadHtml(strHtml);
HtmlAgilityPack.HtmlNodeCollection colnodePs = objHtmlDocument.DocumentNode.SelectNodes("//p");
List<string> lststrText = new List<string>();
foreach (HtmlAgilityPack.HtmlNode nodeP in colnodePs)
{
  lststrText.Add(nodeP.InnerHtml);
}

問題はString_A2_2が角括弧で囲まれていることです。
そのため、htmlagility packはlststrTextに4ではなく5つの文字列を返します。
htmlagilityパックに"<strong>Elem_A</strong>String_A2_2 <String_A2_2> asdas"要素3を返すようにすることは可能ですか?
または、私はいくつかの前処理をして要素を閉じることができますか?
lststrTextの現在の内容は次のとおりです。

lststrText[0] = "<strong>Elem_A</strong>String_A1_2 String_A1_2"  
lststrText[1] = "<strong>Elem_B</strong>String_B1_2 String_B1_2"  
lststrText[2] = ""  
lststrText[3] = ""  
lststrText[4] = "<strong>Elem_B</strong>String_B2_2 String_B2_2"

受け入れられた回答

ほとんどのHTMLパーサーは、動作中のDOMを構築しようとします。つまり、ダングリングタグは受け入れられません。彼らは改宗されるか、何らかの形で閉じられるでしょう。

ノードの選択だけが重要で、速度と膨大な量のデータが問題にならない場合は、代わりに正規表現ですべての<p>タグを取得できます。

Regex reMatchP = new Regex(@"<(p)>.*?</\1>");
foreach (Match m in reMatchP.Matches(strHtml))
{
   Console.WriteLine(m.Value);
}

この正規表現は、<p>タグが整形式であり、閉じていることを前提としています。

あなたのプログラムでこのRegexをたくさん実行する場合は、次のように宣言する必要があります:

static Regex reMatchP = new Regex(@"<(p)>.*?</\1>", RegexOptions.Compiled);

[編集:アジリティパックの変更]

HtmlAgilityパックを使用する場合は、HtmlDocument.csのPushNodeEnd関数を変更できます。

if (HtmlNode.IsCDataElement(CurrentNodeName()))
{
   _state = ParseState.PcData;
   return true;
}

// new code start
if ( !AllowedTags.Contains(_currentnode.Name) )
{
    close = true;
}
// new code end

AllowedTagsは、b、p、br、span、divなどの既知のすべてのタグのリストになります。

出力は100%ではありませんが、十分に近いですか?

<strong>Elem_A</strong>String_A1_2 String_A1_2
<strong>Elem_B</strong>String_B1_2 String_B1_2
<strong>Elem_A</strong>String_A2_2 <ignorestring_a2_2></ignorestring_a2_2> asdas
<strong>Elem_B</strong>String_B2_2 String_B2_2

人気のある回答

TidyNetを使って、あなたが言及した前後の処理を行うことができます。あなたの答えを編集して、それがなぜあなたのケースに該当しないのか説明できますか?




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