C# XML的学习总结

XML(Extensible Markup Language)可扩展的标记语言

1.文档头部声明:

<?xml version="1.0" encoding="utf-8" ?>

?XML标记说明它是一个XML文档,version为版本号,encoding属性表明是编码格式为”utf-8”,standalone取”yes”时,表明该文件未引用其它外部文件。

2.注释:

<!--下面是学生名单-->

   注释的格式和html类似:<!--“注释的内容”-->,使用注释时需要注意:1.注释不可以出现在XML声明之前.2.注释中不可以出现”--”字符,如:<!--下面是学生--名单> 3.注释不可以嵌套.

3.根元素:

<学生名单>  XXX  </学生名单>

每个文档必须有有一个根元素,没有根元素将会在解析的时候出现错误

4.元素(标记),是XML中用来定义数据的一个基本的单位,元素是由标记要定义的,同时标记分为非空标记和空标记:

(1)非空标记

<学号>201701</学号>

<姓名>张三三</姓名>

<班级>0102</班级>

非空即当标记中包含有内容,格式为:<标记>内容<标记>

(2)空标记

<学生 id=”1”></学生>

空标记中只有属性,两个标签中的内容是为空的。

XML位于System.Xml命名空间,以下为XML结构列表:

标 记

描 述

XmlDocument

XML文档

XmlNode

XML中单个的节点,如<学生名单>

XmlAttribute

XML元素中的属性

XmlText

表示元素或属性的文本内容

XmlElement

最小元素,如<姓名>张三三</姓名>

XmlComment

表示XML注释的内容

XmlDeclaration

XML文档第一行的声明

XML文档的创建

最终效果:

<?xml version="1.0" encoding="UTF-8"?>

<学生名单>

  <学生 id="1">

    <姓名>张三三</姓名>

  </学生>

</学生名单>

//创建一个XML文档对象
XmlDocument doc = new XmlDocument();
//声明XML头部信息
XmlDeclaration dec = doc.CreateXmlDeclaration("1.0", "UTF-8", null);
//添加进doc对象子节点
doc.AppendChild(dec);
//创建根节点
XmlElement root = doc.CreateElement("学生名单");
doc.AppendChild(root);
//再创建根节点下的子节点
XmlElement student = doc.CreateElement("学生");
//设置子节点属性
student.SetAttribute("id", "1");
//子节点下再创建标记
XmlElement studentName = doc.CreateElement("姓名");
//<姓名>的内容
XmlText xmlText = doc.CreateTextNode("张三三");
//将内容添加到<姓名>标记
studentName.AppendChild(xmlText);
//再将<姓名>标记添加到<学生>标记的子节点下
student.AppendChild(studentName);
//最后把<学生>标记添加到根节点<学生名单>子节点下
root.AppendChild(student);
//doc文档对象保存写入
doc.Save("Student.xml");

总结:创建一个xml

1 创建一个XML文档对象   new XmlDocument

2  声明XML头部信息         doc.CreateXmlDeclaration("1.0", "UTF-8", null);

3   创建根节点   doc.CreateElement("学生名单");

4  再创建根节点下的子节点  doc.CreateElement("学生");

5  设置子节点属性    student.SetAttribute("id", "1");

6  子节点下再创建标记  doc.CreateElement("姓名");

7  创建标记的内容    doc.CreateTextNode("张三三");

8 最后把头部信息,根节点加入到doc,把根节点下的节点加入到根节点,一一归属

XML文档的读取

C#中XML读取有三种方式,XmlDocument,XmlTextReader,Linq to Xml

//获取<学生>子节点
XmlNodeList personNodes = root.GetElementsByTagName("学生");
//使用foreach循环读出集合
foreach (XmlNode node in personNodes)
{
    string id = ((XmlElement)node).GetAttribute("id");
    string name = ((XmlElement)node).GetElementsByTagName("姓名")[0].InnerText;
}

总结:

1 加载根目录下XML文件  doc.Load("XMLFile1.xml");

2 //获取根节点  XmlElement root = doc.DocumentElement;

3 //获取<学生>子节点 root.GetElementsByTagName("学生");

4 使用foreach循环读出集合  GetAttribute 读属性,GetElementsByTagName读标签

 增加

XmlDocument doc = new XmlDocument();
//加载根目录下XML文件
doc.Load(xmlPath);
//获取根节点
XmlElement root = doc.DocumentElement;
XmlElement student = doc.CreateElement("学生");
root.AppendChild(student);
//最后一步不要忘记了保存
doc.Save(xmlPath);

1 读取xml

2 获取根节点  doc.DocumentElement;

3 加入创建的新节点 AppendChild

4 重新保存

//筛选出符合条件的标记

XmlElement selectEle = (XmlElement)root.SelectSingleNode("/学生名单/学生[@id='4']");

//获取该标记下的子元素

XmlElement nameEle = (XmlElement)selectEle.GetElementsByTagName("姓名")[0];

//修改<姓名>标记中的内容

nameEle.InnerText = "大明";

//还是那句话不要忘记保存

doc.Save(xmlPath);

1 搜索 SelectSingleNode

2 获取 GetElementsByTagName

3 修改 InnerText

4 保存

 删除标记

  删除和修改类似,也是筛选出符合条件的标记,然后移除 

//筛选出符合条件的标记
XmlElement selectEle = (XmlElement)root.SelectSingleNode("/学生名单/学生[@id='4']");
//删除指定子元素
root.RemoveChild(selectEle);
//还是那句话不要忘记保存
doc.Save(xmlPath);

1 搜索

2 删除

3 保存

最后发现序列化能加快开发进度,使用序列化

序列化

方法的使用

指定可以序列化的对象的类型。

XmlSerializer serializer = new XmlSerializer(o.GetType());

使用流和配置文件创建一个新的XmlWriter实例。从而把序列化的类写入流中

using( XmlWriter writer = XmlWriter.Create(stream, settings) ) {
                serializer.Serialize(writer, o); 
            }

创建内存流并读取

using( MemoryStream stream = new MemoryStream() ) { 
                using( StreamReader reader = new StreamReader(stream, encoding) ) {
                    return reader.ReadToEnd();
                }
            }

创建文件流

  using( FileStream file = new FileStream(path, FileMode.Create, FileAccess.Write) ) { }

读取文件流 

File.ReadAllText(path, encoding);

基本思路:

序列化:

序列化为xml字符串:1 把对象序列化为xml格式的内存流,再写入,再读取出来。

序列化为文件:1 把对象序列化为xml格式的文件流,再写入进去。

反序列化为对象 把字符串转化为内存流,再读取出来,最后转化为对象

文件反序列化为对象  把文件里面的字符串读取出来,把字符串转化为内存流,再读取出来,最后转化为对象

默认情况下(不加任何Attribute),类型中的属性或者字段,都会生成XmlElement。

比如:

public int IntValue { get; set; } 
class XmlHelper
    {
        private static void XmlSerializeInternal(Stream stream, object o, Encoding encoding)
        {
            if (o == null)
                throw new ArgumentNullException("o");
            if (encoding == null)
                throw new ArgumentNullException("encoding"); 
            XmlSerializer serializer = new XmlSerializer(o.GetType());

            XmlWriterSettings settings = new XmlWriterSettings();
            settings.Indent = true;
            settings.NewLineChars = "\r\n";
            settings.Encoding = encoding;
            settings.IndentChars = "    ";

            using (XmlWriter writer = XmlWriter.Create(stream, settings))
            {
                serializer.Serialize(writer, o);
                writer.Close();
            }
        }

        /// <summary>
        /// 将一个对象序列化为XML字符串
        /// </summary>
        /// <param name="o">要序列化的对象</param>
        /// <param name="encoding">编码方式</param>
        /// <returns>序列化产生的XML字符串</returns>
        public static string XmlSerialize(object o, Encoding encoding)
        {
            using (MemoryStream stream = new MemoryStream())
            {
                XmlSerializeInternal(stream, o, encoding);

                stream.Position = 0;
                using (StreamReader reader = new StreamReader(stream, encoding))
                {
                    return reader.ReadToEnd();
                }
            }
        }

        /// <summary>
        /// 将一个对象按XML序列化的方式写入到一个文件
        /// </summary>
        /// <param name="o">要序列化的对象</param>
        /// <param name="path">保存文件路径</param>
        /// <param name="encoding">编码方式</param>
        public static void XmlSerializeToFile(object o, string path, Encoding encoding)
        {
            if (string.IsNullOrEmpty(path))
                throw new ArgumentNullException("path");

            using (FileStream file = new FileStream(path, FileMode.Create, FileAccess.Write))
            {
                XmlSerializeInternal(file, o, encoding);
            }
        }

        /// <summary>
        /// 从XML字符串中反序列化对象
        /// </summary>
        /// <typeparam name="T">结果对象类型</typeparam>
        /// <param name="s">包含对象的XML字符串</param>
        /// <param name="encoding">编码方式</param>
        /// <returns>反序列化得到的对象</returns>
        public static T XmlDeserialize<T>(string s, Encoding encoding)
        {
            if (string.IsNullOrEmpty(s))
                throw new ArgumentNullException("s");
            if (encoding == null)
                throw new ArgumentNullException("encoding");

            XmlSerializer mySerializer = new XmlSerializer(typeof(T));
            using (MemoryStream ms = new MemoryStream(encoding.GetBytes(s)))
            {
                using (StreamReader sr = new StreamReader(ms, encoding))
                {
                    return (T)mySerializer.Deserialize(sr);
                }
            }
        }

        /// <summary>
        /// 读入一个文件,并按XML的方式反序列化对象。
        /// </summary>
        /// <typeparam name="T">结果对象类型</typeparam>
        /// <param name="path">文件路径</param>
        /// <param name="encoding">编码方式</param>
        /// <returns>反序列化得到的对象</returns>
        public static T XmlDeserializeFromFile<T>(string path, Encoding encoding)
        {
            if (string.IsNullOrEmpty(path))
                throw new ArgumentNullException("path");
            if (encoding == null)
                throw new ArgumentNullException("encoding");

            string xml = File.ReadAllText(path, encoding);
            return XmlDeserialize<T>(xml, encoding);
        }
    }

参考文献:

https://www.cnblogs.com/leonliuyifan/p/7044438.html

https://blog.csdn.net/wzy0754/article/details/57585538

猜你喜欢

转载自blog.csdn.net/qq_25744257/article/details/85760851
今日推荐