400 lines
7.2 KiB
C++
400 lines
7.2 KiB
C++
|
/*
|
||
|
* SenchaObject.cpp
|
||
|
*
|
||
|
* Created on: Dec 5, 2012
|
||
|
* Author: attero
|
||
|
*/
|
||
|
|
||
|
#include "SenchaObject.h"
|
||
|
|
||
|
SenchaObject::SenchaObject() {
|
||
|
set_null_value();
|
||
|
}
|
||
|
|
||
|
SenchaObject::~SenchaObject() {
|
||
|
// Do nothing
|
||
|
}
|
||
|
|
||
|
bool SenchaObject::is_true()
|
||
|
{
|
||
|
if(type == invalid || type == null)
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
if(type == boolean) return truthy;
|
||
|
else return true;
|
||
|
|
||
|
}
|
||
|
|
||
|
void SenchaObject::set_value(std::string text)
|
||
|
{
|
||
|
if(text[0] == '\"' && text[text.size()-1] == '\"')
|
||
|
{
|
||
|
this->text = text.substr(1, text.size()-2);
|
||
|
type = string_literal;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void SenchaObject::set_new_string(std::string text)
|
||
|
{
|
||
|
this->text = text;
|
||
|
type = string_literal;
|
||
|
}
|
||
|
|
||
|
void SenchaObject::set_null_value()
|
||
|
{
|
||
|
this->type = null;
|
||
|
this->integer = 0;
|
||
|
this->number = 0;
|
||
|
this->text = "";
|
||
|
}
|
||
|
|
||
|
void SenchaObject::set_value(int integer)
|
||
|
{
|
||
|
this->integer = integer;
|
||
|
type = integer_number;
|
||
|
}
|
||
|
|
||
|
void SenchaObject::set_value(double number)
|
||
|
{
|
||
|
this->number = number;
|
||
|
type = float_number;
|
||
|
}
|
||
|
|
||
|
void SenchaObject::set_value(bool logic)
|
||
|
{
|
||
|
this->truthy = logic;
|
||
|
type = boolean;
|
||
|
}
|
||
|
|
||
|
std::string SenchaObject::repr()
|
||
|
{
|
||
|
std::string representation = "";
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
representation = "type: string\n";
|
||
|
representation += this->text;
|
||
|
break;
|
||
|
case integer_number:
|
||
|
representation = "type: integer\n";
|
||
|
representation += to_string(this->integer);
|
||
|
break;
|
||
|
case float_number:
|
||
|
representation = "type: float\n";
|
||
|
representation += to_string(this->number);
|
||
|
break;
|
||
|
case null:
|
||
|
representation = "type: null\n";
|
||
|
representation += "null";
|
||
|
break;
|
||
|
case symbol:
|
||
|
representation = "type: symbol\n";
|
||
|
representation += this->text;
|
||
|
break;
|
||
|
case invalid:
|
||
|
representation = "type: invalid\n";
|
||
|
representation += "some crap";
|
||
|
break;
|
||
|
case boolean:
|
||
|
representation = "type: boolean\n";
|
||
|
representation += to_string(this->truthy);
|
||
|
break;
|
||
|
}
|
||
|
return representation;
|
||
|
}
|
||
|
std::string SenchaObject::str()
|
||
|
{
|
||
|
std::string representation = "";
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
representation += this->text;
|
||
|
break;
|
||
|
case integer_number:
|
||
|
representation += to_string(this->integer);
|
||
|
break;
|
||
|
case float_number:
|
||
|
representation += to_string(this->number);
|
||
|
break;
|
||
|
case null:
|
||
|
representation += "null";
|
||
|
break;
|
||
|
case symbol:
|
||
|
representation += this->text;
|
||
|
break;
|
||
|
case invalid:
|
||
|
representation += "some crap";
|
||
|
break;
|
||
|
case boolean:
|
||
|
representation += to_string(this->truthy);
|
||
|
break;
|
||
|
}
|
||
|
return representation;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator+(const SenchaObject& right)const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
if(type == right.type)
|
||
|
{
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
result.set_new_string(this->text + right.text);
|
||
|
break;
|
||
|
case integer_number:
|
||
|
result.set_value(this->integer + right.integer);
|
||
|
break;
|
||
|
case float_number:
|
||
|
result.set_value(this->number + right.number);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
else if(type == float_number && right.type == integer_number )
|
||
|
{
|
||
|
result.set_value(this->number + right.integer);
|
||
|
}
|
||
|
else if(type == integer_number && right.type == float_number)
|
||
|
{
|
||
|
result.set_value(this->integer + right.number);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
result.type = invalid;
|
||
|
}
|
||
|
|
||
|
return result;
|
||
|
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator-(const SenchaObject& right)const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
if(type == right.type)
|
||
|
{
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
result.type = invalid;
|
||
|
break;
|
||
|
case integer_number:
|
||
|
result.set_value(this->integer - right.integer);
|
||
|
break;
|
||
|
case float_number:
|
||
|
result.set_value(this->number - right.number);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
else if(type == float_number && right.type == integer_number )
|
||
|
{
|
||
|
result.set_value(this->number - right.integer);
|
||
|
}
|
||
|
else if(type == integer_number && right.type == float_number)
|
||
|
{
|
||
|
result.set_value(this->integer - right.number);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
result.type = invalid;
|
||
|
}
|
||
|
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator*(const SenchaObject& right)const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
if(type == right.type)
|
||
|
{
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
result.type = invalid;
|
||
|
break;
|
||
|
case integer_number:
|
||
|
result.set_value(this->integer * right.integer);
|
||
|
break;
|
||
|
case float_number:
|
||
|
result.set_value(this->number * right.number);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
else if(type == float_number && right.type == integer_number )
|
||
|
{
|
||
|
result.set_value(this->number * right.integer);
|
||
|
}
|
||
|
else if(type == integer_number && right.type == float_number)
|
||
|
{
|
||
|
result.set_value(this->integer * right.number);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
result.type = invalid;
|
||
|
}
|
||
|
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator/(const SenchaObject& right)const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
if(type == right.type)
|
||
|
{
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
result.type = invalid;
|
||
|
break;
|
||
|
case integer_number:
|
||
|
result.set_value(this->integer / right.integer);
|
||
|
break;
|
||
|
case float_number:
|
||
|
result.set_value(this->number / right.number);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
else if(type == float_number && right.type == integer_number )
|
||
|
{
|
||
|
result.set_value(this->number / right.integer);
|
||
|
}
|
||
|
else if(type == integer_number && right.type == float_number)
|
||
|
{
|
||
|
result.set_value(this->integer / right.number);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
result.type = invalid;
|
||
|
}
|
||
|
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator==(const SenchaObject& right)const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
bool value = false;
|
||
|
result.type = boolean;
|
||
|
|
||
|
if(type == right.type)
|
||
|
{
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
if(this->text == right.text)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
break;
|
||
|
case integer_number:
|
||
|
if(this->integer == right.integer)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
break;
|
||
|
case float_number:
|
||
|
if(this->number == right.number)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
result.truthy = value;
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator!=(const SenchaObject& right) const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
result.type = boolean;
|
||
|
|
||
|
result = (*this == right);
|
||
|
if(result.truthy)
|
||
|
result.truthy = false;
|
||
|
else result.truthy = true;
|
||
|
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
|
||
|
SenchaObject SenchaObject::operator>(const SenchaObject& right) const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
bool value = false;
|
||
|
result.type = boolean;
|
||
|
|
||
|
if(type == right.type)
|
||
|
{
|
||
|
switch(type){
|
||
|
case string_literal:
|
||
|
if(this->text > right.text)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
break;
|
||
|
case integer_number:
|
||
|
if(this->integer > right.integer)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
break;
|
||
|
case float_number:
|
||
|
if(this->number > right.number)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
else if(type == float_number && right.type == integer_number )
|
||
|
{
|
||
|
value = (this->number > right.integer);
|
||
|
}
|
||
|
else if(type == integer_number && right.type == float_number)
|
||
|
{
|
||
|
value = (this->integer > right.number);
|
||
|
}
|
||
|
|
||
|
result.truthy = value;
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator>= (const SenchaObject& right) const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
bool value = false;
|
||
|
result.type = boolean;
|
||
|
|
||
|
if((*this == right).truthy || ((*this) > right).truthy)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
result.truthy = value;
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator< (const SenchaObject& right) const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
bool value = false;
|
||
|
result.type = boolean;
|
||
|
|
||
|
if(!((*this) >= right).truthy)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
result.truthy = value;
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
SenchaObject SenchaObject::operator<= (const SenchaObject& right) const
|
||
|
{
|
||
|
SenchaObject result;
|
||
|
bool value = false;
|
||
|
result.type = boolean;
|
||
|
|
||
|
if(!((*this) > right).truthy)
|
||
|
{
|
||
|
value = true;
|
||
|
}
|
||
|
result.truthy = value;
|
||
|
return result;
|
||
|
}
|
||
|
|
||
|
//TODO change code above to something more generic
|