static int DaoCstruct_Compare( DaoCstruct *left, DaoCstruct *right, DMap *cycmap ) { if( left == right ) return 0; if( DaoType_ChildOf( left->ctype, right->ctype ) ){ if( left->ctype->core->Compare ){ return left->ctype->core->Compare( (DaoValue*) left, (DaoValue*) right, cycmap ); }else if( right->ctype->core->Compare ){ return - right->ctype->core->Compare( (DaoValue*) right, (DaoValue*) left, cycmap ); } }else if( DaoType_ChildOf( right->ctype, left->ctype ) ){ if( right->ctype->core->Compare ){ return - right->ctype->core->Compare( (DaoValue*) right, (DaoValue*) left, cycmap ); }else if( left->ctype->core->Compare ){ return left->ctype->core->Compare( (DaoValue*) left, (DaoValue*) right, cycmap ); } } if( left->ctype != right->ctype ){ return number_compare( (size_t)left->ctype, (size_t)right->ctype ); }else if( left->type == DAO_CDATA ){ DaoCdata *l = (DaoCdata*) left; DaoCdata *r = (DaoCdata*) right; return number_compare( (size_t)l->data, (size_t)r->data ); } return number_compare( (size_t)left, (size_t)right ); }
int DaoValue_Compare( DaoValue *left, DaoValue *right ) { double L, R; int res = 0; if( left == right ) return 0; if( left == NULL || right == NULL ) return left < right ? -100 : 100; if( left->type != right->type ){ res = left->type < right->type ? -100 : 100; if( right->type == DAO_TUPLE && right->xTuple.subtype == DAO_PAIR ){ if( (res = DaoValue_Compare( left, right->xTuple.items[0] )) <= 0 ) return res; if( (res = DaoValue_Compare( left, right->xTuple.items[1] )) >= 0 ) return res; return 0; }else if( left->type == DAO_TUPLE && left->xTuple.subtype == DAO_PAIR ){ if( (res = DaoValue_Compare( left->xTuple.items[0], right )) >= 0 ) return res; if( (res = DaoValue_Compare( left->xTuple.items[1], right )) <= 0 ) return res; return 0; } #ifdef DAO_WITH_LONGINT if( left->type == DAO_LONG && (right->type && right->type <= DAO_DOUBLE) ){ if( right->type == DAO_INTEGER ){ return DLong_CompareToInteger( left->xLong.value, right->xInteger.value ); } return DLong_CompareToDouble( left->xLong.value, DaoValue_GetDouble( right ) ); }else if( right->type == DAO_LONG && (left->type && left->type <= DAO_DOUBLE) ){ if( left->type == DAO_INTEGER ){ return - DLong_CompareToInteger( right->xLong.value, left->xInteger.value ); } return - DLong_CompareToDouble( right->xLong.value, DaoValue_GetDouble( left ) ); } #endif if( left->type < DAO_INTEGER || left->type > DAO_DOUBLE ) return res; if( right->type < DAO_INTEGER || right->type > DAO_DOUBLE ) return res; L = DaoValue_GetDouble( left ); R = DaoValue_GetDouble( right ); return L == R ? 0 : (L < R ? -1 : 1); } switch( left->type ){ case DAO_NONE : return 0; case DAO_INTEGER : return number_compare( left->xInteger.value, right->xInteger.value ); case DAO_FLOAT : return number_compare( left->xFloat.value, right->xFloat.value ); case DAO_DOUBLE : return number_compare( left->xDouble.value, right->xDouble.value ); case DAO_COMPLEX : return DaoComplex_Compare( & left->xComplex, & right->xComplex ); #ifdef DAO_WITH_LONGINT case DAO_LONG : return DLong_Compare( left->xLong.value, right->xLong.value ); #endif case DAO_STRING : return DString_Compare( left->xString.data, right->xString.data ); case DAO_ENUM : return DaoEnum_Compare( & left->xEnum, & right->xEnum ); case DAO_TUPLE : return DaoTuple_Compare( & left->xTuple, & right->xTuple ); case DAO_LIST : return DaoList_Compare( & left->xList, & right->xList ); case DAO_CDATA : case DAO_CSTRUCT : case DAO_CTYPE : return DaoCstruct_Compare( left, right ); #ifdef DAO_WITH_NUMARRAY case DAO_ARRAY : return DaoArray_Compare( & left->xArray, & right->xArray ); #endif } return left < right ? -100 : 100; /* needed for map */ }
int DaoValue_CompareExt( DaoValue *left, DaoValue *right, DMap *cycmap ) { DMap *input = cycmap; void *pters[2]; int res = 0; if( left == right ) return 0; if( left == NULL || right == NULL ) return left < right ? -100 : 100; if( left->type != right->type ){ double L, R; res = left->type < right->type ? -100 : 100; if( left->type < DAO_BOOLEAN || left->type > DAO_FLOAT ) return res; if( right->type < DAO_BOOLEAN || right->type > DAO_FLOAT ) return res; L = DaoValue_GetFloat( left ); R = DaoValue_GetFloat( right ); return L == R ? 0 : (L < R ? -1 : 1); } switch( left->type ){ case DAO_TUPLE : case DAO_LIST : case DAO_OBJECT : case DAO_CDATA : case DAO_CSTRUCT : pters[0] = left; pters[1] = right; if( cycmap != NULL ){ DNode *it = DMap_Find( cycmap, pters ); if( it != NULL ) return left < right ? -100 : 100; } if( cycmap == NULL ) cycmap = DHash_New(DAO_DATA_VOID2,0); DMap_Insert( cycmap, pters, NULL ); break; } switch( left->type ){ case DAO_NONE : break; case DAO_BOOLEAN : res = number_compare( left->xBoolean.value, right->xBoolean.value ); break; case DAO_INTEGER : res = number_compare( left->xInteger.value, right->xInteger.value ); break; case DAO_FLOAT : res = number_compare( left->xFloat.value, right->xFloat.value ); break; case DAO_COMPLEX : res = DaoComplex_Compare( (DaoComplex*) left, (DaoComplex*) right ); break; case DAO_STRING : res = DString_CompareUTF8( left->xString.value, right->xString.value ); break; case DAO_ENUM : res = DaoEnum_Compare( (DaoEnum*) left, (DaoEnum*) right ); break; case DAO_TUPLE : res = DaoTuple_Compare( (DaoTuple*) left, (DaoTuple*) right, cycmap ); break; case DAO_LIST : res = DaoList_Compare( (DaoList*) left, (DaoList*) right, cycmap ); break; case DAO_OBJECT : res = DaoObject_Compare( (DaoObject*)left, (DaoObject*)right, cycmap ); break; case DAO_CDATA : case DAO_CSTRUCT : res = DaoCstruct_Compare( (DaoCstruct*)left, (DaoCstruct*)right, cycmap ); break; case DAO_TYPE : res = DaoType_Compare( (DaoType*) left, (DaoType*) right ); break; #ifdef DAO_WITH_NUMARRAY case DAO_ARRAY : res = DaoArray_Compare( (DaoArray*) left, (DaoArray*) right ); break; #endif default: res = left < right ? -100 : 100; break; /* Needed for map; */ } if( cycmap != input ) DMap_Delete( cycmap ); return res; }
int DaoCstruct_Compare( DaoValue *left, DaoValue *right ) { if( left == right ) return 0; if( left->xCstruct.ctype != right->xCstruct.ctype ){ return number_compare( (size_t)left->xCstruct.ctype, (size_t)right->xCstruct.ctype ); } if( left->type == DAO_CDATA ){ return number_compare( (size_t)left->xCdata.data, (size_t)right->xCdata.data ); } return number_compare( (size_t)left, (size_t)right ); }
static bool _check_conditions(NumberValidator *v, Number const *n, ValidationState *s, void *ctxt) { if (v->integer && !number_is_integer(n)) { validation_state_notify_error(s, VEC_NOT_INTEGER_NUMBER, ctxt); return false; } if (v->expected_set && 0 != number_compare(n, &v->expected_value)) { validation_state_notify_error(s, VEC_UNEXPECTED_VALUE, ctxt); return false; } if (v->min_set) { int cmp = number_compare(n, &v->min); if (cmp == -1 || (cmp == 0 && v->min_exclusive)) { validation_state_notify_error(s, VEC_NUMBER_TOO_SMALL, ctxt); return false; } } if (v->max_set) { int cmp = number_compare(n, &v->max); if (cmp == 1 || (cmp == 0 && v->max_exclusive)) { validation_state_notify_error(s, VEC_NUMBER_TOO_BIG, ctxt); return false; } } return true; }
static object rando(object x, object rs) { enum type tx; object base,out,z; fixnum fbase; double d; tx = type_of(x); if (number_compare(x, small_fixnum(0)) != 1) FEwrong_type_argument(TSpositive_number, x); if (tx==t_bignum) { out=new_bignum(); base=x; fbase=-1; } else { out=big_fixnum1; fbase=tx==t_fixnum ? fix(x) : MOST_POSITIVE_FIX; mpz_set_si(MP(big_fixnum2),fbase); base=big_fixnum2; } mpz_urandomm(MP(out),&rs->rnd.rnd_state,MP(base)); switch (tx) { case t_fixnum: return make_fixnum(mpz_get_si(MP(out))); case t_bignum: return normalize_big(out); case t_shortfloat: case t_longfloat: d=mpz_get_d(MP(out)); d/=(double)fbase; z=alloc_object(tx); if (tx==t_shortfloat) sf(z)=sf(x)*d; else lf(z)=lf(x)*d; return z; default: FEerror("~S is not an integer nor a floating-point number.", 1, x); return(Cnil); } }
static int DaoObject_Compare( DaoObject *left, DaoObject *right, DMap *cycmap ) { DaoValue *base1 = left->parent; DaoValue *base2 = right->parent; if( left == right ) return 0; while( base1 != NULL && base1->type == DAO_OBJECT ) base1 = base1->xObject.parent; while( base2 != NULL && base2->type == DAO_OBJECT ) base2 = base2->xObject.parent; if( DaoType_ChildOf( left->defClass->objType, right->defClass->objType ) ){ if( base1 != NULL ){ return DaoCstruct_Compare( (DaoCstruct*) base1, (DaoCstruct*) base2, cycmap ); } }else if( DaoType_ChildOf( right->defClass->objType, left->defClass->objType ) ){ if( base1 != NULL ){ return DaoCstruct_Compare( (DaoCstruct*) base1, (DaoCstruct*) base2, cycmap ); } } return number_compare( (size_t)left, (size_t)right ); }
int DaoEnum_Compare( DaoEnum *L, DaoEnum *R ) { DaoEnum E; DNode *N = NULL; DMap *ML = L->etype->mapNames; DMap *MR = R->etype->mapNames; uchar_t FL = L->etype->flagtype; uchar_t FR = R->etype->flagtype; char SL = L->etype->name->mbs[0]; char SR = R->etype->name->mbs[0]; if( L->etype == R->etype ){ return L->value == R->value ? 0 : ( L->value < R->value ? -1 : 1 ); }else if( SL == '$' && SR == '$' && FL == 0 && FR == 0 ){ return DString_Compare( L->etype->name, R->etype->name ); }else if( SL == '$' && SR == '$' ){ if( L->etype->mapNames->size != R->etype->mapNames->size ){ return number_compare( L->etype->mapNames->size, R->etype->mapNames->size ); }else{ for(N=DMap_First(ML);N;N=DMap_Next(ML,N)){ if( DMap_Find( MR, N->key.pVoid ) ==0 ) return -1; } return 0; } }else if( SL == '$' ){ E.etype = R->etype; E.value = R->value; DaoEnum_SetValue( & E, L, NULL ); return E.value == R->value ? 0 : ( E.value < R->value ? -1 : 1 ); }else if( SR == '$' ){ E.etype = L->etype; E.value = L->value; DaoEnum_SetValue( & E, R, NULL ); return L->value == E.value ? 0 : ( L->value < E.value ? -1 : 1 ); }else{ return L->value == R->value ? 0 : ( L->value < R->value ? -1 : 1 ); } }
static int DaoType_Compare( DaoType *left, DaoType *right ) { if( DaoType_MatchTo( left, right, NULL ) >= DAO_MT_EQ ) return 0; return number_compare( (size_t)left, (size_t)right ); }