aakshintala / toy-query-engine

MIT License
0 stars 0 forks source link

Bored... Idiomatic CSV reading via Iterators. #1

Open PyRO69 opened 2 years ago

PyRO69 commented 2 years ago
class CSVReader {
    struct CSVItr {
        CSVItr() : m_stream(nullptr) {}
        CSVItr(std::istream& in) : m_stream((in.good() ? &in : nullptr)) { ++(*this); }

        CSVItr& operator++() {
            readNextRow();
            return *this;
        }
        CSVItr operator++(int) {
            auto tmp = *this;
            ++(*this);
            return tmp;
        }
        const auto& operator*() {
            return m_currRow;
        }
        bool operator==(const CSVItr& other) {
            return this == &other || (this->m_stream == nullptr && other.m_stream == nullptr);
        }
        bool operator!=(const CSVItr& other) {
            return !(*this == other);
        }

        private:
        void readNextRow() {
            if (!m_stream) { return; }
            m_currRow.clear();
            std::string row, col;
            std::getline(*m_stream, row);
            std::stringstream ss(row);
            while(std::getline(ss, col, ',')) {
                m_currRow.push_back(col);            
            }
            if (!(*m_stream)) { m_stream = nullptr; }
        }
        std::istream* m_stream;
        std::vector<std::string> m_currRow;
    };

    public:
    CSVReader(std::istream& str) : m_stream(str) {}

    CSVItr begin() {
        return CSVItr(m_stream);
    }
    CSVItr end() {
        return CSVItr();
    }

    private:
    std::istream& m_stream;
};

int main()
{
    std::string test = "1,2,3\n4,5,6";
    std::stringstream testStr(test);
    CSVReader reader(testStr);
    int Row = 1;
    for (auto& row : reader) {
        std::cout << "Row = " << Row++ << "\n";
        for (auto& val : row) {
            std::cout << val << ",";   
        }
        std::cout << "\n";
    }

    return 0;
}

Output

Row = 1
1,2,3,
Row = 2
4,5,6,
Ret: 0
PyRO69 commented 2 years ago

I was bored so i figured thinking about this for 15m would be a good workout. I realized I'd forgotten some of the File IO libraries :D

PyRO69 commented 2 years ago

A fancier version would be to incorporate tuples and parse out to native types instead of strings. But too much template programming for that.