如何在不定义父节点的情况下反序列化 XML 文件?
How can I deserialize a XML file without defining the parent node?
我知道有很多关于xml文件反序列化的内容,但是我至今没有找到解决办法。我的 XML 看起来像这样
<Data>
<Products>
<Product name="product1" brand="brand1">
<ProductValues>
<ProductValue name="price" value="100"/>
<ProductValue name="stock" value="23"/>
</ProductValues>
</Product>
<Product name="product2" brand="brand1">
<ProductValues>
<ProductValue name="price" value="100"/>
<ProductValue name="stock" value="23"/>
</ProductValues>
</Product>
<Product name="product2" brand="brand1">
<ProductValues>
<ProductValue name="price" value="100"/>
<ProductValue name="stock" value="23"/>
</ProductValues>
</Product>
</Products>
... <!-- And more products -->
</Data>
我有一个 Product 和 ProductValue class,其中相应的字段标记为 XmlAttribute
public class Product
{
[XmlAttribute]
public string name;
[XmlAttribute]
public string brand;
public ProductValue[] ProductValues
...
}
一切正常发现,如果我创建一个新的 class,它被称为 Data
并且有一个字段 public Product[] products
并且我像这样反序列化
XmlSerializer serializer = new XmlSerializer(typeof(Data));
using (FileStream stream = new FileStream(path, FileMode.Open, FileAccess.Read))
{
Data data = (Data)serializer.Deserialize(stream);
}
我不想为此创建一个额外的 class,也不想创建一个像 here 这样的额外字段,但只使用数组类型 XmlSerializer serializer = new XmlSerializer(typeof(Product[]));
实例化序列化程序以接收本地 Product[]
。但是如果我这样做,我会得到错误 <Data xmlns="> was not expected
使用 Xml Linq:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = @"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
List<Product> products = doc.Descendants("Product").Select(x => new Product() {
name = (string)x.Attribute("name"),
brand = (string)x.Attribute("brand"),
ProductValues = x.Descendants("ProductValue")
.GroupBy(y => (string)y.Attribute("name"), z => (string)z.Attribute("value"))
.ToDictionary(y => y.Key, z => z.FirstOrDefault())
}).ToList();
}
}
public class Product
{
public string name { get; set; }
public string brand { get; set; }
public Dictionary<string, string> ProductValues { get; set; }
}
}
正如@Rand Random 指出的可能的重复,我查看了那个问题,最后 git 它结合了 this and this.
XmlReader reader = XmlReader.Create(path);
reader.MoveToContent();
reader.ReadToDescendant("Products");
XmlSerializer serializer = new XmlSerializer(typeof(Product[]), new XmlRootAttribute() { ElementName = "Products" });
var products = (Product[])serializer.Deserialize(reader);
我知道有很多关于xml文件反序列化的内容,但是我至今没有找到解决办法。我的 XML 看起来像这样
<Data>
<Products>
<Product name="product1" brand="brand1">
<ProductValues>
<ProductValue name="price" value="100"/>
<ProductValue name="stock" value="23"/>
</ProductValues>
</Product>
<Product name="product2" brand="brand1">
<ProductValues>
<ProductValue name="price" value="100"/>
<ProductValue name="stock" value="23"/>
</ProductValues>
</Product>
<Product name="product2" brand="brand1">
<ProductValues>
<ProductValue name="price" value="100"/>
<ProductValue name="stock" value="23"/>
</ProductValues>
</Product>
</Products>
... <!-- And more products -->
</Data>
我有一个 Product 和 ProductValue class,其中相应的字段标记为 XmlAttribute
public class Product
{
[XmlAttribute]
public string name;
[XmlAttribute]
public string brand;
public ProductValue[] ProductValues
...
}
一切正常发现,如果我创建一个新的 class,它被称为 Data
并且有一个字段 public Product[] products
并且我像这样反序列化
XmlSerializer serializer = new XmlSerializer(typeof(Data));
using (FileStream stream = new FileStream(path, FileMode.Open, FileAccess.Read))
{
Data data = (Data)serializer.Deserialize(stream);
}
我不想为此创建一个额外的 class,也不想创建一个像 here 这样的额外字段,但只使用数组类型 XmlSerializer serializer = new XmlSerializer(typeof(Product[]));
实例化序列化程序以接收本地 Product[]
。但是如果我这样做,我会得到错误 <Data xmlns="> was not expected
使用 Xml Linq:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = @"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
List<Product> products = doc.Descendants("Product").Select(x => new Product() {
name = (string)x.Attribute("name"),
brand = (string)x.Attribute("brand"),
ProductValues = x.Descendants("ProductValue")
.GroupBy(y => (string)y.Attribute("name"), z => (string)z.Attribute("value"))
.ToDictionary(y => y.Key, z => z.FirstOrDefault())
}).ToList();
}
}
public class Product
{
public string name { get; set; }
public string brand { get; set; }
public Dictionary<string, string> ProductValues { get; set; }
}
}
正如@Rand Random 指出的可能的重复,我查看了那个问题,最后 git 它结合了 this and this.
XmlReader reader = XmlReader.Create(path);
reader.MoveToContent();
reader.ReadToDescendant("Products");
XmlSerializer serializer = new XmlSerializer(typeof(Product[]), new XmlRootAttribute() { ElementName = "Products" });
var products = (Product[])serializer.Deserialize(reader);