summaryrefslogtreecommitdiffstats
path: root/ml/dlib/dlib/vectorstream
diff options
context:
space:
mode:
Diffstat (limited to 'ml/dlib/dlib/vectorstream')
-rw-r--r--ml/dlib/dlib/vectorstream/unserialize.h98
-rw-r--r--ml/dlib/dlib/vectorstream/unserialize_abstract.h58
-rw-r--r--ml/dlib/dlib/vectorstream/vectorstream.h138
-rw-r--r--ml/dlib/dlib/vectorstream/vectorstream_abstract.h62
4 files changed, 356 insertions, 0 deletions
diff --git a/ml/dlib/dlib/vectorstream/unserialize.h b/ml/dlib/dlib/vectorstream/unserialize.h
new file mode 100644
index 000000000..dbfe5584b
--- /dev/null
+++ b/ml/dlib/dlib/vectorstream/unserialize.h
@@ -0,0 +1,98 @@
+// Copyright (C) 2016 Davis E. King (davis@dlib.net)
+// License: Boost Software License See LICENSE.txt for the full license.
+#ifndef DLIB_uNSERIALIZE_Hh_
+#define DLIB_uNSERIALIZE_Hh_
+
+#include "unserialize_abstract.h"
+
+#include "../serialize.h"
+#include "../algs.h"
+#include "vectorstream.h"
+
+
+
+namespace dlib
+{
+ class unserialize : public std::istream
+ {
+ class mystreambuf : public std::streambuf
+ {
+ typedef std::vector<char>::size_type size_type;
+ size_type read_pos; // buffer[read_pos] == next byte to read from buffer
+ public:
+ std::vector<char> buffer;
+ std::istream& str;
+
+ template <typename T>
+ mystreambuf(
+ const T& item,
+ std::istream& str_
+ ) :
+ read_pos(0),
+ str(str_)
+ {
+ // put the item into our buffer.
+ vectorstream vstr(buffer);
+ serialize(item, vstr);
+ }
+
+
+ // ------------------------ INPUT FUNCTIONS ------------------------
+
+ int_type underflow(
+ )
+ {
+ if (read_pos < buffer.size())
+ return static_cast<unsigned char>(buffer[read_pos]);
+ else
+ return str.peek();
+ }
+
+ int_type uflow(
+ )
+ {
+ if (read_pos < buffer.size())
+ return static_cast<unsigned char>(buffer[read_pos++]);
+ else
+ return str.get();
+ }
+
+ std::streamsize xsgetn (
+ char* s,
+ std::streamsize n
+ )
+ {
+ if (read_pos < buffer.size())
+ {
+ const size_type num = std::min<size_type>(n, buffer.size()-read_pos);
+ std::memcpy(s, &buffer[read_pos], num);
+ read_pos += num;
+ return num;
+ }
+ else
+ {
+ return str.rdbuf()->sgetn(s,n);
+ }
+ return 0;
+ }
+
+ };
+
+ public:
+
+ template <typename T>
+ unserialize (
+ const T& item,
+ std::istream& str
+ ) :
+ std::istream(&buf),
+ buf(item, str)
+ {}
+
+ private:
+ mystreambuf buf;
+ };
+}
+
+#endif // DLIB_uNSERIALIZE_Hh_
+
diff --git a/ml/dlib/dlib/vectorstream/unserialize_abstract.h b/ml/dlib/dlib/vectorstream/unserialize_abstract.h
new file mode 100644
index 000000000..b7d67836c
--- /dev/null
+++ b/ml/dlib/dlib/vectorstream/unserialize_abstract.h
@@ -0,0 +1,58 @@
+// Copyright (C) 2016 Davis E. King (davis@dlib.net)
+// License: Boost Software License See LICENSE.txt for the full license.
+#undef DLIB_uNSERIALIZE_ABSTRACT_Hh_
+#ifdef DLIB_uNSERIALIZE_ABSTRACT_Hh_
+
+#include "../serialize.h"
+#include <iostream>
+
+namespace dlib
+{
+ class unserialize : public std::istream
+ {
+ /*!
+ WHAT THIS OBJECT REPRESENTS
+ This is a tool that allows you to effectively put an object you just
+ deserialized from a stream back into the stream. Its use is best
+ illustrated via an example.
+
+ void example(std::istream& in)
+ {
+ // Suppose that in contains serialized copies of three "some_type"
+ // objects. You could read them as follows:
+ some_type obj1, obj2, obj3;
+
+ deserialize(obj1, in); // reads obj1 from stream.
+ deserialize(obj2, in); // reads obj2 from stream.
+
+ unserialize in2(obj2, in); // make the in2 stream that has obj2 at its front.
+ deserialize(obj2, in2); // reads obj2 from stream again.
+ deserialize(obj3, in2); // reads obj3 from stream.
+ }
+
+ The reason unserialize is useful is because it allows you to peek at the
+ next object in a stream and potentially do something different based on
+ what object is coming next, but still allowing subsequent deserialize()
+ statements to be undisturbed by the fact that you peeked at the data.
+ !*/
+
+ public:
+
+ template <typename T>
+ unserialize (
+ const T& item,
+ std::istream& in
+ );
+ /*!
+ requires
+ - T must be serializable
+ ensures
+ - The bytes in this stream begin with a serialized copy of item followed
+ immediately by the bytes in the given istream.
+ !*/
+ };
+}
+
+#endif // DLIB_uNSERIALIZE_ABSTRACT_Hh_
+
+
diff --git a/ml/dlib/dlib/vectorstream/vectorstream.h b/ml/dlib/dlib/vectorstream/vectorstream.h
new file mode 100644
index 000000000..a1b7b8b07
--- /dev/null
+++ b/ml/dlib/dlib/vectorstream/vectorstream.h
@@ -0,0 +1,138 @@
+// Copyright (C) 2012 Davis E. King (davis@dlib.net)
+// License: Boost Software License See LICENSE.txt for the full license.
+#ifndef DLIB_VECTORStREAM_Hh_
+#define DLIB_VECTORStREAM_Hh_
+
+#include "vectorstream_abstract.h"
+
+#include <cstring>
+#include <iostream>
+#include <streambuf>
+#include <vector>
+#include <cstdio>
+#include "../algs.h"
+
+
+#ifdef _MSC_VER
+// Disable the warning about inheriting from std::iostream 'via dominance' since this warning is a warning about
+// visual studio conforming to the standard and is ignorable. See http://connect.microsoft.com/VisualStudio/feedback/details/733720/inheriting-from-std-fstream-produces-c4250-warning
+// for further details if interested.
+#pragma warning(disable : 4250)
+#endif // _MSC_VER
+
+namespace dlib
+{
+ class vectorstream : public std::iostream
+ {
+ class vector_streambuf : public std::streambuf
+ {
+ typedef std::vector<char>::size_type size_type;
+ size_type read_pos; // buffer[read_pos] == next byte to read from buffer
+ public:
+ std::vector<char>& buffer;
+
+ vector_streambuf(
+ std::vector<char>& buffer_
+ ) :
+ read_pos(0),
+ buffer(buffer_)
+ {}
+
+
+ void seekg(size_type pos)
+ {
+ read_pos = pos;
+ }
+
+ // ------------------------ OUTPUT FUNCTIONS ------------------------
+
+ int_type overflow ( int_type c)
+ {
+ if (c != EOF) buffer.push_back(static_cast<char>(c));
+ return c;
+ }
+
+ std::streamsize xsputn ( const char* s, std::streamsize num)
+ {
+ buffer.insert(buffer.end(), s, s+num);
+ return num;
+ }
+
+ // ------------------------ INPUT FUNCTIONS ------------------------
+
+ int_type underflow(
+ )
+ {
+ if (read_pos < buffer.size())
+ return static_cast<unsigned char>(buffer[read_pos]);
+ else
+ return EOF;
+ }
+
+ int_type uflow(
+ )
+ {
+ if (read_pos < buffer.size())
+ return static_cast<unsigned char>(buffer[read_pos++]);
+ else
+ return EOF;
+ }
+
+ int_type pbackfail(
+ int_type c
+ )
+ {
+ // if they are trying to push back a character that they didn't read last
+ // that is an error
+ const unsigned long prev = read_pos-1;
+ if (c != EOF && prev < buffer.size() &&
+ c != static_cast<unsigned char>(buffer[prev]))
+ {
+ return EOF;
+ }
+
+ read_pos = prev;
+ return 1;
+ }
+
+ std::streamsize xsgetn (
+ char* s,
+ std::streamsize n
+ )
+ {
+ if (read_pos < buffer.size())
+ {
+ const size_type num = std::min<size_type>(n, buffer.size()-read_pos);
+ std::memcpy(s, &buffer[read_pos], num);
+ read_pos += num;
+ return num;
+ }
+ return 0;
+ }
+
+ };
+
+ public:
+
+ vectorstream (
+ std::vector<char>& buffer
+ ) :
+ std::iostream(&buf),
+ buf(buffer)
+ {}
+
+ std::istream& seekg (
+ std::streampos pos
+ )
+ {
+ buf.seekg(pos);
+ return *this;
+ }
+
+ private:
+ vector_streambuf buf;
+ };
+}
+
+#endif // DLIB_VECTORStREAM_Hh_
+
diff --git a/ml/dlib/dlib/vectorstream/vectorstream_abstract.h b/ml/dlib/dlib/vectorstream/vectorstream_abstract.h
new file mode 100644
index 000000000..f5fe1004c
--- /dev/null
+++ b/ml/dlib/dlib/vectorstream/vectorstream_abstract.h
@@ -0,0 +1,62 @@
+// Copyright (C) 2012 Davis E. King (davis@dlib.net)
+// License: Boost Software License See LICENSE.txt for the full license.
+#undef DLIB_VECTORStREAM_ABSTRACT_Hh_
+#ifdef DLIB_VECTORStREAM_ABSTRACT_Hh_
+
+#include <iostream>
+#include <vector>
+
+namespace dlib
+{
+ class vectorstream : public std::iostream
+ {
+ /*!
+ WHAT THIS OBJECT REPRESENTS
+ This is an iostream object that reads and writes from an in-memory buffer.
+ It functions very much the same way as the std::stringstream object.
+ However, while the std::stringstream holds its buffer internally and it can
+ only be accessed by copying it out, the vectorstream uses an external
+ std::vector<char> as its buffer. That is, it holds a reference to an
+ external vector and does not contain any internal buffers of its own.
+
+ This object is useful as a slightly more efficient alternative to the
+ std::stringstream since you can avoid the overhead of copying buffer
+ contents to and from the stream. This is particularly useful when used as
+ a source or target for serialization routines.
+ !*/
+
+ public:
+
+ vectorstream (
+ std::vector<char>& buffer
+ );
+ /*!
+ ensures
+ - This object will use the given vector as its read/write buffer. That is:
+ - Any data written to this stream will be appended to the given buffer
+ - Any data read from this stream is read from the given buffer,
+ starting with buffer[0], then buffer[1], and so on. Just like
+ std::stringstream, writes to the stream do not move the position of
+ the next byte that will be read from the buffer.
+ - This constructor does not copy the buffer. Only a reference to it will
+ be used. Therefore, any time data is written to this stream it will
+ immediately show up in the buffer.
+ !*/
+
+ std::istream& seekg (
+ std::streampos pos
+ );
+ /*!
+ ensures
+ - The next read from this object will read from the position buffer[pos],
+ where buffer is the std::vector given to this object's constructor. Note
+ that if pos >= buffer.size() then the next read will simply return EOF.
+ - returns *this
+ !*/
+
+ };
+}
+
+#endif // DLIB_VECTORStREAM_ABSTRACT_Hh_
+
+