Esempio n. 1
0
variant variant::operator/(const variant& v) const
{
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
		int denominator = v.as_decimal();

		if(denominator == 0) {
			throw type_error((formatter() << "divide by zero error").str());
		}

		long long long_int = as_decimal();

		long_int *= 10000;

		long_int /= denominator;

		if( long_int%10 >= 5) {
			long_int /= 10;
			++long_int;
		} else
			long_int/=10;

		return variant(  static_cast<int>(long_int) , variant::DECIMAL_VARIANT);
	}


	const int numerator = as_int();
	const int denominator = v.as_int();
	if(denominator == 0) {
		throw type_error((formatter() << "divide by zero error").str());;
	}

	return variant(numerator/denominator);
}
Esempio n. 2
0
bool variant::operator==(const variant& v) const
{
	if(type_ != v.type_) {
		if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
			return as_decimal() == v.as_decimal();
		}

		return false;
	}

	switch(type_) {
	case TYPE_NULL: {
		return v.is_null();
	}

	case TYPE_STRING: {
		return string_->str == v.string_->str;
	}

	case TYPE_INT: {
		return int_value_ == v.int_value_;
	}

	case TYPE_DECIMAL: {
		return decimal_value_ == v.decimal_value_;
	}

	case TYPE_LIST: {
		if(num_elements() != v.num_elements()) {
			return false;
		}

		for(size_t n = 0; n != num_elements(); ++n) {
			if((*this)[n] != v[n]) {
				return false;
			}
		}

		return true;
	}

	case TYPE_MAP: {
		return map_->elements == v.map_->elements;
	}

	case TYPE_CALLABLE_LOADING: {
		return false;
	}

	case TYPE_CALLABLE: {
		return callable_->equals(v.callable_);
	}
	case TYPE_FUNCTION: {
		return fn_ == v.fn_;
	}
	}

	assert(false);
	return false;
}
Esempio n. 3
0
variant variant::operator*(const variant& v) const
{
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
		return variant(as_decimal() * v.as_decimal());
	}

	if(type_ == TYPE_LIST) {
		int ncopies = v.as_int();
		if(ncopies < 0) {
			ncopies *= -1;
		}
		const std::vector<variant>& items = list_->elements;
		std::vector<variant> res;
		res.reserve(items.size()*ncopies);
		for(int n = 0; n != ncopies; ++n) {
			for(int m = 0; m != items.size(); ++m) {
				res.push_back(items[m]);
			}
		}

		return variant(&res);
	}
	
	return variant(as_int() * v.as_int());
}
Esempio n. 4
0
variant variant::operator-(const variant& v) const
{
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
		return variant( as_decimal() - v.as_decimal() , DECIMAL_VARIANT);
	}

	return variant(as_int() - v.as_int());
}
Esempio n. 5
0
bool variant::operator<=(const variant& v) const
{
	if(type_ != v.type_) {
		if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
			return as_decimal() <= v.as_decimal();
		}

		return type_ < v.type_;
	}

	switch(type_) {
	case TYPE_NULL: {
		return true;
	}

	case TYPE_STRING: {
		return string_->str <= v.string_->str;
	}

	case TYPE_INT: {
		return int_value_ <= v.int_value_;
	}

	case TYPE_DECIMAL: {
		return decimal_value_ <= v.decimal_value_;
	}

	case TYPE_LIST: {
		for(size_t n = 0; n != num_elements() && n != v.num_elements(); ++n) {
			if((*this)[n] < v[n]) {
				return true;
			} else if((*this)[n] > v[n]) {
				return false;
			}
		}

		return num_elements() <= v.num_elements();
	}

	case TYPE_MAP: {
		return map_->elements <= v.map_->elements;
	}

	case TYPE_CALLABLE_LOADING: {
		return false;
	}

	case TYPE_CALLABLE: {
		return !v.callable_->less(callable_);
	}
	}

	assert(false);
	return false;
}
Esempio n. 6
0
variant variant::operator^(const variant& v) const
{
	if( type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL ) {
		double res = pow( as_decimal().value()/double(VARIANT_DECIMAL_PRECISION),
		                v.as_decimal().value()/double(VARIANT_DECIMAL_PRECISION));		
		res *= DECIMAL_PRECISION;
#if defined(TARGET_BLACKBERRY)
		return variant(static_cast<int64_t>(llround(res)), DECIMAL_VARIANT);
#else
		return variant(static_cast<int64_t>(res), DECIMAL_VARIANT);
#endif
	}

	return variant(static_cast<int>(pow(static_cast<double>(as_int()), v.as_int())));
}
Esempio n. 7
0
variant variant::operator/(const variant& v) const
{
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
		if(v.as_decimal().value() == 0) {
			throw type_error((formatter() << "divide by zero error").str());
		}

		return variant(as_decimal() / v.as_decimal());
	}

	const int numerator = as_int();
	const int denominator = v.as_int();
	if(denominator == 0) {
		throw type_error(formatter() << "divide by zero error");
	}

	return variant(numerator/denominator);
}
Esempio n. 8
0
variant variant::operator^(const variant& v) const
{
	if( type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL ) {

		double res = pow( as_decimal()/1000.0 , v.as_decimal()/1000.0 );

		res *= 1000;
		int i =  static_cast<int>( res );

		res -= i;

		if( res > 0.5 )
			i++;

		return variant( i , variant::DECIMAL_VARIANT);
	}

	return variant(static_cast<int>(
			round_portable(pow(static_cast<double>(as_int()), v.as_int()))));
}
Esempio n. 9
0
variant variant::operator*(const variant& v) const
{
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {

		long long long_int = as_decimal();

		long_int *= v.as_decimal();

		long_int /= 100;

		if( long_int%10 >= 5) {
			long_int /= 10;
			++long_int;
		} else
			long_int/=10;

		return variant( static_cast<int>(long_int) , variant::DECIMAL_VARIANT );
	}

	return variant(as_int() * v.as_int());
}
Esempio n. 10
0
variant variant::operator+(const variant& v) const
{
	if(type_ == TYPE_LIST) {
		if(v.type_ == TYPE_LIST) {
			std::vector<variant> res;
			res.reserve(list_->elements.size() + v.list_->elements.size());
			for(size_t i = 0; i<list_->elements.size(); ++i) {
				const variant& var = list_->elements[i];
				res.push_back(var);
			}

			for(size_t j = 0; j<v.list_->elements.size(); ++j) {
				const variant& var = v.list_->elements[j];
				res.push_back(var);
			}

			return variant(&res);
		}
	}
	if(type_ == TYPE_MAP) {
		if(v.type_ == TYPE_MAP) {
			std::map<variant,variant> res(map_->elements);

			for(std::map<variant,variant>::const_iterator i = v.map_->elements.begin(); i != v.map_->elements.end(); ++i) {
				res[i->first] = i->second;
			}

			return variant(&res);
		}
	}
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
		return variant( as_decimal() + v.as_decimal() , DECIMAL_VARIANT);
	}

	return variant(as_int() + v.as_int());
}
Esempio n. 11
0
variant variant::operator+(const variant& v) const
{
	if(type_ == TYPE_INT && v.type_ == TYPE_INT) {
		//strictly an optimization -- this is handled below, but the case
		//of adding two integers is the most common so we want it to be fast.
		return variant(int_value_ + v.int_value_);
	}

	if(type_ == TYPE_STRING) {
		if(v.type_ == TYPE_MAP) {
			return variant(as_string() + v.as_string());
		} else if(v.type_ == TYPE_STRING) {
			return variant(as_string() + v.as_string());
		}

		std::string s;
		v.serialize_to_string(s);
		return variant(as_string() + s);
	}

	if(v.type_ == TYPE_STRING) {
		std::string s;
		serialize_to_string(s);
		return variant(s + v.as_string());
	}
	if(type_ == TYPE_DECIMAL || v.type_ == TYPE_DECIMAL) {
		return variant(as_decimal() + v.as_decimal());
	}

	if(type_ == TYPE_INT) {
		return variant(int_value_ + v.as_int());
	}

	if(type_ == TYPE_NULL) {
		return v;
	} else if(v.type_ == TYPE_NULL) {
		return *this;
	}

	if(type_ == TYPE_LIST) {
		if(v.type_ == TYPE_LIST) {
			std::vector<variant> res;
			res.reserve(list_->elements.size() + v.list_->elements.size());
			for(size_t i = 0; i<list_->elements.size(); ++i) {
				const variant& var = list_->elements[i];
				res.push_back(var);
			}

			for(size_t j = 0; j<v.list_->elements.size(); ++j) {
				const variant& var = v.list_->elements[j];
				res.push_back(var);
			}

			return variant(&res);
		}
	}
	if(type_ == TYPE_MAP) {
		if(v.type_ == TYPE_MAP) {
			std::map<variant,variant> res(map_->elements);

			for(std::map<variant,variant>::const_iterator i = v.map_->elements.begin(); i != v.map_->elements.end(); ++i) {
				res[i->first] = i->second;
			}

			return variant(&res);
		}
	}

	return variant(as_int() + v.as_int());
}