another bit of refactoring

This commit is contained in:
VaclavT 2021-07-12 21:25:31 +02:00
parent 5e4480c767
commit eebfaacde4
10 changed files with 70 additions and 101 deletions

2
.vscode/launch.json vendored
View File

@ -8,7 +8,7 @@
"name": "(lldb) Launch",
"type": "cppdbg",
"request": "launch",
"program": "${workspaceFolder}/build/msql",
"program": "${workspaceFolder}/build/usql",
"args": [],
"stopAtEntry": false,
"cwd": "${fileDirname}",

View File

@ -12,7 +12,7 @@ project(usql)
set(PROJECT_NAME usql)
set(SOURCE
exception.cpp lexer.cpp parser.cpp executor.cpp main.cpp table.cpp table.h row.cpp row.h csvreader.cpp csvreader.h)
exception.cpp lexer.cpp parser.cpp usql.cpp main.cpp table.cpp table.h row.cpp row.h csvreader.cpp csvreader.h)
add_executable(${PROJECT_NAME} ${SOURCE})

View File

@ -1,6 +1,5 @@
#include "csvreader.h"
#include <climits>
namespace usql {

View File

@ -1,7 +1,7 @@
#pragma once
#include <math.h>
#include <cmath>
#include <string>
#include <vector>
#include <regex>

View File

@ -1,5 +1,5 @@
#include "parser.h"
#include "executor.h"
#include "usql.h"
// https://dev.to/joaoh82/what-would-sqlite-look-like-if-written-in-rust-part-1-2np4
@ -8,9 +8,6 @@
// drop table
int main(int argc, char *argv[]) {
usql::Parser parser{};
usql::Executor executor{};
std::vector<std::string> sql_commands{
"create table a (i integer not null, s varchar(64), f float null)",
"insert into a (i, s) values(1, 'one')",
@ -35,13 +32,13 @@ int main(int argc, char *argv[]) {
};
usql::uSQL uSql{};
for (auto command : sql_commands) {
std::cout << command << std::endl;
auto node = parser.parse(command);
auto result = executor.execute(*node);
auto result = uSql.execute(command);
result->print();
// std::cout << std::endl;
}
return 0;

View File

@ -33,7 +33,6 @@ namespace usql {
column_name,
column_value,
column_def,
not_implemented_yet,
error
};

View File

@ -43,7 +43,7 @@ namespace usql {
m_columns[col_index] = std::make_unique<ColFloatValue>(value);
}
void Row::setColumnValue(int col_index, std::string value) {
void Row::setColumnValue(int col_index, const std::string &value) {
m_columns[col_index] = std::make_unique<ColStringValue>(value);
};

30
row.h
View File

@ -7,28 +7,10 @@
namespace usql {
class ColumnValue {
private:
ColumnType m_type;
union {
int int_value;
double float_value;
};
};
struct ColValue {
virtual bool isNull() { return false; };
virtual bool isInteger() { return false; };
virtual bool isFloat() { return false; };
virtual bool isString() { return false; };
virtual bool isNull() { return false; };;;;
virtual int integerValue() { throw Exception("Not supported"); };
@ -50,9 +32,7 @@ namespace usql {
ColIntegerValue(int value) : m_integer(value) {};
ColIntegerValue(const ColIntegerValue &other) : m_integer(other.m_integer) {}
virtual bool isInteger() { return true; };
ColIntegerValue(const ColIntegerValue &other) : m_integer(other.m_integer) {};
virtual int integerValue() { return m_integer; };
@ -70,8 +50,6 @@ namespace usql {
ColFloatValue(const ColFloatValue &other) : m_float(other.m_float) {}
virtual bool isFloat() { return true; }
virtual int integerValue() { return (int) m_float; };
virtual double floatValue() { return m_float; };
@ -88,8 +66,6 @@ namespace usql {
ColStringValue(const ColStringValue &other) : m_string(other.m_string) {};
virtual bool isString() { return true; }
virtual int integerValue() { return std::stoi(m_string); };
virtual double floatValue() { return std::stod(m_string); };
@ -113,7 +89,7 @@ namespace usql {
void setColumnValue(int col_index, double value);
void setColumnValue(int col_index, std::string value);
void setColumnValue(int col_index, const std::string &value);
ColValue &operator[](int i) {
return *m_columns[i];

View File

@ -1,4 +1,4 @@
#include "executor.h"
#include "usql.h"
#include "exception.h"
#include "csvreader.h"
@ -7,39 +7,14 @@
namespace usql {
Executor::Executor() {
m_tables.clear();
std::unique_ptr<Table> uSQL::execute(const std::string &command) {
auto node = m_parser.parse(command);
return execute(*node);
}
Table *Executor::find_table(const std::string name) {
auto name_cmp = [name](Table t) { return t.m_name == name; };
auto table_def = std::find_if(begin(m_tables), end(m_tables), name_cmp);
if (table_def != std::end(m_tables)) {
return table_def.operator->();
} else {
throw Exception("table not found (" + name + ")");
}
}
std::unique_ptr<Table> Executor::create_stmt_result_table(int code, std::string text) {
std::vector<ColDefNode> result_tbl_col_defs{};
result_tbl_col_defs.push_back(ColDefNode("code", ColumnType::integer_type, 0, 1, false));
result_tbl_col_defs.push_back(ColDefNode("desc", ColumnType::varchar_type, 1, 255, false));
auto table_def = std::make_unique<Table>("result", result_tbl_col_defs);
Row new_row = table_def->createEmptyRow();
new_row.setColumnValue(0, code);
new_row.setColumnValue(1, text);
table_def->addRow(new_row);
return std::move(table_def);
}
std::unique_ptr<Table> Executor::execute(Node &node) {
std::unique_ptr<Table> uSQL::execute(Node &node) {
// TODO optimize execution nodes here
switch (node.node_type) {
case NodeType::create_table:
@ -57,11 +32,10 @@ namespace usql {
default:
return create_stmt_result_table(-1, "unknown statement");
}
}
std::unique_ptr<Table> Executor::execute_create_table(CreateTableNode &node) {
std::unique_ptr<Table> uSQL::execute_create_table(CreateTableNode &node) {
// TODO check table does not exists
Table table{node.table_name, node.cols_defs};
m_tables.push_back(table);
@ -70,7 +44,7 @@ namespace usql {
}
std::unique_ptr<Table> Executor::execute_insert_into_table(InsertIntoTableNode &node) {
std::unique_ptr<Table> uSQL::execute_insert_into_table(InsertIntoTableNode &node) {
// TODO check column names.size = values.size
// find table
@ -101,7 +75,7 @@ namespace usql {
}
std::unique_ptr<Table> Executor::execute_select(SelectFromTableNode &node) {
std::unique_ptr<Table> uSQL::execute_select(SelectFromTableNode &node) {
// TODO create plan for accessing rows
// find source table
@ -111,7 +85,7 @@ namespace usql {
std::vector<ColDefNode> result_tbl_col_defs{};
std::vector<int> source_table_col_index{};
int i = 0; // new column order
for (ColNameNode rc : node.cols_names) {
for (auto rc : node.cols_names) {
ColDefNode cdef = table->get_column_def(rc.name);
source_table_col_index.push_back(cdef.order);
@ -151,7 +125,7 @@ namespace usql {
}
std::unique_ptr<Table> Executor::execute_delete(DeleteFromTableNode &node) {
std::unique_ptr<Table> uSQL::execute_delete(DeleteFromTableNode &node) {
// TODO create plan for accessing rows
// find source table
@ -172,7 +146,7 @@ namespace usql {
}
std::unique_ptr<Table> Executor::execute_update(UpdateTableNode &node) {
std::unique_ptr<Table> uSQL::execute_update(UpdateTableNode &node) {
// TODO create plan for accessing rows
// find source table
@ -209,7 +183,7 @@ namespace usql {
}
std::unique_ptr<Table> Executor::execute_load(LoadIntoTableNode &node) {
std::unique_ptr<Table> uSQL::execute_load(LoadIntoTableNode &node) {
// find source table
Table *table_def = find_table(node.table_name);
@ -251,8 +225,8 @@ namespace usql {
}
bool Executor::evalWhere(Node *where, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const {
bool uSQL::evalWhere(Node *where, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const {
switch (where->node_type) { // no where clause
case NodeType::true_node:
return true;
@ -268,8 +242,8 @@ namespace usql {
}
bool Executor::evalRelationalOperator(const RelationalOperatorNode &filter, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const {
bool uSQL::evalRelationalOperator(const RelationalOperatorNode &filter, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const {
std::unique_ptr<ValueNode> left_value = evalNode(table, row, filter.left.get());
std::unique_ptr<ValueNode> right_value = evalNode(table, row, filter.right.get());
@ -313,7 +287,7 @@ namespace usql {
std::unique_ptr<ValueNode>
Executor::evalNode(Table *table, std::vector<Row, std::allocator<Row>>::iterator &row, Node *node) const {
uSQL::evalNode(Table *table, std::vector<Row, std::allocator<Row>>::iterator &row, Node *node) const {
if (node->node_type == NodeType::database_value) {
DatabaseValueNode *dvl = static_cast<DatabaseValueNode *>(node);
ColDefNode col_def = table->get_column_def(
@ -347,8 +321,8 @@ namespace usql {
}
bool Executor::evalLogicalOperator(LogicalOperatorNode &node, Table *pTable,
std::vector<Row, std::allocator<Row>>::iterator &iter) const {
bool uSQL::evalLogicalOperator(LogicalOperatorNode &node, Table *pTable,
std::vector<Row, std::allocator<Row>>::iterator &iter) const {
bool left = evalRelationalOperator(static_cast<const RelationalOperatorNode &>(*node.left), pTable, iter);
if ((node.op == LogicalOperatorType::and_operator && !left) ||
@ -361,8 +335,8 @@ namespace usql {
std::unique_ptr<ValueNode>
Executor::evalArithmetic(ColumnType outType, ArithmeticalOperatorNode &node, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const {
uSQL::evalArithmetic(ColumnType outType, ArithmeticalOperatorNode &node, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const {
if (node.op == ArithmeticalOperatorType::copy_value) {
return evalNode(table, row, node.left.get());
}
@ -416,4 +390,32 @@ namespace usql {
throw Exception("implement me!!");
}
Table *uSQL::find_table(const std::string name) {
auto name_cmp = [name](const Table& t) { return t.m_name == name; };
auto table_def = std::find_if(begin(m_tables), end(m_tables), name_cmp);
if (table_def != std::end(m_tables)) {
return table_def.operator->();
} else {
throw Exception("table not found (" + name + ")");
}
}
std::unique_ptr<Table> uSQL::create_stmt_result_table(int code, std::string text) {
std::vector<ColDefNode> result_tbl_col_defs{};
result_tbl_col_defs.push_back(ColDefNode("code", ColumnType::integer_type, 0, 1, false));
result_tbl_col_defs.push_back(ColDefNode("desc", ColumnType::varchar_type, 1, 255, false));
auto table_def = std::make_unique<Table>("result", result_tbl_col_defs);
Row new_row = table_def->createEmptyRow();
new_row.setColumnValue(0, code);
new_row.setColumnValue(1, text);
table_def->addRow(new_row);
return std::move(table_def);
}
}

View File

@ -7,34 +7,26 @@
namespace usql {
class Executor {
private:
class uSQL {
public:
Executor();
std::unique_ptr<Table> execute(Node &node);
std::unique_ptr<Table> execute(const std::string &command);
private:
std::unique_ptr<Table> execute(Node &node);
std::unique_ptr<Table> execute_create_table(CreateTableNode &node);
std::unique_ptr<Table> execute_insert_into_table(InsertIntoTableNode &node);
std::unique_ptr<Table> execute_select(SelectFromTableNode &node);
std::unique_ptr<Table> execute_delete(DeleteFromTableNode &node);
std::unique_ptr<Table> execute_update(UpdateTableNode &node);
std::unique_ptr<Table> execute_load(LoadIntoTableNode &node);
Table *find_table(const std::string name);
std::unique_ptr<Table> create_stmt_result_table(int code, std::string text);
private:
std::vector<Table> m_tables;
private:
bool evalWhere(Node *where, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const;
@ -49,6 +41,10 @@ namespace usql {
std::unique_ptr<ValueNode> evalArithmetic(ColumnType outType, ArithmeticalOperatorNode &node, Table *table,
std::vector<Row, std::allocator<Row>>::iterator &row) const;
private:
Parser m_parser;
std::vector<Table> m_tables;
};
}