Arrays!
parent
82a5924c4e
commit
7d60b159cc
|
@ -9,11 +9,19 @@
|
|||
|
||||
SenchaObject Assignment::evaluate()
|
||||
{
|
||||
//TODO do something different with name evaluation
|
||||
auto left_value = static_cast<ASTExpression *>(children[0])->evaluate();
|
||||
if(left_value.name != "")
|
||||
{
|
||||
name = left_value.name;
|
||||
}
|
||||
auto right_value = static_cast<ASTExpression *>(children[1])->evaluate();
|
||||
auto context = context_manager->get_top();
|
||||
context->add(name, right_value);
|
||||
|
||||
return children[0]->execute();
|
||||
left_value = right_value;
|
||||
left_value.name = name;
|
||||
return left_value;
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -34,10 +34,12 @@ DeclarationStatement::DeclarationStatement(ContextManager * context_manager)
|
|||
this->context_manager = context_manager;
|
||||
this->name_of_context = "global";
|
||||
is_function = false;
|
||||
body = NULL;
|
||||
body = nullptr;
|
||||
right_value = SenchaObject();
|
||||
children.push_back(new ConstantExpression(SenchaObject()));
|
||||
this->type = "DeclarationStatement";
|
||||
this->is_array = false;
|
||||
array_size_expression = nullptr;
|
||||
}
|
||||
|
||||
void DeclarationStatement::add_name(std::string name)
|
||||
|
@ -45,6 +47,11 @@ void DeclarationStatement::add_name(std::string name)
|
|||
this->name = name;
|
||||
}
|
||||
|
||||
void DeclarationStatement::add_array_size(ASTExpression * expression)
|
||||
{
|
||||
this->is_array = true;
|
||||
array_size_expression = expression;
|
||||
}
|
||||
|
||||
void DeclarationStatement::add_argument(std::string name)
|
||||
{
|
||||
|
@ -59,6 +66,21 @@ SenchaObject DeclarationStatement::execute()
|
|||
context_manager->context("global")->register_function(name, sf);
|
||||
return SenchaObject();
|
||||
}
|
||||
else if(is_array)
|
||||
{
|
||||
auto expr_value = array_size_expression->evaluate();
|
||||
if(expr_value.type == SenchaObject::integer_number)
|
||||
{
|
||||
int array_size = expr_value.integer;
|
||||
Context * context = context_manager->get_top();
|
||||
for(int i = 0; i< array_size; i++)
|
||||
{
|
||||
context->add("_" + name + "_" + to_string(i), SenchaObject());
|
||||
}
|
||||
}
|
||||
return SenchaObject();
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
auto context = context_manager->get_top();
|
||||
|
|
|
@ -25,6 +25,8 @@ public:
|
|||
std::string name_of_context;
|
||||
SenchaObject right_value;
|
||||
ASTStatement * body;
|
||||
bool is_array;
|
||||
ASTExpression * array_size_expression;
|
||||
std::vector<std::string> arguments;
|
||||
bool is_function;
|
||||
|
||||
|
@ -32,7 +34,7 @@ public:
|
|||
DeclarationStatement(ContextManager * context);
|
||||
void add_name(std::string);
|
||||
|
||||
|
||||
void add_array_size(ASTExpression * size_expression);
|
||||
void add_argument(std::string name);
|
||||
void add_body(ASTStatement * statement);
|
||||
|
||||
|
|
|
@ -8,7 +8,14 @@
|
|||
#include "PostfixExpression.h"
|
||||
|
||||
PostfixExpression::PostfixExpression(std::string name, ContextManager * context_manager):
|
||||
name(name), context_manager(context_manager), native(false)
|
||||
name(name), operation("call"), context_manager(context_manager)
|
||||
{
|
||||
type= "PostfixExpression";
|
||||
access_index_expr = nullptr;
|
||||
}
|
||||
|
||||
PostfixExpression::PostfixExpression(std::string name, ContextManager * context_manager, ASTExpression * access_index_expr):
|
||||
name(name), operation("access"), context_manager(context_manager), access_index_expr(access_index_expr)
|
||||
{
|
||||
type= "PostfixExpression";
|
||||
}
|
||||
|
@ -30,11 +37,52 @@ void PostfixExpression::add_argument(ASTExpression * expression)
|
|||
|
||||
SenchaObject PostfixExpression::evaluate()
|
||||
{
|
||||
return context_manager->execute_function(name, arguments);
|
||||
SenchaObject result = SenchaObject();
|
||||
if(operation == "call")
|
||||
return context_manager->execute_function(name, arguments);
|
||||
else if(operation == "access")
|
||||
{
|
||||
SenchaObject called_value = context_manager->get_top()->get(name);
|
||||
SenchaObject access_index = access_index_expr->execute();
|
||||
//std::cout << "index is: " << access_index.repr() << std::endl;
|
||||
if(access_index.type == SenchaObject::integer_number)
|
||||
{
|
||||
if(called_value.type == SenchaObject::string_literal)
|
||||
{
|
||||
SenchaArray array(name, context_manager->get_top(), called_value.text);
|
||||
return array.get(access_index.integer);
|
||||
}
|
||||
else
|
||||
{
|
||||
SenchaArray array(name, context_manager->get_top());
|
||||
return array.get(access_index.integer);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
result.type = SenchaObject::invalid;
|
||||
return result;
|
||||
}
|
||||
|
||||
SenchaObject PostfixExpression::execute() {
|
||||
return context_manager->execute_function(name, arguments);
|
||||
SenchaObject result = SenchaObject();
|
||||
if(operation == "call")
|
||||
return context_manager->execute_function(name, arguments);
|
||||
else if(operation == "access")
|
||||
{
|
||||
SenchaObject called_value = context_manager->get_top()->get(name);
|
||||
SenchaObject access_index = access_index_expr->execute();
|
||||
if(access_index.type == SenchaObject::integer_number)
|
||||
{
|
||||
if(called_value.type == SenchaObject::string_literal)
|
||||
{
|
||||
SenchaArray array(name, context_manager->get_top(), called_value.text);
|
||||
return array.get(access_index.integer);
|
||||
}
|
||||
}
|
||||
}
|
||||
result.type = SenchaObject::invalid;
|
||||
return result;
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
#include "ASTExpression.h"
|
||||
#include "ASTStatement.h"
|
||||
#include "../ContextManager.h"
|
||||
#include "../Elements/SenchaArray.h"
|
||||
|
||||
/**
|
||||
* PostfixExpression is in current implementation an abstraction
|
||||
|
@ -18,9 +19,10 @@
|
|||
class PostfixExpression : public ASTExpression {
|
||||
public:
|
||||
std::string name;
|
||||
std::string operation;
|
||||
ContextManager * context_manager;
|
||||
bool native;
|
||||
std::vector<ASTExpression *> arguments;
|
||||
ASTExpression * access_index_expr;
|
||||
void add_argument(ASTExpression * expression);
|
||||
|
||||
virtual SenchaObject evaluate();
|
||||
|
@ -28,6 +30,7 @@ public:
|
|||
|
||||
|
||||
PostfixExpression( std::string name, ContextManager * context);
|
||||
PostfixExpression(std::string name, ContextManager * context_manager, ASTExpression * access_index_expr);
|
||||
virtual ~PostfixExpression();
|
||||
};
|
||||
|
||||
|
|
|
@ -24,6 +24,10 @@ SenchaObject VariableExpression::evaluate()
|
|||
auto context = context_manager->get_top();
|
||||
//std::cout << "I'm retrieving variable " + name + " from " + context->name << std::endl;
|
||||
SenchaObject result = context->get(name);
|
||||
if(result.type == SenchaObject::string_literal)
|
||||
{
|
||||
result = context->get_updated_string(name);
|
||||
}
|
||||
//std::cout << "And it's: " + result.repr() << std::endl;
|
||||
result.name = name;
|
||||
return result;
|
||||
|
|
|
@ -146,19 +146,28 @@ void ASTInspector::visit(PostfixExpression * postfix_expression)
|
|||
depth_level++;
|
||||
std::string visit_notes = "";
|
||||
visit_notes += "Postfix expression:\n";
|
||||
|
||||
visit_notes += postfix_expression->name;
|
||||
visit_notes += " operating on arguments:\n";
|
||||
|
||||
write_report(visit_notes);
|
||||
for(auto argument : postfix_expression->arguments)
|
||||
if(postfix_expression->operation == "call")
|
||||
{
|
||||
argument->accept(this);
|
||||
visit_notes += postfix_expression->name;
|
||||
visit_notes += " operating on arguments:\n";
|
||||
|
||||
write_report(visit_notes);
|
||||
for(auto argument : postfix_expression->arguments)
|
||||
{
|
||||
argument->accept(this);
|
||||
}
|
||||
}
|
||||
else if (postfix_expression->operation == "access")
|
||||
{
|
||||
visit_notes += "Accessing " + postfix_expression->name;
|
||||
visit_notes += "by index:\n";
|
||||
write_report(visit_notes);
|
||||
postfix_expression->access_index_expr->accept(this);
|
||||
}
|
||||
|
||||
|
||||
write_report("End of postfix expression\n");
|
||||
depth_level--;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -22,6 +22,24 @@ bool Context::contains_function(std::string name)
|
|||
return contains_sfunction(name) || contains_nfunction(name);
|
||||
}
|
||||
|
||||
SenchaObject Context::get_updated_string(std::string name)
|
||||
{
|
||||
SenchaObject result = get(name);
|
||||
if(result.type == SenchaObject::string_literal)
|
||||
{
|
||||
for(unsigned int i = 0; i < result.text.size(); i++)
|
||||
{
|
||||
std::string indexed_name = "_" + name + "_" + to_string(i);
|
||||
if(object_store.count(indexed_name) != 0)
|
||||
{
|
||||
result.text[i] = object_store[indexed_name].text[0];
|
||||
}
|
||||
}
|
||||
}
|
||||
add(name, result);
|
||||
return result;
|
||||
}
|
||||
|
||||
bool Context::contains_sfunction(std::string name)
|
||||
{
|
||||
return this->registered_sfunctions.count(name) == 1;
|
||||
|
|
|
@ -30,6 +30,7 @@ public:
|
|||
void register_function(std::string name, PointerToNativeFunction f);
|
||||
void register_function(std::string name, SenchaFunction * f);
|
||||
SenchaObject execute_native_function(std::string name, std::vector<ASTExpression *> arguments);
|
||||
SenchaObject get_updated_string(std::string name);
|
||||
std::string debug() ;
|
||||
void add(std::string name, SenchaObject object);
|
||||
void set(std::string name, SenchaObject object);
|
||||
|
|
|
@ -7,9 +7,14 @@
|
|||
|
||||
#include "SenchaArray.h"
|
||||
|
||||
SenchaArray::SenchaArray() {
|
||||
|
||||
|
||||
SenchaArray::SenchaArray(std::string name, Context * context) {
|
||||
// TODO Auto-generated constructor stub
|
||||
max_index = 0;
|
||||
this->context = context;
|
||||
this->name = name;
|
||||
context->add(name, SenchaObject());
|
||||
}
|
||||
|
||||
SenchaArray::~SenchaArray() {
|
||||
|
@ -17,32 +22,43 @@ SenchaArray::~SenchaArray() {
|
|||
}
|
||||
|
||||
|
||||
SenchaArray::SenchaArray(std::string text)
|
||||
SenchaArray::SenchaArray(std::string name, Context * context, std::string text)
|
||||
{
|
||||
max_index = 0;
|
||||
this->context = context;
|
||||
this->name = name;
|
||||
for(unsigned int i = 0; i < text.size(); i++)
|
||||
{
|
||||
SenchaObject temp;
|
||||
std::string letter_string = text.substr(i, 1) ;
|
||||
temp.text = letter_string;
|
||||
temp.type = SenchaObject::string_literal;
|
||||
objects.push_back(temp);
|
||||
context->add("_" + name+ "_" + to_string(i), temp);
|
||||
//objects.push_back(temp);
|
||||
}
|
||||
max_index = objects.size();
|
||||
max_index = text.size();
|
||||
//context->add(name, SenchaObject(text));
|
||||
}
|
||||
|
||||
SenchaObject SenchaArray::get(IndexNumber index)
|
||||
{
|
||||
return objects[index];
|
||||
SenchaObject result = context->get("_" + name +"_" +to_string(index));
|
||||
result.name = "_" + name + "_" + to_string(index);
|
||||
return result;
|
||||
//return objects[index];
|
||||
}
|
||||
|
||||
SenchaArray::IndexNumber SenchaArray::add(SenchaObject value)
|
||||
{
|
||||
objects.push_back(value);
|
||||
context->add("_" + name+ "_" + to_string(max_index), value);
|
||||
max_index++;
|
||||
//objects.push_back(value);
|
||||
max_index = objects.size();
|
||||
return max_index;
|
||||
}
|
||||
|
||||
void SenchaArray::set(IndexNumber index, SenchaObject value)
|
||||
{
|
||||
objects[index] = value;
|
||||
//objects[index] = value;
|
||||
context->add("_" + name +"_" +to_string(index), value);
|
||||
}
|
||||
|
|
|
@ -7,16 +7,16 @@
|
|||
|
||||
#ifndef SENCHAARRAY_H_
|
||||
#define SENCHAARRAY_H_
|
||||
#include <vector>
|
||||
#include "SenchaObject.h"
|
||||
#include "Element.h"
|
||||
#include "../Context.h"
|
||||
|
||||
class SenchaArray: public Element {
|
||||
public:
|
||||
SenchaArray();
|
||||
SenchaArray(std::string);
|
||||
|
||||
std::vector<SenchaObject> objects;
|
||||
SenchaArray(std::string name, Context * context);
|
||||
SenchaArray(std::string name, Context * context, std::string);
|
||||
Context * context;
|
||||
std::string name;
|
||||
typedef int IndexNumber;
|
||||
|
||||
IndexNumber add(SenchaObject value);
|
||||
|
|
|
@ -165,6 +165,18 @@ ASTStatement * Parser::statement()
|
|||
}
|
||||
return declaration;
|
||||
}
|
||||
else if(accept("array"))
|
||||
{
|
||||
DeclarationStatement * declaration = new DeclarationStatement(context_manager);
|
||||
std::string identifier = tok_value;
|
||||
read_next();
|
||||
declaration->add_name(identifier);
|
||||
expect("[");
|
||||
declaration->add_array_size(expr());
|
||||
expect("]");
|
||||
accept(";");
|
||||
return declaration;
|
||||
}
|
||||
else if(accept("if"))
|
||||
{
|
||||
IfNode * ifStatement = new IfNode();
|
||||
|
@ -301,7 +313,15 @@ ASTExpression * Parser::postfix_expr()
|
|||
expect(")");
|
||||
}
|
||||
return function_call;
|
||||
}
|
||||
}
|
||||
if(peek_one_ahead("["))
|
||||
{
|
||||
read_next();
|
||||
read_next();
|
||||
PostfixExpression * access = new PostfixExpression(name, context_manager, expr());
|
||||
accept("]");
|
||||
return access;
|
||||
}
|
||||
}
|
||||
return prim_expr();
|
||||
}
|
||||
|
@ -385,7 +405,10 @@ ASTExpression * Parser::expr()
|
|||
ASTExpression * left = log_expr();
|
||||
if(accept("="))
|
||||
{
|
||||
ASTExpression * right = expr();
|
||||
ASTExpression * right = expr();
|
||||
std::string name_of_left_side = left->evaluate().name;
|
||||
if(name_of_left_side != "")
|
||||
name = name_of_left_side;
|
||||
Assignment * assignment = new Assignment( context_manager, name, left, right);
|
||||
return assignment;
|
||||
}
|
||||
|
|
|
@ -30,7 +30,7 @@ private:
|
|||
std::string prepare_some_function_declarations();
|
||||
std::vector<InputOutputPair> prepare_logical_input();
|
||||
|
||||
virtual std::string all_tests();
|
||||
virtual std::string all_tests();
|
||||
|
||||
};
|
||||
|
||||
|
|
|
@ -199,6 +199,7 @@ void interactive()
|
|||
parser.interpret();
|
||||
parser.program->execute_last();
|
||||
inspector.visit(parser.tree.root);
|
||||
cout << context_manager.get_top()->debug() << endl;
|
||||
//cout << parser.show_tokens();
|
||||
cout << inspector.get_report();
|
||||
inspector.forget_everything();
|
||||
|
|
Loading…
Reference in New Issue