223 lines
4.7 KiB
C#
223 lines
4.7 KiB
C#
using System;
|
|
using sharp.extensions;
|
|
namespace BigInt
|
|
{
|
|
public class Integer: IntBase
|
|
{
|
|
public static readonly Integer ZERO = new Integer();
|
|
public static readonly Integer ONE = new Integer(new UInt32[] { 1 });
|
|
|
|
public Integer()
|
|
{
|
|
this.RawValue = new UInt32[1];
|
|
}
|
|
|
|
public Integer(UInt32[] value)
|
|
{
|
|
this.RawValue = BigIntMath.reduceSigned(value);
|
|
}
|
|
public Integer(byte[] ivalue)
|
|
{
|
|
UInt32[] v = new UInt32[(ivalue.Length + 3) >> 2];
|
|
ivalue = ivalue.Extend(v.Length << 2);
|
|
|
|
for (int n = 0; n < v.Length; n++)
|
|
{
|
|
v[n] = BitConverter.ToUInt32(ivalue, n << 2);
|
|
}
|
|
this.RawValue = BigIntMath.reduceSigned(v);
|
|
}
|
|
public Integer(UInt32[] value, IntField field)
|
|
{
|
|
this.RawValue = BigIntMath.reduceSigned(value);
|
|
}
|
|
public Integer(Integer src)
|
|
{
|
|
this.RawValue = src.RawValue;
|
|
}
|
|
|
|
public bool Sign(){
|
|
return BigIntMath.sign(rawValue);
|
|
}
|
|
|
|
public int Log2(){
|
|
return BigIntMath.log2(rawValue);
|
|
}
|
|
|
|
public Integer Pow(int n)
|
|
{
|
|
if (n == 0)
|
|
{
|
|
return ONE;
|
|
}
|
|
else if (n == 1)
|
|
{
|
|
return this;
|
|
}
|
|
else if (n > 1)
|
|
{
|
|
Integer result = this;
|
|
n--;
|
|
while ((n--) > 0)
|
|
{
|
|
result = (result * this);
|
|
}
|
|
return result;
|
|
}
|
|
throw new ArgumentException("Integer.Pow(n): not implemented for negative exponent");
|
|
}
|
|
|
|
public Integer Ones()
|
|
{
|
|
UInt32[] result = BigIntMath.ones(rawValue);
|
|
return new Integer(result);
|
|
}
|
|
|
|
public Integer Twos()
|
|
{
|
|
UInt32[] result = BigIntMath.twos(rawValue);
|
|
return new Integer(result);
|
|
}
|
|
|
|
|
|
public static Integer fromHexString(string hex)
|
|
{
|
|
return new Integer(HexString.toBytes(hex).Reverse());
|
|
}
|
|
|
|
public override string ToString()
|
|
{
|
|
return String.Format("[{0}: Sign: {2,5} / {1}]", this.GetType().Name, toHexString(), Sign() );
|
|
}
|
|
|
|
|
|
|
|
private Integer __op_add(Integer b)
|
|
{
|
|
int width = (rawValue.Length > b.RawValue.Length ? rawValue.Length : b.RawValue.Length) + 1;
|
|
UInt32[] v = BigIntMath.extendSigned(rawValue, width);
|
|
UInt32[] vb = BigIntMath.extendSigned(b.RawValue, width);
|
|
return new Integer(BigIntMath.reduceSigned(BigIntMath.add(v,vb)));
|
|
}
|
|
private Integer __op_sub(Integer b)
|
|
{
|
|
int width = (rawValue.Length > b.RawValue.Length ? rawValue.Length : b.RawValue.Length) + 1;
|
|
UInt32[] v = BigIntMath.extendSigned(rawValue, width);
|
|
UInt32[] vb = BigIntMath.extendSigned(b.RawValue, width);
|
|
return new Integer(BigIntMath.reduceSigned(BigIntMath.sub(v,vb)));
|
|
}
|
|
|
|
private int __op_cmp(Integer b)
|
|
{
|
|
return BigIntMath.cmp(rawValue, b.RawValue);
|
|
}
|
|
|
|
private Integer __op_div(Integer b)
|
|
{
|
|
UInt32[] result = BigIntMath.sdiv(rawValue, b.RawValue);
|
|
return new Integer(result);
|
|
}
|
|
|
|
private Integer __op_mod(Integer b)
|
|
{
|
|
UInt32[] result = BigIntMath.smod(rawValue, b.RawValue);
|
|
return new Integer(result);
|
|
}
|
|
|
|
private Integer __op_mul(Integer b)
|
|
{
|
|
UInt32[] value = BigIntMath.smul(rawValue, b.RawValue);
|
|
return new Integer(value);
|
|
}
|
|
|
|
private Integer __op_new(uint[] value)
|
|
{
|
|
return new Integer(value);
|
|
}
|
|
|
|
private Integer __op_shl(int b)
|
|
{
|
|
UInt32[] value = BigIntMath.extendSigned(rawValue, RawValue.Length + ((b + 31) >> 5));
|
|
BigIntMath.shl(value,b);
|
|
return new Integer(value);
|
|
}
|
|
|
|
private Integer __op_shr(int b)
|
|
{
|
|
UInt32[] value = rawValue.Segment(0);
|
|
BigIntMath.shr(value, b);
|
|
return new Integer(value);
|
|
}
|
|
|
|
public static implicit operator Integer(UInteger ui)
|
|
{
|
|
return new Integer( BigIntMath.signedFromUnsigned( ui.RawValue ));
|
|
}
|
|
public static implicit operator Integer(int i)
|
|
{
|
|
return new Integer(new UInt32[]{(UInt32)i});
|
|
}
|
|
|
|
|
|
|
|
public static Integer operator +(Integer a, Integer b)
|
|
{
|
|
return a.__op_add(b);
|
|
}
|
|
public static Integer operator -(Integer a, Integer b)
|
|
{
|
|
return a.__op_sub(b);
|
|
}
|
|
public static Integer operator *(Integer a, Integer b)
|
|
{
|
|
return a.__op_mul(b);
|
|
}
|
|
|
|
public static Integer operator /(Integer a, Integer b)
|
|
{
|
|
return a.__op_div(b);
|
|
}
|
|
public static Integer operator %(Integer a, Integer b)
|
|
{
|
|
return a.__op_mod(b);
|
|
}
|
|
|
|
public static bool operator <(Integer a, Integer b)
|
|
{
|
|
return a.__op_cmp(b) < 0;
|
|
}
|
|
public static bool operator >(Integer a, Integer b)
|
|
{
|
|
return a.__op_cmp(b) > 0;
|
|
}
|
|
public static bool operator ==(Integer a, Integer b)
|
|
{
|
|
if ((object)a == (object)b)
|
|
{
|
|
return true;
|
|
}
|
|
if (((object)a == null) || ((object)b == null))
|
|
{
|
|
return false;
|
|
}
|
|
return a.__op_cmp(b) == 0;
|
|
}
|
|
public static bool operator !=(Integer a, Integer b)
|
|
{
|
|
return a.__op_cmp(b) != 0;
|
|
}
|
|
|
|
public static Integer operator <<(Integer a, int b)
|
|
{
|
|
return a.__op_shl(b);
|
|
}
|
|
public static Integer operator >>(Integer a, int b)
|
|
{
|
|
return a.__op_shr(b);
|
|
}
|
|
|
|
|
|
|
|
}
|
|
}
|