public void Multiply(Natural factor1, Natural factor2, out Natural product) { if (factor1 == Natural.Zero || factor2 == Natural.Zero) { product = Natural.Zero; } else if (factor1 == Natural.One) { product = factor2.Clone(); } else { Natural counter = factor2.Clone(); product = factor1.Clone(); product.PushLength(factor1.usedDigits * factor2.usedDigits); while (counter > 1) // We already have 1 factor1 { Natural.Add(product, factor1); Natural.Decrement(counter); } product.PopLength(); } }
public void Multiply(Natural factor1, Natural factor2, out Natural product) { if (factor1 == 0 || factor2 == 0) { product = Natural.Zero; } else if (factor2 == 1) { product = factor1.Clone(); } else { product = Natural.Zero; for (int i = 0; i < factor1.usedDigits; i++) { Digit d = factor1.digits[i]; Natural partial = MulDigit(factor2, d); Natural.ShiftLeft(partial, i); Natural.Add(product, partial); } } }
public void Multiply(Natural factor1, Natural factor2) { if (factor1 == Natural.Zero || factor2 == Natural.Zero) { factor1.SetValue(Natural.Zero); } else if (factor1 == Natural.One) { factor1.SetValue(factor2); } else { Natural increase = factor1.Clone(); Natural decrease = factor2.Clone(); factor1.PushLength(factor1.usedDigits * factor2.usedDigits); while (decrease > 1) // We already have 1 factor1 { Natural.Add(factor1, increase); Natural.Decrement(decrease); } factor1.PopLength(); } }
static bool LucasLehmerTest(ulong exponent, Natural mersenneNumber, ref ulong startI, ref Natural startS)//3815 { Natural s = startS.Clone(); for (ulong i = startI; i < exponent; s = ModMersenneNumber2(Square(s), (int)exponent), i++) { ; } if (startS < mersenneNumber) { startI++; startS *= startS; } return(s == mersenneNumber - 3); }
public void DivRem(Natural dividend, Natural divisor, out Natural quotient, out Natural remainder) { if (divisor == 0) throw new DivideByZeroException(); dividend = dividend.Clone(); quotient = 0; while (dividend >= divisor) { Natural.Subtract(dividend, divisor); Natural.Increment(quotient); } remainder = dividend; }
private void InternalDivRem(Natural dividend, Natural divisor, out Natural quotient, out Natural remainder) { int dcmp = dividend.CompareTo(divisor); if (dcmp == 0) { quotient = Natural.One; remainder = Natural.Zero; } else if (dcmp < 0) // dividend < divisor { quotient = Natural.Zero; remainder = dividend.Clone(); // Do we have to clone? } else // dividend > divisor { Natural modifiedDivisor = divisor.Clone(); Natural subquotient = Natural.One; long bitshifts = Natural.Log2(dividend) - Natural.Log2(modifiedDivisor); // Gets how many factors of two from divisor to dividend Natural.BitShiftLeft(modifiedDivisor, bitshifts); // Shifts divisor that many times (multiply by 2^bitshifts) Natural.BitShiftLeft(subquotient, bitshifts); int cmp = dividend.CompareTo(modifiedDivisor); if (cmp < 0) // Dividend < modifiedDivisors - shifted 1 too much { Natural.BitShiftRight(subquotient, 1); // Divide by 2 to get the right quotient Natural.BitShiftRight(modifiedDivisor, 1); } else if (cmp == 0) // Divisor equal to dividend! { quotient = subquotient; remainder = Natural.Zero; return; } // dividend > modifiedDivisor Natural newDividend = Natural.Subtract(dividend, modifiedDivisor); // Optimize away the clone (put this in private function - clone up front) InternalDivRem(newDividend, divisor, out quotient, out remainder); // Repeat division on difference between dividend and modifiedDivisor Natural.Add(quotient, subquotient); // Add the quotient we calculated in this iteration } }
public void Subtract(Natural minuend, Natural subtrahend, out Natural difference) { difference = minuend.Clone(); Subtract(difference, subtrahend); }
public void DivRem(Natural dividend, Natural divisor, out Natural quotient, out Natural remainder) { InternalDivRem(dividend.Clone(), divisor, out quotient, out remainder); }
public void Add(Natural addend1, Natural addend2, out Natural sum) { sum = addend1.Clone(); Add(sum, addend2); }
public Integer(Natural natural) { this.natural = natural.Clone(); Positive = true; }
public Natural Abs() => natural.Clone();