Skip to content

Performance improvements #365

Description

@TurpentineDistillery

I propose some minor changes that yield substantial performance improvements.

diff --git a/src/json.hpp b/src/json.hpp
index a302bb0..0a8ab78 100644
--- a/src/json.hpp
+++ b/src/json.hpp
@@ -8755,10 +8755,10 @@ basic_json_parser_66:
                 {
                     // copy unprocessed characters to line buffer
                     m_line_buffer.clear();
-                    for (m_cursor = m_start; m_cursor != m_limit; ++m_cursor)
-                    {
-                        m_line_buffer.append(1, static_cast<const char>(*m_cursor));
-                    }
+                    m_line_buffer.append(
+                            reinterpret_cast<const typename string_t::value_type*>(m_start),
+                            static_cast<size_t>(m_limit - m_start));
+                    m_cursor = m_limit;
                 }

                 // append n characters to make sure that there is sufficient
@@ -8770,11 +8770,13 @@ basic_json_parser_66:
             {
                 // delete processed characters from line buffer
                 m_line_buffer.erase(0, static_cast<size_t>(offset_start));
+
                 // read next line from input stream
-                std::string line;
-                std::getline(*m_stream, line, '\n');
+                m_line_buffer_tmp.clear();
+                std::getline(*m_stream, m_line_buffer_tmp, '\n');
                 // add line with newline symbol to the line buffer
-                m_line_buffer += line + "\n";
+                m_line_buffer += m_line_buffer_tmp;
+                m_line_buffer.push_back('\n');
             }

             // set pointers
@@ -8861,9 +8863,15 @@ basic_json_parser_66:
             // iterate the result between the quotes
             for (const lexer_char_t* i = m_start + 1; i < m_cursor - 1; ++i)
             {
-                // process escaped characters
-                if (*i == '\\')
-                {
+                // number of non-escaped characters
+                const size_t n = static_cast<size_t>(std::find(i, m_cursor - 1, '\\') - i);
+
+                if(n != 0) {
+                    result.append(reinterpret_cast<const typename string_t::value_type*>(i), n);
+                    i += n-1; // -1 because will ++i
+                } else {
+                    // processing escaped character
+
                     // read next character
                     ++i;

@@ -8950,12 +8958,6 @@ basic_json_parser_66:
                         }
                     }
                 }
-                else
-                {
-                    // all other characters are just copied to the end of the
-                    // string
-                    result.append(1, static_cast<typename string_t::value_type>(*i));
-                }
             }

             return result;
@@ -9139,6 +9141,8 @@ basic_json_parser_66:
         std::istream* m_stream = nullptr;
         /// line buffer buffer for m_stream
         string_t m_line_buffer {};
+        /// used for filling m_line_buffer
+        string_t m_line_buffer_tmp {};
         /// the buffer pointer
         const lexer_char_t* m_content = nullptr;
         /// pointer to the beginning of the current symbol
Before
parse jeopardy.json                           1  1746079858 ns/op
parse canada.json                            50    49808100 ns/op
parse citm_catalog.json                      50    30050798 ns/op
parse twitter.json                          100    15523826 ns/op
parse numbers/floats.json                     5   539260495 ns/op
parse numbers/signed_ints.json                5   346619225 ns/op
parse numbers/unsigned_ints.json              5   348103862 ns/op
dump jeopardy.json                            1  1882424034 ns/op
dump jeopardy.json with indent                1  2333816314 ns/op

After:
parse jeopardy.json                           1  1392954141 ns/op
parse canada.json                            50    47828487 ns/op
parse citm_catalog.json                     100    19988139 ns/op
parse twitter.json                          100    10175643 ns/op
parse numbers/floats.json                     5   428099836 ns/op
parse numbers/signed_ints.json                5   232719693 ns/op
parse numbers/unsigned_ints.json              5   234741840 ns/op
dump jeopardy.json                            1  1871500322 ns/op
dump jeopardy.json with indent                1  2512231626 ns/op

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Projects

No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions