From fe325716d1a53766ad2f19ba85e368bf4222dca7 Mon Sep 17 00:00:00 2001 From: Pavel Artemkin Date: Thu, 15 Apr 2021 12:56:23 +0500 Subject: [PATCH] wrap RowCollection into unique_ptr to avoid problems with move constructor (#160) --- include/internal/csv_reader.cpp | 34 ++++++++++++------------ include/internal/csv_reader.hpp | 6 ++--- include/internal/csv_reader_iterator.cpp | 8 +++--- 3 files changed, 24 insertions(+), 24 deletions(-) diff --git a/include/internal/csv_reader.cpp b/include/internal/csv_reader.cpp index 38a333df..d2dff741 100644 --- a/include/internal/csv_reader.cpp +++ b/include/internal/csv_reader.cpp @@ -30,7 +30,7 @@ namespace csv { auto trim_chars = format.get_trim_chars(); std::stringstream source(head.data()); RowCollection rows; - + StreamParser parser(source, format); parser.set_output(rows); parser.next(); @@ -71,7 +71,7 @@ namespace csv { double final_score = 0; size_t header_row = 0; - // Final score is equal to the largest + // Final score is equal to the largest // row size times rows of that size for (auto& pair : row_tally) { auto row_size = pair.first; @@ -174,7 +174,7 @@ namespace csv { CSV_INLINE CSVFormat CSVReader::get_format() const { CSVFormat new_format = this->_format; - // Since users are normally not allowed to set + // Since users are normally not allowed to set // column names and header row simulatenously, // we will set the backing variables directly here new_format.col_names = this->col_names->get_col_names(); @@ -205,12 +205,12 @@ namespace csv { CSV_INLINE void CSVReader::trim_header() { if (!this->header_trimmed) { - for (int i = 0; i <= this->_format.header && !this->records.empty(); i++) { + for (int i = 0; i <= this->_format.header && !this->records->empty(); i++) { if (i == this->_format.header && this->col_names->empty()) { - this->set_col_names(this->records.pop_front()); + this->set_col_names(this->records->pop_front()); } else { - this->records.pop_front(); + this->records->pop_front(); } } @@ -240,9 +240,9 @@ namespace csv { */ CSV_INLINE bool CSVReader::read_csv(size_t bytes) { // Tell read_row() to listen for CSV rows - this->records.notify_all(); + this->records->notify_all(); - this->parser->set_output(this->records); + this->parser->set_output(*this->records); this->parser->next(bytes); if (!this->header_trimmed) { @@ -250,7 +250,7 @@ namespace csv { } // Tell read_row() to stop waiting - this->records.kill_all(); + this->records->kill_all(); return true; } @@ -271,10 +271,10 @@ namespace csv { */ CSV_INLINE bool CSVReader::read_row(CSVRow &row) { while (true) { - if (this->records.empty()) { - if (this->records.is_waitable()) + if (this->records->empty()) { + if (this->records->is_waitable()) // Reading thread is currently active => wait for it to populate records - this->records.wait(); + this->records->wait(); else if (this->parser->eof()) // End of file and no more records return false; @@ -286,9 +286,9 @@ namespace csv { this->read_csv_worker = std::thread(&CSVReader::read_csv, this, internals::ITERATION_CHUNK_SIZE); } } - else if (this->records.front().size() != this->n_cols && + else if (this->records->front().size() != this->n_cols && this->_format.variable_column_policy != VariableColumnPolicy::KEEP) { - auto errored_row = this->records.pop_front(); + auto errored_row = this->records->pop_front(); if (this->_format.variable_column_policy == VariableColumnPolicy::THROW) { if (errored_row.size() < this->n_cols) @@ -298,12 +298,12 @@ namespace csv { } } else { - row = std::move(this->records.pop_front()); + row = std::move(this->records->pop_front()); this->_n_rows++; return true; } } - + return false; } -} \ No newline at end of file +} diff --git a/include/internal/csv_reader.hpp b/include/internal/csv_reader.hpp index a2a46f05..0977a985 100644 --- a/include/internal/csv_reader.hpp +++ b/include/internal/csv_reader.hpp @@ -156,7 +156,7 @@ namespace csv { std::vector get_col_names() const; int index_of(csv::string_view col_name) const; ///@} - + /** @name CSV Metadata: Attributes */ ///@{ /** Whether or not the file or stream contains valid CSV rows, @@ -199,7 +199,7 @@ namespace csv { std::unique_ptr parser = nullptr; /** Queue of parsed CSV rows */ - RowCollection records = RowCollection(100); + std::unique_ptr records{new RowCollection(100)}; size_t n_cols = 0; /**< The number of columns in this CSV */ size_t _n_rows = 0; /**< How many rows (minus header) have been read so far */ @@ -228,4 +228,4 @@ namespace csv { void trim_header(); }; -} \ No newline at end of file +} diff --git a/include/internal/csv_reader_iterator.cpp b/include/internal/csv_reader_iterator.cpp index 6916f952..9ebff2d3 100644 --- a/include/internal/csv_reader_iterator.cpp +++ b/include/internal/csv_reader_iterator.cpp @@ -7,15 +7,15 @@ namespace csv { /** Return an iterator to the first row in the reader */ CSV_INLINE CSVReader::iterator CSVReader::begin() { - if (this->records.empty()) { + if (this->records->empty()) { this->read_csv_worker = std::thread(&CSVReader::read_csv, this, internals::ITERATION_CHUNK_SIZE); this->read_csv_worker.join(); // Still empty => return end iterator - if (this->records.empty()) return this->end(); + if (this->records->empty()) return this->end(); } - CSVReader::iterator ret(this, std::move(this->records.pop_front())); + CSVReader::iterator ret(this, std::move(this->records->pop_front())); return ret; } @@ -59,4 +59,4 @@ namespace csv { return temp; } -} \ No newline at end of file +}