我正在研究一些代码,以读取包含XML声明的XML片段,例如,解析编码。从MSDN,我应该能够做到这一点:
var nt = new NameTable(); var mgr = new XmlNamespaceManager(nt); var context = new XmlParserContext(null, mgr, null, XmlSpace.None); var reader = new System.Xml.XmlTextReader(@"", System.Xml.XmlNodeType.XmlDeclaration, context);
但是,System.Xml.XmlException
在调用System.Xml.XmlTextReader
构造函数时出现错误消息:
XmlNodeType XmlDeclaration不支持部分内容解析。
我已经用引号对这个错误进行了谷歌搜索-恰好找到零结果(编辑:现在有一个结果:该帖子)-并且没有引号,这没有任何用处。我还查看了MSDN中的XmlNodeType,它并没有说不支持它。
我在这里想念什么? 如何XmlTextReader
从XML声明片段中获取实例?
注意,我的目标只是确定部分构建的XML文档的编码,在此我假设它至少包含一个声明节点。因此,我正在尝试获取reader.Encoding
。如果还有其他方法可以做到,那么我对此持开放态度。
目前,我正在使用regex手动解析声明,这不是最好的方法。
更新:从XML文档或XML片段获取编码:
这是一种使用XmlReader.Create获得编码而不必求助于假根的方法。
private static string GetXmlEncoding(string xmlString) { if (string.IsNullOrWhiteSpace(xmlString)) throw new ArgumentException("The provided string value is null or empty."); using (var stringReader = new StringReader(xmlString)) { var settings = new XmlReaderSettings { ConformanceLevel = ConformanceLevel.Fragment }; using (var xmlReader = XmlReader.Create(stringReader, settings)) { if (!xmlReader.Read()) throw new ArgumentException( "The provided XML string does not contain enough data to be valid XML (see https://msdn.microsoft.com/en-us/library/system.xml.xmlreader.read)"); var result = xmlReader.GetAttribute("encoding"); return result; } } }
这是输出,带有完整的和片段的XML:
如果要使用System.Text.Encoding,可以将代码修改为如下所示:
private static Encoding GetXmlEncoding(string xmlString) { using (StringReader stringReader = new StringReader(xmlString)) { var settings = new XmlReaderSettings { ConformanceLevel = ConformanceLevel.Fragment }; var reader = XmlReader.Create(stringReader, settings); reader.Read(); var encoding = reader.GetAttribute("encoding"); var result = Encoding.GetEncoding(encoding); return result; } }
旧答案:
如您所述,XmlTextReader的Encoding -property包含编码。
这是一个完整的控制台应用程序的源代码,希望它很有用:
class Program { static void Main(string[] args) { var asciiXML = @""; var utf8XML = @" Tove Jani Reminder Don't forget me this weekend!"; var asciiResult = GetXmlEncoding(asciiXML); var utfResult = GetXmlEncoding(utf8XML); Console.WriteLine(asciiResult); Console.WriteLine(utfResult); Console.ReadLine(); } private static Encoding GetXmlEncoding(string s) { var stream = new MemoryStream(Encoding.UTF8.GetBytes(s)); using (var xmlreader = new XmlTextReader(stream)) { xmlreader.MoveToContent(); var encoding = xmlreader.Encoding; return encoding; } } } Tove Jani Reminder Don't forget me this weekend!
这是程序的输出:
如果您知道XML仅包含声明,则可以添加一个空的根吗?因此,例如:
var fragmentResult = GetXmlEncoding(xmlFragment + "");