OpenCV中序列化及反序列化方法
前言
OpenCV提供了多种序列化操作的方式:
1.FileStorage: 这是OpenCV本身提供的序列化保存方法,非常适合保存参数。
2.二进制序列化: OpenCV mat 可以通过二进制序列化来保存,可以保存所有的mat类型。
3.XML和YAML序列化: 在OpenCV中,操作XML/YAML数据结构是cv::FileStorage。要打开磁盘上的指定文件,可以使用它的构造函数或this的open()函数。
4.JSON序列化: 在OpenCV中,可以使用JSON序列化OpenCV Mat的对象。
5.reshape函数: OpenCV的reshape函数既可以改变矩阵的通道数,又可以对矩阵元素进行序列化。
本文主要示例用FileStorage对xml数据进行序列化。FileStorage类提供了一种方便的方法来读写XML和YAML文件,你可以使用这个类来读写文件中的文本、数字、vector和map数据 。
一、对xml/yml进行序列化
示例如下:
#include <opencv2/opencv.hpp>
using namespace std;
using namespace cv;
int main()
{
FileStorage fs("test.xml", FileStorage::WRITE);
int a1 = 2;
char a2 = -1;
string str = "hello world!";
int arr[10] = { 1,2,3,4,5,6,7,8,9,10 };
vector<string> ve = {"hello","world"};
map<string, int> m;
m["Jack"] = 100;
m["Poly"] = 99;
m["Henry"] = 98;
//写入文件操作
fs << "int_data" << a1;
fs << "char_data" << a2;
fs << "string_data" << str;
//写入数组
fs << "array_data" << "["; //数组开始
for (int i = 0; i < 10; i++)
{
fs << arr[i];
}
fs << "]"; //数组结束
//写入vector
fs <<"vector"<<ve;
//写入map
fs << "map_data" << "{"; //map的开始写入
map<string, int>::iterator it = m.begin();
for (; it != m.end(); it++)
{
fs << it->first << it->second;
}
fs << "}"; //map写入结束
fs.release();
system("pause");
return 0;
}
生成的xml文件如下:
生成的yml文件如下:
二、对xml/yml进行反序列化
示例如下:
int main()
{
FileStorage fs("test.xml", FileStorage::READ);
auto b1 = (int)fs["int_data"];
auto b2 = (int)fs["char_data"];
auto str1 = (string)fs["string_data"];
cout << b1 << endl;
cout << b2 << endl;
cout << str1 << endl;
int arr[10];
vector<string> ve(2);
map<string, int> m;
//读入数组
FileNode arr_node = fs["array_data"];
FileNodeIterator fni = arr_node.begin();
FileNodeIterator fniEnd = arr_node.end();
int count = 0;
for (; fni != fniEnd; fni++)
{
arr[count++] = (int)(*fni) + 10;
}
for (auto value : arr)
{
cout << value << endl;
}
//读入vector
int count1 = 0;
FileNode vec_node = fs["vector"];
FileNodeIterator vecBegin = vec_node.begin();
FileNodeIterator vecEnd = vec_node.end();
for (; vecBegin != vecEnd; vecBegin++)
{
ve[count1++] = (string)(*vecBegin) + "S";
}
for (auto value : ve)
{
cout << value << endl;
}
//读入map
FileNode map_node = fs["map_data"];
m["a1"] = (int)map_node["Jack"];
m["a2"] = (int)map_node["Poly"];
m["a3"] = (int)map_node["Henry"];
cout << m["a1"] << endl;
cout << m["a2"] << endl;
cout << m["a3"] << endl;
system("pause");
return 0;
}
反序列化结果: