示例#1
0
        public T Multiply(T other)
        {
            // Create an extended list which can contain results from both coefficient collections.
            List <BigInteger> b = new List <BigInteger>(new BigInteger[(Degree * 2) - 1]);

            // Compute each product linearly for every index in our list.
            for (int i = 0; i < Coefficients.Count; i++)
            {
                for (int j = 0; j < other.Coefficients.Count; j++)
                {
                    b[i + j] += Coefficients.ElementAt(i) * other.Coefficients.ElementAt(j);
                }
            }

            for (int exp = Degree - 2; exp >= 0; exp--)
            {
                BigInteger top = b[b.Count - 1];
                b.RemoveAt(b.Count - 1);
                for (int i = 0; i < ModulusCoefficients.Count; i++)
                {
                    b[exp + i] -= top * ModulusCoefficients.ElementAt(i);
                }
            }

            // Perform modular division to wrap our coefficients around p.
            return(New(b.Select(x => x.Mod(Bn128Curve.P))));
        }
示例#2
0
        public T Inverse()
        {
            // Define our initial variables and give them their initial assignments.
            BigInteger[] newt = new BigInteger[Degree + 1];
            newt[0] = 1;

            BigInteger[] t = new BigInteger[Degree + 1];

            BigInteger[] newr = new BigInteger[Coefficients.Count + 1];
            Coefficients.CopyTo(newr, 0);

            BigInteger[] r = new BigInteger[ModulusCoefficients.Count + 1];
            ModulusCoefficients.CopyTo(r, 0);
            r[r.Length - 1] = 1;

            // Loop while there are elements which are non-zero.
            while (GetDegree(newr) != 0)
            {
                BigInteger[] quotient = DividePolynomialRounded(r, newr);
                Array.Resize(ref quotient, Degree + 1);

                BigInteger[] tempt = (BigInteger[])t.Clone();
                BigInteger[] tempr = (BigInteger[])r.Clone();
                for (int i = 0; i < Degree + 1; i++)
                {
                    for (int j = 0; j < Degree + 1 - i; j++)
                    {
                        tempt[i + j] -= newt[i] * quotient[j];
                        tempr[i + j] -= newr[i] * quotient[j];
                    }
                }

                // Perform modulo on tempt
                for (int i = 0; i < tempt.Length; i++)
                {
                    tempt[i] = tempt[i].Mod(Bn128Curve.P);
                }

                // Perform modulo on tempr
                for (int i = 0; i < tempr.Length; i++)
                {
                    tempr[i] = tempr[i].Mod(Bn128Curve.P);
                }

                // Swap state for the next iteration.
                (newt, newr, t, r) = (tempt, tempr, newt, newr);
            }

            // Resize the array to the degree size accordingly, divide and return.
            Array.Resize(ref newt, Degree);
            return(New(newt).Divide(newr[0]));
        }