03U*_*Usr 6 c# xml linq xml-parsing
<?xml version="1.0" standalone="yes"?>
<CompanyInfo>
<Employee name="Jon" deptId="123">
<Region name="West">
<Area code="96" />
</Region>
<Region name="East">
<Area code="88" />
</Region>
</Employee>
</CompanyInfo>
public class Employee
{
public string EmployeeName { get; set; }
public string DeptId { get; set; }
public List<string> RegionList {get; set;}
}
public class Region
{
public string RegionName { get; set; }
public string AreaCode { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
我试图读取这个XML数据,到目前为止我已经尝试过这个:
XDocument xml = XDocument.Load(@"C:\data.xml");
var xElement = xml.Element("CompanyInfo");
if (xElement != null)
foreach (var child in xElement.Elements())
{
Console.WriteLine(child.Name);
foreach (var item in child.Attributes())
{
Console.WriteLine(item.Name + ": " + item.Value);
}
foreach (var childElement in child.Elements())
{
Console.WriteLine("--->" + childElement.Name);
foreach (var ds in childElement.Attributes())
{
Console.WriteLine(ds.Name + ": " + ds.Value);
}
foreach (var element in childElement.Elements())
{
Console.WriteLine("------->" + element.Name);
foreach (var ds in element.Attributes())
{
Console.WriteLine(ds.Name + ": " + ds.Value);
}
}
}
}
Run Code Online (Sandbox Code Playgroud)
这使我能够获取每个节点,其属性名称和值,因此我可以将这些数据保存到数据库中的相关字段中,但这似乎是一种漫长的方式并且不灵活,例如,如果XML结构更改了所有这些foreach语句需求重新访问,也很难以这种方式过滤数据,我需要写一些if语句来过滤数据(例如从West获取员工等...)
我正在寻找一种更灵活的方式,使用linq,如下所示:
List<Employees> employees =
(from employee in xml.Descendants("CompanyInfo")
select new employee
{
EmployeeName = employee.Element("employee").Value,
EmployeeDeptId = ?? get data,
RegionName = ?? get data,
AreaCode = ?? get data,,
}).ToList<Employee>();
Run Code Online (Sandbox Code Playgroud)
但我不确定如何从子节点获取值并应用过滤(仅限某些员工).这可能吗?任何帮助表示赞赏.
谢谢
var employees = (from e in xml.Root.Elements("Employee")
let r = e.Element("Region")
where (string)r.Attribute("name") == "West"
select new Employee
{
EmployeeName = (string)e.Attribute("employee"),
EmployeeDeptId = (string)e.Attribute("deptId"),
RegionName = (string)r.Attribute("name"),
AreaCode = (string)r.Element("Area").Attribute("code"),
}).ToList();
Run Code Online (Sandbox Code Playgroud)
但是当XML文件结构发生变化时,它仍然需要进行查询修订.
编辑
查询每位员工的多个区域:
var employees = (from e in xml.Root.Elements("Employee")
select new Employee
{
EmployeeName = (string)e.Attribute("employee"),
DeptId = (string)e.Attribute("deptId"),
RegionList = e.Elements("Region")
.Select(r => new Region {
RegionName = (string)r.Attribute("name"),
AreaCode = (string)r.Element("Area").Attribute("code")
}).ToList()
}).ToList();
Run Code Online (Sandbox Code Playgroud)
然后,您可以仅筛选来自给定区域的员工的列表:
var westEmployees = employees.Where(x => x.RegionList.Any(r => r.RegionName == "West")).ToList();
Run Code Online (Sandbox Code Playgroud)
您可以跟踪结构:
from employee in xml
.Element("CompanyInfo") // must be root
.Elements("Employee") // only directly children of CompanyInfo
Run Code Online (Sandbox Code Playgroud)
或者不太严格
from employee in xml.Descendants("Employee") // all employees at any level
Run Code Online (Sandbox Code Playgroud)
然后获取您想要的信息:
select new Employee
{
EmployeeName = employee.Attribute("name").Value,
EmployeeDeptId = employee.Attribute("deptId").Value,
RegionName = employee.Element("Region").Attribute("name").Value,
AreaCode = employee.Element("Region").Element("Area").Attribute("code").Value,
}
Run Code Online (Sandbox Code Playgroud)
有关多个地区的其他信息,假设一个List<Region> Regions
属性:
select new Employee
{
EmployeeName = employee.Attribute("name").Value,
EmployeeDeptId = employee.Attribute("deptId").Value,
//RegionName = employee.Element("Region").Attribute("name").Value,
//AreaCode = employee.Element("Region").Element("Area").Attribute("code").Value,
Regions = (from r in employee.Elements("Region") select new Region
{
Name = r.Attribute("name").Value,
Code = r.Element("Area").Attribute("code").Value,
}).ToList();
}
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
37426 次 |
最近记录: |