opencv on mbed

Dependencies:   mbed

Committer:
joeverbout
Date:
Thu Mar 31 21:16:38 2016 +0000
Revision:
0:ea44dc9ed014
OpenCV on mbed attempt

Who changed what in which revision?

UserRevisionLine numberNew contents of line
joeverbout 0:ea44dc9ed014 1 /*M///////////////////////////////////////////////////////////////////////////////////////
joeverbout 0:ea44dc9ed014 2 //
joeverbout 0:ea44dc9ed014 3 // IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
joeverbout 0:ea44dc9ed014 4 //
joeverbout 0:ea44dc9ed014 5 // By downloading, copying, installing or using the software you agree to this license.
joeverbout 0:ea44dc9ed014 6 // If you do not agree to this license, do not download, install,
joeverbout 0:ea44dc9ed014 7 // copy or use the software.
joeverbout 0:ea44dc9ed014 8 //
joeverbout 0:ea44dc9ed014 9 //
joeverbout 0:ea44dc9ed014 10 // License Agreement
joeverbout 0:ea44dc9ed014 11 // For Open Source Computer Vision Library
joeverbout 0:ea44dc9ed014 12 //
joeverbout 0:ea44dc9ed014 13 // Copyright (C) 2000-2008, Intel Corporation, all rights reserved.
joeverbout 0:ea44dc9ed014 14 // Copyright (C) 2009, Willow Garage Inc., all rights reserved.
joeverbout 0:ea44dc9ed014 15 // Copyright (C) 2013, OpenCV Foundation, all rights reserved.
joeverbout 0:ea44dc9ed014 16 // Third party copyrights are property of their respective owners.
joeverbout 0:ea44dc9ed014 17 //
joeverbout 0:ea44dc9ed014 18 // Redistribution and use in source and binary forms, with or without modification,
joeverbout 0:ea44dc9ed014 19 // are permitted provided that the following conditions are met:
joeverbout 0:ea44dc9ed014 20 //
joeverbout 0:ea44dc9ed014 21 // * Redistribution's of source code must retain the above copyright notice,
joeverbout 0:ea44dc9ed014 22 // this list of conditions and the following disclaimer.
joeverbout 0:ea44dc9ed014 23 //
joeverbout 0:ea44dc9ed014 24 // * Redistribution's in binary form must reproduce the above copyright notice,
joeverbout 0:ea44dc9ed014 25 // this list of conditions and the following disclaimer in the documentation
joeverbout 0:ea44dc9ed014 26 // and/or other materials provided with the distribution.
joeverbout 0:ea44dc9ed014 27 //
joeverbout 0:ea44dc9ed014 28 // * The name of the copyright holders may not be used to endorse or promote products
joeverbout 0:ea44dc9ed014 29 // derived from this software without specific prior written permission.
joeverbout 0:ea44dc9ed014 30 //
joeverbout 0:ea44dc9ed014 31 // This software is provided by the copyright holders and contributors "as is" and
joeverbout 0:ea44dc9ed014 32 // any express or implied warranties, including, but not limited to, the implied
joeverbout 0:ea44dc9ed014 33 // warranties of merchantability and fitness for a particular purpose are disclaimed.
joeverbout 0:ea44dc9ed014 34 // In no event shall the Intel Corporation or contributors be liable for any direct,
joeverbout 0:ea44dc9ed014 35 // indirect, incidental, special, exemplary, or consequential damages
joeverbout 0:ea44dc9ed014 36 // (including, but not limited to, procurement of substitute goods or services;
joeverbout 0:ea44dc9ed014 37 // loss of use, data, or profits; or business interruption) however caused
joeverbout 0:ea44dc9ed014 38 // and on any theory of liability, whether in contract, strict liability,
joeverbout 0:ea44dc9ed014 39 // or tort (including negligence or otherwise) arising in any way out of
joeverbout 0:ea44dc9ed014 40 // the use of this software, even if advised of the possibility of such damage.
joeverbout 0:ea44dc9ed014 41 //
joeverbout 0:ea44dc9ed014 42 //M*/
joeverbout 0:ea44dc9ed014 43
joeverbout 0:ea44dc9ed014 44 #ifndef __OPENCV_CORE_PERSISTENCE_HPP__
joeverbout 0:ea44dc9ed014 45 #define __OPENCV_CORE_PERSISTENCE_HPP__
joeverbout 0:ea44dc9ed014 46
joeverbout 0:ea44dc9ed014 47 #ifndef __cplusplus
joeverbout 0:ea44dc9ed014 48 # error persistence.hpp header must be compiled as C++
joeverbout 0:ea44dc9ed014 49 #endif
joeverbout 0:ea44dc9ed014 50
joeverbout 0:ea44dc9ed014 51 //! @addtogroup core_c
joeverbout 0:ea44dc9ed014 52 //! @{
joeverbout 0:ea44dc9ed014 53
joeverbout 0:ea44dc9ed014 54 /** @brief "black box" representation of the file storage associated with a file on disk.
joeverbout 0:ea44dc9ed014 55
joeverbout 0:ea44dc9ed014 56 Several functions that are described below take CvFileStorage\* as inputs and allow the user to
joeverbout 0:ea44dc9ed014 57 save or to load hierarchical collections that consist of scalar values, standard CXCore objects
joeverbout 0:ea44dc9ed014 58 (such as matrices, sequences, graphs), and user-defined objects.
joeverbout 0:ea44dc9ed014 59
joeverbout 0:ea44dc9ed014 60 OpenCV can read and write data in XML (<http://www.w3c.org/XML>) or YAML (<http://www.yaml.org>)
joeverbout 0:ea44dc9ed014 61 formats. Below is an example of 3x3 floating-point identity matrix A, stored in XML and YAML files
joeverbout 0:ea44dc9ed014 62 using CXCore functions:
joeverbout 0:ea44dc9ed014 63 XML:
joeverbout 0:ea44dc9ed014 64 @code{.xml}
joeverbout 0:ea44dc9ed014 65 <?xml version="1.0">
joeverbout 0:ea44dc9ed014 66 <opencv_storage>
joeverbout 0:ea44dc9ed014 67 <A type_id="opencv-matrix">
joeverbout 0:ea44dc9ed014 68 <rows>3</rows>
joeverbout 0:ea44dc9ed014 69 <cols>3</cols>
joeverbout 0:ea44dc9ed014 70 <dt>f</dt>
joeverbout 0:ea44dc9ed014 71 <data>1. 0. 0. 0. 1. 0. 0. 0. 1.</data>
joeverbout 0:ea44dc9ed014 72 </A>
joeverbout 0:ea44dc9ed014 73 </opencv_storage>
joeverbout 0:ea44dc9ed014 74 @endcode
joeverbout 0:ea44dc9ed014 75 YAML:
joeverbout 0:ea44dc9ed014 76 @code{.yaml}
joeverbout 0:ea44dc9ed014 77 %YAML:1.0
joeverbout 0:ea44dc9ed014 78 A: !!opencv-matrix
joeverbout 0:ea44dc9ed014 79 rows: 3
joeverbout 0:ea44dc9ed014 80 cols: 3
joeverbout 0:ea44dc9ed014 81 dt: f
joeverbout 0:ea44dc9ed014 82 data: [ 1., 0., 0., 0., 1., 0., 0., 0., 1.]
joeverbout 0:ea44dc9ed014 83 @endcode
joeverbout 0:ea44dc9ed014 84 As it can be seen from the examples, XML uses nested tags to represent hierarchy, while YAML uses
joeverbout 0:ea44dc9ed014 85 indentation for that purpose (similar to the Python programming language).
joeverbout 0:ea44dc9ed014 86
joeverbout 0:ea44dc9ed014 87 The same functions can read and write data in both formats; the particular format is determined by
joeverbout 0:ea44dc9ed014 88 the extension of the opened file, ".xml" for XML files and ".yml" or ".yaml" for YAML.
joeverbout 0:ea44dc9ed014 89 */
joeverbout 0:ea44dc9ed014 90 typedef struct CvFileStorage CvFileStorage;
joeverbout 0:ea44dc9ed014 91 typedef struct CvFileNode CvFileNode;
joeverbout 0:ea44dc9ed014 92
joeverbout 0:ea44dc9ed014 93 //! @} core_c
joeverbout 0:ea44dc9ed014 94
joeverbout 0:ea44dc9ed014 95 #include "opencv2/core/types.hpp"
joeverbout 0:ea44dc9ed014 96 #include "opencv2/core/mat.hpp"
joeverbout 0:ea44dc9ed014 97
joeverbout 0:ea44dc9ed014 98 namespace cv {
joeverbout 0:ea44dc9ed014 99
joeverbout 0:ea44dc9ed014 100 /** @addtogroup core_xml
joeverbout 0:ea44dc9ed014 101
joeverbout 0:ea44dc9ed014 102 XML/YAML file storages. {#xml_storage}
joeverbout 0:ea44dc9ed014 103 =======================
joeverbout 0:ea44dc9ed014 104 Writing to a file storage.
joeverbout 0:ea44dc9ed014 105 --------------------------
joeverbout 0:ea44dc9ed014 106 You can store and then restore various OpenCV data structures to/from XML (<http://www.w3c.org/XML>)
joeverbout 0:ea44dc9ed014 107 or YAML (<http://www.yaml.org>) formats. Also, it is possible store and load arbitrarily complex
joeverbout 0:ea44dc9ed014 108 data structures, which include OpenCV data structures, as well as primitive data types (integer and
joeverbout 0:ea44dc9ed014 109 floating-point numbers and text strings) as their elements.
joeverbout 0:ea44dc9ed014 110
joeverbout 0:ea44dc9ed014 111 Use the following procedure to write something to XML or YAML:
joeverbout 0:ea44dc9ed014 112 -# Create new FileStorage and open it for writing. It can be done with a single call to
joeverbout 0:ea44dc9ed014 113 FileStorage::FileStorage constructor that takes a filename, or you can use the default constructor
joeverbout 0:ea44dc9ed014 114 and then call FileStorage::open. Format of the file (XML or YAML) is determined from the filename
joeverbout 0:ea44dc9ed014 115 extension (".xml" and ".yml"/".yaml", respectively)
joeverbout 0:ea44dc9ed014 116 -# Write all the data you want using the streaming operator `<<`, just like in the case of STL
joeverbout 0:ea44dc9ed014 117 streams.
joeverbout 0:ea44dc9ed014 118 -# Close the file using FileStorage::release. FileStorage destructor also closes the file.
joeverbout 0:ea44dc9ed014 119
joeverbout 0:ea44dc9ed014 120 Here is an example:
joeverbout 0:ea44dc9ed014 121 @code
joeverbout 0:ea44dc9ed014 122 #include "opencv2/opencv.hpp"
joeverbout 0:ea44dc9ed014 123 #include <time.h>
joeverbout 0:ea44dc9ed014 124
joeverbout 0:ea44dc9ed014 125 using namespace cv;
joeverbout 0:ea44dc9ed014 126
joeverbout 0:ea44dc9ed014 127 int main(int, char** argv)
joeverbout 0:ea44dc9ed014 128 {
joeverbout 0:ea44dc9ed014 129 FileStorage fs("test.yml", FileStorage::WRITE);
joeverbout 0:ea44dc9ed014 130
joeverbout 0:ea44dc9ed014 131 fs << "frameCount" << 5;
joeverbout 0:ea44dc9ed014 132 time_t rawtime; time(&rawtime);
joeverbout 0:ea44dc9ed014 133 fs << "calibrationDate" << asctime(localtime(&rawtime));
joeverbout 0:ea44dc9ed014 134 Mat cameraMatrix = (Mat_<double>(3,3) << 1000, 0, 320, 0, 1000, 240, 0, 0, 1);
joeverbout 0:ea44dc9ed014 135 Mat distCoeffs = (Mat_<double>(5,1) << 0.1, 0.01, -0.001, 0, 0);
joeverbout 0:ea44dc9ed014 136 fs << "cameraMatrix" << cameraMatrix << "distCoeffs" << distCoeffs;
joeverbout 0:ea44dc9ed014 137 fs << "features" << "[";
joeverbout 0:ea44dc9ed014 138 for( int i = 0; i < 3; i++ )
joeverbout 0:ea44dc9ed014 139 {
joeverbout 0:ea44dc9ed014 140 int x = rand() % 640;
joeverbout 0:ea44dc9ed014 141 int y = rand() % 480;
joeverbout 0:ea44dc9ed014 142 uchar lbp = rand() % 256;
joeverbout 0:ea44dc9ed014 143
joeverbout 0:ea44dc9ed014 144 fs << "{:" << "x" << x << "y" << y << "lbp" << "[:";
joeverbout 0:ea44dc9ed014 145 for( int j = 0; j < 8; j++ )
joeverbout 0:ea44dc9ed014 146 fs << ((lbp >> j) & 1);
joeverbout 0:ea44dc9ed014 147 fs << "]" << "}";
joeverbout 0:ea44dc9ed014 148 }
joeverbout 0:ea44dc9ed014 149 fs << "]";
joeverbout 0:ea44dc9ed014 150 fs.release();
joeverbout 0:ea44dc9ed014 151 return 0;
joeverbout 0:ea44dc9ed014 152 }
joeverbout 0:ea44dc9ed014 153 @endcode
joeverbout 0:ea44dc9ed014 154 The sample above stores to XML and integer, text string (calibration date), 2 matrices, and a custom
joeverbout 0:ea44dc9ed014 155 structure "feature", which includes feature coordinates and LBP (local binary pattern) value. Here
joeverbout 0:ea44dc9ed014 156 is output of the sample:
joeverbout 0:ea44dc9ed014 157 @code{.yaml}
joeverbout 0:ea44dc9ed014 158 %YAML:1.0
joeverbout 0:ea44dc9ed014 159 frameCount: 5
joeverbout 0:ea44dc9ed014 160 calibrationDate: "Fri Jun 17 14:09:29 2011\n"
joeverbout 0:ea44dc9ed014 161 cameraMatrix: !!opencv-matrix
joeverbout 0:ea44dc9ed014 162 rows: 3
joeverbout 0:ea44dc9ed014 163 cols: 3
joeverbout 0:ea44dc9ed014 164 dt: d
joeverbout 0:ea44dc9ed014 165 data: [ 1000., 0., 320., 0., 1000., 240., 0., 0., 1. ]
joeverbout 0:ea44dc9ed014 166 distCoeffs: !!opencv-matrix
joeverbout 0:ea44dc9ed014 167 rows: 5
joeverbout 0:ea44dc9ed014 168 cols: 1
joeverbout 0:ea44dc9ed014 169 dt: d
joeverbout 0:ea44dc9ed014 170 data: [ 1.0000000000000001e-01, 1.0000000000000000e-02,
joeverbout 0:ea44dc9ed014 171 -1.0000000000000000e-03, 0., 0. ]
joeverbout 0:ea44dc9ed014 172 features:
joeverbout 0:ea44dc9ed014 173 - { x:167, y:49, lbp:[ 1, 0, 0, 1, 1, 0, 1, 1 ] }
joeverbout 0:ea44dc9ed014 174 - { x:298, y:130, lbp:[ 0, 0, 0, 1, 0, 0, 1, 1 ] }
joeverbout 0:ea44dc9ed014 175 - { x:344, y:158, lbp:[ 1, 1, 0, 0, 0, 0, 1, 0 ] }
joeverbout 0:ea44dc9ed014 176 @endcode
joeverbout 0:ea44dc9ed014 177
joeverbout 0:ea44dc9ed014 178 As an exercise, you can replace ".yml" with ".xml" in the sample above and see, how the
joeverbout 0:ea44dc9ed014 179 corresponding XML file will look like.
joeverbout 0:ea44dc9ed014 180
joeverbout 0:ea44dc9ed014 181 Several things can be noted by looking at the sample code and the output:
joeverbout 0:ea44dc9ed014 182
joeverbout 0:ea44dc9ed014 183 - The produced YAML (and XML) consists of heterogeneous collections that can be nested. There are 2
joeverbout 0:ea44dc9ed014 184 types of collections: named collections (mappings) and unnamed collections (sequences). In mappings
joeverbout 0:ea44dc9ed014 185 each element has a name and is accessed by name. This is similar to structures and std::map in
joeverbout 0:ea44dc9ed014 186 C/C++ and dictionaries in Python. In sequences elements do not have names, they are accessed by
joeverbout 0:ea44dc9ed014 187 indices. This is similar to arrays and std::vector in C/C++ and lists, tuples in Python.
joeverbout 0:ea44dc9ed014 188 "Heterogeneous" means that elements of each single collection can have different types.
joeverbout 0:ea44dc9ed014 189
joeverbout 0:ea44dc9ed014 190 Top-level collection in YAML/XML is a mapping. Each matrix is stored as a mapping, and the matrix
joeverbout 0:ea44dc9ed014 191 elements are stored as a sequence. Then, there is a sequence of features, where each feature is
joeverbout 0:ea44dc9ed014 192 represented a mapping, and lbp value in a nested sequence.
joeverbout 0:ea44dc9ed014 193
joeverbout 0:ea44dc9ed014 194 - When you write to a mapping (a structure), you write element name followed by its value. When you
joeverbout 0:ea44dc9ed014 195 write to a sequence, you simply write the elements one by one. OpenCV data structures (such as
joeverbout 0:ea44dc9ed014 196 cv::Mat) are written in absolutely the same way as simple C data structures - using `<<`
joeverbout 0:ea44dc9ed014 197 operator.
joeverbout 0:ea44dc9ed014 198
joeverbout 0:ea44dc9ed014 199 - To write a mapping, you first write the special string `{` to the storage, then write the
joeverbout 0:ea44dc9ed014 200 elements as pairs (`fs << <element_name> << <element_value>`) and then write the closing
joeverbout 0:ea44dc9ed014 201 `}`.
joeverbout 0:ea44dc9ed014 202
joeverbout 0:ea44dc9ed014 203 - To write a sequence, you first write the special string `[`, then write the elements, then
joeverbout 0:ea44dc9ed014 204 write the closing `]`.
joeverbout 0:ea44dc9ed014 205
joeverbout 0:ea44dc9ed014 206 - In YAML (but not XML), mappings and sequences can be written in a compact Python-like inline
joeverbout 0:ea44dc9ed014 207 form. In the sample above matrix elements, as well as each feature, including its lbp value, is
joeverbout 0:ea44dc9ed014 208 stored in such inline form. To store a mapping/sequence in a compact form, put `:` after the
joeverbout 0:ea44dc9ed014 209 opening character, e.g. use `{:` instead of `{` and `[:` instead of `[`. When the
joeverbout 0:ea44dc9ed014 210 data is written to XML, those extra `:` are ignored.
joeverbout 0:ea44dc9ed014 211
joeverbout 0:ea44dc9ed014 212 Reading data from a file storage.
joeverbout 0:ea44dc9ed014 213 ---------------------------------
joeverbout 0:ea44dc9ed014 214 To read the previously written XML or YAML file, do the following:
joeverbout 0:ea44dc9ed014 215 -# Open the file storage using FileStorage::FileStorage constructor or FileStorage::open method.
joeverbout 0:ea44dc9ed014 216 In the current implementation the whole file is parsed and the whole representation of file
joeverbout 0:ea44dc9ed014 217 storage is built in memory as a hierarchy of file nodes (see FileNode)
joeverbout 0:ea44dc9ed014 218
joeverbout 0:ea44dc9ed014 219 -# Read the data you are interested in. Use FileStorage::operator [], FileNode::operator []
joeverbout 0:ea44dc9ed014 220 and/or FileNodeIterator.
joeverbout 0:ea44dc9ed014 221
joeverbout 0:ea44dc9ed014 222 -# Close the storage using FileStorage::release.
joeverbout 0:ea44dc9ed014 223
joeverbout 0:ea44dc9ed014 224 Here is how to read the file created by the code sample above:
joeverbout 0:ea44dc9ed014 225 @code
joeverbout 0:ea44dc9ed014 226 FileStorage fs2("test.yml", FileStorage::READ);
joeverbout 0:ea44dc9ed014 227
joeverbout 0:ea44dc9ed014 228 // first method: use (type) operator on FileNode.
joeverbout 0:ea44dc9ed014 229 int frameCount = (int)fs2["frameCount"];
joeverbout 0:ea44dc9ed014 230
joeverbout 0:ea44dc9ed014 231 String date;
joeverbout 0:ea44dc9ed014 232 // second method: use FileNode::operator >>
joeverbout 0:ea44dc9ed014 233 fs2["calibrationDate"] >> date;
joeverbout 0:ea44dc9ed014 234
joeverbout 0:ea44dc9ed014 235 Mat cameraMatrix2, distCoeffs2;
joeverbout 0:ea44dc9ed014 236 fs2["cameraMatrix"] >> cameraMatrix2;
joeverbout 0:ea44dc9ed014 237 fs2["distCoeffs"] >> distCoeffs2;
joeverbout 0:ea44dc9ed014 238
joeverbout 0:ea44dc9ed014 239 cout << "frameCount: " << frameCount << endl
joeverbout 0:ea44dc9ed014 240 << "calibration date: " << date << endl
joeverbout 0:ea44dc9ed014 241 << "camera matrix: " << cameraMatrix2 << endl
joeverbout 0:ea44dc9ed014 242 << "distortion coeffs: " << distCoeffs2 << endl;
joeverbout 0:ea44dc9ed014 243
joeverbout 0:ea44dc9ed014 244 FileNode features = fs2["features"];
joeverbout 0:ea44dc9ed014 245 FileNodeIterator it = features.begin(), it_end = features.end();
joeverbout 0:ea44dc9ed014 246 int idx = 0;
joeverbout 0:ea44dc9ed014 247 std::vector<uchar> lbpval;
joeverbout 0:ea44dc9ed014 248
joeverbout 0:ea44dc9ed014 249 // iterate through a sequence using FileNodeIterator
joeverbout 0:ea44dc9ed014 250 for( ; it != it_end; ++it, idx++ )
joeverbout 0:ea44dc9ed014 251 {
joeverbout 0:ea44dc9ed014 252 cout << "feature #" << idx << ": ";
joeverbout 0:ea44dc9ed014 253 cout << "x=" << (int)(*it)["x"] << ", y=" << (int)(*it)["y"] << ", lbp: (";
joeverbout 0:ea44dc9ed014 254 // you can also easily read numerical arrays using FileNode >> std::vector operator.
joeverbout 0:ea44dc9ed014 255 (*it)["lbp"] >> lbpval;
joeverbout 0:ea44dc9ed014 256 for( int i = 0; i < (int)lbpval.size(); i++ )
joeverbout 0:ea44dc9ed014 257 cout << " " << (int)lbpval[i];
joeverbout 0:ea44dc9ed014 258 cout << ")" << endl;
joeverbout 0:ea44dc9ed014 259 }
joeverbout 0:ea44dc9ed014 260 fs2.release();
joeverbout 0:ea44dc9ed014 261 @endcode
joeverbout 0:ea44dc9ed014 262
joeverbout 0:ea44dc9ed014 263 Format specification {#format_spec}
joeverbout 0:ea44dc9ed014 264 --------------------
joeverbout 0:ea44dc9ed014 265 `([count]{u|c|w|s|i|f|d})`... where the characters correspond to fundamental C++ types:
joeverbout 0:ea44dc9ed014 266 - `u` 8-bit unsigned number
joeverbout 0:ea44dc9ed014 267 - `c` 8-bit signed number
joeverbout 0:ea44dc9ed014 268 - `w` 16-bit unsigned number
joeverbout 0:ea44dc9ed014 269 - `s` 16-bit signed number
joeverbout 0:ea44dc9ed014 270 - `i` 32-bit signed number
joeverbout 0:ea44dc9ed014 271 - `f` single precision floating-point number
joeverbout 0:ea44dc9ed014 272 - `d` double precision floating-point number
joeverbout 0:ea44dc9ed014 273 - `r` pointer, 32 lower bits of which are written as a signed integer. The type can be used to
joeverbout 0:ea44dc9ed014 274 store structures with links between the elements.
joeverbout 0:ea44dc9ed014 275
joeverbout 0:ea44dc9ed014 276 `count` is the optional counter of values of a given type. For example, `2if` means that each array
joeverbout 0:ea44dc9ed014 277 element is a structure of 2 integers, followed by a single-precision floating-point number. The
joeverbout 0:ea44dc9ed014 278 equivalent notations of the above specification are `iif`, `2i1f` and so forth. Other examples: `u`
joeverbout 0:ea44dc9ed014 279 means that the array consists of bytes, and `2d` means the array consists of pairs of doubles.
joeverbout 0:ea44dc9ed014 280
joeverbout 0:ea44dc9ed014 281 @see @ref filestorage.cpp
joeverbout 0:ea44dc9ed014 282 */
joeverbout 0:ea44dc9ed014 283
joeverbout 0:ea44dc9ed014 284 //! @{
joeverbout 0:ea44dc9ed014 285
joeverbout 0:ea44dc9ed014 286 /** @example filestorage.cpp
joeverbout 0:ea44dc9ed014 287 A complete example using the FileStorage interface
joeverbout 0:ea44dc9ed014 288 */
joeverbout 0:ea44dc9ed014 289
joeverbout 0:ea44dc9ed014 290 ////////////////////////// XML & YAML I/O //////////////////////////
joeverbout 0:ea44dc9ed014 291
joeverbout 0:ea44dc9ed014 292 class CV_EXPORTS FileNode;
joeverbout 0:ea44dc9ed014 293 class CV_EXPORTS FileNodeIterator;
joeverbout 0:ea44dc9ed014 294
joeverbout 0:ea44dc9ed014 295 /** @brief XML/YAML file storage class that encapsulates all the information necessary for writing or reading
joeverbout 0:ea44dc9ed014 296 data to/from a file.
joeverbout 0:ea44dc9ed014 297 */
joeverbout 0:ea44dc9ed014 298 class CV_EXPORTS_W FileStorage
joeverbout 0:ea44dc9ed014 299 {
joeverbout 0:ea44dc9ed014 300 public:
joeverbout 0:ea44dc9ed014 301 //! file storage mode
joeverbout 0:ea44dc9ed014 302 enum Mode
joeverbout 0:ea44dc9ed014 303 {
joeverbout 0:ea44dc9ed014 304 READ = 0, //!< value, open the file for reading
joeverbout 0:ea44dc9ed014 305 WRITE = 1, //!< value, open the file for writing
joeverbout 0:ea44dc9ed014 306 APPEND = 2, //!< value, open the file for appending
joeverbout 0:ea44dc9ed014 307 MEMORY = 4, //!< flag, read data from source or write data to the internal buffer (which is
joeverbout 0:ea44dc9ed014 308 //!< returned by FileStorage::release)
joeverbout 0:ea44dc9ed014 309 FORMAT_MASK = (7<<3), //!< mask for format flags
joeverbout 0:ea44dc9ed014 310 FORMAT_AUTO = 0, //!< flag, auto format
joeverbout 0:ea44dc9ed014 311 FORMAT_XML = (1<<3), //!< flag, XML format
joeverbout 0:ea44dc9ed014 312 FORMAT_YAML = (2<<3) //!< flag, YAML format
joeverbout 0:ea44dc9ed014 313 };
joeverbout 0:ea44dc9ed014 314 enum
joeverbout 0:ea44dc9ed014 315 {
joeverbout 0:ea44dc9ed014 316 UNDEFINED = 0,
joeverbout 0:ea44dc9ed014 317 VALUE_EXPECTED = 1,
joeverbout 0:ea44dc9ed014 318 NAME_EXPECTED = 2,
joeverbout 0:ea44dc9ed014 319 INSIDE_MAP = 4
joeverbout 0:ea44dc9ed014 320 };
joeverbout 0:ea44dc9ed014 321
joeverbout 0:ea44dc9ed014 322 /** @brief The constructors.
joeverbout 0:ea44dc9ed014 323
joeverbout 0:ea44dc9ed014 324 The full constructor opens the file. Alternatively you can use the default constructor and then
joeverbout 0:ea44dc9ed014 325 call FileStorage::open.
joeverbout 0:ea44dc9ed014 326 */
joeverbout 0:ea44dc9ed014 327 CV_WRAP FileStorage();
joeverbout 0:ea44dc9ed014 328
joeverbout 0:ea44dc9ed014 329 /** @overload
joeverbout 0:ea44dc9ed014 330 @param source Name of the file to open or the text string to read the data from. Extension of the
joeverbout 0:ea44dc9ed014 331 file (.xml or .yml/.yaml) determines its format (XML or YAML respectively). Also you can append .gz
joeverbout 0:ea44dc9ed014 332 to work with compressed files, for example myHugeMatrix.xml.gz. If both FileStorage::WRITE and
joeverbout 0:ea44dc9ed014 333 FileStorage::MEMORY flags are specified, source is used just to specify the output file format (e.g.
joeverbout 0:ea44dc9ed014 334 mydata.xml, .yml etc.).
joeverbout 0:ea44dc9ed014 335 @param flags Mode of operation. See FileStorage::Mode
joeverbout 0:ea44dc9ed014 336 @param encoding Encoding of the file. Note that UTF-16 XML encoding is not supported currently and
joeverbout 0:ea44dc9ed014 337 you should use 8-bit encoding instead of it.
joeverbout 0:ea44dc9ed014 338 */
joeverbout 0:ea44dc9ed014 339 CV_WRAP FileStorage(const String& source, int flags, const String& encoding=String());
joeverbout 0:ea44dc9ed014 340
joeverbout 0:ea44dc9ed014 341 /** @overload */
joeverbout 0:ea44dc9ed014 342 FileStorage(CvFileStorage* fs, bool owning=true);
joeverbout 0:ea44dc9ed014 343
joeverbout 0:ea44dc9ed014 344 //! the destructor. calls release()
joeverbout 0:ea44dc9ed014 345 virtual ~FileStorage();
joeverbout 0:ea44dc9ed014 346
joeverbout 0:ea44dc9ed014 347 /** @brief Opens a file.
joeverbout 0:ea44dc9ed014 348
joeverbout 0:ea44dc9ed014 349 See description of parameters in FileStorage::FileStorage. The method calls FileStorage::release
joeverbout 0:ea44dc9ed014 350 before opening the file.
joeverbout 0:ea44dc9ed014 351 @param filename Name of the file to open or the text string to read the data from.
joeverbout 0:ea44dc9ed014 352 Extension of the file (.xml or .yml/.yaml) determines its format (XML or YAML respectively).
joeverbout 0:ea44dc9ed014 353 Also you can append .gz to work with compressed files, for example myHugeMatrix.xml.gz. If both
joeverbout 0:ea44dc9ed014 354 FileStorage::WRITE and FileStorage::MEMORY flags are specified, source is used just to specify
joeverbout 0:ea44dc9ed014 355 the output file format (e.g. mydata.xml, .yml etc.).
joeverbout 0:ea44dc9ed014 356 @param flags Mode of operation. One of FileStorage::Mode
joeverbout 0:ea44dc9ed014 357 @param encoding Encoding of the file. Note that UTF-16 XML encoding is not supported currently and
joeverbout 0:ea44dc9ed014 358 you should use 8-bit encoding instead of it.
joeverbout 0:ea44dc9ed014 359 */
joeverbout 0:ea44dc9ed014 360 CV_WRAP virtual bool open(const String& filename, int flags, const String& encoding=String());
joeverbout 0:ea44dc9ed014 361
joeverbout 0:ea44dc9ed014 362 /** @brief Checks whether the file is opened.
joeverbout 0:ea44dc9ed014 363
joeverbout 0:ea44dc9ed014 364 @returns true if the object is associated with the current file and false otherwise. It is a
joeverbout 0:ea44dc9ed014 365 good practice to call this method after you tried to open a file.
joeverbout 0:ea44dc9ed014 366 */
joeverbout 0:ea44dc9ed014 367 CV_WRAP virtual bool isOpened() const;
joeverbout 0:ea44dc9ed014 368
joeverbout 0:ea44dc9ed014 369 /** @brief Closes the file and releases all the memory buffers.
joeverbout 0:ea44dc9ed014 370
joeverbout 0:ea44dc9ed014 371 Call this method after all I/O operations with the storage are finished.
joeverbout 0:ea44dc9ed014 372 */
joeverbout 0:ea44dc9ed014 373 CV_WRAP virtual void release();
joeverbout 0:ea44dc9ed014 374
joeverbout 0:ea44dc9ed014 375 /** @brief Closes the file and releases all the memory buffers.
joeverbout 0:ea44dc9ed014 376
joeverbout 0:ea44dc9ed014 377 Call this method after all I/O operations with the storage are finished. If the storage was
joeverbout 0:ea44dc9ed014 378 opened for writing data and FileStorage::WRITE was specified
joeverbout 0:ea44dc9ed014 379 */
joeverbout 0:ea44dc9ed014 380 CV_WRAP virtual String releaseAndGetString();
joeverbout 0:ea44dc9ed014 381
joeverbout 0:ea44dc9ed014 382 /** @brief Returns the first element of the top-level mapping.
joeverbout 0:ea44dc9ed014 383 @returns The first element of the top-level mapping.
joeverbout 0:ea44dc9ed014 384 */
joeverbout 0:ea44dc9ed014 385 CV_WRAP FileNode getFirstTopLevelNode() const;
joeverbout 0:ea44dc9ed014 386
joeverbout 0:ea44dc9ed014 387 /** @brief Returns the top-level mapping
joeverbout 0:ea44dc9ed014 388 @param streamidx Zero-based index of the stream. In most cases there is only one stream in the file.
joeverbout 0:ea44dc9ed014 389 However, YAML supports multiple streams and so there can be several.
joeverbout 0:ea44dc9ed014 390 @returns The top-level mapping.
joeverbout 0:ea44dc9ed014 391 */
joeverbout 0:ea44dc9ed014 392 CV_WRAP FileNode root(int streamidx=0) const;
joeverbout 0:ea44dc9ed014 393
joeverbout 0:ea44dc9ed014 394 /** @brief Returns the specified element of the top-level mapping.
joeverbout 0:ea44dc9ed014 395 @param nodename Name of the file node.
joeverbout 0:ea44dc9ed014 396 @returns Node with the given name.
joeverbout 0:ea44dc9ed014 397 */
joeverbout 0:ea44dc9ed014 398 FileNode operator[](const String& nodename) const;
joeverbout 0:ea44dc9ed014 399
joeverbout 0:ea44dc9ed014 400 /** @overload */
joeverbout 0:ea44dc9ed014 401 CV_WRAP FileNode operator[](const char* nodename) const;
joeverbout 0:ea44dc9ed014 402
joeverbout 0:ea44dc9ed014 403 /** @brief Returns the obsolete C FileStorage structure.
joeverbout 0:ea44dc9ed014 404 @returns Pointer to the underlying C FileStorage structure
joeverbout 0:ea44dc9ed014 405 */
joeverbout 0:ea44dc9ed014 406 CvFileStorage* operator *() { return fs.get(); }
joeverbout 0:ea44dc9ed014 407
joeverbout 0:ea44dc9ed014 408 /** @overload */
joeverbout 0:ea44dc9ed014 409 const CvFileStorage* operator *() const { return fs.get(); }
joeverbout 0:ea44dc9ed014 410
joeverbout 0:ea44dc9ed014 411 /** @brief Writes multiple numbers.
joeverbout 0:ea44dc9ed014 412
joeverbout 0:ea44dc9ed014 413 Writes one or more numbers of the specified format to the currently written structure. Usually it is
joeverbout 0:ea44dc9ed014 414 more convenient to use operator `<<` instead of this method.
joeverbout 0:ea44dc9ed014 415 @param fmt Specification of each array element, see @ref format_spec "format specification"
joeverbout 0:ea44dc9ed014 416 @param vec Pointer to the written array.
joeverbout 0:ea44dc9ed014 417 @param len Number of the uchar elements to write.
joeverbout 0:ea44dc9ed014 418 */
joeverbout 0:ea44dc9ed014 419 void writeRaw( const String& fmt, const uchar* vec, size_t len );
joeverbout 0:ea44dc9ed014 420
joeverbout 0:ea44dc9ed014 421 /** @brief Writes the registered C structure (CvMat, CvMatND, CvSeq).
joeverbout 0:ea44dc9ed014 422 @param name Name of the written object.
joeverbout 0:ea44dc9ed014 423 @param obj Pointer to the object.
joeverbout 0:ea44dc9ed014 424 @see ocvWrite for details.
joeverbout 0:ea44dc9ed014 425 */
joeverbout 0:ea44dc9ed014 426 void writeObj( const String& name, const void* obj );
joeverbout 0:ea44dc9ed014 427
joeverbout 0:ea44dc9ed014 428 /** @brief Returns the normalized object name for the specified name of a file.
joeverbout 0:ea44dc9ed014 429 @param filename Name of a file
joeverbout 0:ea44dc9ed014 430 @returns The normalized object name.
joeverbout 0:ea44dc9ed014 431 */
joeverbout 0:ea44dc9ed014 432 static String getDefaultObjectName(const String& filename);
joeverbout 0:ea44dc9ed014 433
joeverbout 0:ea44dc9ed014 434 Ptr<CvFileStorage> fs; //!< the underlying C FileStorage structure
joeverbout 0:ea44dc9ed014 435 String elname; //!< the currently written element
joeverbout 0:ea44dc9ed014 436 std::vector<char> structs; //!< the stack of written structures
joeverbout 0:ea44dc9ed014 437 int state; //!< the writer state
joeverbout 0:ea44dc9ed014 438 };
joeverbout 0:ea44dc9ed014 439
joeverbout 0:ea44dc9ed014 440 template<> CV_EXPORTS void DefaultDeleter<CvFileStorage>::operator ()(CvFileStorage* obj) const;
joeverbout 0:ea44dc9ed014 441
joeverbout 0:ea44dc9ed014 442 /** @brief File Storage Node class.
joeverbout 0:ea44dc9ed014 443
joeverbout 0:ea44dc9ed014 444 The node is used to store each and every element of the file storage opened for reading. When
joeverbout 0:ea44dc9ed014 445 XML/YAML file is read, it is first parsed and stored in the memory as a hierarchical collection of
joeverbout 0:ea44dc9ed014 446 nodes. Each node can be a “leaf” that is contain a single number or a string, or be a collection of
joeverbout 0:ea44dc9ed014 447 other nodes. There can be named collections (mappings) where each element has a name and it is
joeverbout 0:ea44dc9ed014 448 accessed by a name, and ordered collections (sequences) where elements do not have names but rather
joeverbout 0:ea44dc9ed014 449 accessed by index. Type of the file node can be determined using FileNode::type method.
joeverbout 0:ea44dc9ed014 450
joeverbout 0:ea44dc9ed014 451 Note that file nodes are only used for navigating file storages opened for reading. When a file
joeverbout 0:ea44dc9ed014 452 storage is opened for writing, no data is stored in memory after it is written.
joeverbout 0:ea44dc9ed014 453 */
joeverbout 0:ea44dc9ed014 454 class CV_EXPORTS_W_SIMPLE FileNode
joeverbout 0:ea44dc9ed014 455 {
joeverbout 0:ea44dc9ed014 456 public:
joeverbout 0:ea44dc9ed014 457 //! type of the file storage node
joeverbout 0:ea44dc9ed014 458 enum Type
joeverbout 0:ea44dc9ed014 459 {
joeverbout 0:ea44dc9ed014 460 NONE = 0, //!< empty node
joeverbout 0:ea44dc9ed014 461 INT = 1, //!< an integer
joeverbout 0:ea44dc9ed014 462 REAL = 2, //!< floating-point number
joeverbout 0:ea44dc9ed014 463 FLOAT = REAL, //!< synonym or REAL
joeverbout 0:ea44dc9ed014 464 STR = 3, //!< text string in UTF-8 encoding
joeverbout 0:ea44dc9ed014 465 STRING = STR, //!< synonym for STR
joeverbout 0:ea44dc9ed014 466 REF = 4, //!< integer of size size_t. Typically used for storing complex dynamic structures where some elements reference the others
joeverbout 0:ea44dc9ed014 467 SEQ = 5, //!< sequence
joeverbout 0:ea44dc9ed014 468 MAP = 6, //!< mapping
joeverbout 0:ea44dc9ed014 469 TYPE_MASK = 7,
joeverbout 0:ea44dc9ed014 470 FLOW = 8, //!< compact representation of a sequence or mapping. Used only by YAML writer
joeverbout 0:ea44dc9ed014 471 USER = 16, //!< a registered object (e.g. a matrix)
joeverbout 0:ea44dc9ed014 472 EMPTY = 32, //!< empty structure (sequence or mapping)
joeverbout 0:ea44dc9ed014 473 NAMED = 64 //!< the node has a name (i.e. it is element of a mapping)
joeverbout 0:ea44dc9ed014 474 };
joeverbout 0:ea44dc9ed014 475 /** @brief The constructors.
joeverbout 0:ea44dc9ed014 476
joeverbout 0:ea44dc9ed014 477 These constructors are used to create a default file node, construct it from obsolete structures or
joeverbout 0:ea44dc9ed014 478 from the another file node.
joeverbout 0:ea44dc9ed014 479 */
joeverbout 0:ea44dc9ed014 480 CV_WRAP FileNode();
joeverbout 0:ea44dc9ed014 481
joeverbout 0:ea44dc9ed014 482 /** @overload
joeverbout 0:ea44dc9ed014 483 @param fs Pointer to the obsolete file storage structure.
joeverbout 0:ea44dc9ed014 484 @param node File node to be used as initialization for the created file node.
joeverbout 0:ea44dc9ed014 485 */
joeverbout 0:ea44dc9ed014 486 FileNode(const CvFileStorage* fs, const CvFileNode* node);
joeverbout 0:ea44dc9ed014 487
joeverbout 0:ea44dc9ed014 488 /** @overload
joeverbout 0:ea44dc9ed014 489 @param node File node to be used as initialization for the created file node.
joeverbout 0:ea44dc9ed014 490 */
joeverbout 0:ea44dc9ed014 491 FileNode(const FileNode& node);
joeverbout 0:ea44dc9ed014 492
joeverbout 0:ea44dc9ed014 493 /** @brief Returns element of a mapping node or a sequence node.
joeverbout 0:ea44dc9ed014 494 @param nodename Name of an element in the mapping node.
joeverbout 0:ea44dc9ed014 495 @returns Returns the element with the given identifier.
joeverbout 0:ea44dc9ed014 496 */
joeverbout 0:ea44dc9ed014 497 FileNode operator[](const String& nodename) const;
joeverbout 0:ea44dc9ed014 498
joeverbout 0:ea44dc9ed014 499 /** @overload
joeverbout 0:ea44dc9ed014 500 @param nodename Name of an element in the mapping node.
joeverbout 0:ea44dc9ed014 501 */
joeverbout 0:ea44dc9ed014 502 CV_WRAP FileNode operator[](const char* nodename) const;
joeverbout 0:ea44dc9ed014 503
joeverbout 0:ea44dc9ed014 504 /** @overload
joeverbout 0:ea44dc9ed014 505 @param i Index of an element in the sequence node.
joeverbout 0:ea44dc9ed014 506 */
joeverbout 0:ea44dc9ed014 507 CV_WRAP FileNode operator[](int i) const;
joeverbout 0:ea44dc9ed014 508
joeverbout 0:ea44dc9ed014 509 /** @brief Returns type of the node.
joeverbout 0:ea44dc9ed014 510 @returns Type of the node. See FileNode::Type
joeverbout 0:ea44dc9ed014 511 */
joeverbout 0:ea44dc9ed014 512 CV_WRAP int type() const;
joeverbout 0:ea44dc9ed014 513
joeverbout 0:ea44dc9ed014 514 //! returns true if the node is empty
joeverbout 0:ea44dc9ed014 515 CV_WRAP bool empty() const;
joeverbout 0:ea44dc9ed014 516 //! returns true if the node is a "none" object
joeverbout 0:ea44dc9ed014 517 CV_WRAP bool isNone() const;
joeverbout 0:ea44dc9ed014 518 //! returns true if the node is a sequence
joeverbout 0:ea44dc9ed014 519 CV_WRAP bool isSeq() const;
joeverbout 0:ea44dc9ed014 520 //! returns true if the node is a mapping
joeverbout 0:ea44dc9ed014 521 CV_WRAP bool isMap() const;
joeverbout 0:ea44dc9ed014 522 //! returns true if the node is an integer
joeverbout 0:ea44dc9ed014 523 CV_WRAP bool isInt() const;
joeverbout 0:ea44dc9ed014 524 //! returns true if the node is a floating-point number
joeverbout 0:ea44dc9ed014 525 CV_WRAP bool isReal() const;
joeverbout 0:ea44dc9ed014 526 //! returns true if the node is a text string
joeverbout 0:ea44dc9ed014 527 CV_WRAP bool isString() const;
joeverbout 0:ea44dc9ed014 528 //! returns true if the node has a name
joeverbout 0:ea44dc9ed014 529 CV_WRAP bool isNamed() const;
joeverbout 0:ea44dc9ed014 530 //! returns the node name or an empty string if the node is nameless
joeverbout 0:ea44dc9ed014 531 CV_WRAP String name() const;
joeverbout 0:ea44dc9ed014 532 //! returns the number of elements in the node, if it is a sequence or mapping, or 1 otherwise.
joeverbout 0:ea44dc9ed014 533 CV_WRAP size_t size() const;
joeverbout 0:ea44dc9ed014 534 //! returns the node content as an integer. If the node stores floating-point number, it is rounded.
joeverbout 0:ea44dc9ed014 535 operator int() const;
joeverbout 0:ea44dc9ed014 536 //! returns the node content as float
joeverbout 0:ea44dc9ed014 537 operator float() const;
joeverbout 0:ea44dc9ed014 538 //! returns the node content as double
joeverbout 0:ea44dc9ed014 539 operator double() const;
joeverbout 0:ea44dc9ed014 540 //! returns the node content as text string
joeverbout 0:ea44dc9ed014 541 operator String() const;
joeverbout 0:ea44dc9ed014 542 #ifndef OPENCV_NOSTL
joeverbout 0:ea44dc9ed014 543 operator std::string() const;
joeverbout 0:ea44dc9ed014 544 #endif
joeverbout 0:ea44dc9ed014 545
joeverbout 0:ea44dc9ed014 546 //! returns pointer to the underlying file node
joeverbout 0:ea44dc9ed014 547 CvFileNode* operator *();
joeverbout 0:ea44dc9ed014 548 //! returns pointer to the underlying file node
joeverbout 0:ea44dc9ed014 549 const CvFileNode* operator* () const;
joeverbout 0:ea44dc9ed014 550
joeverbout 0:ea44dc9ed014 551 //! returns iterator pointing to the first node element
joeverbout 0:ea44dc9ed014 552 FileNodeIterator begin() const;
joeverbout 0:ea44dc9ed014 553 //! returns iterator pointing to the element following the last node element
joeverbout 0:ea44dc9ed014 554 FileNodeIterator end() const;
joeverbout 0:ea44dc9ed014 555
joeverbout 0:ea44dc9ed014 556 /** @brief Reads node elements to the buffer with the specified format.
joeverbout 0:ea44dc9ed014 557
joeverbout 0:ea44dc9ed014 558 Usually it is more convenient to use operator `>>` instead of this method.
joeverbout 0:ea44dc9ed014 559 @param fmt Specification of each array element. See @ref format_spec "format specification"
joeverbout 0:ea44dc9ed014 560 @param vec Pointer to the destination array.
joeverbout 0:ea44dc9ed014 561 @param len Number of elements to read. If it is greater than number of remaining elements then all
joeverbout 0:ea44dc9ed014 562 of them will be read.
joeverbout 0:ea44dc9ed014 563 */
joeverbout 0:ea44dc9ed014 564 void readRaw( const String& fmt, uchar* vec, size_t len ) const;
joeverbout 0:ea44dc9ed014 565
joeverbout 0:ea44dc9ed014 566 //! reads the registered object and returns pointer to it
joeverbout 0:ea44dc9ed014 567 void* readObj() const;
joeverbout 0:ea44dc9ed014 568
joeverbout 0:ea44dc9ed014 569 // do not use wrapper pointer classes for better efficiency
joeverbout 0:ea44dc9ed014 570 const CvFileStorage* fs;
joeverbout 0:ea44dc9ed014 571 const CvFileNode* node;
joeverbout 0:ea44dc9ed014 572 };
joeverbout 0:ea44dc9ed014 573
joeverbout 0:ea44dc9ed014 574
joeverbout 0:ea44dc9ed014 575 /** @brief used to iterate through sequences and mappings.
joeverbout 0:ea44dc9ed014 576
joeverbout 0:ea44dc9ed014 577 A standard STL notation, with node.begin(), node.end() denoting the beginning and the end of a
joeverbout 0:ea44dc9ed014 578 sequence, stored in node. See the data reading sample in the beginning of the section.
joeverbout 0:ea44dc9ed014 579 */
joeverbout 0:ea44dc9ed014 580 class CV_EXPORTS FileNodeIterator
joeverbout 0:ea44dc9ed014 581 {
joeverbout 0:ea44dc9ed014 582 public:
joeverbout 0:ea44dc9ed014 583 /** @brief The constructors.
joeverbout 0:ea44dc9ed014 584
joeverbout 0:ea44dc9ed014 585 These constructors are used to create a default iterator, set it to specific element in a file node
joeverbout 0:ea44dc9ed014 586 or construct it from another iterator.
joeverbout 0:ea44dc9ed014 587 */
joeverbout 0:ea44dc9ed014 588 FileNodeIterator();
joeverbout 0:ea44dc9ed014 589
joeverbout 0:ea44dc9ed014 590 /** @overload
joeverbout 0:ea44dc9ed014 591 @param fs File storage for the iterator.
joeverbout 0:ea44dc9ed014 592 @param node File node for the iterator.
joeverbout 0:ea44dc9ed014 593 @param ofs Index of the element in the node. The created iterator will point to this element.
joeverbout 0:ea44dc9ed014 594 */
joeverbout 0:ea44dc9ed014 595 FileNodeIterator(const CvFileStorage* fs, const CvFileNode* node, size_t ofs=0);
joeverbout 0:ea44dc9ed014 596
joeverbout 0:ea44dc9ed014 597 /** @overload
joeverbout 0:ea44dc9ed014 598 @param it Iterator to be used as initialization for the created iterator.
joeverbout 0:ea44dc9ed014 599 */
joeverbout 0:ea44dc9ed014 600 FileNodeIterator(const FileNodeIterator& it);
joeverbout 0:ea44dc9ed014 601
joeverbout 0:ea44dc9ed014 602 //! returns the currently observed element
joeverbout 0:ea44dc9ed014 603 FileNode operator *() const;
joeverbout 0:ea44dc9ed014 604 //! accesses the currently observed element methods
joeverbout 0:ea44dc9ed014 605 FileNode operator ->() const;
joeverbout 0:ea44dc9ed014 606
joeverbout 0:ea44dc9ed014 607 //! moves iterator to the next node
joeverbout 0:ea44dc9ed014 608 FileNodeIterator& operator ++ ();
joeverbout 0:ea44dc9ed014 609 //! moves iterator to the next node
joeverbout 0:ea44dc9ed014 610 FileNodeIterator operator ++ (int);
joeverbout 0:ea44dc9ed014 611 //! moves iterator to the previous node
joeverbout 0:ea44dc9ed014 612 FileNodeIterator& operator -- ();
joeverbout 0:ea44dc9ed014 613 //! moves iterator to the previous node
joeverbout 0:ea44dc9ed014 614 FileNodeIterator operator -- (int);
joeverbout 0:ea44dc9ed014 615 //! moves iterator forward by the specified offset (possibly negative)
joeverbout 0:ea44dc9ed014 616 FileNodeIterator& operator += (int ofs);
joeverbout 0:ea44dc9ed014 617 //! moves iterator backward by the specified offset (possibly negative)
joeverbout 0:ea44dc9ed014 618 FileNodeIterator& operator -= (int ofs);
joeverbout 0:ea44dc9ed014 619
joeverbout 0:ea44dc9ed014 620 /** @brief Reads node elements to the buffer with the specified format.
joeverbout 0:ea44dc9ed014 621
joeverbout 0:ea44dc9ed014 622 Usually it is more convenient to use operator `>>` instead of this method.
joeverbout 0:ea44dc9ed014 623 @param fmt Specification of each array element. See @ref format_spec "format specification"
joeverbout 0:ea44dc9ed014 624 @param vec Pointer to the destination array.
joeverbout 0:ea44dc9ed014 625 @param maxCount Number of elements to read. If it is greater than number of remaining elements then
joeverbout 0:ea44dc9ed014 626 all of them will be read.
joeverbout 0:ea44dc9ed014 627 */
joeverbout 0:ea44dc9ed014 628 FileNodeIterator& readRaw( const String& fmt, uchar* vec,
joeverbout 0:ea44dc9ed014 629 size_t maxCount=(size_t)INT_MAX );
joeverbout 0:ea44dc9ed014 630
joeverbout 0:ea44dc9ed014 631 struct SeqReader
joeverbout 0:ea44dc9ed014 632 {
joeverbout 0:ea44dc9ed014 633 int header_size;
joeverbout 0:ea44dc9ed014 634 void* seq; /* sequence, beign read; CvSeq */
joeverbout 0:ea44dc9ed014 635 void* block; /* current block; CvSeqBlock */
joeverbout 0:ea44dc9ed014 636 schar* ptr; /* pointer to element be read next */
joeverbout 0:ea44dc9ed014 637 schar* block_min; /* pointer to the beginning of block */
joeverbout 0:ea44dc9ed014 638 schar* block_max; /* pointer to the end of block */
joeverbout 0:ea44dc9ed014 639 int delta_index;/* = seq->first->start_index */
joeverbout 0:ea44dc9ed014 640 schar* prev_elem; /* pointer to previous element */
joeverbout 0:ea44dc9ed014 641 };
joeverbout 0:ea44dc9ed014 642
joeverbout 0:ea44dc9ed014 643 const CvFileStorage* fs;
joeverbout 0:ea44dc9ed014 644 const CvFileNode* container;
joeverbout 0:ea44dc9ed014 645 SeqReader reader;
joeverbout 0:ea44dc9ed014 646 size_t remaining;
joeverbout 0:ea44dc9ed014 647 };
joeverbout 0:ea44dc9ed014 648
joeverbout 0:ea44dc9ed014 649 //! @} core_xml
joeverbout 0:ea44dc9ed014 650
joeverbout 0:ea44dc9ed014 651 /////////////////// XML & YAML I/O implementation //////////////////
joeverbout 0:ea44dc9ed014 652
joeverbout 0:ea44dc9ed014 653 //! @relates cv::FileStorage
joeverbout 0:ea44dc9ed014 654 //! @{
joeverbout 0:ea44dc9ed014 655
joeverbout 0:ea44dc9ed014 656 CV_EXPORTS void write( FileStorage& fs, const String& name, int value );
joeverbout 0:ea44dc9ed014 657 CV_EXPORTS void write( FileStorage& fs, const String& name, float value );
joeverbout 0:ea44dc9ed014 658 CV_EXPORTS void write( FileStorage& fs, const String& name, double value );
joeverbout 0:ea44dc9ed014 659 CV_EXPORTS void write( FileStorage& fs, const String& name, const String& value );
joeverbout 0:ea44dc9ed014 660 CV_EXPORTS void write( FileStorage& fs, const String& name, const Mat& value );
joeverbout 0:ea44dc9ed014 661 CV_EXPORTS void write( FileStorage& fs, const String& name, const SparseMat& value );
joeverbout 0:ea44dc9ed014 662 CV_EXPORTS void write( FileStorage& fs, const String& name, const std::vector<KeyPoint>& value);
joeverbout 0:ea44dc9ed014 663 CV_EXPORTS void write( FileStorage& fs, const String& name, const std::vector<DMatch>& value);
joeverbout 0:ea44dc9ed014 664
joeverbout 0:ea44dc9ed014 665 CV_EXPORTS void writeScalar( FileStorage& fs, int value );
joeverbout 0:ea44dc9ed014 666 CV_EXPORTS void writeScalar( FileStorage& fs, float value );
joeverbout 0:ea44dc9ed014 667 CV_EXPORTS void writeScalar( FileStorage& fs, double value );
joeverbout 0:ea44dc9ed014 668 CV_EXPORTS void writeScalar( FileStorage& fs, const String& value );
joeverbout 0:ea44dc9ed014 669
joeverbout 0:ea44dc9ed014 670 //! @}
joeverbout 0:ea44dc9ed014 671
joeverbout 0:ea44dc9ed014 672 //! @relates cv::FileNode
joeverbout 0:ea44dc9ed014 673 //! @{
joeverbout 0:ea44dc9ed014 674
joeverbout 0:ea44dc9ed014 675 CV_EXPORTS void read(const FileNode& node, int& value, int default_value);
joeverbout 0:ea44dc9ed014 676 CV_EXPORTS void read(const FileNode& node, float& value, float default_value);
joeverbout 0:ea44dc9ed014 677 CV_EXPORTS void read(const FileNode& node, double& value, double default_value);
joeverbout 0:ea44dc9ed014 678 CV_EXPORTS void read(const FileNode& node, String& value, const String& default_value);
joeverbout 0:ea44dc9ed014 679 CV_EXPORTS void read(const FileNode& node, Mat& mat, const Mat& default_mat = Mat() );
joeverbout 0:ea44dc9ed014 680 CV_EXPORTS void read(const FileNode& node, SparseMat& mat, const SparseMat& default_mat = SparseMat() );
joeverbout 0:ea44dc9ed014 681 CV_EXPORTS void read(const FileNode& node, std::vector<KeyPoint>& keypoints);
joeverbout 0:ea44dc9ed014 682 CV_EXPORTS void read(const FileNode& node, std::vector<DMatch>& matches);
joeverbout 0:ea44dc9ed014 683
joeverbout 0:ea44dc9ed014 684 template<typename _Tp> static inline void read(const FileNode& node, Point_<_Tp>& value, const Point_<_Tp>& default_value)
joeverbout 0:ea44dc9ed014 685 {
joeverbout 0:ea44dc9ed014 686 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 687 value = temp.size() != 2 ? default_value : Point_<_Tp>(saturate_cast<_Tp>(temp[0]), saturate_cast<_Tp>(temp[1]));
joeverbout 0:ea44dc9ed014 688 }
joeverbout 0:ea44dc9ed014 689
joeverbout 0:ea44dc9ed014 690 template<typename _Tp> static inline void read(const FileNode& node, Point3_<_Tp>& value, const Point3_<_Tp>& default_value)
joeverbout 0:ea44dc9ed014 691 {
joeverbout 0:ea44dc9ed014 692 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 693 value = temp.size() != 3 ? default_value : Point3_<_Tp>(saturate_cast<_Tp>(temp[0]), saturate_cast<_Tp>(temp[1]),
joeverbout 0:ea44dc9ed014 694 saturate_cast<_Tp>(temp[2]));
joeverbout 0:ea44dc9ed014 695 }
joeverbout 0:ea44dc9ed014 696
joeverbout 0:ea44dc9ed014 697 template<typename _Tp> static inline void read(const FileNode& node, Size_<_Tp>& value, const Size_<_Tp>& default_value)
joeverbout 0:ea44dc9ed014 698 {
joeverbout 0:ea44dc9ed014 699 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 700 value = temp.size() != 2 ? default_value : Size_<_Tp>(saturate_cast<_Tp>(temp[0]), saturate_cast<_Tp>(temp[1]));
joeverbout 0:ea44dc9ed014 701 }
joeverbout 0:ea44dc9ed014 702
joeverbout 0:ea44dc9ed014 703 template<typename _Tp> static inline void read(const FileNode& node, Complex<_Tp>& value, const Complex<_Tp>& default_value)
joeverbout 0:ea44dc9ed014 704 {
joeverbout 0:ea44dc9ed014 705 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 706 value = temp.size() != 2 ? default_value : Complex<_Tp>(saturate_cast<_Tp>(temp[0]), saturate_cast<_Tp>(temp[1]));
joeverbout 0:ea44dc9ed014 707 }
joeverbout 0:ea44dc9ed014 708
joeverbout 0:ea44dc9ed014 709 template<typename _Tp> static inline void read(const FileNode& node, Rect_<_Tp>& value, const Rect_<_Tp>& default_value)
joeverbout 0:ea44dc9ed014 710 {
joeverbout 0:ea44dc9ed014 711 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 712 value = temp.size() != 4 ? default_value : Rect_<_Tp>(saturate_cast<_Tp>(temp[0]), saturate_cast<_Tp>(temp[1]),
joeverbout 0:ea44dc9ed014 713 saturate_cast<_Tp>(temp[2]), saturate_cast<_Tp>(temp[3]));
joeverbout 0:ea44dc9ed014 714 }
joeverbout 0:ea44dc9ed014 715
joeverbout 0:ea44dc9ed014 716 template<typename _Tp, int cn> static inline void read(const FileNode& node, Vec<_Tp, cn>& value, const Vec<_Tp, cn>& default_value)
joeverbout 0:ea44dc9ed014 717 {
joeverbout 0:ea44dc9ed014 718 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 719 value = temp.size() != cn ? default_value : Vec<_Tp, cn>(&temp[0]);
joeverbout 0:ea44dc9ed014 720 }
joeverbout 0:ea44dc9ed014 721
joeverbout 0:ea44dc9ed014 722 template<typename _Tp> static inline void read(const FileNode& node, Scalar_<_Tp>& value, const Scalar_<_Tp>& default_value)
joeverbout 0:ea44dc9ed014 723 {
joeverbout 0:ea44dc9ed014 724 std::vector<_Tp> temp; FileNodeIterator it = node.begin(); it >> temp;
joeverbout 0:ea44dc9ed014 725 value = temp.size() != 4 ? default_value : Scalar_<_Tp>(saturate_cast<_Tp>(temp[0]), saturate_cast<_Tp>(temp[1]),
joeverbout 0:ea44dc9ed014 726 saturate_cast<_Tp>(temp[2]), saturate_cast<_Tp>(temp[3]));
joeverbout 0:ea44dc9ed014 727 }
joeverbout 0:ea44dc9ed014 728
joeverbout 0:ea44dc9ed014 729 static inline void read(const FileNode& node, Range& value, const Range& default_value)
joeverbout 0:ea44dc9ed014 730 {
joeverbout 0:ea44dc9ed014 731 Point2i temp(value.start, value.end); const Point2i default_temp = Point2i(default_value.start, default_value.end);
joeverbout 0:ea44dc9ed014 732 read(node, temp, default_temp);
joeverbout 0:ea44dc9ed014 733 value.start = temp.x; value.end = temp.y;
joeverbout 0:ea44dc9ed014 734 }
joeverbout 0:ea44dc9ed014 735
joeverbout 0:ea44dc9ed014 736 //! @}
joeverbout 0:ea44dc9ed014 737
joeverbout 0:ea44dc9ed014 738 /** @brief Writes string to a file storage.
joeverbout 0:ea44dc9ed014 739 @relates cv::FileStorage
joeverbout 0:ea44dc9ed014 740 */
joeverbout 0:ea44dc9ed014 741 CV_EXPORTS FileStorage& operator << (FileStorage& fs, const String& str);
joeverbout 0:ea44dc9ed014 742
joeverbout 0:ea44dc9ed014 743 //! @cond IGNORED
joeverbout 0:ea44dc9ed014 744
joeverbout 0:ea44dc9ed014 745 namespace internal
joeverbout 0:ea44dc9ed014 746 {
joeverbout 0:ea44dc9ed014 747 class CV_EXPORTS WriteStructContext
joeverbout 0:ea44dc9ed014 748 {
joeverbout 0:ea44dc9ed014 749 public:
joeverbout 0:ea44dc9ed014 750 WriteStructContext(FileStorage& _fs, const String& name, int flags, const String& typeName = String());
joeverbout 0:ea44dc9ed014 751 ~WriteStructContext();
joeverbout 0:ea44dc9ed014 752 private:
joeverbout 0:ea44dc9ed014 753 FileStorage* fs;
joeverbout 0:ea44dc9ed014 754 };
joeverbout 0:ea44dc9ed014 755
joeverbout 0:ea44dc9ed014 756 template<typename _Tp, int numflag> class VecWriterProxy
joeverbout 0:ea44dc9ed014 757 {
joeverbout 0:ea44dc9ed014 758 public:
joeverbout 0:ea44dc9ed014 759 VecWriterProxy( FileStorage* _fs ) : fs(_fs) {}
joeverbout 0:ea44dc9ed014 760 void operator()(const std::vector<_Tp>& vec) const
joeverbout 0:ea44dc9ed014 761 {
joeverbout 0:ea44dc9ed014 762 size_t count = vec.size();
joeverbout 0:ea44dc9ed014 763 for (size_t i = 0; i < count; i++)
joeverbout 0:ea44dc9ed014 764 write(*fs, vec[i]);
joeverbout 0:ea44dc9ed014 765 }
joeverbout 0:ea44dc9ed014 766 private:
joeverbout 0:ea44dc9ed014 767 FileStorage* fs;
joeverbout 0:ea44dc9ed014 768 };
joeverbout 0:ea44dc9ed014 769
joeverbout 0:ea44dc9ed014 770 template<typename _Tp> class VecWriterProxy<_Tp, 1>
joeverbout 0:ea44dc9ed014 771 {
joeverbout 0:ea44dc9ed014 772 public:
joeverbout 0:ea44dc9ed014 773 VecWriterProxy( FileStorage* _fs ) : fs(_fs) {}
joeverbout 0:ea44dc9ed014 774 void operator()(const std::vector<_Tp>& vec) const
joeverbout 0:ea44dc9ed014 775 {
joeverbout 0:ea44dc9ed014 776 int _fmt = DataType<_Tp>::fmt;
joeverbout 0:ea44dc9ed014 777 char fmt[] = { (char)((_fmt >> 8) + '1'), (char)_fmt, '\0' };
joeverbout 0:ea44dc9ed014 778 fs->writeRaw(fmt, !vec.empty() ? (uchar*)&vec[0] : 0, vec.size() * sizeof(_Tp));
joeverbout 0:ea44dc9ed014 779 }
joeverbout 0:ea44dc9ed014 780 private:
joeverbout 0:ea44dc9ed014 781 FileStorage* fs;
joeverbout 0:ea44dc9ed014 782 };
joeverbout 0:ea44dc9ed014 783
joeverbout 0:ea44dc9ed014 784 template<typename _Tp, int numflag> class VecReaderProxy
joeverbout 0:ea44dc9ed014 785 {
joeverbout 0:ea44dc9ed014 786 public:
joeverbout 0:ea44dc9ed014 787 VecReaderProxy( FileNodeIterator* _it ) : it(_it) {}
joeverbout 0:ea44dc9ed014 788 void operator()(std::vector<_Tp>& vec, size_t count) const
joeverbout 0:ea44dc9ed014 789 {
joeverbout 0:ea44dc9ed014 790 count = std::min(count, it->remaining);
joeverbout 0:ea44dc9ed014 791 vec.resize(count);
joeverbout 0:ea44dc9ed014 792 for (size_t i = 0; i < count; i++, ++(*it))
joeverbout 0:ea44dc9ed014 793 read(**it, vec[i], _Tp());
joeverbout 0:ea44dc9ed014 794 }
joeverbout 0:ea44dc9ed014 795 private:
joeverbout 0:ea44dc9ed014 796 FileNodeIterator* it;
joeverbout 0:ea44dc9ed014 797 };
joeverbout 0:ea44dc9ed014 798
joeverbout 0:ea44dc9ed014 799 template<typename _Tp> class VecReaderProxy<_Tp, 1>
joeverbout 0:ea44dc9ed014 800 {
joeverbout 0:ea44dc9ed014 801 public:
joeverbout 0:ea44dc9ed014 802 VecReaderProxy( FileNodeIterator* _it ) : it(_it) {}
joeverbout 0:ea44dc9ed014 803 void operator()(std::vector<_Tp>& vec, size_t count) const
joeverbout 0:ea44dc9ed014 804 {
joeverbout 0:ea44dc9ed014 805 size_t remaining = it->remaining;
joeverbout 0:ea44dc9ed014 806 size_t cn = DataType<_Tp>::channels;
joeverbout 0:ea44dc9ed014 807 int _fmt = DataType<_Tp>::fmt;
joeverbout 0:ea44dc9ed014 808 char fmt[] = { (char)((_fmt >> 8)+'1'), (char)_fmt, '\0' };
joeverbout 0:ea44dc9ed014 809 size_t remaining1 = remaining / cn;
joeverbout 0:ea44dc9ed014 810 count = count < remaining1 ? count : remaining1;
joeverbout 0:ea44dc9ed014 811 vec.resize(count);
joeverbout 0:ea44dc9ed014 812 it->readRaw(fmt, !vec.empty() ? (uchar*)&vec[0] : 0, count*sizeof(_Tp));
joeverbout 0:ea44dc9ed014 813 }
joeverbout 0:ea44dc9ed014 814 private:
joeverbout 0:ea44dc9ed014 815 FileNodeIterator* it;
joeverbout 0:ea44dc9ed014 816 };
joeverbout 0:ea44dc9ed014 817
joeverbout 0:ea44dc9ed014 818 } // internal
joeverbout 0:ea44dc9ed014 819
joeverbout 0:ea44dc9ed014 820 //! @endcond
joeverbout 0:ea44dc9ed014 821
joeverbout 0:ea44dc9ed014 822 //! @relates cv::FileStorage
joeverbout 0:ea44dc9ed014 823 //! @{
joeverbout 0:ea44dc9ed014 824
joeverbout 0:ea44dc9ed014 825 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 826 void write(FileStorage& fs, const _Tp& value)
joeverbout 0:ea44dc9ed014 827 {
joeverbout 0:ea44dc9ed014 828 write(fs, String(), value);
joeverbout 0:ea44dc9ed014 829 }
joeverbout 0:ea44dc9ed014 830
joeverbout 0:ea44dc9ed014 831 template<> inline
joeverbout 0:ea44dc9ed014 832 void write( FileStorage& fs, const int& value )
joeverbout 0:ea44dc9ed014 833 {
joeverbout 0:ea44dc9ed014 834 writeScalar(fs, value);
joeverbout 0:ea44dc9ed014 835 }
joeverbout 0:ea44dc9ed014 836
joeverbout 0:ea44dc9ed014 837 template<> inline
joeverbout 0:ea44dc9ed014 838 void write( FileStorage& fs, const float& value )
joeverbout 0:ea44dc9ed014 839 {
joeverbout 0:ea44dc9ed014 840 writeScalar(fs, value);
joeverbout 0:ea44dc9ed014 841 }
joeverbout 0:ea44dc9ed014 842
joeverbout 0:ea44dc9ed014 843 template<> inline
joeverbout 0:ea44dc9ed014 844 void write( FileStorage& fs, const double& value )
joeverbout 0:ea44dc9ed014 845 {
joeverbout 0:ea44dc9ed014 846 writeScalar(fs, value);
joeverbout 0:ea44dc9ed014 847 }
joeverbout 0:ea44dc9ed014 848
joeverbout 0:ea44dc9ed014 849 template<> inline
joeverbout 0:ea44dc9ed014 850 void write( FileStorage& fs, const String& value )
joeverbout 0:ea44dc9ed014 851 {
joeverbout 0:ea44dc9ed014 852 writeScalar(fs, value);
joeverbout 0:ea44dc9ed014 853 }
joeverbout 0:ea44dc9ed014 854
joeverbout 0:ea44dc9ed014 855 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 856 void write(FileStorage& fs, const Point_<_Tp>& pt )
joeverbout 0:ea44dc9ed014 857 {
joeverbout 0:ea44dc9ed014 858 write(fs, pt.x);
joeverbout 0:ea44dc9ed014 859 write(fs, pt.y);
joeverbout 0:ea44dc9ed014 860 }
joeverbout 0:ea44dc9ed014 861
joeverbout 0:ea44dc9ed014 862 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 863 void write(FileStorage& fs, const Point3_<_Tp>& pt )
joeverbout 0:ea44dc9ed014 864 {
joeverbout 0:ea44dc9ed014 865 write(fs, pt.x);
joeverbout 0:ea44dc9ed014 866 write(fs, pt.y);
joeverbout 0:ea44dc9ed014 867 write(fs, pt.z);
joeverbout 0:ea44dc9ed014 868 }
joeverbout 0:ea44dc9ed014 869
joeverbout 0:ea44dc9ed014 870 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 871 void write(FileStorage& fs, const Size_<_Tp>& sz )
joeverbout 0:ea44dc9ed014 872 {
joeverbout 0:ea44dc9ed014 873 write(fs, sz.width);
joeverbout 0:ea44dc9ed014 874 write(fs, sz.height);
joeverbout 0:ea44dc9ed014 875 }
joeverbout 0:ea44dc9ed014 876
joeverbout 0:ea44dc9ed014 877 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 878 void write(FileStorage& fs, const Complex<_Tp>& c )
joeverbout 0:ea44dc9ed014 879 {
joeverbout 0:ea44dc9ed014 880 write(fs, c.re);
joeverbout 0:ea44dc9ed014 881 write(fs, c.im);
joeverbout 0:ea44dc9ed014 882 }
joeverbout 0:ea44dc9ed014 883
joeverbout 0:ea44dc9ed014 884 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 885 void write(FileStorage& fs, const Rect_<_Tp>& r )
joeverbout 0:ea44dc9ed014 886 {
joeverbout 0:ea44dc9ed014 887 write(fs, r.x);
joeverbout 0:ea44dc9ed014 888 write(fs, r.y);
joeverbout 0:ea44dc9ed014 889 write(fs, r.width);
joeverbout 0:ea44dc9ed014 890 write(fs, r.height);
joeverbout 0:ea44dc9ed014 891 }
joeverbout 0:ea44dc9ed014 892
joeverbout 0:ea44dc9ed014 893 template<typename _Tp, int cn> static inline
joeverbout 0:ea44dc9ed014 894 void write(FileStorage& fs, const Vec<_Tp, cn>& v )
joeverbout 0:ea44dc9ed014 895 {
joeverbout 0:ea44dc9ed014 896 for(int i = 0; i < cn; i++)
joeverbout 0:ea44dc9ed014 897 write(fs, v.val[i]);
joeverbout 0:ea44dc9ed014 898 }
joeverbout 0:ea44dc9ed014 899
joeverbout 0:ea44dc9ed014 900 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 901 void write(FileStorage& fs, const Scalar_<_Tp>& s )
joeverbout 0:ea44dc9ed014 902 {
joeverbout 0:ea44dc9ed014 903 write(fs, s.val[0]);
joeverbout 0:ea44dc9ed014 904 write(fs, s.val[1]);
joeverbout 0:ea44dc9ed014 905 write(fs, s.val[2]);
joeverbout 0:ea44dc9ed014 906 write(fs, s.val[3]);
joeverbout 0:ea44dc9ed014 907 }
joeverbout 0:ea44dc9ed014 908
joeverbout 0:ea44dc9ed014 909 static inline
joeverbout 0:ea44dc9ed014 910 void write(FileStorage& fs, const Range& r )
joeverbout 0:ea44dc9ed014 911 {
joeverbout 0:ea44dc9ed014 912 write(fs, r.start);
joeverbout 0:ea44dc9ed014 913 write(fs, r.end);
joeverbout 0:ea44dc9ed014 914 }
joeverbout 0:ea44dc9ed014 915
joeverbout 0:ea44dc9ed014 916 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 917 void write( FileStorage& fs, const std::vector<_Tp>& vec )
joeverbout 0:ea44dc9ed014 918 {
joeverbout 0:ea44dc9ed014 919 cv::internal::VecWriterProxy<_Tp, DataType<_Tp>::fmt != 0> w(&fs);
joeverbout 0:ea44dc9ed014 920 w(vec);
joeverbout 0:ea44dc9ed014 921 }
joeverbout 0:ea44dc9ed014 922
joeverbout 0:ea44dc9ed014 923
joeverbout 0:ea44dc9ed014 924 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 925 void write(FileStorage& fs, const String& name, const Point_<_Tp>& pt )
joeverbout 0:ea44dc9ed014 926 {
joeverbout 0:ea44dc9ed014 927 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 928 write(fs, pt);
joeverbout 0:ea44dc9ed014 929 }
joeverbout 0:ea44dc9ed014 930
joeverbout 0:ea44dc9ed014 931 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 932 void write(FileStorage& fs, const String& name, const Point3_<_Tp>& pt )
joeverbout 0:ea44dc9ed014 933 {
joeverbout 0:ea44dc9ed014 934 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 935 write(fs, pt);
joeverbout 0:ea44dc9ed014 936 }
joeverbout 0:ea44dc9ed014 937
joeverbout 0:ea44dc9ed014 938 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 939 void write(FileStorage& fs, const String& name, const Size_<_Tp>& sz )
joeverbout 0:ea44dc9ed014 940 {
joeverbout 0:ea44dc9ed014 941 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 942 write(fs, sz);
joeverbout 0:ea44dc9ed014 943 }
joeverbout 0:ea44dc9ed014 944
joeverbout 0:ea44dc9ed014 945 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 946 void write(FileStorage& fs, const String& name, const Complex<_Tp>& c )
joeverbout 0:ea44dc9ed014 947 {
joeverbout 0:ea44dc9ed014 948 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 949 write(fs, c);
joeverbout 0:ea44dc9ed014 950 }
joeverbout 0:ea44dc9ed014 951
joeverbout 0:ea44dc9ed014 952 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 953 void write(FileStorage& fs, const String& name, const Rect_<_Tp>& r )
joeverbout 0:ea44dc9ed014 954 {
joeverbout 0:ea44dc9ed014 955 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 956 write(fs, r);
joeverbout 0:ea44dc9ed014 957 }
joeverbout 0:ea44dc9ed014 958
joeverbout 0:ea44dc9ed014 959 template<typename _Tp, int cn> static inline
joeverbout 0:ea44dc9ed014 960 void write(FileStorage& fs, const String& name, const Vec<_Tp, cn>& v )
joeverbout 0:ea44dc9ed014 961 {
joeverbout 0:ea44dc9ed014 962 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 963 write(fs, v);
joeverbout 0:ea44dc9ed014 964 }
joeverbout 0:ea44dc9ed014 965
joeverbout 0:ea44dc9ed014 966 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 967 void write(FileStorage& fs, const String& name, const Scalar_<_Tp>& s )
joeverbout 0:ea44dc9ed014 968 {
joeverbout 0:ea44dc9ed014 969 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 970 write(fs, s);
joeverbout 0:ea44dc9ed014 971 }
joeverbout 0:ea44dc9ed014 972
joeverbout 0:ea44dc9ed014 973 static inline
joeverbout 0:ea44dc9ed014 974 void write(FileStorage& fs, const String& name, const Range& r )
joeverbout 0:ea44dc9ed014 975 {
joeverbout 0:ea44dc9ed014 976 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+FileNode::FLOW);
joeverbout 0:ea44dc9ed014 977 write(fs, r);
joeverbout 0:ea44dc9ed014 978 }
joeverbout 0:ea44dc9ed014 979
joeverbout 0:ea44dc9ed014 980 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 981 void write( FileStorage& fs, const String& name, const std::vector<_Tp>& vec )
joeverbout 0:ea44dc9ed014 982 {
joeverbout 0:ea44dc9ed014 983 cv::internal::WriteStructContext ws(fs, name, FileNode::SEQ+(DataType<_Tp>::fmt != 0 ? FileNode::FLOW : 0));
joeverbout 0:ea44dc9ed014 984 write(fs, vec);
joeverbout 0:ea44dc9ed014 985 }
joeverbout 0:ea44dc9ed014 986
joeverbout 0:ea44dc9ed014 987 //! @} FileStorage
joeverbout 0:ea44dc9ed014 988
joeverbout 0:ea44dc9ed014 989 //! @relates cv::FileNode
joeverbout 0:ea44dc9ed014 990 //! @{
joeverbout 0:ea44dc9ed014 991
joeverbout 0:ea44dc9ed014 992 static inline
joeverbout 0:ea44dc9ed014 993 void read(const FileNode& node, bool& value, bool default_value)
joeverbout 0:ea44dc9ed014 994 {
joeverbout 0:ea44dc9ed014 995 int temp;
joeverbout 0:ea44dc9ed014 996 read(node, temp, (int)default_value);
joeverbout 0:ea44dc9ed014 997 value = temp != 0;
joeverbout 0:ea44dc9ed014 998 }
joeverbout 0:ea44dc9ed014 999
joeverbout 0:ea44dc9ed014 1000 static inline
joeverbout 0:ea44dc9ed014 1001 void read(const FileNode& node, uchar& value, uchar default_value)
joeverbout 0:ea44dc9ed014 1002 {
joeverbout 0:ea44dc9ed014 1003 int temp;
joeverbout 0:ea44dc9ed014 1004 read(node, temp, (int)default_value);
joeverbout 0:ea44dc9ed014 1005 value = saturate_cast<uchar>(temp);
joeverbout 0:ea44dc9ed014 1006 }
joeverbout 0:ea44dc9ed014 1007
joeverbout 0:ea44dc9ed014 1008 static inline
joeverbout 0:ea44dc9ed014 1009 void read(const FileNode& node, schar& value, schar default_value)
joeverbout 0:ea44dc9ed014 1010 {
joeverbout 0:ea44dc9ed014 1011 int temp;
joeverbout 0:ea44dc9ed014 1012 read(node, temp, (int)default_value);
joeverbout 0:ea44dc9ed014 1013 value = saturate_cast<schar>(temp);
joeverbout 0:ea44dc9ed014 1014 }
joeverbout 0:ea44dc9ed014 1015
joeverbout 0:ea44dc9ed014 1016 static inline
joeverbout 0:ea44dc9ed014 1017 void read(const FileNode& node, ushort& value, ushort default_value)
joeverbout 0:ea44dc9ed014 1018 {
joeverbout 0:ea44dc9ed014 1019 int temp;
joeverbout 0:ea44dc9ed014 1020 read(node, temp, (int)default_value);
joeverbout 0:ea44dc9ed014 1021 value = saturate_cast<ushort>(temp);
joeverbout 0:ea44dc9ed014 1022 }
joeverbout 0:ea44dc9ed014 1023
joeverbout 0:ea44dc9ed014 1024 static inline
joeverbout 0:ea44dc9ed014 1025 void read(const FileNode& node, short& value, short default_value)
joeverbout 0:ea44dc9ed014 1026 {
joeverbout 0:ea44dc9ed014 1027 int temp;
joeverbout 0:ea44dc9ed014 1028 read(node, temp, (int)default_value);
joeverbout 0:ea44dc9ed014 1029 value = saturate_cast<short>(temp);
joeverbout 0:ea44dc9ed014 1030 }
joeverbout 0:ea44dc9ed014 1031
joeverbout 0:ea44dc9ed014 1032 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1033 void read( FileNodeIterator& it, std::vector<_Tp>& vec, size_t maxCount = (size_t)INT_MAX )
joeverbout 0:ea44dc9ed014 1034 {
joeverbout 0:ea44dc9ed014 1035 cv::internal::VecReaderProxy<_Tp, DataType<_Tp>::fmt != 0> r(&it);
joeverbout 0:ea44dc9ed014 1036 r(vec, maxCount);
joeverbout 0:ea44dc9ed014 1037 }
joeverbout 0:ea44dc9ed014 1038
joeverbout 0:ea44dc9ed014 1039 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1040 void read( const FileNode& node, std::vector<_Tp>& vec, const std::vector<_Tp>& default_value = std::vector<_Tp>() )
joeverbout 0:ea44dc9ed014 1041 {
joeverbout 0:ea44dc9ed014 1042 if(!node.node)
joeverbout 0:ea44dc9ed014 1043 vec = default_value;
joeverbout 0:ea44dc9ed014 1044 else
joeverbout 0:ea44dc9ed014 1045 {
joeverbout 0:ea44dc9ed014 1046 FileNodeIterator it = node.begin();
joeverbout 0:ea44dc9ed014 1047 read( it, vec );
joeverbout 0:ea44dc9ed014 1048 }
joeverbout 0:ea44dc9ed014 1049 }
joeverbout 0:ea44dc9ed014 1050
joeverbout 0:ea44dc9ed014 1051 //! @} FileNode
joeverbout 0:ea44dc9ed014 1052
joeverbout 0:ea44dc9ed014 1053 //! @relates cv::FileStorage
joeverbout 0:ea44dc9ed014 1054 //! @{
joeverbout 0:ea44dc9ed014 1055
joeverbout 0:ea44dc9ed014 1056 /** @brief Writes data to a file storage.
joeverbout 0:ea44dc9ed014 1057 */
joeverbout 0:ea44dc9ed014 1058 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1059 FileStorage& operator << (FileStorage& fs, const _Tp& value)
joeverbout 0:ea44dc9ed014 1060 {
joeverbout 0:ea44dc9ed014 1061 if( !fs.isOpened() )
joeverbout 0:ea44dc9ed014 1062 return fs;
joeverbout 0:ea44dc9ed014 1063 if( fs.state == FileStorage::NAME_EXPECTED + FileStorage::INSIDE_MAP )
joeverbout 0:ea44dc9ed014 1064 CV_Error( Error::StsError, "No element name has been given" );
joeverbout 0:ea44dc9ed014 1065 write( fs, fs.elname, value );
joeverbout 0:ea44dc9ed014 1066 if( fs.state & FileStorage::INSIDE_MAP )
joeverbout 0:ea44dc9ed014 1067 fs.state = FileStorage::NAME_EXPECTED + FileStorage::INSIDE_MAP;
joeverbout 0:ea44dc9ed014 1068 return fs;
joeverbout 0:ea44dc9ed014 1069 }
joeverbout 0:ea44dc9ed014 1070
joeverbout 0:ea44dc9ed014 1071 /** @brief Writes data to a file storage.
joeverbout 0:ea44dc9ed014 1072 */
joeverbout 0:ea44dc9ed014 1073 static inline
joeverbout 0:ea44dc9ed014 1074 FileStorage& operator << (FileStorage& fs, const char* str)
joeverbout 0:ea44dc9ed014 1075 {
joeverbout 0:ea44dc9ed014 1076 return (fs << String(str));
joeverbout 0:ea44dc9ed014 1077 }
joeverbout 0:ea44dc9ed014 1078
joeverbout 0:ea44dc9ed014 1079 /** @brief Writes data to a file storage.
joeverbout 0:ea44dc9ed014 1080 */
joeverbout 0:ea44dc9ed014 1081 static inline
joeverbout 0:ea44dc9ed014 1082 FileStorage& operator << (FileStorage& fs, char* value)
joeverbout 0:ea44dc9ed014 1083 {
joeverbout 0:ea44dc9ed014 1084 return (fs << String(value));
joeverbout 0:ea44dc9ed014 1085 }
joeverbout 0:ea44dc9ed014 1086
joeverbout 0:ea44dc9ed014 1087 //! @} FileStorage
joeverbout 0:ea44dc9ed014 1088
joeverbout 0:ea44dc9ed014 1089 //! @relates cv::FileNodeIterator
joeverbout 0:ea44dc9ed014 1090 //! @{
joeverbout 0:ea44dc9ed014 1091
joeverbout 0:ea44dc9ed014 1092 /** @brief Reads data from a file storage.
joeverbout 0:ea44dc9ed014 1093 */
joeverbout 0:ea44dc9ed014 1094 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1095 FileNodeIterator& operator >> (FileNodeIterator& it, _Tp& value)
joeverbout 0:ea44dc9ed014 1096 {
joeverbout 0:ea44dc9ed014 1097 read( *it, value, _Tp());
joeverbout 0:ea44dc9ed014 1098 return ++it;
joeverbout 0:ea44dc9ed014 1099 }
joeverbout 0:ea44dc9ed014 1100
joeverbout 0:ea44dc9ed014 1101 /** @brief Reads data from a file storage.
joeverbout 0:ea44dc9ed014 1102 */
joeverbout 0:ea44dc9ed014 1103 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1104 FileNodeIterator& operator >> (FileNodeIterator& it, std::vector<_Tp>& vec)
joeverbout 0:ea44dc9ed014 1105 {
joeverbout 0:ea44dc9ed014 1106 cv::internal::VecReaderProxy<_Tp, DataType<_Tp>::fmt != 0> r(&it);
joeverbout 0:ea44dc9ed014 1107 r(vec, (size_t)INT_MAX);
joeverbout 0:ea44dc9ed014 1108 return it;
joeverbout 0:ea44dc9ed014 1109 }
joeverbout 0:ea44dc9ed014 1110
joeverbout 0:ea44dc9ed014 1111 //! @} FileNodeIterator
joeverbout 0:ea44dc9ed014 1112
joeverbout 0:ea44dc9ed014 1113 //! @relates cv::FileNode
joeverbout 0:ea44dc9ed014 1114 //! @{
joeverbout 0:ea44dc9ed014 1115
joeverbout 0:ea44dc9ed014 1116 /** @brief Reads data from a file storage.
joeverbout 0:ea44dc9ed014 1117 */
joeverbout 0:ea44dc9ed014 1118 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1119 void operator >> (const FileNode& n, _Tp& value)
joeverbout 0:ea44dc9ed014 1120 {
joeverbout 0:ea44dc9ed014 1121 read( n, value, _Tp());
joeverbout 0:ea44dc9ed014 1122 }
joeverbout 0:ea44dc9ed014 1123
joeverbout 0:ea44dc9ed014 1124 /** @brief Reads data from a file storage.
joeverbout 0:ea44dc9ed014 1125 */
joeverbout 0:ea44dc9ed014 1126 template<typename _Tp> static inline
joeverbout 0:ea44dc9ed014 1127 void operator >> (const FileNode& n, std::vector<_Tp>& vec)
joeverbout 0:ea44dc9ed014 1128 {
joeverbout 0:ea44dc9ed014 1129 FileNodeIterator it = n.begin();
joeverbout 0:ea44dc9ed014 1130 it >> vec;
joeverbout 0:ea44dc9ed014 1131 }
joeverbout 0:ea44dc9ed014 1132
joeverbout 0:ea44dc9ed014 1133 //! @} FileNode
joeverbout 0:ea44dc9ed014 1134
joeverbout 0:ea44dc9ed014 1135 //! @relates cv::FileNodeIterator
joeverbout 0:ea44dc9ed014 1136 //! @{
joeverbout 0:ea44dc9ed014 1137
joeverbout 0:ea44dc9ed014 1138 static inline
joeverbout 0:ea44dc9ed014 1139 bool operator == (const FileNodeIterator& it1, const FileNodeIterator& it2)
joeverbout 0:ea44dc9ed014 1140 {
joeverbout 0:ea44dc9ed014 1141 return it1.fs == it2.fs && it1.container == it2.container &&
joeverbout 0:ea44dc9ed014 1142 it1.reader.ptr == it2.reader.ptr && it1.remaining == it2.remaining;
joeverbout 0:ea44dc9ed014 1143 }
joeverbout 0:ea44dc9ed014 1144
joeverbout 0:ea44dc9ed014 1145 static inline
joeverbout 0:ea44dc9ed014 1146 bool operator != (const FileNodeIterator& it1, const FileNodeIterator& it2)
joeverbout 0:ea44dc9ed014 1147 {
joeverbout 0:ea44dc9ed014 1148 return !(it1 == it2);
joeverbout 0:ea44dc9ed014 1149 }
joeverbout 0:ea44dc9ed014 1150
joeverbout 0:ea44dc9ed014 1151 static inline
joeverbout 0:ea44dc9ed014 1152 ptrdiff_t operator - (const FileNodeIterator& it1, const FileNodeIterator& it2)
joeverbout 0:ea44dc9ed014 1153 {
joeverbout 0:ea44dc9ed014 1154 return it2.remaining - it1.remaining;
joeverbout 0:ea44dc9ed014 1155 }
joeverbout 0:ea44dc9ed014 1156
joeverbout 0:ea44dc9ed014 1157 static inline
joeverbout 0:ea44dc9ed014 1158 bool operator < (const FileNodeIterator& it1, const FileNodeIterator& it2)
joeverbout 0:ea44dc9ed014 1159 {
joeverbout 0:ea44dc9ed014 1160 return it1.remaining > it2.remaining;
joeverbout 0:ea44dc9ed014 1161 }
joeverbout 0:ea44dc9ed014 1162
joeverbout 0:ea44dc9ed014 1163 //! @} FileNodeIterator
joeverbout 0:ea44dc9ed014 1164
joeverbout 0:ea44dc9ed014 1165 //! @cond IGNORED
joeverbout 0:ea44dc9ed014 1166
joeverbout 0:ea44dc9ed014 1167 inline FileNode FileStorage::getFirstTopLevelNode() const { FileNode r = root(); FileNodeIterator it = r.begin(); return it != r.end() ? *it : FileNode(); }
joeverbout 0:ea44dc9ed014 1168 inline FileNode::FileNode() : fs(0), node(0) {}
joeverbout 0:ea44dc9ed014 1169 inline FileNode::FileNode(const CvFileStorage* _fs, const CvFileNode* _node) : fs(_fs), node(_node) {}
joeverbout 0:ea44dc9ed014 1170 inline FileNode::FileNode(const FileNode& _node) : fs(_node.fs), node(_node.node) {}
joeverbout 0:ea44dc9ed014 1171 inline bool FileNode::empty() const { return node == 0; }
joeverbout 0:ea44dc9ed014 1172 inline bool FileNode::isNone() const { return type() == NONE; }
joeverbout 0:ea44dc9ed014 1173 inline bool FileNode::isSeq() const { return type() == SEQ; }
joeverbout 0:ea44dc9ed014 1174 inline bool FileNode::isMap() const { return type() == MAP; }
joeverbout 0:ea44dc9ed014 1175 inline bool FileNode::isInt() const { return type() == INT; }
joeverbout 0:ea44dc9ed014 1176 inline bool FileNode::isReal() const { return type() == REAL; }
joeverbout 0:ea44dc9ed014 1177 inline bool FileNode::isString() const { return type() == STR; }
joeverbout 0:ea44dc9ed014 1178 inline CvFileNode* FileNode::operator *() { return (CvFileNode*)node; }
joeverbout 0:ea44dc9ed014 1179 inline const CvFileNode* FileNode::operator* () const { return node; }
joeverbout 0:ea44dc9ed014 1180 inline FileNode::operator int() const { int value; read(*this, value, 0); return value; }
joeverbout 0:ea44dc9ed014 1181 inline FileNode::operator float() const { float value; read(*this, value, 0.f); return value; }
joeverbout 0:ea44dc9ed014 1182 inline FileNode::operator double() const { double value; read(*this, value, 0.); return value; }
joeverbout 0:ea44dc9ed014 1183 inline FileNode::operator String() const { String value; read(*this, value, value); return value; }
joeverbout 0:ea44dc9ed014 1184 inline FileNodeIterator FileNode::begin() const { return FileNodeIterator(fs, node); }
joeverbout 0:ea44dc9ed014 1185 inline FileNodeIterator FileNode::end() const { return FileNodeIterator(fs, node, size()); }
joeverbout 0:ea44dc9ed014 1186 inline void FileNode::readRaw( const String& fmt, uchar* vec, size_t len ) const { begin().readRaw( fmt, vec, len ); }
joeverbout 0:ea44dc9ed014 1187 inline FileNode FileNodeIterator::operator *() const { return FileNode(fs, (const CvFileNode*)(const void*)reader.ptr); }
joeverbout 0:ea44dc9ed014 1188 inline FileNode FileNodeIterator::operator ->() const { return FileNode(fs, (const CvFileNode*)(const void*)reader.ptr); }
joeverbout 0:ea44dc9ed014 1189 inline String::String(const FileNode& fn): cstr_(0), len_(0) { read(fn, *this, *this); }
joeverbout 0:ea44dc9ed014 1190
joeverbout 0:ea44dc9ed014 1191 //! @endcond
joeverbout 0:ea44dc9ed014 1192
joeverbout 0:ea44dc9ed014 1193 } // cv
joeverbout 0:ea44dc9ed014 1194
joeverbout 0:ea44dc9ed014 1195 #endif // __OPENCV_CORE_PERSISTENCE_HPP__
joeverbout 0:ea44dc9ed014 1196