Exemple #1
0
bool Integer::operator>(Numeric* c)const{
  Integer* entier = dynamic_cast<Integer*>(c);
  if(entier==NULL){
    Real* reel = dynamic_cast<Real*>(c);
    if (reel == NULL){
      Rational* rationnel = dynamic_cast<Rational*>(c);
      if (rationnel == NULL)
        return false;
      return ((double)_value > rationnel->toDouble());
    }
    return ((double)_value > reel->getValue());
  }
  return (_value > entier->getValue());
}
void Complex::mul(Object *b)
{
     if(b->getType() == "Complex")
     {
         Complex *c = (Complex *)b; 
         this->real = (this->real)*(c->getValue1())-(this->imag)*(c->getValue2());
         this->imag = (this->real)*(c->getValue2())+(this->imag)*(c->getValue1()); 
     } 
     else if(b->getType() == "Real") 
     {
          Real *c = (Real *)b;
          this->real *= c->getValue(); 
          this->imag *= c->getValue(); 
     }
     else if(b->getType() == "Rational")
     {
          //Rational->Real 
          Real *c = (Real *)new Real(0.0);//这种垃圾如何回收? 
          Rational *d = (Rational *)b; 
          c->changeValue((double)(d->getValue1())/(d->getValue2()));  
          this->mul(c); //递归 
          delete c;          //这里回收挖~ 
     }
     else if(b->getType() == "Integer")
     {
          //Integer->Rational
          Rational *c = (Rational *)new Rational(0,1);
          Integer *d = (Integer *)b;
          c->changeValue1(d->getValue());
          this->mul(c);  //递归 
          delete c; 
     } 
     else
     {
         cerr << "Error calcution"  << endl; 
     } 
}
/*** Evaluate this object ***/
Object* SpecialFunction::evaluate()
{
	if(args.size() == 0)
		throw Excep(getLineNumber(), getColumnNumber(), "Expected argument to special function!");

	std::auto_ptr<Object> arg1(args.at(0)->evaluate());

	if(id == SPF_INDEX)
	{
		if(args.size() != 2)
			throw Excep(getLineNumber(), getColumnNumber(), "Invalid number of arguments passed to special function!");

		std::auto_ptr<Object> arg2(args.at(1)->evaluate());

		if(arg2->getType() == OBJ_TEXT)
		{
			if(arg1->getType() != OBJ_TEXT)
				throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_TEXT, arg1->getType(), 1);

			Text* cast1 = static_cast<Text*>(arg1.get());
			Text* cast2 = static_cast<Text*>(arg2.get());

			size_t index = cast2->getValue().find(cast1->getValue());

			if(index != std::string::npos)
				return new Integer(index + 1);

			return new Integer(0);
		}

		if(arg2->getType() == OBJ_SEQUENCE)
		{
				Sequence* cast = dynamic_cast<Sequence*>(arg2.get());

				for(unsigned int i = 0; i < cast->getLength(); i++)
				{
					std::auto_ptr<Logical> eqOp(static_cast<Logical*>(Equal(arg1->clone(), cast->getObject(i)->clone()).evaluate()));
					if(eqOp->getValue() == true)
						return new Integer(i + 1);
				}

				return new Integer(0);
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_TEXT | OBJ_SEQUENCE, arg2->getType(), 2);
	}

	if(args.size() > 1)
		throw Excep(getLineNumber(), getColumnNumber(), "Invalid number of arguments passed to special function!");

	if(id == SPF_ABS)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			if(cast->getValue() < 0)
				return new Integer(-cast->getValue());
			return new Integer(cast->getValue());
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			if(cast->getValue() < 0)
				return new Real(-cast->getValue());
			return new Real(cast->getValue());
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_SIGN)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			if(cast->getValue() < 0)
				return new Integer(-1);
			if(cast->getValue() > 0)
				return new Integer(1);
			return new Integer(0);
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			if(cast->getValue() < 0)
				return new Integer(-1);
			if(cast->getValue() > 0)
				return new Integer(1);
			return new Integer(0);
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_SQRT)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());

			if(cast->getValue() < 0)
				throw NegativeValueException(getLineNumber(), getColumnNumber(), cast->getValue(), 1);

			double res = sqrt((double) cast->getValue());
			if((long) res == res)
				return new Integer((long) res);
			return new Real(res);
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());

			if(cast->getValue() < 0)
				throw NegativeValueException(getLineNumber(), getColumnNumber(), cast->getValue(), 1);

			double res = sqrt((double) cast->getValue());
			return new Real(res);
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_ENTIER)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Integer(cast->getValue());
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Integer(floor(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_ROUND)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Integer(cast->getValue());
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			long rounded = cast->getValue() < 0.0 ? ceil(cast->getValue() - 0.5) : floor(cast->getValue() + 0.5);
			return new Integer(rounded);
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_RAND)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());

			if(cast->getValue() < 0)
				throw NegativeValueException(getLineNumber(), getColumnNumber(), cast->getValue(), 1);

			double f = (double) rand() / RAND_MAX;
			return new Real( f * cast->getValue() );
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());

			if(cast->getValue() < 0)
				throw NegativeValueException(getLineNumber(), getColumnNumber(), cast->getValue(), 1);

			double f = (double) rand() / RAND_MAX;
			return new Real( f * cast->getValue() );
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_INTRAND)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			if(cast->getValue() < 0)
				throw NegativeValueException(getLineNumber(), getColumnNumber(), cast->getValue(), 1);
			return new Integer( rand() % cast->getValue() + 1 );
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			if(cast->getValue() < 0)
				throw NegativeValueException(getLineNumber(), getColumnNumber(), cast->getValue(), 1);
			return new Integer( rand() % (long) cast->getValue() + 1 );
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_ISEMPTY)
	{
		return new Logical(arg1->getType() == OBJ_EMPTY);
	}

	if(id == SPF_ISLOG)
	{
		return new Logical(arg1->getType() == OBJ_LOGICAL);
	}

	if(id == SPF_ISINT)
	{
		return new Logical(arg1->getType() == OBJ_INTEGER);
	}

	if(id == SPF_ISREAL)
	{
		return new Logical(arg1->getType() == OBJ_REAL);
	}

	if(id == SPF_ISTEXT)
	{
		return new Logical(arg1->getType() == OBJ_TEXT);
	}

	if(id == SPF_ISSEQ)
	{
		return new Logical(arg1->getType() == OBJ_SEQUENCE);
	}

	if(id == SPF_ISPROC)
	{
		return new Logical(arg1->getType() == OBJ_PROCEDURE);
	}

	if(id == SPF_ISFUN)
	{
		return new Logical(arg1->getType() == OBJ_FUNCTION || arg1->getType() == OBJ_SPFUNCTION);
	}

	if(id == SPF_SIN)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Real(sin((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Real(sin(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_COS)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Real(cos((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Real(cos(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_TG)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Real(tan((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Real(tan(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_ARCSIN)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			if(errno == EDOM)
				throw new Excep(getLineNumber(), getColumnNumber(), "Invalid value passed to special function!");
			return new Real(exp((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			if(errno == EDOM)
				throw new Excep(getLineNumber(), getColumnNumber(), "Invalid value passed to special function!");
			return new Real(exp(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_ARCTG)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			if(errno == EDOM)
				throw new Excep(getLineNumber(), getColumnNumber(), "Invalid value passed to special function!");
			return new Real(exp((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			if(errno == EDOM)
				throw new Excep(getLineNumber(), getColumnNumber(), "Invalid value passed to special function!");
			return new Real(exp(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_EXP)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Real(exp((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Real(exp(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_LN)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Real(log((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Real(log(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	if(id == SPF_LG)
	{
		if(arg1->getType() == OBJ_INTEGER)
		{
			Integer* cast = static_cast<Integer*>(arg1.get());
			return new Real(log10((double) cast->getValue()));
		}

		if(arg1->getType() == OBJ_REAL)
		{
			Real* cast = static_cast<Real*>(arg1.get());
			return new Real(log10(cast->getValue()));
		}

		throw InvalidTypeException(getLineNumber(), getColumnNumber(), OBJ_INTEGER | OBJ_REAL, arg1->getType(), 1);
	}

	throw Excep(getLineNumber(), getColumnNumber(), "Invalid special function!");
}