public static void FastAdd(BinaryVector acumalator, BinaryVector addent) { for (int idx = 0; idx < Math.Min(acumalator.data.Length, addent.data.Length); idx++) { acumalator.data[idx] ^= addent.data[idx]; } }
public static void printarr(BinaryVector arr) { long colLength = arr.Length; for (int j = 0; j < colLength; j++) { Console.Write(string.Format("{0} ", arr[j])); } Console.WriteLine(); }
public SolveRequest(int rows, long columns) { this.columns = columns; B = rows; L = 0; Coefficients = new BinaryVector[rows]; V = new List <long>(); VOut = new List <BigInteger>(); for (int i = 0; i < rows; i++) { Coefficients[i] = new BinaryVector(columns); } }
public static void FastFill(bit bit, BinaryVector vector) { long fill = 0; if (bit == bit.ONE) { fill = ~fill; } for (int idx = 0; idx < vector.data.Length; idx++) { vector.data[idx] = fill; } }
public static SolveResult Gaussian(SolveRequest solvereq) { GuassianSolveResult result = new GuassianSolveResult(solvereq.B, solvereq.L); for (int i = 0; i < Math.Min(solvereq.B, solvereq.L); i++) { if (solvereq.Coefficients[i][i] == 0) { for (int j = i + 1; j < solvereq.B; j++) { if (solvereq.Coefficients[j][i] == 1) { BinaryVector tmp = solvereq.Coefficients[j]; solvereq.Coefficients[j] = solvereq.Coefficients[i]; solvereq.Coefficients[i] = tmp; break; } } } if (solvereq.Coefficients[i][i] == 1) { for (int j = 0; j < solvereq.B; j++) { if (j != i) { if (solvereq.Coefficients[j][i] == 1) { BinaryVector.FastAdd(solvereq.Coefficients[j], solvereq.Coefficients[i]); } } } } else { solvereq.Coefficients[i][i] = 1;//<-this may or may not work BinaryVector col = new BinaryVector(solvereq.B); for (int j = 0; j < solvereq.B; j++) { col[j] = solvereq.Coefficients[j][i]; } result.reducedMatrix.Add(col); } } result.End(); return(result); }
public static bool GetFactor(BigInteger n, SolveRequest req, SolveResult res, out BigInteger factor) { while (!res.HasNext()) { BinaryVector v = res.GetNextSolution(); // Program.printarr(v); BigInteger S = 1; BigInteger A = 1; for (int i = 0; i < req.L; i++) { if (v[i] == 1) { S *= req.VOut[i]; A *= req.V[i]; } } BigInteger sqrtS = S.Sqrt(); BigInteger f1 = A - sqrtS; BigInteger f2 = A + sqrtS; // Console.WriteLine("A={0}, S={1}, sqrt(S)={2}, f1={3}, f2={4}",A,S,sqrtS,f1,f2); factor = BigInteger.GreatestCommonDivisor(f1, n); if (factor != n && factor != 1) { return(true); } factor = BigInteger.GreatestCommonDivisor(f2, n); if (factor != n && factor != 1) { return(true); } } factor = -1; return(false); }
private void incrementBit(int idx) { if (idx == freeMult.Length) { done = true; return; } if (freeMult[idx] == 1) { freeMult[idx] = 0; incrementBit(idx + 1); } else { freeMult[idx] = 1; } if (freeMult[idx] == 1) { BinaryVector.FastAdd(currSolution, reducedMatrix[idx]); } }
public void ResetSolution() { currSolution = new BinaryVector(currSolution.Length); freeMult = new BinaryVector(reducedMatrix.Count); done = false; }
public void End() { freeMult = new BinaryVector(reducedMatrix.Count); }
public GuassianSolveResult(long B, long L) { currSolution = new BinaryVector(L); done = false; reducedMatrix = new List <BinaryVector>(); }
//memory saving method - is slower, but better for multithreading public static void Sieve(SieveInitInfo sievereq, SieveResult sieveres, long startIdx, long L) { //want to optimize this further (predefine size of SmoothRelations to approximated B value) sieveres.SmoothRelations = new List <BinaryVector>(); sieveres.V = new List <long>(); sieveres.B = sievereq.B; sieveres.VOut = new List <BigInteger>(); long[] nextIdxA = new long[sievereq.B]; long[] nextIdxB = new long[sievereq.B]; for (int i = 0; i < sievereq.B; i++) { long interval = sievereq.PrimeIntervals[i]; long primeStart = sievereq.PrimeStarts[i][0]; long unoffset = startIdx - primeStart; long rounded = (long)Math.Ceiling((unoffset) * 1D / interval) * interval; long remappedStart = rounded + primeStart; nextIdxA[i] = remappedStart; if (sievereq.PrimeStarts[i].Count == 1) { nextIdxB[i] = -1; } else { interval = sievereq.PrimeIntervals[i]; primeStart = sievereq.PrimeStarts[i][1]; unoffset = startIdx - primeStart; rounded = (long)Math.Ceiling((unoffset) * 1D / interval) * interval; remappedStart = rounded + primeStart; nextIdxB[i] = remappedStart; } } BinaryVector currVect = new BinaryVector(sievereq.B); BigInteger currVal; for (long i = startIdx; i < L + startIdx; i++) { currVal = sievereq.PolyFunction.F(i + sievereq.AStart); for (int j = 0; j < sievereq.B; j++) { if (nextIdxA[j] == i) { while (currVal % sievereq.PrimeIntervals[j] == 0) { currVal /= sievereq.PrimeIntervals[j]; currVect[j] = currVect[j] + 1; } nextIdxA[j] += sievereq.PrimeIntervals[j]; } if (nextIdxB[j] == i) { while (currVal % sievereq.PrimeIntervals[j] == 0) { currVal /= sievereq.PrimeIntervals[j]; currVect[j] = currVect[j] + 1; } nextIdxB[j] += sievereq.PrimeIntervals[j]; } } if (currVal == 1) { sieveres.SmoothRelations.Add(currVect); currVect = new BinaryVector(sievereq.B); sieveres.V.Add(i + sievereq.AStart); sieveres.VOut.Add(sievereq.PolyFunction.F(i + sievereq.AStart)); sieveres.SmoothsFound++; } else { BinaryVector.FastFill(0, currVect); } } }