🔨 using std::array to buffer input

This commit is contained in:
Niels Lohmann 2017-06-17 20:47:53 +02:00
parent 889006f006
commit 1fbb82de89
No known key found for this signature in database
GPG key ID: 7F3CEA63AE251B69
2 changed files with 24 additions and 23 deletions

View file

@ -8761,15 +8761,15 @@ class basic_json
// native support // native support
/// input adapter for input stream /// input adapter for input stream
static std::shared_ptr<input_adapter> create(std::istream& i, const size_t buffer_size = 16384) static std::shared_ptr<input_adapter> create(std::istream& i)
{ {
return std::shared_ptr<input_adapter>(new cached_input_stream_adapter(i, buffer_size)); return std::shared_ptr<input_adapter>(new cached_input_stream_adapter<16384>(i));
} }
/// input adapter for input stream /// input adapter for input stream
static std::shared_ptr<input_adapter> create(std::istream&& i, const size_t buffer_size = 16384) static std::shared_ptr<input_adapter> create(std::istream&& i)
{ {
return std::shared_ptr<input_adapter>(new cached_input_stream_adapter(i, buffer_size)); return std::shared_ptr<input_adapter>(new cached_input_stream_adapter<16384>(i));
} }
/// input adapter for buffer /// input adapter for buffer
@ -8841,11 +8841,12 @@ class basic_json
using input_adapter_t = std::shared_ptr<input_adapter>; using input_adapter_t = std::shared_ptr<input_adapter>;
/// input adapter for cached stream input /// input adapter for cached stream input
template<std::size_t N>
class cached_input_stream_adapter : public input_adapter class cached_input_stream_adapter : public input_adapter
{ {
public: public:
cached_input_stream_adapter(std::istream& i, const size_t buffer_size) cached_input_stream_adapter(std::istream& i)
: is(i), start_position(is.tellg()), buffer(buffer_size, '\0') : is(i), start_position(is.tellg())
{ {
// immediately abort if stream is erroneous // immediately abort if stream is erroneous
if (JSON_UNLIKELY(i.fail())) if (JSON_UNLIKELY(i.fail()))
@ -8853,10 +8854,7 @@ class basic_json
JSON_THROW(parse_error::create(111, 0, "bad input stream")); JSON_THROW(parse_error::create(111, 0, "bad input stream"));
} }
// initial fill fill_buffer();
is.read(buffer.data(), static_cast<std::streamsize>(buffer.size()));
// store number of bytes in the buffer
fill_size = static_cast<size_t>(is.gcount());
// skip byte order mark // skip byte order mark
if (fill_size >= 3 and buffer[0] == '\xEF' and buffer[1] == '\xBB' and buffer[2] == '\xBF') if (fill_size >= 3 and buffer[0] == '\xEF' and buffer[1] == '\xBB' and buffer[2] == '\xBF')
@ -8884,20 +8882,17 @@ class basic_json
// check if refilling is necessary and possible // check if refilling is necessary and possible
if (buffer_pos == fill_size and not eof) if (buffer_pos == fill_size and not eof)
{ {
// refill fill_buffer();
is.read(buffer.data(), static_cast<std::streamsize>(buffer.size()));
// store number of bytes in the buffer
fill_size = static_cast<size_t>(is.gcount());
// the buffer is ready // check and remember that filling did not yield new input
buffer_pos = 0;
// remember that filling did not yield new input
if (fill_size == 0) if (fill_size == 0)
{ {
eof = true; eof = true;
return std::char_traits<char>::eof(); return std::char_traits<char>::eof();
} }
// the buffer is ready
buffer_pos = 0;
} }
++processed_chars; ++processed_chars;
@ -8910,9 +8905,9 @@ class basic_json
std::string result(length, '\0'); std::string result(length, '\0');
// save stream position // save stream position
auto current_pos = is.tellg(); const auto current_pos = is.tellg();
// save stream flags // save stream flags
auto flags = is.rdstate(); const auto flags = is.rdstate();
// clear stream flags // clear stream flags
is.clear(); is.clear();
@ -8930,6 +8925,14 @@ class basic_json
} }
private: private:
void fill_buffer()
{
// fill
is.read(buffer.data(), static_cast<std::streamsize>(buffer.size()));
// store number of bytes in the buffer
fill_size = static_cast<size_t>(is.gcount());
}
/// the associated input stream /// the associated input stream
std::istream& is; std::istream& is;
@ -8947,7 +8950,7 @@ class basic_json
const std::streampos start_position; const std::streampos start_position;
/// internal buffer /// internal buffer
std::vector<char> buffer; std::array<char, N> buffer;
}; };
/// input adapter for buffer input /// input adapter for buffer input

View file

@ -1175,7 +1175,6 @@ TEST_CASE("regression tests")
// create and print a JSON from the map // create and print a JSON from the map
json j = m1; json j = m1;
std::cout << j << std::endl;
// get the map out of JSON // get the map out of JSON
std::map<std::string, int> m2 = j; std::map<std::string, int> m2 = j;
@ -1191,7 +1190,6 @@ TEST_CASE("regression tests")
// create and print a JSON from the map // create and print a JSON from the map
json j = m1; json j = m1;
std::cout << j << std::endl;
// get the map out of JSON // get the map out of JSON
std::map<std::string, std::string> m2 = j; std::map<std::string, std::string> m2 = j;