Fixes Issue 8837 - BigInt needs better operator constraints.

This commit is contained in:
Andrej Mitrovic 2013-02-04 22:06:20 +01:00
parent 705f1a9bdf
commit 7c616db71a

View file

@ -27,6 +27,7 @@ module std.bigint;
private import std.internal.math.biguintcore;
private import std.format : FormatSpec, FormatException;
private import std.traits;
/** A struct representing an arbitrary precision integer
*
@ -105,14 +106,14 @@ public:
}
///
this(T: long) (T x)
this(T)(T x) if (isIntegral!T)
{
data = data.init; // @@@: Workaround for compiler bug
opAssign(x);
}
///
BigInt opAssign(T: long)(T x)
BigInt opAssign(T)(T x) if (isIntegral!T)
{
data = cast(ulong)((x < 0) ? -x : x);
sign = (x < 0);
@ -130,7 +131,7 @@ public:
// BigInt op= integer
BigInt opOpAssign(string op, T)(T y)
if ((op=="+" || op=="-" || op=="*" || op=="/" || op=="%"
|| op==">>" || op=="<<" || op=="^^") && is (T: long))
|| op==">>" || op=="<<" || op=="^^") && isIntegral!T)
{
ulong u = cast(ulong)(y < 0 ? -y : y);
@ -252,7 +253,7 @@ public:
// BigInt op integer
BigInt opBinary(string op, T)(T y)
if ((op=="+" || op == "*" || op=="-" || op=="/"
|| op==">>" || op=="<<" || op=="^^") && is (T: long))
|| op==">>" || op=="<<" || op=="^^") && isIntegral!T)
{
BigInt r = this;
return r.opOpAssign!(op)(y);
@ -260,7 +261,7 @@ public:
//
int opBinary(string op, T : int)(T y)
if (op == "%")
if (op == "%" && isIntegral!T)
{
assert(y!=0);
uint u = y < 0 ? -y : y;
@ -272,14 +273,14 @@ public:
// Commutative operators
BigInt opBinaryRight(string op, T)(T y)
if ((op=="+" || op=="*") && !is(T: BigInt))
if ((op=="+" || op=="*") && isIntegral!T)
{
return opBinary!(op)(y);
}
// BigInt = integer op BigInt
BigInt opBinaryRight(string op, T)(T y)
if (op == "-" && is(T: long))
if (op == "-" && isIntegral!T)
{
ulong u = cast(ulong)(y < 0 ? -y : y);
BigInt r;
@ -294,7 +295,7 @@ public:
// integer = integer op BigInt
T opBinaryRight(string op, T)(T x)
if ((op=="%" || op=="/") && is(T: long))
if ((op=="%" || op=="/") && isIntegral!T)
{
static if (op == "%")
{
@ -350,7 +351,7 @@ public:
}
///
bool opEquals(T: long)(T y) const
bool opEquals(T)(T y) const if (isIntegral!T)
{
if (sign != (y<0))
return 0;
@ -358,7 +359,7 @@ public:
}
///
int opCmp(T:long)(T y)
int opCmp(T)(T y) if (isIntegral!T)
{
if (sign != (y<0) )
return sign ? -1 : 1;