我有这样的xml:
<?xml version="1.0" encoding="utf-8"?>
<InputData>
<MaxCPUBurst>12</MaxCPUBurst>
<MaxPriority>30</MaxPriority>
<Processes>
<Student>
<CPUBurst>12</CPUBurst>
<Id>1</Id>
<Priority>5</Priority>
<Resources>2</Resources>
<Group>1</Group>
<Name>Sidorov Sidor Sidorovich</Name>
</Student>
<Student>
<CPUBurst>11</CPUBurst
><Id>2</Id>
<Priority>8</Priority>
<Resources>1</Resources>
<Group>2</Group>
<Name>Olegov Oleg Olegovich</Name>
</Student>
<Student>
<CPUBurst>14</CPUBurst>
<Id>7</Id>
<Resources>1</Resources>
<Name>Ivanova Anastasiya Igorevna</Name>
</Student>
</Processes>
</InputData>
以这种方式反序列化:
public class InputData {
public int MaxCPUBurst { get; set; }
public int MaxPriority { get; set; }
public int QuantDuration { get; set; }
public string PlanningMethod { get; set; }
public List<Student> Processes;
}
public class Student {
public int CPUBurst { get; set; }
public int id { get; set; }
public int Priority { get; set; }
public int Group { get; set; }
public string Name { get; set; }
}
static void Main(string[] args) {
XmlDocument contentxml = new XmlDocument();
contentxml.Load("INPUT.xml");
XmlSerializer serializer = new XmlSerializer(typeof(InputData));
InputData inData;
using (StringReader reader = new StringReader(contentxml.OuterXml)) {
inData = (InputData)(serializer.Deserialize(reader));
}
Console.WriteLine(inData.Processes.First().Name);
Console.WriteLine(inData.Processes.Last().Name);
Console.WriteLine("Press any key");
Console.ReadLine();
}
如您所见,第3名学生没有优先级和组。如果未指定此值,则必须设置随机值。什么是适当的方法来做到这一点?
我可以在反序列化后检查所有反序列化的数据,但听起来很愚蠢。
答案 0 :(得分:1)
反序列化后检查数据并不愚蠢。
由于您没有使用关系数据库,换句话说 - 结构化持久性提供程序,我会说在反序列化之后需要进行数据检查。
您正在读取的文件可以由系统中的其他应用程序更改,也可以由用户直接更改,因此为了避免流程中的NullReferenceException
(以及隐式的应用程序崩溃),您需要验证/规范化您的数据。
作为建议,您可以为此创建两种扩展方法:
public static class DataExtensions
{
private static readonly Random _random = new Random();
public static void Normalize(this List<Student> students)
{
for(int i=0; i<students.Count; i++)
{
students[i].Normalize();
}
}
public static void Normalize(this Student student)
{
if(student.Group == 0)
student.Group = _random.Next();
if(student.Priority == 0)
student.Priority = _random.Next();
}
}
在您的Main
方法中,只需使用:
inData.Students.Normalize();
答案 1 :(得分:0)
我仍然在如何在序列化之前规范化您的数据,但之后快速而肮脏的方式将是这样的:
inData.Processes.Where(x => x.Priority == 0 && x.Group == 0)
.ToList()
.ForEach(std => {
Random r = new Random();
std.Priority = r.Next(1,10);
std.Group = r.Next(1,10);
});
编辑:如果你真的想在序列化之前进行规范化,你可以这样做:
XElement root = XElement.Load(@"path\to\xml");
XmlSerializer serializer = new XmlSerializer(typeof(InputData));
InputData inData;
root.Elements("Processes")
.Elements("Student")
.Where (r => r.Element("Group") == null && r.Element("Priority") == null)
.ToList()
.ForEach(x => {
Random r = new Random();
x.Add(new XElement("Group", r.Next(1,10)));
x.Add(new XElement("Priority", r.Next(1,10)));
});
using (StringReader reader = new StringReader(root.ToString()))
{
inData = (InputData)(serializer.Deserialize(reader));
}
在这里,您要检查元素组和优先级是否存在。如果他们不这样做 - 你将它们添加到foreach循环中。如果我们想要超精确,我们还需要添加Id并将其设置为0,就像每个人一样。
答案 2 :(得分:0)
我很确定如果在类构造函数中设置随机数据,如果Xml文件中有可用数据,则会覆盖它,如果没有,则不会覆盖。
这种方式只有那些没有Xml版本的项目才会有随机数据。