2016-12-16 79 views
0

我一直试图解析下面的XML文件,并取得了一些成功。C#解析复杂的XML LINQ

<?xml version="1.0"?> 
<Settings> 
    <Tasks> 
     <Task ID="1" Name="task_1" Active="1" NextEID="25" AR="0" CacheNames="random"> 
      <Schedules> 
       <Schedule OnlyUntilFirstSuccess="0" FailIfNoSuccessInSched="0" RunEvenIfNotif="0"> 
        <Days> 
         <DayOfWeek>Monday</DayOfWeek> 
         <DayOfWeek>Tuesday</DayOfWeek> 
         <DayOfWeek>Wednesday</DayOfWeek> 
         <DayOfWeek>Thursday</DayOfWeek> 
         <DayOfWeek>Friday</DayOfWeek> 
         <DayOfWeek>Saturday</DayOfWeek> 
         <DayOfWeek>Sunday</DayOfWeek> 
        </Days> 
        <Frequency> 
         <Interval StartTime="09:45" EndTime="09:45" EveryMinutes="0"></Interval> 
        </Frequency> 
       </Schedule> 
      </Schedules> 
     </Task> 
     <Task ID="2" Name="task_2" Active="1" NextEID="25" AR="0" CacheNames="random"> 
      <Schedules> 
       <Schedule OnlyUntilFirstSuccess="0" FailIfNoSuccessInSched="0" RunEvenIfNotif="0"> 
        <Days> 
         <DayOfWeek>Monday</DayOfWeek> 
         <DayOfWeek>Tuesday</DayOfWeek> 
         <DayOfWeek>Wednesday</DayOfWeek> 
         <DayOfWeek>Thursday</DayOfWeek> 
         <DayOfWeek>Friday</DayOfWeek> 
         <DayOfWeek>Saturday</DayOfWeek> 
         <DayOfWeek>Sunday</DayOfWeek> 
        </Days> 
        <Frequency> 
         <Interval StartTime="12:45" EndTime="09:45" EveryMinutes="0"></Interval> 
        </Frequency> 
       </Schedule> 
      </Schedules> 
     </Task> 
    </Tasks> 
</Settings> 

使用一些在线教程我已经拼凑下面的C#代码:

public static void ParseXml() 
     { 
      string strFile = "File.xml"; 

      XDocument xdoc = XDocument.Load(strFile); 

      var tasks = from s in xdoc.Descendants("Tasks") 
         select new 
         { 
          taskID = s.Element("Task").Attribute("ID").Value, 
          taskName = s.Element("Task").Attribute("Name").Value, 
          taskActive = s.Element("Task").Attribute("Active").Value, 
          taskSchedule = s.Element("Task").Element("Schedules").Element("Schedule").Element("Days") 
         }; 

      foreach (var t in tasks) 
      { 
       Console.WriteLine("Task Id :: {0}", t.taskID); 
       Console.WriteLine("Task Name :: {0}", t.taskName); 
       Console.WriteLine("Task Status :: {0}", t.taskActive); 
       Console.WriteLine("Task Schedule :: {0}", t.taskSchedule); 
      } 

      Console.ReadKey(); 
     } 

我的目标是要分析出每一个任务,任务ID,名称,天,频率。我想最终能够使用这些值来绘制散点图图上的TaskID和StartTime。我尝试创建以下类,认为它可以帮助我处理文件,但我不知道如何将它们结合在一起。

 public class Task 
     { 
      public static int taskId { get; set; } 
      public static string taskName { get; set; } 
     } 

     public class Schedule 
     { 
      public enum DayOfWeek 
      { 
       Monday, 
       Tuesday, 
       Wednsday, 
       Thursday, 
       Friday, 
       Saturday, 
       Sunday 
      } 
     } 

     public class Frequency 
     { 
      public static DateTime startTime { get; set; } 
      public static DateTime endTime { get; set; } 
      public static int everyMins { get; set; } 
     } 

任何帮助/方向将不胜感激。如果有的话,请不要发布解决方案。请解释它,以便我可以从中学习并在将来为这个社区做出贡献。

谢谢! Gabe

回答

0

首先,您需要根据源XML构建您的类。因此,Settings类别中您有Tasks等等。像这样的东西。当然,我还没有放入所有的XML属性。但你应该得到的主旨。您需要装饰表示XML属性的属性的[XMLAttribute]属性。所有属性名称都区分大小写。所以请确保它们匹配(ID而不是Id)。有办法解决此使用属性,但:

public class Settings 
    { 
     public List<Task> Tasks { get; set; } 
    } 

    public class Task 
    { 
     [XmlAttribute] 
     public int ID { get; set; } 

     [XmlAttribute] 
     public string Name { get; set; } 
     public List<Schedule> Schedules { get; set; } 

    } 

    public class Schedule 
    { 
     [XmlAttribute] 
     public string OnlyUntilFirstSuccess { get; set; } 
     public List<DayOfWeek> Days { get; set; } 
     public Frequency Frequency { get; set; } 

    } 
    public class Frequency 
    { 
     public Interval Interval { get; set; } 
    } 

    public class Interval 
    { 
     [XmlAttribute] 
     public string StartTime { get; set; } 
     [XmlAttribute] 
     public string EndTime { get; set; } 
     [XmlAttribute] 
     public int EveryMins { get; set; } 
    } 

然后你可以使用一个XmlSerializer到XML序列化类。所以,你的ParseXml()方法应该是这个样子:

public static void ParseXml() 
    { 
     string fileName = "File.xml"; 
     XDocument xdoc = XDocument.Load(fileName); 
     using (TextReader reader = new StringReader(xdoc.ToString())) 
     { 
      try 
      { 
       var settings = (Settings)new XmlSerializer(typeof(Settings)).Deserialize(reader); 
      } 
      catch (Exception ex) 
      { 
       // Handle exceptions as you see fit 
      } 
     } 
    } 

其他注意事项:不命名变量strxxxxx表示他们是字符串,标准惯例是公共变量名称以大写字母。 此外,你需要以下:

using System; 
using System.Collections.Generic; 
using System.IO; 
using System.Xml.Linq; 
using System.Xml.Serialization; 
+0

所以,如果我的XML文件中包含其他元素\我需要创建一个类为每个就算我不关心他们为我的整个项目的属性? –

+0

@ Ashwin Nair - 什么是私有变量的约定?那些是小写的?我经常看到名称前面带有下划线“_”的变量。下划线表示什么? –

+0

@ Ashwin Nair - 还有几个问题,我不确定我是否理解你宣布Frequency和Interval类的方式。你能详细解释一下吗?我也看过代码,其中属性上的装饰器不仅指定对象类型,而且指定属性名称:[XMLAttribute(“EveryMinutes”)]是不必要的?如果是的话为什么 –