Exemple #1
0
  std::string FloatStr(const BigRat& q, const MachineInt& SigFig)
  {
    if (IsNegative(SigFig) || !IsSignedLong(SigFig) || IsZero(SigFig))
      CoCoA_ERROR(ERR::BadArg, "FloatStr");
//    if (IsOneDen(q)) return FloatStr(num(q), SigFig);
    return FloatStr(MantissaAndExponent10(q, SigFig), AsSignedLong(SigFig));
  }
Exemple #2
0
  std::string DecimalStr(const BigInt& N, const MachineInt& DecimalPlaces)
  {
    if (IsNegative(DecimalPlaces) || !IsSignedLong(DecimalPlaces) || IsZero(DecimalPlaces))
      CoCoA_ERROR(ERR::BadArg, "FixedStr");

    return ToString(N);
  }
Exemple #3
0
  std::string FloatStr(const BigInt& N, const MachineInt& SigFig)
  {
    if (IsNegative(SigFig) || !IsSignedLong(SigFig) || IsZero(SigFig))
      CoCoA_ERROR(ERR::BadArg, "FloatStr");
//???    if (abs(N) < power(10,SigFig)) return ToString(N);

    return FloatStr(MantissaAndExponent10(N, SigFig), AsSignedLong(SigFig));
  }
Exemple #4
0
LPPRoblemStatus lpengine::Solve() {
  LPPRoblemStatus current_status = LPPRoblemStatus::STATUS_NONE;

  if (IsSemiPositive(p_.b_) && IsNegative(p_.c_n_)) {
    std::cout << " -- Initial dictionary is Optimal" << std::endl;
    current_status = LPPRoblemStatus::STATUS_OPTIMAL;

  } else if (CheckDicfeasible(p_.x_b_hat_)) {
    std::cout << "-- Initial dictionary is primal feasible" << std::endl;
    p_.solver_type_ = LPSolverType::LP_SIMPLEX_PRIMAL;
    current_status = LPPRoblemStatus::STATUS_ITTERATING;
    while (current_status == LPPRoblemStatus::STATUS_ITTERATING) {
      current_status = PrimalSimplexStep();
    }

  } else if (CheckDicfeasible(p_.z_n_hat_)) {
    std::cout << "-- Initial dictionary is dual feasible" << std::endl;
    p_.solver_type_ = LPSolverType::LP_SIMPLEX_DUAL;
    current_status = LPPRoblemStatus::STATUS_ITTERATING;
    while (current_status == LPPRoblemStatus::STATUS_ITTERATING) {
      current_status = DualSimplexStep();
    }

  } else {
    std::cout << "-- Initial Primal and Dual dictionaries are not feasible"
              << std::endl
              << "-- Running PHASE1 algorithm" << std::endl;
    // modify the problem to feasible Dual problem and solve till optimal
    p_.ChangeToAuxiliary();
//    p_.PrintDictionary();
    std::cout << "--Aux dic is: ";
    if (CheckDicfeasible(p_.z_n_hat_)) {
      std::cout << "Dual feasible" << std::endl;

    } else {
      std::cout << "Error-> still not feasible" << std::endl;
      std::cout << "Exitting ..." << std::endl;
      current_status = LPPRoblemStatus::STATUS_INFEASIBLE;
      exit(EXIT_FAILURE);
    }
    p_.solver_type_ = LPSolverType::LP_SIMPLEX_DUAL;
    current_status = LPPRoblemStatus::STATUS_ITTERATING;
    while (current_status == LPPRoblemStatus::STATUS_ITTERATING) {
      current_status = DualSimplexStep();
    }

    p_.PrintDictionary();


  }

  // Problem is feasible and bounded at this point then do Simplex steps

  PrintStatusMsg(current_status);
  return current_status;
}
Exemple #5
0
EXPORT_C RInteger TInteger::InverseModL(const TInteger& aMod) const
	{
	assert(aMod.NotNegative());

	RInteger result;
	if(IsNegative() || *this>=aMod)
		{
		RInteger temp = ModuloL(aMod);
		CleanupClosePushL(temp);
		result = temp.InverseModL(aMod);
		CleanupStack::PopAndDestroy(&temp);
		return result;
		}

	if(aMod.IsEven())
		{
		if( !aMod || IsEven() )
			{
			return RInteger::NewL(Zero());
			}
		if( *this == One() )
			{
			return RInteger::NewL(One());
			}
		RInteger u = aMod.InverseModL(*this); 
		CleanupClosePushL(u);
		if(!u)
			{
			result = RInteger::NewL(Zero());
			}
		else 
			{
			//calculates (aMod*(*this-u)+1)/(*this) 
			result = MinusL(u);
			CleanupClosePushL(result);
			result *= aMod;
			++result;
			result /= *this;
			CleanupStack::Pop(&result); 
			}
		CleanupStack::PopAndDestroy(&u);
		return result;
		}

	result = RInteger::NewEmptyL(aMod.Size());
	CleanupClosePushL(result);
	RInteger workspace = RInteger::NewEmptyL(aMod.Size() * 4);
	TUint k = AlmostInverse(result.Ptr(), workspace.Ptr(), Ptr(), Size(),
		aMod.Ptr(), aMod.Size());
	DivideByPower2Mod(result.Ptr(), result.Ptr(), k, aMod.Ptr(), aMod.Size());
	workspace.Close();
	CleanupStack::Pop(&result);

	return result;
	}
Exemple #6
0
 const PolyRing& RingQQt(const MachineInt& NumIndets)
 {
   static vector<PolyRing*> QQtTable;
   if (IsNegative(NumIndets) || IsZero(NumIndets)) CoCoA_ERROR(ERR::NotPositive, "RingQQt");
   const long n = AsSignedLong(NumIndets);
   if (n >= len(QQtTable)) QQtTable.resize(n+1); // will fill with NULL ptrs
   if (QQtTable[n] == 0/*NULL ptr*/)
   {
     vector<symbol> IndetNames;
     if (n == 1) IndetNames = symbols("t"); else IndetNames = SymbolRange("t",1,n);
     QQtTable[n] = new SparsePolyRing(NewPolyRing(RingQQ(), IndetNames)); // wasteful copy!!
     RegisterDtorForGlobal(QQtTable[n], &RingQQtDtor);
   }
   return *QQtTable[n];
 }
Exemple #7
0
Estimate Estimate::TruncateNegative(const char *origin) const
{
    if (IsNegative()) throw DomainException(origin);

    if (IsPositive()) return *this;

    // (the theory says
    // we can't always give the correct DomainException, so we shouldn't try)	

    // Get an interval centered at half the upper bound, with the same error.
    LongFloat center((m_Value + m_Error.AsLongFloat()) >> 1);
    Estimate a(center, ErrorEstimate(center));

    assert(!a.IsPositive());

    return a;

    //return a.SetError(a);
}
Exemple #8
0
/**
* Creates a new buffer containing the big-endian binary representation of this
* integer.
*
* Note that it does not support the exporting of negative integers.
*
* @return	The new buffer.
* 
* @leave KErrNegativeExportNotSupported	If this instance is a negative integer.
*
*/
EXPORT_C HBufC8* TInteger::BufferLC() const
	{
	if(IsNegative())
		{
		User::Leave(KErrNegativeExportNotSupported);
		}
	TUint bytes = ByteCount();
	HBufC8* buf = HBufC8::NewMaxLC(bytes);
	TUint8* bufPtr = (TUint8*)(buf->Ptr());
	TUint8* regPtr = (TUint8*)Ptr();

	// we internally store the number little endian, as a string we want it big
	// endian
	for(TUint i=0,j=bytes-1; i<bytes; )
		{
		bufPtr[i++] = regPtr[j--];
		}
	return buf;
	}
Exemple #9
0
EXPORT_C TInteger& TInteger::operator--()
	{
    if (IsNegative())
		{
        if (Increment(Ptr(), Size()))
			{
            CleanGrowL(2*Size());
            (Ptr())[Size()/2]=1;
			}
		}
    else
		{
        if (Decrement(Ptr(), Size()))
			{
			this->CopyL(-1);
			}
		}
    return *this;	
	}
Exemple #10
0
EXPORT_C HBufC8* TInteger::BufferWithNoTruncationLC() const
 	{
 	if(IsNegative())
 		{
 		User::Leave(KErrNegativeExportNotSupported);
 		}
 	
 	TUint wordCount = Size();
 	TUint bytes = (wordCount)*WORD_SIZE;
     
  	HBufC8* buf = HBufC8::NewMaxLC(bytes);
 	TUint8* bufPtr = (TUint8*)(buf->Ptr());
	TUint8* regPtr = (TUint8*)Ptr();
	for(TUint i=0,j=bytes-1; i<bytes; )
 		{
 		bufPtr[i++] = regPtr[j--];
 		}
  
	return buf;
	}
Exemple #11
0
 std::string DecimalStr(const BigRat& q, const MachineInt& DecimalPlaces)
 {
   if (IsNegative(DecimalPlaces) || !IsSignedLong(DecimalPlaces) || IsZero(DecimalPlaces))
     CoCoA_ERROR(ERR::BadArg, "FixedStr");
   if (IsOneDen(q)) return DecimalStr(num(q), DecimalPlaces);
   const long DigitsAfterPoint = AsSignedLong(DecimalPlaces);
   const BigInt N = RoundDiv(abs(num(q))*power(10,DigitsAfterPoint),den(q));
   string digits = ToString(N);
   if (len(digits) < 1+DigitsAfterPoint)
   {
     digits = string(DigitsAfterPoint+1-len(digits), '0') + digits;
   }
   string ans;
   if (q < 0) ans = '-';
   const long IntegerPart = len(digits) - DigitsAfterPoint;
   ans.insert(ans.end(), &digits[0], &digits[IntegerPart]);
   ans += '.';
   ans.insert(ans.end(), &digits[IntegerPart], &digits[IntegerPart+DigitsAfterPoint]);
   return ans;
 }
Exemple #12
0
void Light::SetIntensitySortValue(float distance)
{
    // When sorting lights globally, give priority to directional lights so that they will be combined into the ambient pass
    if (!IsNegative())
    {
        if (lightType_ != LIGHT_DIRECTIONAL)
            sortValue_ = Max(distance, M_MIN_NEARCLIP) / GetIntensityDivisor();
        else
            sortValue_ = M_EPSILON / GetIntensityDivisor();
    }
    else
    {
        // Give extra priority to negative lights in the global sorting order so that they're handled first, right after ambient.
        // Positive lights are added after them
        if (lightType_ != LIGHT_DIRECTIONAL)
            sortValue_ = -Max(distance, M_MIN_NEARCLIP) * GetIntensityDivisor();
        else
            sortValue_ = -M_LARGE_VALUE * GetIntensityDivisor();
    }
}
Exemple #13
0
 bool NotNegative() const { return !IsNegative(); }
Exemple #14
0
//-----------------------------------------------------------------------------
// Inline Methods
//-----------------------------------------------------------------------------
inline bool PolyPlane::BehindPlane( const Vec3& point ) 
{
	return IsNegative( SignedDistance(point) );
}
Exemple #15
0
/* item[n] = start + n * delta */
static 
Array MakeLinearList(Array start, Array end, int *n, Array delta)
{
    int i, j;
    Array a_start = NULL, a_end = NULL, a_delta = NULL;
    int delstart = 0, delend = 0, deldelta = 0;
    Array alist[3];
    Array output = NULL;
    int count = 1;
    int bytes;
    Type t;
    Category c;
    int rank;
    int shape[MAXSHAPE];
    int nitems;
    int i_start, i_end, i_delta;
    float f_start, f_end, f_delta, f_count;
    Pointer dp;
    int *ip;
    Object in[MAXCOMPINPUTS];  /* hardcoded in compute */
    Object out;
    String compstr = NULL;
    char cbuf[64];
    Error rc;

    /* do this or die in compute */
    for (i=0; i<MAXCOMPINPUTS; i++)
	in[i] = NULL;

    /* find common format of start, end, delta and check for 4 parms */
    i = 0;
    if (start)
	alist[i++] = start; 

    if (end)
	alist[i++] = end;

    if (delta)
	alist[i++] = delta;

    if (n) {
	count = *n;
	if (i == 3) {
	    DXWarning("too many inputs specified; ignoring delta");
	    i--;
	    delta = NULL;
	} 
    } 
    else if (i == 2)
	count = 2;

    
    if (i < 2) {
	DXSetError(ERROR_BAD_PARAMETER, 
		   "not enough inputs specified to generate a list");
	return NULL;
    }

    if (!DXQueryArrayCommonV(&t, &c, &rank, shape, i, alist)) {
	DXAddMessage("start, end and/or delta");
	return NULL;
    }

    /* shortcut the process here if the data is scalar integer or
     *  scalar float.  otherwise, if the data is vector or ubyte
     *  or whatever, fall through and use Compute so we can increment
     *  by irregular values.
     */
    if (t != TYPE_INT && t != TYPE_FLOAT)
	goto complicated;
    if (c != CATEGORY_REAL || rank != 0)
	goto complicated;


    /* compute missing value(s):
     * start = end - ((count - 1) * delta) 
     * end = start + ((count - 1) * delta) 
     * count = ((end - start) / delta) + 1 
     * delta = (end - start) / (count - 1) 
     */

    /* convert to the common format */
    if (start)
	a_start = DXArrayConvertV(start, t, c, rank, shape);
    if (end)
	a_end   = DXArrayConvertV(end,   t, c, rank, shape);
    if (delta)
	a_delta = DXArrayConvertV(delta, t, c, rank, shape);


    /* for integer, scalar lists */
    if (t == TYPE_INT) {
	if (!start) {
	    i_end = *(int *)DXGetArrayData(a_end);
	    i_delta = *(int *)DXGetArrayData(a_delta);
	    
	    i_start = i_end - ((count - 1) * i_delta);
	}

	if (!end) {
	    i_start = *(int *)DXGetArrayData(a_start);
	    i_delta = *(int *)DXGetArrayData(a_delta);
	    
	    i_end = i_start + ((count - 1) * i_delta);
	} 

	if (!delta) {
	    /* if count == 1, generate a zero of the right type.  otherwise
	     *  divide to figure out the right delta to make count-1 steps 
	     *  between start and end.  it's count-1 because if you want
	     *  N numbers between start and end, you have N-1 increments.
	     */
	    i_start = *(int *)DXGetArrayData(a_start);
	    i_end = *(int *)DXGetArrayData(a_end);
	    if (count == 1)
		i_delta = 0;
	    else
		i_delta = (i_end - i_start) / (count - 1);
	    
	    /* try to catch the case where delta ends up being 0 (like
	     * because the inputs are int and the count is larger than
	     * the difference between start and end).  allow it to be zero
	     * only if start == end;  i suppose if you ask for 10 things
	     * where start == end you should be able to get them.
	     */
	    if (i_delta == 0 && i_start != i_end) {
		DXSetError(ERROR_BAD_PARAMETER, 
		     "count too large to generate list between start and end");
		goto error;
	    }
	    
	}

	/* if all three arrays are there, count must be missing */
	if (i == 3) {
	    i_start = *(int *)DXGetArrayData(a_start);
	    i_end = *(int *)DXGetArrayData(a_end);
	    i_delta = *(int *)DXGetArrayData(a_delta);

	    if (i_delta == 0)
		count = 1;
	    else {
		if ((i_end >= i_start && i_delta > 0) ||
		    (i_end < i_start && i_delta < 0))
		    count = (int)(((double)i_end-i_start) / (double)i_delta) +1;
		else {
		    if (i_delta < 0)
			DXSetError(ERROR_BAD_PARAMETER,
			   "delta must be positive if start is less than end");
		    else
			DXSetError(ERROR_BAD_PARAMETER,
			   "delta must be negative if end is less than start");
		    goto error;
		}
	    }
	}

	output = (Array)DXNewRegularArray(TYPE_INT, 1, count, 
					 (Pointer)&i_start, (Pointer)&i_delta);
    }

    /* for float, scalar lists */
    if (t == TYPE_FLOAT) {
	if (!start) {
	    f_end = *(float *)DXGetArrayData(a_end);
	    f_delta = *(float *)DXGetArrayData(a_delta);
	    
	    f_start = f_end - ((count - 1.0) * f_delta);
	}

	if (!end) {
	    f_start = *(float *)DXGetArrayData(a_start);
	    f_delta = *(float *)DXGetArrayData(a_delta);
	    
	    f_end = f_start + ((count - 1.0) * f_delta);
	}

	if (!delta) {
	    /* if count == 1, generate a zero of the right type.  otherwise
	     *  divide to figure out the right delta to make count-1 steps 
	     *  between start and end.  it's count-1 because if you want
	     *  N numbers between start and end, you have N-1 increments.
	     */
	    f_start = *(float *)DXGetArrayData(a_start);
	    f_end = *(float *)DXGetArrayData(a_end);
	    if (count == 1)
		f_delta = 0.0;
	    else 
		f_delta = (f_end - f_start) / (count - 1.0);

	    /* try to catch the case where delta ends up being 0 (like
	     * because the inputs are int and the count is larger than
	     * the difference between start and end).  allow it to be zero
	     * only if start == end;  i suppose if you ask for 10 things
	     * where start == end you should be able to get them.
	     */
	    if (f_delta == 0.0 && f_start != f_end) {
		DXSetError(ERROR_BAD_PARAMETER, 
		   "count too large to generate list between start and end");
		goto error;
	    }
	}

	/* if all three arrays are there, count must be missing */
	if (i == 3) {
	    f_start = *(float *)DXGetArrayData(a_start);
	    f_end = *(float *)DXGetArrayData(a_end);
	    f_delta = *(float *)DXGetArrayData(a_delta);

	    if (f_delta == 0.0)
		count = 1;
	    else {
		if ((f_end >= f_start && f_delta > 0) ||
		    (f_end < f_start && f_delta < 0)) {
		    /* the intermediate float variable below is to minimize
		     * float round-off error.  if delta is 0.1 and you
		     * ask for a list between 0 and 1, it does the math in
		     * double, the delta used is actually 0.10000001, and 
		     * you get counts = 10.9999999 instead of 11.  when
		     * converted directly to int it becomes just 10 and your 
		     * list ends at 0.9 instead of 1.  
		     * math in base 2 has some problems.
		     */
		    f_count = ((f_end - f_start) / f_delta) +1;
		    count = (int)f_count;
		} else {
		    if (f_delta < 0)
			DXSetError(ERROR_BAD_PARAMETER,
			   "delta must be positive if start is less than end");
		    else
			DXSetError(ERROR_BAD_PARAMETER,
			   "delta must be negative if end is less than start");
		    goto error;
		}
	    }
	}

	output = (Array)DXNewRegularArray(TYPE_FLOAT, 1, count, 
					 (Pointer)&f_start, (Pointer)&f_delta);
    }
    
    DXDelete((Object)a_start);
    DXDelete((Object)a_end);
    DXDelete((Object)a_delta);
    
    /* return Array */
    return output;
    

    /* input is a vector, or a data type different from int or float.
     * use compute so this code doesn't have to be replicated for each
     * different shape and type.
     */

  complicated:
    nitems = 1;
    for (j=0; j<rank; j++)
	nitems *= shape[j];

    /* compute missing value(s):
     * start = end - ((count - 1) * delta) 
     * end = start + ((count - 1) * delta) 
     * count = ((end - start) / delta) + 1 
     * delta = (end - start) / (count - 1) 
     */

    if (!start) {
	compstr = DXNewString("$0 - (($1 - 1) * $2)");
	if (!compstr)
	    goto error;
	
	in[0] = (Object)compstr;
	in[1] = (Object)end;
	in[3] = (Object)delta;
	in[2] = (Object)DXNewArray(TYPE_INT, CATEGORY_REAL, 0);
	if (!in[2])
	    goto error;
	if (!DXAddArrayData((Array)in[2], 0, 1, (Pointer)&count))
	    goto error;

	/* i need to explain this - it's basically so if compute was 
         * going to try to cache this, it could add a reference and
         * then later when i call delete the object won't get deleted
         * out from underneath compute.  (i know compute doesn't cache
         * things, but a different module might.)
	 */
	DXReference((Object)compstr);
	DXReference(in[2]);

	rc = m_Compute(in, &out);

	DXDelete((Object)compstr);
	compstr = NULL;
	DXDelete(in[2]);
	in[2] = NULL;

	if (rc == ERROR)
	    goto error;

	start = (Array)out;
	delstart++;
    }

    if (!end) {
	compstr = DXNewString("$0 + (($1 - 1) * $2)");
	if (!compstr)
	    goto error;
	
	in[0] = (Object)compstr;
	in[1] = (Object)start;
	in[3] = (Object)delta;
	in[2] = (Object)DXNewArray(TYPE_INT, CATEGORY_REAL, 0);
	if (!in[2])
	    goto error;
	if (!DXAddArrayData((Array)in[2], 0, 1, (Pointer)&count))
	    goto error;

	DXReference((Object)compstr);
	DXReference(in[2]);

	rc = m_Compute(in, &out);

	DXDelete((Object)compstr);
	compstr = NULL;
	DXDelete(in[2]);
	in[2] = NULL;

	if (rc == ERROR)
	    goto error;

	end = (Array)out;
	delend++;
    }

    if (!delta) {
	/* if count == 1, generate a zero of the right type.  otherwise
         *  divide to figure out the right delta to make count-1 steps 
	 *  between start and end.  it's count-1 because if you want
         *  N numbers between start and end, you have N-1 increments.
	 */
	if (count == 1)
	    compstr = DXNewString("$1 - $1");
	else
	    compstr = DXNewString("($2 - $0) / ($1 - 1)");
	if (!compstr)
	    goto error;
	
	in[0] = (Object)compstr;
	in[1] = (Object)start;
	in[3] = (Object)end;
	in[2] = (Object)DXNewArray(TYPE_INT, CATEGORY_REAL, 0);
	if (!in[2])
	    goto error;
	if (!DXAddArrayData((Array)in[2], 0, 1, (Pointer)&count))
	    goto error;

	DXReference((Object)compstr);
	DXReference(in[2]);

	rc = m_Compute(in, &out);

	DXDelete((Object)compstr);
	compstr = NULL;
	DXDelete(in[2]);
	in[2] = NULL;

	if (rc == ERROR)
	    goto error;

	delta = (Array)out;
	deldelta++;

	/* try to catch the case where delta ends up being 0 (like
	 * because the inputs are int and the count is larger than
	 * the difference between start and end).  allow it to be zero
	 * only if start == end;  i suppose if you ask for 10 things
	 * where start == end you should be able to get them.
	 */
	if (IsZero(delta) && !IsEqual(start, end)) {
	    DXSetError(ERROR_BAD_PARAMETER, 
		    "count too large to generate list between start and end");
	    goto error;
	}

    }

    /* if all three arrays are there, count must be missing */
    if (i == 3) {
	char tbuf[512];
	int firsttime = 1;
	int lastcount = 0;

	/* this loop allows us to to handle vectors or matricies as
	 *  well as scalars.   it requires that the deltas compute to
         *  a consistent count.  like start=[0 2 4], end=[4 8 16],
	 *  would work if delta=[1 2 4] but not if delta was [1 2 2].
	 */
	for (j=0; j < nitems; j++) {
	    /* i think this code only works for vectors - i'm not sure
             * what it will do with rank=2 data.
	     */

	    /* this point of this next compute expression:
	     * if the delta is 0, don't divide by zero - the count is 1. 
	     * if the end is smaller than the start, the delta has to be
             *  negative.  if it's not, return -1.  you can't generate a
             *  negative count from the equations, so this is a safe signal.
	     */
	    sprintf(tbuf, 
		    "float($2.%d) == 0.0   ? "
		    "  1 : "
		    " (  (($1.%d >= $0.%d) && ($2.%d > 0) || "
		    "     ($1.%d <  $0.%d) && ($2.%d < 0))    ? "
		    "       int(float($1.%d - $0.%d) / float($2.%d)) + 1 : "
		    "       -1 ) ", 
		    j, j, j, j, j, j, j, j, j, j);
	    compstr = DXNewString(tbuf);
	    if (!compstr)
		goto error;
	    
	    in[0] = (Object)compstr;
	    in[1] = (Object)start;
	    in[2] = (Object)end;
	    in[3] = (Object)delta;
	    
	    DXReference((Object)compstr);

	    rc = m_Compute(in, &out);
	    
	    DXDelete((Object)compstr);
	    compstr = NULL;
	    
	    if (rc == ERROR)
		goto error;
	    
	    if (!DXExtractInteger(out, &count)) {
		DXSetError(ERROR_BAD_PARAMETER, 
			   "can't compute number of items");
		goto error;
	    }

	    DXDelete((Object)out);
	    if (count == 0)
		continue;

	    if (count < 0) {
		if (IsNegative(delta))
		    DXSetError(ERROR_BAD_PARAMETER,
			 "delta must be positive if start is less than end");
		else
		    DXSetError(ERROR_BAD_PARAMETER,
			 "delta must be negative if end is less than start");
		goto error;
	    }

	    if (firsttime) {
		lastcount = count;
		firsttime = 0;
	    } else {
		if (count != lastcount) {
		    DXSetError(ERROR_BAD_PARAMETER, 
			   "inconsistent number of items required by inputs");
		    goto error;
		}
	    }
	}    
    }

    /* now have 4 consistant values - once again make sure they are
     * converted into an identical format.
     */
    a_start = DXArrayConvertV(start, t, c, rank, shape);
    a_end   = DXArrayConvertV(end,   t, c, rank, shape);
    a_delta = DXArrayConvertV(delta, t, c, rank, shape);

    /* make empty array with n items */
    output = DXNewArrayV(t, c, rank, shape);
    if (!output)
	goto error;

    if (!DXAddArrayData(output, 0, count, NULL))
	goto error;

    dp = DXGetArrayData(output);
    if (!dp)
	goto error;

    /* foreach n */
    /*  call compute to add delta */
    /*  memcpy to right offset in array */
    /* end */

    bytes = DXGetItemSize(output);

    sprintf(cbuf, "%s($0 + ($1 * $2))", TypeName(t));
    compstr = DXNewString(cbuf);
    if (!compstr)
	goto error;
    
    in[0] = (Object)compstr;
    in[1] = (Object)a_start;
    in[3] = (Object)a_delta;

    in[2] = (Object)DXNewArray(TYPE_INT, CATEGORY_REAL, 0);
    if (!in[2])
	goto error;
    if (!DXAddArrayData((Array)in[2], 0, 1, NULL))
	goto error;
    ip = (int *)DXGetArrayData((Array)in[2]);
    
    DXReference((Object)compstr);
    DXReference(in[2]);

    for (i=0; i<count; i++) {

	*ip = i;

	rc = m_Compute(in, &out);
	if (rc == ERROR)
	    goto error;

	memcpy(INCVOID(dp, bytes*i), DXGetArrayData((Array)out), bytes);
	DXDelete((Object)out);
    }

    DXDelete((Object)compstr);
    DXDelete(in[2]);
    DXDelete((Object)a_start);
    DXDelete((Object)a_end);
    DXDelete((Object)a_delta);
    if (delstart)
	DXDelete((Object)start);
    if (delend)
	DXDelete((Object)end);
    if (deldelta)
	DXDelete((Object)delta);

    /* return Array */
    return output;
    
  error:
    DXDelete((Object)output);
    DXDelete((Object)compstr);
    DXDelete((Object)a_start);
    DXDelete((Object)a_end);
    DXDelete((Object)a_delta);
    if (delstart)
	DXDelete((Object)start);
    if (delend)
	DXDelete((Object)end);
    if (deldelta)
	DXDelete((Object)delta);

    return NULL;
}
Exemple #16
0
double
DigitEntry::GetDoubleValue() const
{
    double value = GetPositiveInteger() + GetPositiveFractional();
    return IsNegative() ? -value : value;
}
Exemple #17
0
int
DigitEntry::GetIntegerValue() const
{
    int value = GetPositiveInteger();
    return IsNegative() ? -value : value;
}
Exemple #18
0
fixed
DigitEntry::GetFixedValue() const
{
  fixed value = fixed(GetPositiveInteger()) + GetPositiveFractional();
  return IsNegative() ? -value : value;
}
Exemple #19
0
// The resulting hull will not contain interior points
// Note that this is a cheap and cheerful implementation that can only handle
// reasonably small point sets. However, except for the final hull it doesn't do any dynamic
// memory allocation - all the work happens on the stack.
Hull* Hull::MakeHull(int numPoints, const Point3* pPoints)
{
    assert(numPoints >= 4);
    assert(pPoints);

    // check first 4 points are disjoint
    // TODO: make it search points so it can cope better with this
    assert(Length(pPoints[1] - pPoints[0]) > 0.01f);
    assert(Length(pPoints[2] - pPoints[0]) > 0.01f);
    assert(Length(pPoints[3] - pPoints[0]) > 0.01f);
    assert(Length(pPoints[2] - pPoints[1]) > 0.01f);
    assert(Length(pPoints[3] - pPoints[1]) > 0.01f);
    assert(Length(pPoints[3] - pPoints[2]) > 0.01f);

    s_pPoints = pPoints;

    // put all temp faces on a free list
    TmpFace tmpFaces[kMaxFaces];

    s_firstFreeTmpFace = 0;
    s_firstUsedTmpFace = -1;
    s_pTmpFaces = tmpFaces;

    for (short i = 0; i < kMaxEdges; i++)
    {
        tmpFaces[i].m_index = i;
        tmpFaces[i].m_next = i + 1;
    }
    tmpFaces[kMaxFaces - 1].m_next = -1;

    // put all temp edges on a free list
    TmpEdge tmpEdges[kMaxEdges];

    s_firstFreeTmpEdge = 0;
    s_firstUsedTmpEdge = -1;
    s_pTmpEdges = tmpEdges;

    for (short i = 0; i < kMaxEdges; i++)
    {
        tmpEdges[i].m_index = i;
        tmpEdges[i].m_next = i + 1;
    }
    tmpEdges[kMaxEdges - 1].m_next = -1;

    // make initial tetrahedron
    Plane plane = Plane(pPoints[0], pPoints[1], pPoints[2]);

    Scalar dot = Dot(plane, pPoints[3]);
    assert(Abs(dot) > 0.01f);			// first 4 points are co-planar

    if (IsNegative(dot))
    {
        AddTmpFace(0, 1, 2);
        AddTmpFace(1, 0, 3);
        AddTmpFace(0, 2, 3);
        AddTmpFace(2, 1, 3);
    }
    else
    {
        AddTmpFace(2, 1, (short)0);
        AddTmpFace(1, 2, 3);
        AddTmpFace(2, 0, 3);
        AddTmpFace(0, 1, 3);
    }

    // merge all remaining points
    for (int i = 4; i < numPoints; i++)
        if (RemoveVisibleFaces(pPoints[i]) > 0)
            FillHole(i);

    return MakeHullFromTemp();
}
Exemple #20
0
int Hull::AddContactsHullHull(Separation& sep, const Point3* pVertsA, const Point3* pVertsB,
                              const Transform& trA, const Transform& trB,const Hull& hullA,const Hull& hullB,
                              HullContactCollector* hullContactCollector)
{
    const int maxContacts = hullContactCollector->GetMaxNumContacts();

    Vector3 normalWorld = sep.m_axis;

    // edge->edge contact is always a single point
    if (sep.m_separator == Separation::kFeatureBoth)
    {
        const Hull::Edge& edgeA = hullA.GetEdge(sep.m_featureA);
        const Hull::Edge& edgeB = hullB.GetEdge(sep.m_featureB);

        float ta, tb;
        Line la(pVertsA[edgeA.m_verts[0]], pVertsA[edgeA.m_verts[1]]);
        Line lb(pVertsB[edgeB.m_verts[0]], pVertsB[edgeB.m_verts[1]]);

        Intersect(la, lb, ta, tb);

#ifdef VALIDATE_CONTACT_POINTS
        AssertPointInsideHull(contact.m_points[0].m_pos, trA, hullA);
        AssertPointInsideHull(contact.m_points[0].m_pos, trB, hullB);
#endif


        Point3 posWorld = Lerp(la.m_start, la.m_end, ta);
        float depth = -sep.m_dist;
        Vector3 tangent = Normalize(pVertsA[edgeA.m_verts[1]] - pVertsA[edgeA.m_verts[0]]);

        sep.m_contact = hullContactCollector->BatchAddContactGroup(sep,1,normalWorld,tangent,&posWorld,&depth);

    }
    // face->face contact is polygon
    else
    {
        short faceA = sep.m_featureA;
        short faceB = sep.m_featureB;

        Vector3 tangent;

        // find face of hull A that is most opposite contact axis
        // TODO: avoid having to transform planes here
        if (sep.m_separator == Separation::kFeatureB)
        {
            const Hull::Edge& edgeB = hullB.GetEdge(hullB.GetFaceFirstEdge(faceB));
            tangent = Normalize(pVertsB[edgeB.m_verts[1]] - pVertsB[edgeB.m_verts[0]]);

            Scalar dmin = Scalar::Consts::MaxValue;
            for (short face = 0; face < hullA.m_numFaces; face++)
            {
                Vector3 normal = hullA.GetPlane(face).GetNormal() * trA;
                Scalar d = Dot(normal, sep.m_axis);
                if (d < dmin)
                {
                    dmin = d;
                    faceA = face;
                }
            }
        }
        else
        {
            const Hull::Edge& edgeA = hullA.GetEdge(hullA.GetFaceFirstEdge(faceA));
            tangent = Normalize(pVertsA[edgeA.m_verts[1]] - pVertsA[edgeA.m_verts[0]]);

            Scalar dmin = Scalar::Consts::MaxValue;
            for (short face = 0; face < hullB.m_numFaces; face++)
            {
                Vector3 normal = hullB.GetPlane(face).GetNormal() * trB;
                Scalar d = Dot(normal, -sep.m_axis);
                if (d < dmin)
                {
                    dmin = d;
                    faceB = face;
                }
            }
        }

        Point3 workspace[2][Hull::kMaxVerts];

        // setup initial clip face (minimizing face from hull B)
        int numContacts = 0;
        for (short edge = hullB.GetFaceFirstEdge(faceB); edge != -1; edge = hullB.GetFaceNextEdge(faceB, edge))
            workspace[0][numContacts++] = pVertsB[ hullB.GetEdgeVertex0(faceB, edge) ];

        // clip polygon to back of planes of all faces of hull A that are adjacent to witness face
        Point3* pVtxIn = workspace[0];
        Point3* pVtxOut = workspace[1];

#if 0
        for (short edge = hullA.GetFaceFirstEdge(faceA); edge != -1; edge = hullA.GetFaceNextEdge(faceA, edge))
        {
            Plane planeA = hullA.GetPlane( hullA.GetEdgeOtherFace(edge, faceA) ) * trA;
            numContacts = ClipFace(numContacts, &pVtxIn, &pVtxOut, planeA);
        }
#else
        for (short f = 0; f < hullA.GetNumFaces(); f++)
        {
            Plane planeA = hullA.GetPlane(f) * trA;
            numContacts = ClipFace(numContacts, &pVtxIn, &pVtxOut, planeA);
        }
#endif

        // only keep points that are behind the witness face
        Plane planeA = hullA.GetPlane(faceA) * trA;

        float depths[Hull::kMaxVerts];
        int numPoints = 0;
        for (int i = 0; i < numContacts; i++)
        {
            Scalar d = Dot(planeA, pVtxIn[i]);
            if (IsNegative(d))
            {
                depths[numPoints] = (float)-d;
                pVtxIn[numPoints] = pVtxIn[i];

#ifdef VALIDATE_CONTACT_POINTS
                AssertPointInsideHull(pVtxIn[numPoints], trA, hullA);
                AssertPointInsideHull(pVtxIn[numPoints], trB, hullB);
#endif
                numPoints++;
            }
        }

        //we can also use a persistentManifold/reducer class
        // keep maxContacts points at most
        if (numPoints > 0)
        {
            if (numPoints > maxContacts)
            {
                int step = (numPoints << 8) / maxContacts;

                numPoints = maxContacts;
                for (int i = 0; i < numPoints; i++)
                {
                    int nth = (step * i) >> 8;

                    depths[i] = depths[nth];
                    pVtxIn[i] = pVtxIn[nth];


#ifdef VALIDATE_CONTACT_POINTS
                    AssertPointInsideHull(contact.m_points[i].m_pos, trA, hullA);
                    AssertPointInsideHull(contact.m_points[i].m_pos, trB, hullB);
#endif
                }
            }

            sep.m_contact = hullContactCollector->BatchAddContactGroup(sep,numPoints,normalWorld,tangent,pVtxIn,depths);

        }
        return numPoints;
    }
Exemple #21
0
 std::string ScientificStr(const BigRat& q, const MachineInt& SigFig)
 {
   if (IsNegative(SigFig) || !IsSignedLong(SigFig) || IsZero(SigFig))
     CoCoA_ERROR(ERR::BadArg, "ScientificStr");
   return ScientificStr(MantissaAndExponent10(q, SigFig), AsSignedLong(SigFig));
 }
Exemple #22
0
	static bool IsNegative(FloatConstant* value) {
		return IsNegative(value->Value(), value->GetType()->GetSubtype());
	}