diff --git a/bigint.mod/bigint.bmx b/bigint.mod/bigint.bmx index cca230f28..3e6883fe4 100644 --- a/bigint.mod/bigint.bmx +++ b/bigint.mod/bigint.bmx @@ -37,17 +37,24 @@ End Rem Type TBigUnsigned Field bigPtr:Byte Ptr + + + Method New(value:String) + Create(value) + End Method + + Method New(value:Int) + CreateWithInt(value) + End Method + + Method Create:TBigUnsigned(value:String = "") - Local this:TBigUnsigned = New TBigUnsigned - this.bigPtr = bmx_bigint_BigUnsigned_create(value) - Return this + bigPtr = bmx_bigint_BigUnsigned_create(value) End Method Method CreateWithInt:TBigUnsigned(value:Int) - Local this:TBigUnsigned = New TBigUnsigned - this.bigPtr = bmx_bigint_BigUnsigned_CreateWithInt(value) - Return this + bigPtr = bmx_bigint_BigUnsigned_CreateWithInt(value) End Method Method IsZero:Int() @@ -61,7 +68,19 @@ Type TBigUnsigned Method GreaterThan:Int(value:TBigUnsigned) End Method - + + + Method Add:TBigUnsigned(value:TBigUnsigned) + bmx_bigint_BigUnsigned_add(bigPtr, value.bigPtr) + return self + End Method + + + Method Divide:TBigUnsigned(value:TBigUnsigned) + bmx_bigint_BigUnsigned_divide(bigPtr, value.bigPtr) + return self + End Method + Method ToString:String() @@ -79,3 +98,223 @@ End Type + + +Rem +bbdoc: A TBigUnsigned object represents an integer of size limited only by available memory. +End Rem +Type TBigInteger + + Field bigPtr:Byte Ptr + + + Method New(value:String) + Create(value) + End Method + + Method New(value:Int) + CreateWithInt(value) + End Method + + + + Method Create:TBigInteger(value:String = "") + bigPtr = bmx_bigint_BigInteger_create(value) + End Method + + Method CreateWithInt:TBigInteger(value:Int) + bigPtr = bmx_bigint_BigInteger_CreateWithInt(value) + End Method + + Method IsZero:Int() + End Method + + Method Equals:Int(value:TBigInteger) + Return bmx_bigint_BigInteger_equal(bigPtr, value.bigPtr) + End Method + + Method LessThan:Int(value:TBigInteger) + Return bmx_bigint_BigInteger_lessThan(bigPtr, value.bigPtr) + End Method + + Method LessThanOrEqual:Int(value:TBigInteger) + Return bmx_bigint_BigInteger_lessThanOrEqual(bigPtr, value.bigPtr) + End Method + + Method GreaterThan:Int(value:TBigInteger) + Return bmx_bigint_BigInteger_greaterThan(bigPtr, value.bigPtr) + End Method + + Method GreaterThanOrEqual:Int(value:TBigInteger) + Return bmx_bigint_BigInteger_greaterThanOrEqual(bigPtr, value.bigPtr) + End Method + + + Method Add:TBigInteger(value:TBigInteger) + bmx_bigint_BigInteger_add(bigPtr, value.bigPtr) + return self + End Method + + + Method Subtract:TBigInteger(value:TBigInteger) + bmx_bigint_BigInteger_add(bigPtr, value.bigPtr) + return self + End Method + + + Method Modulo:TBigInteger(value:TBigInteger) + bmx_bigint_BigInteger_modulo(bigPtr, value.bigPtr) + return self + End Method + + + Method Divide:TBigInteger(value:TBigInteger) + bmx_bigint_BigInteger_divide(bigPtr, value.bigPtr) + return self + End Method + + + Method Multiply:TBigInteger(value:TBigInteger) + bmx_bigint_BigInteger_multiply(bigPtr, value.bigPtr) + return self + End Method + + + + Method CreateAddResult:TBigInteger(value:TBigInteger) + Local result:TBigInteger = new TBigInteger() + result.bigPtr = bmx_bigint_new_BigInteger_add(bigPtr, value.bigPtr) + return result + End Method + + + Method CreateSubtractResult:TBigInteger(value:TBigInteger) + Local result:TBigInteger = new TBigInteger() + result.bigPtr = bmx_bigint_new_BigInteger_subtract(bigPtr, value.bigPtr) + return result + End Method + + + Method CreateModuloResult:TBigInteger(value:TBigInteger) + Local result:TBigInteger = new TBigInteger() + result.bigPtr = bmx_bigint_new_BigInteger_modulo(bigPtr, value.bigPtr) + return result + End Method + + + Method CreateDivideResult:TBigInteger(value:TBigInteger) + Local result:TBigInteger = new TBigInteger() + result.bigPtr = bmx_bigint_new_BigInteger_divide(bigPtr, value.bigPtr) + return result + End Method + + + Method CreateMultiplyResult:TBigInteger(value:TBigInteger) + Local result:TBigInteger = new TBigInteger() + result.bigPtr = bmx_bigint_new_BigInteger_multiply(bigPtr, value.bigPtr) + return result + End Method + + + 'add value directly + Method Operator :+(value:TBigInteger) + Add(value) + End Method + + + 'add value and return sum! + Method Operator +:TBigInteger(value:TBigInteger) + Return CreateAddResult(value) + End Method + + + 'subtract value directly + Method Operator :-(value:TBigInteger) + Subtract(value) + End Method + + + 'subtract value and return difference! + Method Operator -:TBigInteger(value:TBigInteger) + Return CreateSubtractResult(value) + End Method + + + 'multiply value directly + Method Operator :*(value:TBigInteger) + Multiply(value) + End Method + + + 'multiply value and return product! + Method Operator *:TBigInteger(value:TBigInteger) + Return CreateMultiplyResult(value) + End Method + + + 'divide value directly + Method Operator :/(value:TBigInteger) + Divide(value) + End Method + + + 'divide value and return quotient! + Method Operator /:TBigInteger(value:TBigInteger) + Return CreateDivideResult(value) + End Method + + + 'divide value and return remainder / modulo! + Method Operator :mod(value:TBigInteger) + Modulo(value) + End Method + + + 'divide value and return remainder / modulo! + Method Operator mod:TBigInteger(value:TBigInteger) + Return CreateModuloResult(value) + End Method + + + Method Operator >:Int(value:TBigInteger) + Return GreaterThan(value) + End Method + + + Method Operator >=:Int(value:TBigInteger) + Return GreaterThanOrEqual(value) + End Method + + + Method Operator <:Int(value:TBigInteger) + Return LessThan(value) + End Method + + + Method Operator <=:Int(value:TBigInteger) + Return LessThanOrEqual(value) + End Method + + + Method Operator =:Int(value:TBigInteger) + Return Equals(value) + End Method + + Method Operator <>:Int(value:TBigInteger) + Return not Equals(value) + End Method + + + Method ToString:String() + Return bmx_bigint_BigInteger_ToString(bigPtr) + End Method + + Method Delete() + If bigPtr Then + bmx_bigint_BigInteger_free(bigPtr) + bigPtr = Null + End If + End Method + +End Type + diff --git a/bigint.mod/common.bmx b/bigint.mod/common.bmx index 02b3ec3fa..4a7650a5f 100644 --- a/bigint.mod/common.bmx +++ b/bigint.mod/common.bmx @@ -31,6 +31,36 @@ Extern Function bmx_bigint_BigUnsigned_ToString:String(handle:Byte Ptr) + Function bmx_bigint_BigUnsigned_add(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigUnsigned_divide(target:Byte Ptr, value:Byte Ptr) + + + + Function bmx_bigint_BigInteger_create:Byte Ptr(value:String) + Function bmx_bigint_BigInteger_free(handle:Byte Ptr) + Function bmx_bigint_BigInteger_CreateWithInt:Byte Ptr(value:Int) + + Function bmx_bigint_BigInteger_ToString:String(handle:Byte Ptr) + + Function bmx_bigint_BigInteger_equal:Int(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_notequal:Int(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_lessThan:Int(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_lessThanOrEqual:Int(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_greaterThan:Int(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_greaterThanOrEqual:Int(target:Byte Ptr, value:Byte Ptr) + + Function bmx_bigint_BigInteger_add(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_subtract(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_divide(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_multiply(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_BigInteger_modulo(target:Byte Ptr, value:Byte Ptr) + + Function bmx_bigint_new_BigInteger_add:Byte Ptr(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_new_BigInteger_subtract:Byte Ptr(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_new_BigInteger_divide:Byte Ptr(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_new_BigInteger_multiply:Byte Ptr(target:Byte Ptr, value:Byte Ptr) + Function bmx_bigint_new_BigInteger_modulo:Byte Ptr(target:Byte Ptr, value:Byte Ptr) + End Extern diff --git a/bigint.mod/examples/example_02.bmx b/bigint.mod/examples/example_02.bmx new file mode 100644 index 000000000..6217ce90c --- /dev/null +++ b/bigint.mod/examples/example_02.bmx @@ -0,0 +1,53 @@ +SuperStrict + +Framework BaH.BigInt +Import BRL.StandardIO + +'create a +Local bigUnsigned:TBigUnsigned = New TBigUnsigned("100000000000000000000000000000000000000000000000000000000") + +Print "100 + 500 = " + new TBigUnsigned(100).Add( new TBigUnsigned(500) ).ToString() +Print "500 : 10 = " + new TBigUnsigned(500).Divide(new TBigUnsigned(10)).ToString() + + +'now with signs (allows negative numbers) +Print "-100 + 500 = " + new TBigInteger(-100).Add( new TBigInteger(500) ).ToString() +Print "500 : 10 = " + new TBigInteger(500).Divide(new TBigInteger(10)).ToString() +Print "5 : 2 = 2 remaining " + new TBigInteger(5).Modulo(new TBigInteger(2)).ToString() +Print "500 * 20 = " + new TBigInteger(500).Multiply(new TBigInteger(20)).ToString() + +local big1:TBigInteger = new TBigInteger(500) +'do something with it +big1.Add(new TBigInteger(20)) +print big1.ToString() + +'keep big1 intact () +Local big2:TBigInteger = big1.CreateAddResult(new TBigInteger(20)) +print big1.ToString() +print big2.ToString() + + +'checkout overloaded operators +Local op1:TBigInteger = new TBigInteger(100) +Local op2:TBigInteger = new TBigInteger(50) +Local op3:TBigInteger = op1 + op2 +print op3.ToString() +op1 :+ op2 'op1 now 150 +print ((op1 + op2).ToString()) + +'modulo? +print ((new TBigInteger(50) mod new TBigInteger(8)).ToString()) + +'bigger? +if new TBigInteger(50) > new TBigInteger(5) + print "50 > 5" +else + print "50 < 5" +endif + +'same value? +if new TBigInteger(50) = new TBigInteger(50) + print "50 = 50" +else + print "50 <> 50" +endif \ No newline at end of file diff --git a/bigint.mod/glue.cpp b/bigint.mod/glue.cpp index f484f4917..5e8f05d3f 100644 --- a/bigint.mod/glue.cpp +++ b/bigint.mod/glue.cpp @@ -42,10 +42,33 @@ BigUnsigned & MaxBigUnsigned::Big() { } + + + +MaxBigInteger::MaxBigInteger(BigInteger & b) + : big(b) +{ +} + +MaxBigInteger::MaxBigInteger(const std::string & b) + : big(stringToBigInteger(b)) +{ +} + +MaxBigInteger::MaxBigInteger(int value) + : big(value) +{ +} + +BigInteger & MaxBigInteger::Big() { + return big; +} + + // -------------------------------------------------------- MaxBigUnsigned * bmx_bigint_BigUnsigned_create(BBString * value) { - char * p = bbStringToCString(value); + char * p = (char*)bbStringToCString(value); try { MaxBigUnsigned * big = new MaxBigUnsigned(p); bbMemFree(p); @@ -72,3 +95,143 @@ BBString * bmx_bigint_BigUnsigned_ToString(MaxBigUnsigned * big) { return bbStringFromCString(bigUnsignedToString(big->Big()).c_str()); } + +void bmx_bigint_BigUnsigned_add(MaxBigUnsigned * target, MaxBigUnsigned * value) { + target->Big().add(target->Big(), value->Big()); +} +void bmx_bigint_BigUnsigned_subtract(MaxBigUnsigned * target, MaxBigUnsigned * value) { + target->Big().subtract(target->Big(), value->Big()); +} + +void bmx_bigint_BigUnsigned_divide(MaxBigUnsigned * target, MaxBigUnsigned * value) { + target->Big().divideWithRemainder(target->Big(), value->Big()); +} + + + + +// -------------------------------------------------------- + +MaxBigInteger * bmx_bigint_BigInteger_create(BBString * value) { + char * p = (char*)bbStringToCString(value); + try { + MaxBigInteger * big = new MaxBigInteger(p); + bbMemFree(p); + return big; + } catch(char const* err) { + bbMemFree(p); + bbExThrow((BBObject*)bbStringFromCString(err)); + } +} + +MaxBigInteger * bmx_bigint_BigInteger_CreateWithInt(int value) { + try { + return new MaxBigInteger(value); + } catch(char const* err) { + bbExThrow((BBObject*)bbStringFromCString(err)); + } +} + +void bmx_bigint_BigInteger_free(MaxBigInteger * big) { + delete big; +} + +BBString * bmx_bigint_BigInteger_ToString(MaxBigInteger * big) { + return bbStringFromCString(bigIntegerToString(big->Big()).c_str()); +} + + +int bmx_bigint_BigInteger_equal(MaxBigInteger * a, MaxBigInteger * b) { + if(a->Big() == b->Big()) + return 1; + return 0; +} + +int bmx_bigint_BigInteger_notequal(MaxBigInteger * a, MaxBigInteger * b) { + if(a->Big() != b->Big()) + return 1; + return 0; +} + +int bmx_bigint_BigInteger_lessThan(MaxBigInteger * a, MaxBigInteger * b) { + if (a->Big() < b->Big()) + return 1; + return 0; +} + +int bmx_bigint_BigInteger_lessThanOrEqual(MaxBigInteger * a, MaxBigInteger * b) { + if (a->Big() <= b->Big()) + return 1; + return 0; +} + +int bmx_bigint_BigInteger_greaterThan(MaxBigInteger * a, MaxBigInteger * b) { + if(a->Big() > b->Big()) + return 1; + return 0; +} + +int bmx_bigint_BigInteger_greaterThanOrEqual(MaxBigInteger * a, MaxBigInteger * b) { + if(a->Big() >= b->Big()) + return 1; + return 0; +} + + +void bmx_bigint_BigInteger_add(MaxBigInteger * target, MaxBigInteger * value) { +// target->Big().add(target->Big(), value->Big()); + target->Big() += value->Big(); +} + +void bmx_bigint_BigInteger_subtract(MaxBigInteger * target, MaxBigInteger * value) { +// target->Big().subtract(target->Big(), value->Big()); + target->Big() -= value->Big(); +} + +void bmx_bigint_BigInteger_modulo(MaxBigInteger * target, MaxBigInteger * value) { +// MaxBigInteger * quotient = new MaxBigInteger(0); +// target->Big().divideWithRemainder(value->Big(), quotient->Big()); +// delete quotient; + target->Big() %= value->Big(); +} + +void bmx_bigint_BigInteger_divide(MaxBigInteger * target, MaxBigInteger * value) { + target->Big() /= value->Big(); +} + +void bmx_bigint_BigInteger_multiply(MaxBigInteger * target, MaxBigInteger * value) { +// target->Big().multiply(target->Big(), value->Big()); + target->Big() *= value->Big(); +} + + + +MaxBigInteger * bmx_bigint_new_BigInteger_add(MaxBigInteger * target, MaxBigInteger * value) { + MaxBigInteger * result = new MaxBigInteger(target->Big()); + result->Big() += value->Big(); + return result; +} + +MaxBigInteger * bmx_bigint_new_BigInteger_subtract(MaxBigInteger * target, MaxBigInteger * value) { + MaxBigInteger * result = new MaxBigInteger(target->Big()); + result->Big() -= value->Big(); + return result; +} + +MaxBigInteger * bmx_bigint_new_BigInteger_modulo(MaxBigInteger * target, MaxBigInteger * value) { + MaxBigInteger * result = new MaxBigInteger(target->Big()); + result->Big() %= value->Big(); + return result; +} + +MaxBigInteger * bmx_bigint_new_BigInteger_divide(MaxBigInteger * target, MaxBigInteger * value) { + MaxBigInteger * result = new MaxBigInteger(target->Big()); + result->Big() /= value->Big(); + return result; +} + +MaxBigInteger * bmx_bigint_new_BigInteger_multiply(MaxBigInteger * target, MaxBigInteger * value) { + MaxBigInteger * result = new MaxBigInteger(target->Big()); + result->Big() *= value->Big(); + return result; +} diff --git a/bigint.mod/glue.h b/bigint.mod/glue.h index 74b4949b8..c000fc82f 100644 --- a/bigint.mod/glue.h +++ b/bigint.mod/glue.h @@ -35,7 +35,35 @@ extern "C" { void bmx_bigint_BigUnsigned_free(MaxBigUnsigned * big); BBString * bmx_bigint_BigUnsigned_ToString(MaxBigUnsigned * big); + void bmx_bigint_BigUnsigned_add(MaxBigUnsigned * target, MaxBigUnsigned * value); + void bmx_bigint_BigUnsigned_divide(MaxBigUnsigned * target, MaxBigUnsigned * value); + + + + MaxBigInteger * bmx_bigint_BigInteger_create(BBString * value); + MaxBigInteger * bmx_bigint_BigInteger_CreateWithInt(int value); + void bmx_bigint_BigInteger_free(MaxBigInteger * big); + BBString * bmx_bigint_BigInteger_ToString(MaxBigInteger * big); + + void bmx_bigint_BigInteger_add(MaxBigInteger * target, MaxBigInteger * value); + void bmx_bigint_BigInteger_subtract(MaxBigInteger * target, MaxBigInteger * value); + void bmx_bigint_BigInteger_divide(MaxBigInteger * target, MaxBigInteger * value); + void bmx_bigint_BigInteger_multiply(MaxBigInteger * target, MaxBigInteger * value); + void bmx_bigint_BigInteger_modulo(MaxBigInteger * target, MaxBigInteger * value); + + MaxBigInteger * bmx_bigint_new_BigInteger_add(MaxBigInteger * target, MaxBigInteger * value); + MaxBigInteger * bmx_bigint_new_BigInteger_subtract(MaxBigInteger * target, MaxBigInteger * value); + MaxBigInteger * bmx_bigint_new_BigInteger_divide(MaxBigInteger * target, MaxBigInteger * value); + MaxBigInteger * bmx_bigint_new_BigInteger_multiply(MaxBigInteger * target, MaxBigInteger * value); + MaxBigInteger * bmx_bigint_new_BigInteger_modulo(MaxBigInteger * target, MaxBigInteger * value); + + int bmx_bigint_BigInteger_equal(MaxBigInteger * a, MaxBigInteger * b); + int bmx_bigint_BigInteger_notequal(MaxBigInteger * a, MaxBigInteger * b); + int bmx_bigint_BigInteger_lessThan(MaxBigInteger * a, MaxBigInteger * b); + int bmx_bigint_BigInteger_lessThanOrEqual(MaxBigInteger * a, MaxBigInteger * b); + int bmx_bigint_BigInteger_greaterThan(MaxBigInteger * a, MaxBigInteger * b); + int bmx_bigint_BigInteger_greaterThanOrEqual(MaxBigInteger * a, MaxBigInteger * b); } @@ -49,7 +77,20 @@ class MaxBigUnsigned ~MaxBigUnsigned() {}; BigUnsigned & Big(); - private: BigUnsigned big; +}; + + +class MaxBigInteger +{ +public: + MaxBigInteger(BigInteger & b); + MaxBigInteger(const std::string & b); + MaxBigInteger(int value); + ~MaxBigInteger() {}; + + BigInteger & Big(); +private: + BigInteger big; }; \ No newline at end of file