refactored grammar. now includes where clause
This commit is contained in:
parent
dee7fb6468
commit
592d427f7a
|
@ -4,5 +4,5 @@ make clean
|
||||||
make tests
|
make tests
|
||||||
./bin/tests
|
./bin/tests
|
||||||
|
|
||||||
make execution
|
# make execution
|
||||||
./bin/sql_execution "SELECT col1, col2 FROM table GROUP BY col1;"
|
# ./bin/sql_execution "SELECT col1, col2 FROM table GROUP BY col1;"
|
|
@ -32,6 +32,18 @@ SELECT TOK(SELECT)
|
||||||
FROM TOK(FROM)
|
FROM TOK(FROM)
|
||||||
GROUP TOK(GROUP)
|
GROUP TOK(GROUP)
|
||||||
BY TOK(BY)
|
BY TOK(BY)
|
||||||
|
WHERE TOK(WHERE)
|
||||||
|
NOT TOK(NOT)
|
||||||
|
AND TOK(AND)
|
||||||
|
OR TOK(OR)
|
||||||
|
|
||||||
|
|
||||||
|
"=" |
|
||||||
|
"<>" |
|
||||||
|
"<" |
|
||||||
|
">" |
|
||||||
|
"<=" |
|
||||||
|
">=" TOK(COMPARISON)
|
||||||
|
|
||||||
[-+*/(),.;] TOK(yytext[0])
|
[-+*/(),.;] TOK(yytext[0])
|
||||||
|
|
||||||
|
@ -40,6 +52,12 @@ BY TOK(BY)
|
||||||
"."[0-9]* TOK(INTNUM)
|
"."[0-9]* TOK(INTNUM)
|
||||||
|
|
||||||
[A-Za-z][A-Za-z0-9_]* {
|
[A-Za-z][A-Za-z0-9_]* {
|
||||||
|
yylval->sval = strdup(yytext);
|
||||||
|
return NAME;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
'[^'\n]*' {
|
||||||
yylval->sval = strdup(yytext);
|
yylval->sval = strdup(yytext);
|
||||||
return STRING;
|
return STRING;
|
||||||
}
|
}
|
||||||
|
|
138
src/lex_parser.y
138
src/lex_parser.y
|
@ -48,73 +48,131 @@ typedef void* yyscan_t;
|
||||||
List<Expression*>* explist;
|
List<Expression*>* explist;
|
||||||
}
|
}
|
||||||
|
|
||||||
%token SELECT FROM GROUP BY INTNUM
|
%token SELECT FROM GROUP BY WHERE NOT AND OR
|
||||||
%token <sval> STRING
|
%token INTNUM COMPARISON STRING
|
||||||
|
%token <sval> NAME
|
||||||
|
|
||||||
%type <statement> statement
|
%type <statement> statement
|
||||||
%type <select_statement> select_statement
|
%type <select_statement> select_statement
|
||||||
%type <table> from_clause
|
%type <sval> column_name table_name
|
||||||
%type <slist> string_list
|
%type <table> from_clause table_exp
|
||||||
%type <explist> expr_list group_clause
|
|
||||||
%type <expr> expr;
|
%type <expr> expr;
|
||||||
|
%type <slist> table_ref_commalist
|
||||||
|
%type <explist> expr_list group_clause
|
||||||
%%
|
%%
|
||||||
|
|
||||||
|
|
||||||
input:
|
input:
|
||||||
statement opt_semicolon { *statement = $1; };
|
statement opt_semicolon { *statement = $1; }
|
||||||
|
;
|
||||||
|
|
||||||
opt_semicolon:
|
|
||||||
';' | ;
|
|
||||||
|
|
||||||
|
|
||||||
statement:
|
statement:
|
||||||
select_statement { $$ = $1; }
|
select_statement { $$ = $1; }
|
||||||
| { $$ = NULL; };
|
| /* empty */ { $$ = NULL; }
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
select_statement:
|
select_statement:
|
||||||
SELECT expr_list from_clause group_clause
|
SELECT expr_list from_clause where_clause group_clause
|
||||||
{
|
{
|
||||||
SelectStatement* s = new SelectStatement();
|
SelectStatement* s = new SelectStatement();
|
||||||
s->_select_list = $2;
|
s->_select_list = $2;
|
||||||
s->_from_table = $3;
|
s->_from_table = $3;
|
||||||
s->_group_by = $4;
|
s->_group_by = $5;
|
||||||
$$ = s;
|
$$ = s;
|
||||||
};
|
}
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
expr_list:
|
|
||||||
expr { $$ = new List<Expression*>($1); }
|
|
||||||
| expr_list ',' expr { $1->push_back($3); $$ = $1; };
|
|
||||||
|
|
||||||
|
|
||||||
expr:
|
|
||||||
STRING { $$ = new Expression($1); }
|
|
||||||
| STRING '(' STRING ')' { $$ = new Expression($3, $1); };
|
|
||||||
|
|
||||||
|
|
||||||
from_clause:
|
from_clause:
|
||||||
FROM string_list
|
FROM table_exp { $$ = $2; }
|
||||||
{
|
;
|
||||||
TableRef* t = new TableRef(eTableName);
|
|
||||||
t->_table_names = $2;
|
|
||||||
$$ = t;
|
|
||||||
}
|
|
||||||
| FROM '(' select_statement ')'
|
|
||||||
{
|
|
||||||
TableRef* t = new TableRef(eTableSelect);
|
|
||||||
t->_stmt = $3;
|
|
||||||
$$ = t;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
where_clause:
|
||||||
|
WHERE search_condition
|
||||||
|
| /* empty */
|
||||||
|
;
|
||||||
|
|
||||||
group_clause:
|
group_clause:
|
||||||
GROUP BY expr_list { $$ = $3; }
|
GROUP BY expr_list { $$ = $3; }
|
||||||
| { $$ = NULL; };
|
| /* empty */ { $$ = NULL; }
|
||||||
|
;
|
||||||
|
|
||||||
string_list:
|
|
||||||
STRING { $$ = new List<char*>($1); }
|
|
||||||
| string_list ',' STRING { $1->push_back($3); $$ = $1; }
|
|
||||||
|
|
||||||
|
|
||||||
|
table_exp:
|
||||||
|
table_ref_commalist {
|
||||||
|
TableRef* t = new TableRef(eTableName);
|
||||||
|
t->_table_names = $1;
|
||||||
|
$$ = t;
|
||||||
|
}
|
||||||
|
| '(' select_statement ')' {
|
||||||
|
TableRef* t = new TableRef(eTableSelect);
|
||||||
|
t->_stmt = $2;
|
||||||
|
$$ = t;
|
||||||
|
}
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
search_condition:
|
||||||
|
predicate
|
||||||
|
;
|
||||||
|
|
||||||
|
predicate:
|
||||||
|
comparison_predicate
|
||||||
|
;
|
||||||
|
|
||||||
|
comparison_predicate:
|
||||||
|
scalar_exp COMPARISON scalar_exp
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
expr:
|
||||||
|
column_name { $$ = new Expression($1); }
|
||||||
|
| NAME '(' column_name ')' { $$ = new Expression($3, $1); }
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/* Lists */
|
||||||
|
expr_list:
|
||||||
|
expr { $$ = new List<Expression*>($1); }
|
||||||
|
| expr_list ',' expr { $1->push_back($3); $$ = $1; }
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
// TODO: add table_ref to include names and select queries
|
||||||
|
table_ref_commalist:
|
||||||
|
table_name { $$ = new List<char*>($1); }
|
||||||
|
| table_ref_commalist ',' table_name { $1->push_back($3); $$ = $1; }
|
||||||
|
;
|
||||||
|
/* / Lists */
|
||||||
|
|
||||||
|
|
||||||
|
column_name:
|
||||||
|
NAME
|
||||||
|
;
|
||||||
|
|
||||||
|
table_name:
|
||||||
|
NAME
|
||||||
|
| NAME '.' NAME
|
||||||
|
;
|
||||||
|
|
||||||
|
literal:
|
||||||
|
STRING
|
||||||
|
| INTNUM
|
||||||
|
;
|
||||||
|
|
||||||
|
scalar_exp:
|
||||||
|
column_name
|
||||||
|
| literal
|
||||||
|
;
|
||||||
|
|
||||||
|
opt_semicolon:
|
||||||
|
';'
|
||||||
|
| /* empty */
|
||||||
|
;
|
||||||
%%
|
%%
|
|
@ -1,11 +1,12 @@
|
||||||
#ifndef __EXPRESSION_H__
|
#ifndef __EXPRESSION_H__
|
||||||
#define __EXPRESSION_H__
|
#define __EXPRESSION_H__
|
||||||
|
|
||||||
|
#include <cstdlib>
|
||||||
|
|
||||||
|
|
||||||
class Expression {
|
class Expression {
|
||||||
public:
|
public:
|
||||||
Expression(char* name) : name(name) {};
|
Expression(char* name) : name(name), func_name(NULL) {};
|
||||||
Expression(char* name, char* func_name) : name(name), func_name(func_name) {};
|
Expression(char* name, char* func_name) : name(name), func_name(func_name) {};
|
||||||
|
|
||||||
char* name;
|
char* name;
|
||||||
|
|
|
@ -17,7 +17,7 @@ void SelectTest1() {
|
||||||
printf("Test: SelectTest1... ");
|
printf("Test: SelectTest1... ");
|
||||||
fflush(stdout);
|
fflush(stdout);
|
||||||
|
|
||||||
const char* sql = "SELECT age, name, address from table;";
|
const char* sql = "SELECT age, name, address from table WHERE age > 12.5;";
|
||||||
Statement* stmt = SQLParser::parseSQL(sql);
|
Statement* stmt = SQLParser::parseSQL(sql);
|
||||||
ASSERT(stmt != NULL);
|
ASSERT(stmt != NULL);
|
||||||
ASSERT(stmt->_type == eSelect);
|
ASSERT(stmt->_type == eSelect);
|
||||||
|
|
Loading…
Reference in New Issue