27

XmlDocument.LoadXml()try/catch ブロックのようなものを使用せずに、文字列に整形式の XML が含まれているかどうかを確認する方法を知っている人はいますか? 入力が XML である場合とそうでない場合があります。速度と、例外的でない状況では発生しないという一般原則の両方のために、try/catch に頼らずに、入力が XML ではない可能性があることを認識するコードが必要です。例外。現在、これを行うコードがあります。

private bool IsValidXML(string value)
    {
        try
        {
            // Check we actually have a value
            if (string.IsNullOrEmpty(value) == false)
            {
                // Try to load the value into a document
                XmlDocument xmlDoc = new XmlDocument();

                xmlDoc.LoadXml(value);

                // If we managed with no exception then this is valid XML!
                return true;
            }
            else
            {
                // A blank value is not valid xml
                return false;
            }
        }
        catch (System.Xml.XmlException)
        {
            return false;
        }
    }

しかし、try/catch を必要とすべきではないようです。文字列をチェックするたびにデバッガーがここで中断し、厄介な問題を「助けて」くれるため、例外はデバッグ中にメリーヘルを引き起こしています。

4

11 に答える 11

23

例外なしで検証する方法はわかりませんが、デバッガーの設定を変更して、XmlException未処理の場合にのみ中断することができます。これにより、コードがまだ洗練されていなくても、差し迫った問題が解決するはずです。

これを行うには、Debug / Exceptions... / Common Language Runtime Exceptions に移動し、System.Xml.XmlException を見つけてから、"User-unhandled" のみがチェックされている (Thrown ではない) ことを確認します。

于 2009-06-22T09:27:00.530 に答える
6

IsNullOrEmpty が冗長であることを除いて、これは合理的な方法です (LoadXml はそれを適切に把握できます)。IsNullOrEmpty を保持する場合は、if(!string.IsNullOrEmpty(value)) を実行します。

ただし、基本的には、コードではなく、デバッガーが問題です。

于 2009-06-22T09:28:05.100 に答える
4

[System.Diagnostics.DebuggerStepThrough]メソッドに属性を追加しますIsValidXml。これにより、XmlException がデバッガーによってキャッチされることが抑制されます。つまり、最初の変更の例外のキャッチを有効にでき、この特定のメソッドはデバッグされません。

于 2010-09-22T09:40:12.747 に答える
2

例外がスローされることなく、 using XmlDocumentの行に沿って要素をロードできるため、使用には注意してください。<0>some text</0>XmlDocument doc = (XmlDocument)JsonConvert.DeserializeXmlNode(object)

数値要素名は有効な xml ではありません。私の場合、xmlDoc.innerText を xml の SQL サーバー データ型に書き込もうとするまで、エラーは発生しませんでした。

これが私が今検証する方法であり、例外がスローされます
XmlDocument tempDoc = XmlDocument)JsonConvert.DeserializeXmlNode(formData.ToString(), "data"); doc.LoadXml(tempDoc.InnerXml);

于 2015-11-08T21:17:00.787 に答える
1

XmlTextReader クラスは XmlReader の実装であり、高速でパフォーマンスの高いパーサーを提供します。XML は整形式でなければならないというルールを適用します。DTD またはスキーマ情報を持たないため、検証するパーサーでも非検証するパーサーでもありません。ブロック内のテキストを読み取るか、ストリームから文字を読み取ることができます。

そして、XML ストリームの内容全体を読み取るコードを追加した別の MSDN 記事の例。

string str = "<ROOT>AQID</ROOT>";
XmlTextReader r = new XmlTextReader(new StringReader(str));
try
{
  while (r.Read())
  {
  }
}
finally
{
  r.Close();
}

ソース: http://bytes.com/topic/c-sharp/answers/261090-check-wellformedness-xml

于 2011-03-22T06:57:42.237 に答える
0

問題がデバッガーであることに同意しません。一般に、例外ではない場合は、例外を回避する必要があります。IsWellFormed()つまり、入力が整形式のXMLであるかどうかに基づいてtrue / falseを返す ようなメソッドを探している場合は、キャッチされて処理されるかどうかに関係なく、この実装内で例外をスローしないでください。

例外はコストがかかるため、通常の正常な実行中には発生しないはずです。例として、ファイルの存在をチェックするメソッドを作成し、File.Openを使用して、ファイルが存在しない場合に例外をキャッチします。これは不十分な実装になります。代わりFile.Exists()に使用する必要があります(そして、うまくいけば、その実装は、ファイルが存在しない場合に例外をスローするメソッドの周りにtry / catchを配置するだけではなく、存在しないと確信しています)。

于 2012-10-23T17:31:24.463 に答える
0

また、XML文字列の構文の正当性のみを検証する場合(外部スキーマを解決する必要がない場合)は、XmlResolver = null設定を追加することをお勧めします。これにより、セキュリティ (Web アクセスなし) とセキュリティ (悪意のある XML コンテンツがコードに悪質なサイトへのアクセスを指示するのを回避) の両方が保証されます。コードは次のとおりです (C# 2.0 以降が必要です)。

public static bool IsValidXml(string candidateString)
{
    try
    {
        XmlReaderSettings settings = new XmlReaderSettings();
        settings.XmlResolver = null;
        XmlDocument document = new XmlDocument();
        document.XmlResolver = null;
        document.Load(XmlReader.Create(new MemoryStream(Encoding.UTF8.GetBytes(candidateString)), settings));
        return true;
    }
    catch (XmlException)
    {
        return false;
    }
}

C# 6.0 以降に最適化されたバージョン:

public static bool IsValidXml(string candidateString)
{
    try
    {
        var settings = new XmlReaderSettings { XmlResolver = null };
        var document = new XmlDocument() { XmlResolver = null };
        document.Load(XmlReader.Create(new MemoryStream(Encoding.UTF8.GetBytes(candidateString)), settings));
        return true;
    }
    catch (XmlException)
    {
        return false;
    }
}
于 2019-11-08T10:40:24.550 に答える