0

我想使用我自己的 xml 代码(不是 linq to xml)读取文件的<appSettings>部分:App.config

这是我的 app.config:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>   
<appSettings>
    <add key="driver" value="C:/"/>
    <add key="daysToExpire" value="0"/>
    <add key="Interval" value="5000"/>
</appSettings>
<system.net>
    <mailSettings >
        <smtp>
            <network enableSsl="false" 
                     port="25"
                     host="smtp.gmail.com"
                     defaultCredentials="false"
                     />

        </smtp>
    </mailSettings>
</system.net>

我的 C# 代码:

XmlDocument doc = new XmlDocument();
doc.Load(
    Path.Combine(AppDomain.CurrentDomain.BaseDirectory,    "config.xml")
);

XmlNodeList appSettings = doc.SelectNodes("/configuration/appSettings/add");

Driver = appSettings[0].Attributes[0].Value;
Interval = Convert.ToInt16(appSettings[2].Value);
DaysToExpire = Convert.ToInt16(appSettings[1].Value);

appSettings有 3 种模式,但我没有设法访问每一种。

我也想阅读该system.net部分。

4

3 回答 3

2

让我解释一下为什么手动解析 appSettings 不是一个好主意。此外add元素appSettings可以包含clearremove元素,这会影响之前定义的设置。因此,通过以下部分:

<appSettings>
  <add key="driver" value="C:/"/>
  <clear/>
  <add key="daysToExpire" value="0"/>    
  <add key="Interval" value="5000"/>
  <remove key="daysToExpire"/>
</appSettings>

您将只为您的应用程序定义一个设置(间隔)。如果您尝试获取所有add元素,您将获得不正确的设置(所有三个元素都将在字典中):

var configPath = AppDomain.CurrentDomain.SetupInformation.ConfigurationFile;
var xdoc = XDocument.Load(configPath);
var appSettings = xdoc.Root.Element("appSettings").Elements("add")
                      .ToDictionary(a => (string)a.Attribute("key"),
                                    a => (string)a.Attribute("value"));

正确的解析将如下所示:

var appSettings = new Dictionary<string, string>();
foreach(var e in xdoc.Root.Element("appSettings").Elements())
{
    switch(e.Name.LocalName)
    {
        case "add":
            appSettings.Add((string)e.Attribute("key"), 
                            (string)e.Attribute("value"));
            break;
        case "clear":
            appSettings.Clear();
            break;
        case "remove":
            appSettings.Remove((string)e.Attribute("key"));
            break;
    }
}

另一方面,ConfigurationManager已经在这里,它可以正确解析应用程序设置。以下代码将打印出单个间隔设置:

foreach(string key in ConfigurationManager.AppSettings)
    Console.WriteLine("{0}: {1}", key, settings[key]);

另请记住,您的应用程序的实际设置也将包含来自machinne.config文件的设置。ConfigurationManager还将为您获取这些设置。

于 2013-09-09T16:58:48.160 回答
2

LINQ to XML方式:

var xDoc = XDocument.Load("Input.txt");

var appSettings = xDoc.Root.Element("appSettings");
var driver = (string)appSettings.Elements("add")
                                .First(x => (string)x.Attribute("key") == "driver")
                                .Attribute("value");
var daysToExpire = (string)appSettings.Elements("add")
                                      .First(x => (string)x.Attribute("key") == "daysToExpire")
                                      .Attribute("value");
var interval = (string)appSettings.Elements("add")
                                  .First(x => (string)x.Attribute("key") == "Interval")
                                  .Attribute("value");

您需要using System.Linqusing System.Xml.Linq在文件的顶部才能使其工作。

但老实说:你应该使用AppSettings,因为它就是为此而设计的。

于 2013-09-09T16:48:19.977 回答
0

如果您只想阅读 app.config 设置,请使用配置管理器。如果您正在尝试学习如何使用 XmlDocument,您会遇到一些问题。

1)在一般情况下,您真的不应该依赖于 XML 文档中节点的顺序,如果您根据 XML 内容进行解析,您将拥有更稳定的代码。这不是你的实际问题。

2) Considering the node  <add key="daysToExpire" value="0"/>  

这实际上是一个 XmlElement 节点。它包含 2 个 XmlAttribute 节点。它没有值。实际上,en XmlElement 节点永远不会有值(.Value 属性将始终为空)。XmlElement 中的“值”将是 .InnerText(或 .InnerXml)属性。

如果您查看您的代码,您会正确地将驱动程序值读取为属性,但对于其他两个节点,您没有这样做。您仍然有根据索引而不是属性名称检索属性的问题。使用名称是一种更稳定的解析技术。

于 2013-09-09T17:26:34.023 回答