Unity学习笔记--数据持久化XML文件(2)
IXmlSerializable接口:
使用该接口可以帮助处理不能被序列化和反序列化的特殊类得到处理,
使特殊类继承IXmlSerializable接口 ,实现其中的读写方法,检测到读写方法被重写之后,
便会按照自定义实现的接口来实现方法。
using System;
using System.IO;
using System.Runtime.InteropServices;
using System.Xml;
using System.Xml.Schema;
using System.Xml.Serialization;
using UnityEngine;
namespace Building.XML
{
/// <summary>
/// 要存储的类 实现IXMLSerializer接口
/// </summary>
public class Test03:IXmlSerializable
{
public int testInt;
public string testName;
public int age;
public XmlSchema GetSchema()
{
return null;
}
/// <summary>
/// 在进行读操作 反序列化时候调用的方法
/// </summary>
/// <param name="reader"></param>
public void ReadXml(XmlReader reader)
{
//读XML文件
//001 读属性
testInt = int.Parse(reader["testInt"]);
testName = reader["testName"];
//002 读节点
//单个读
reader.Read();//读节点名称
reader.Read();//读节点中内容
//获取内容数值
testInt = int.Parse(reader.Value);
reader.Read();//读结尾
//读下一个开始
reader.Read();
reader.Read();
testName = reader.Value;
reader.Read();
//或者循环读
//=====进行读 对应这要读取的XML文件
/*while (reader.Read())
{
if (reader.NodeType == XmlNodeType.Element)
{
switch (reader.Name)
{
case "testInt":
reader.Read();
testInt = int.Parse(reader.Value);
break;
case "testName":
reader.Read();
testName = reader.Value;
break;
case "testAge":
reader.Read();
age = int.Parse(reader.Value);
break;
}
}
}
*/
reader.Read();
reader.Read();
age = int.Parse(reader.Value);
reader.Read();
//003 读取包裹的元素节点
XmlSerializer xmlSerializerInt = new XmlSerializer(typeof(int));
XmlSerializer xmlSerializerString = new XmlSerializer(typeof(string));
//跳过根节点--默认read停留在开始
reader.Read();
//读包裹开始
reader.ReadStartElement("BlogName");
//读包裹内容
testName = xmlSerializerString.Deserialize(reader).ToString();
reader.ReadEndElement();//读取包裹结束
reader.ReadStartElement("Age");
age = (int)xmlSerializerInt.Deserialize(reader);
reader.ReadEndElement();
}
/// <summary>
/// 在进行写操作 序列化时候调用的方法
/// </summary>
/// <param name="writer"></param>
/// <exception cref="NotImplementedException"></exception>
public void WriteXml(XmlWriter writer)
{
// 向XML文件中写内容
//1 写属性
writer.WriteAttributeString("testInt",testInt.ToString());
writer.WriteAttributeString("testName",testName);
//2 写节点
writer.WriteElementString("testInt",this.testInt.ToString());
testName = "TonyChang";
age = 21;
writer.WriteElementString("testName",testName);
writer.WriteElementString("testAge",age.ToString());
//3.写包裹的节点
XmlSerializer serializerInt = new XmlSerializer(typeof(int));
XmlSerializer serializerString = new XmlSerializer(typeof(string));
writer.WriteStartElement("BlogName");//开始包裹
serializerString.Serialize(writer,testName);//包裹中内容 序列化放到写入流中
writer.WriteEndElement();//结束包裹
writer.WriteStartElement("Age");
serializerInt.Serialize(writer,age);
writer.WriteEndElement();//结束包裹
}
}
public class XMLDemo2:MonoBehaviour
{
private void Start()
{
//采用默认方式(上文中提到的)进行序列化与反序列化
string path = Application.persistentDataPath + "/XMLDemo02.xml";
Test03 test03 = new Test03();
print(path);//打印存储路径
using (StreamWriter streamWriter=new StreamWriter(path))
{
XmlSerializer xmlSerializer = new XmlSerializer(typeof(Test03));
xmlSerializer.Serialize(streamWriter,test03);
}
//反序列化
if (File.Exists(path))
{
using (StreamReader streamReader=new StreamReader(path))
{
XmlSerializer xmlSerializerRead = new XmlSerializer(typeof(Test03));
Test03 test03Read = xmlSerializerRead.Deserialize(streamReader) as Test03;
print(test03.testName);
print(test03Read.age);
}
}
}
}
}

存储的XML的文件样式(注意对照XML存储样式来理解读取和存储的代码)
特别注意在代码中的读取包裹节点时候先要跳过“根节点”,code Line81;
自定义实现支持序列化与反序列化的字典
using System.Collections.Generic;
using System.Xml;
using System.Xml.Schema;
using System.Xml.Serialization;
namespace Building.XML.SerializerDic
{
/// <summary>
/// 支持序列化与反序列化的字典
/// </summary>
/// <typeparam name="TKey"></typeparam>
/// <typeparam name="TValue"></typeparam>
public class SerializerDictionary<TKey,TValue>:Dictionary<TKey,TValue>,IXmlSerializable
{
public XmlSchema GetSchema()
{
return null;
}
/// <summary>
/// 反序列化 读取XML文件调用
/// </summary>
/// <param name="reader"></param>
/// <exception cref="NotImplementedException"></exception>
public void ReadXml(XmlReader reader)
{
//新建写入器 反序列化工具
XmlSerializer xmlSerializerKey = new XmlSerializer(typeof(TKey));
XmlSerializer xmlSerializerValue = new XmlSerializer(typeof(TValue));
//跳过根节点
reader.Read();
while (reader.NodeType!=XmlNodeType.EndElement)
{
TKey tk = (TKey)xmlSerializerKey.Deserialize(reader);
TValue tv = (TValue) xmlSerializerValue.Deserialize(reader);
this.Add(tk,tv);//添加到容器中
}
}
/// <summary>
/// 序列化 写入XML文件时候调用
/// </summary>
/// <param name="writer"></param>
/// <exception cref="NotImplementedException"></exception>
public void WriteXml(XmlWriter writer)
{
//新建写入器 序列化工具
XmlSerializer xmlSerializerKey = new XmlSerializer(typeof(TKey));
XmlSerializer xmlSerializerValue = new XmlSerializer(typeof(TValue));
foreach (KeyValuePair<TKey,TValue> kv in this)
{
xmlSerializerKey.Serialize(writer,kv.Key);
xmlSerializerValue.Serialize(writer,kv.Value);
}
}
}
}
测试代码:
using System.Collections.Generic;
using System.IO;
using System.Xml.Serialization;
using UnityEngine;
namespace Building.XML.SerializerDic
{
public class Test4
{
public int num = 4;
public SerializerDictionary<int, string> sDic;
}
public class XMLDemo3:MonoBehaviour
{
private void Start()
{
string path = Application.persistentDataPath + "/XMLDemo4.xml";
print(path);
Test4 test4 = new Test4();
test4.sDic = new SerializerDictionary<int, string>() {{1, "Tony"}, {2, "Tom"}, {3, "Frank"}};
using (StreamWriter streamWriter=new StreamWriter(path))
{
XmlSerializer xmlSerializerWrite = new XmlSerializer(typeof(Test4));
xmlSerializerWrite.Serialize(streamWriter,test4);
}
//进行反序列化读取
if (File.Exists(path))
{
using (StreamReader streamReader=new StreamReader(path))
{
XmlSerializer xmlSerializerRead = new XmlSerializer(typeof(Test4));
Test4 test4Read=xmlSerializerRead.Deserialize(streamReader) as Test4;
foreach (KeyValuePair<int,string> pair in test4Read.sDic)
{
Debug.Log("key:"+pair.Key+",Value:"+pair.Value);
}
}
}
}
}
}
存储生成的XML文件内容:

XML存储工具类:
using System;
using System.IO;
using System.Xml.Serialization;
using UnityEngine;
namespace Building.XML.SerializerDic
{
public class XMLSerializerManager
{
private static XMLSerializerManager instance=new XMLSerializerManager();
public static XMLSerializerManager Instance=>instance;
private XMLSerializerManager()
{
}
/// <summary>
/// 存储文件
/// </summary>
/// <param name="data">数据内容</param>
/// <param name="FileName">存储文件名称</param>
public void SaveData(object data, string FileName)
{
string path = Application.persistentDataPath + "/" + FileName + ".xml";
using (StreamWriter streamWriter=new StreamWriter(path))
{
XmlSerializer xmlSerializerWriter = new XmlSerializer(data.GetType());
xmlSerializerWriter.Serialize(streamWriter,data);
}
}
public object LodaData(Type type,string FileName)
{
string path = Application.persistentDataPath + "/" + FileName + ".xml";
if (!File.Exists(path))
{
path = Application.streamingAssetsPath + "/" + FileName + ".xml";
if (!File.Exists(path))
{
//如果在持续存储文件夹下未发现 并且在 流文件夹中仍旧未发现
//则利用反射返回一个该类型的实例 其中的数据为默认值
return Activator.CreateInstance(type);
}
}
using (StreamReader streamReader=new StreamReader(path))
{
XmlSerializer xmlSerializerReader = new XmlSerializer(type);
return xmlSerializerReader.Deserialize(streamReader);
}
}
}
}
Unity学习笔记--数据持久化XML文件(2)的更多相关文章
- Android(java)学习笔记185:xml文件生成
1.xml文件: 用元素描述数据,跨平台. 2.利用传统的方式创建xml文件,下面是一个案例: 设计思路:建立一个学生管理系统,创建xml文件保存学生信息: (1)首先是布局文件activity_ma ...
- Android(java)学习笔记128:xml文件生成
1.xml文件: 用元素描述数据,跨平台. 2.利用传统的方式创建xml文件,下面是一个案例: 设计思路:建立一个学生管理系统,创建xml文件保存学生信息: (1)首先是布局文件activity_ma ...
- Android学习笔记(9):使用XML文件和Java代码控制UI界面
Android推荐使用XML文件设置UI界面.然后用Java代码控制逻辑部分,这体现了MVC思想. MVC全名是Model View Controller.是模型(model)-视图(view)-控制 ...
- Android学习笔记之AndroidManifest.xml文件解析(转)
//自已备注: <?xml version="1.0" encoding="utf-8"?>//说明了版本号,字符集 <manifest xm ...
- Android学习笔记之AndroidManifest.xml文件解析
一.关于AndroidManifest.xml AndroidManifest.xml 是每个android程序中必须的文件.它位于整个项目的根目录,描述了package中暴露的组件(activiti ...
- Android学习笔记之AndroidManifest.xml文件解析(详解)
一.关于AndroidManifest.xml AndroidManifest.xml 是每个android程序中必须的文件.它位于整个项目的根目录,描述了package中暴露的组件(activiti ...
- Excel开发学习笔记:读取xml文件及csv文件
遇到一个数据处理自动化的问题,于是打算开发一个基于excel的小工具.在业余时间一边自学一边实践,抽空把一些知识写下来以备今后参考,因为走的是盲人摸象的野路子,幼稚与错误请多包涵. ).Split( ...
- 八、Android学习第七天——XML文件解析方法(转)
(转自:http://wenku.baidu.com/view/af39b3164431b90d6c85c72f.html) 八.Android学习第七天——XML文件解析方法 XML文件:exten ...
- php添加数据到xml文件的例子
php添加数据到xml文件中 时间:2015-12-17 06:30:37来源:网络 导读:php添加数据到xml文件中 xml文件:stu.xml: 复制代码代码如下: <?xml ver ...
- Java NIO 学习笔记(四)----文件通道和网络通道
目录: Java NIO 学习笔记(一)----概述,Channel/Buffer Java NIO 学习笔记(二)----聚集和分散,通道到通道 Java NIO 学习笔记(三)----Select ...
随机推荐
- 时序数据库 InfluxDB 第一篇 安装部署
使用场景: 最近项目上遇到大数据存储的问题,一个IOT融合项目,涉及到大量的工控监测数据存储.当前存储到关系库中的数据已经达到2亿条了.做了很多优化,查询还是很慢.便想着是否有更好的解决方案. 了解到 ...
- grub加密与解密
前言 grub默认无加密,用户可免密以单用户模式进入系统修改root密码.若想增强其安全性,可以将grub加密. GRUB2提供两种类型的密码保护: 修改菜单条目时需要密码,但启动菜单条目时不需要密码 ...
- 使用supervisor守护freeswitch进程
一.安装supervisor yum install -y epel-release yum install -y supervisor systemctl start supervisord sys ...
- CentOS7升级python3到最新版
前言 最近在学习sanic,需要python3.7以上的版本,而centos7默认的python版本是3.6.8,所以升级了一下版本,在此笔录. 步骤 首先,从python官网下载最新版的python ...
- Javascript执行原理 网页引入javascript的三种方式* javascript核心语法 数据类型 Typeof运算符
Javascript执行原理: 用户端发送请求到服务器端 将js解析出来的数据(用户身份表示)绑定在请求路径中 服务器端获取到参数后会响应客户端 客户端通过浏览器解析响应的数据并将数据展现在浏览器上 ...
- 深入了解API接口调用——从获取淘宝商品数据开始
API(Application Programming Interface)是现代软件开发中常用的一种技术,它允许不同的软件系统进行交互和通信.在本文中,我们将深入探讨如何通过API接口来获取淘宝商品 ...
- 怎么选择API接口来获取自己想要的数据
在今天的数字时代,数据变得越来越重要,API接口也成为了获取数据的一种重要方式.无论是开发自己的应用程序还是进行市场营销,数据的获取都是非常必要的.但是,如何选择API接口来获取自己想要的数据呢? 以 ...
- Node.js 使用 officecrypto-tool 读取加密的 Excel (xls, xlsx) 和 Word( docx)文档
Node.js 使用 officecrypto-tool 读取加密的 Excel (xls, xlsx) 和 Word( docx)文档, 还支持 xlsx 和 docx 文件的加密(具体使用看文档) ...
- 《Python魔法大冒险》008 石像怪的挑战:运算符之旅
小鱼和魔法师继续深入魔法森林.不久,他们来到了一个巨大的魔法石圈旁边.石圈中心有一个闪闪发光的魔法水晶,周围则是一些神秘的符号.但令人意外的是,水晶的旁边还有一个巨大的石像怪,它的眼睛散发着红色的光芒 ...
- SpringBoot + Redis + Token 解决接口幂等性问题
前言 SpringBoot实现接口幂等性的方案有很多,其中最常用的一种就是 token + redis 方式来实现. 下面我就通过一个案例代码,帮大家理解这种实现逻辑. 原理 前端获取服务端getTo ...