/// <summary> /// evaluation of this polynomial at a given point /// </summary> /// <param name="a">A.</param> /// <returns>evaluation of this polynomial at a given point</returns> internal int EvaluateAt(int a) { int result = 0; if (a == 0) { // Just return the x^0 coefficient return(GetCoefficient(0)); } int size = coefficients.Length; if (a == 1) { // Just the sum of the coefficients foreach (var coefficient in coefficients) { result = GenericGF.AddOrSubtract(result, coefficient); } return(result); } result = coefficients[0]; for (int i = 1; i < size; i++) { result = GenericGF.AddOrSubtract(field.Multiply(a, result), coefficients[i]); } return(result); }
internal GenericGFPoly[] RunEuclideanAlgorithm(GenericGFPoly a, GenericGFPoly b, int R) { // Assume a's degree is >= b's if (a.Degree < b.Degree) { GenericGFPoly temp = a; a = b; b = temp; } GenericGFPoly rLast = a; GenericGFPoly r = b; GenericGFPoly tLast = field.Zero; GenericGFPoly t = field.One; int halfR = R / 2; // Run Euclidean algorithm until r's degree is less than R/2 while (r.Degree >= halfR) { GenericGFPoly rLastLast = rLast; GenericGFPoly tLastLast = tLast; rLast = r; tLast = t; // Divide rLastLast by rLast, with quotient in q and remainder in r if (rLast.IsZero) { // Oops, Euclidean algorithm already terminated? // throw new ReedSolomonException("r_{i-1} was zero"); return(null); } r = rLastLast; GenericGFPoly q = field.Zero; int denominatorLeadingTerm = rLast.GetCoefficient(rLast.Degree); int dltInverse = field.Inverse(denominatorLeadingTerm); while (r.Degree >= rLast.Degree && !r.IsZero) { int degreeDiff = r.Degree - rLast.Degree; int scale = field.Multiply(r.GetCoefficient(r.Degree), dltInverse); q = q.AddOrSubtract(field.BuildMonomial(degreeDiff, scale)); r = r.AddOrSubtract(rLast.MultiplyByMonomial(degreeDiff, scale)); } t = q.Multiply(tLast).AddOrSubtract(tLastLast); if (r.Degree >= rLast.Degree) { // throw new IllegalStateException("Division algorithm failed to reduce polynomial?"); return(null); } } int sigmaTildeAtZero = t.GetCoefficient(0); if (sigmaTildeAtZero == 0) { // throw new ReedSolomonException("sigmaTilde(0) was zero"); return(null); } int inverse = field.Inverse(sigmaTildeAtZero); GenericGFPoly sigma = t.Multiply(inverse); GenericGFPoly omega = r.Multiply(inverse); return(new GenericGFPoly[] { sigma, omega }); }