Beispiel #1
0
        public OmgNum FindFactor(OmgNum n, int maxIterations = -1)
        {
            m_iterations = 0;

            m_current = n;

            OmgNum x = OmgOp.Random(1.ToOmgNum(), OmgOp.Subtract(n, 2.ToOmgNum()));
            OmgNum y = 1.ToOmgNum();

            OmgNum i     = 0.ToOmgNum();
            OmgNum stage = 2.ToOmgNum();

            OmgNum sub = OmgOp.Subtract(x, y).MakeAbs();
            OmgNum gcd = OmgOp.Gcd(n, sub);

            sub.Release();

            while (gcd.IsOne())
            {
                if (maxIterations >= 0 && m_iterations++ > maxIterations)
                {
                    return(null);
                }

                if (OmgOp.Equal(i, stage))
                {
                    y.Release();
                    y = new OmgNum(x);
                    stage.MultByTwo();
                }

                OmgNum xSquare = OmgOp.Multiply(x, x).Inc();
                x.Release();
                x = OmgOp.Mod(xSquare, n);
                xSquare.Release();

                i.Inc();

                sub = OmgOp.Subtract(x, y).MakeAbs();
                gcd.Release();
                gcd = OmgOp.Gcd(n, sub);
                sub.Release();
            }

            return(gcd);
        }
Beispiel #2
0
        private OmgNum _MakeFastPow(OmgNum left, RawNum right, OmgNum mod)
        {
            if (right.IsZero())
            {
                var res = OmgPool.GetRawZero();
                res.Digits.Add(1);
                return(new OmgNum(res));
            }

            var rightCopy = OmgPool.GetRawZero();

            rightCopy.CopyFrom(right);

            bool even = (rightCopy.Digits[0] & 1) == 0;

            if (even)
            {
                rightCopy.DivByTwo();
                var p = _MakeFastPow(left, rightCopy, mod);

                OmgNum powSquare       = OmgOp.Multiply(p, p);
                OmgNum powSquareModded = OmgOp.Mod(powSquare, mod);

                powSquare.Release();
                p.Release();

                OmgPool.ReleaseNumber(rightCopy);
                return(powSquareModded);
            }
            else
            {
                _SubOne(rightCopy);
                var p = _MakeFastPow(left, rightCopy, mod);

                OmgNum powPlusOne       = OmgOp.Multiply(p, left);
                OmgNum powPlusOneModded = OmgOp.Mod(powPlusOne, mod);

                powPlusOne.Release();
                p.Release();

                OmgPool.ReleaseNumber(rightCopy);
                return(powPlusOneModded);
            }
        }
Beispiel #3
0
        public bool IsPrime(OmgNum tested)
        {
            foreach (var prime in s_smallPrimes)
            {
                if (OmgOp.Less(tested, prime) || OmgOp.Equal(tested, prime))
                {
                    return(true);
                }

                var  mod         = OmgOp.Mod(tested, prime);
                bool isComposite = mod.IsZero();

                mod.Release();

                if (isComposite)
                {
                    return(false);
                }
            }

            return(true);
        }