~aritra1911/cylinder

f50b568577a217da7a56e65babdce8c02e5c1d13 — Aritra Sarkar 3 years ago 360067e
Add Field Types
3 files changed, 114 insertions(+), 0 deletions(-)

A field_test.cpp
A field_type.cpp
A field_type.hpp
A field_test.cpp => field_test.cpp +69 -0
@@ 0,0 1,69 @@
#include <iostream>
#include <string>
#include <vector>
#include "field_type.hpp"

int main(void) {
    int n;
    std::cout << "How many fields? ";
    std::cin >> n;

    std::vector<AbstractField*> record;
    std::vector<std::string> field_names;

    std::cout << "\nEnter space separated field names: ";
    for (int i=0; i<n; i++) {
        std::string name;
        std::cin >> name;
        field_names.push_back(name);
    }

    std::cout << "\nNUMBER = 0\nVARCHAR = 1\nEnter space separated field types: ";

    FieldType type;
    for (int i=0; i<n; i++) {
        std::cin >> (int&)type;
        switch (type) {
            case NUMBER:
                record.push_back(new Field<int>(type, field_names[i]));
                break;

            default:
                record.push_back(new Field<std::string>(type, field_names[i]));
        }
    }

    std::cout << "Enter space separated values: ";
    for (int i = 0; i < n; i++) {
        switch (record[i]->type) {
            case NUMBER:
                std::cin >> static_cast<Field<int>*>(record[i])->value;
                break;

            default:
                std::cin >> static_cast<Field<std::string>*>(record[i])->value;
        }
    }

    std::cout << std::endl;

    for (int i=0; i<n; i++) {
        std::cout << record[i]->name << " : ";
        switch (record[i]->type) {
            case NUMBER:
                std::cout << static_cast<Field<int>*>(record[i])->value;
                break;

            default:
                std::cout << static_cast<Field<std::string>*>(record[i])->value;
        }
        std::cout << std::endl;
    }

    for (int i=0; i<n; i++)
        delete record[i];

    record.clear();

    return 0;
}

A field_type.cpp => field_type.cpp +8 -0
@@ 0,0 1,8 @@
#include <string>
#include "field_type.hpp"

AbstractField::AbstractField(const FieldType& type, const std::string& name) : type(type), name(name) { }

/* Since ~AbstractField() is declared as a pure virtual function, it needs a definition outside the `struct
 * AbstractField' anyway since there is no way to override a destructor. */
AbstractField::~AbstractField() { }

A field_type.hpp => field_type.hpp +37 -0
@@ 0,0 1,37 @@
#ifndef _FIELD_TYPE_HPP
# define _FIELD_TYPE_HPP

# include <string>

enum FieldType {
    NUMBER,  /* Int, TODO: Include Float */
    VARCHAR,  /* std::string, Don't think(TODO) too much right now */
};

/* AbstractField serves as a base for multiple fields of different types, i.e. a collection of AbstractField* in an
 * array can point to multiple Fields of different types. This is how a database record shall be maintained since we
 * don't know prior to user input, what type of Fields we'll be needing and how many of them. FieldType is helpful in
 * determining what type of Field we'll be casting the AbstractField* to.
 *
 * P.S. I'm new to this world of C++ casts and I don't quite know the difference between them. I've experimented with
 * dynamic_cast and static_cast and static_cast seems to be working fine.
 */

struct AbstractField {
    std::string name;
    FieldType type;

    AbstractField(const FieldType&, const std::string&);
    virtual ~AbstractField() = 0;
};

template<class T>
struct Field : AbstractField {
    T value;

    Field(const FieldType& type, const std::string& name) : AbstractField(type, name) { }

    Field(const FieldType& type, const std::string& name, const T& value) : AbstractField(type, name), value(value) { }
};

#endif