public List <BigInteger> GetFactorBase() { //return new List<BigInteger>() {2, 17, 23, 29 }; List <BigInteger> mod = new List <BigInteger>() { 2, 3, 5, 7, 11 }; List <BigInteger> Res = new List <BigInteger>(); if (AbvMath.GetLegendreSymbolValue(2, N) == 1) { Res.Add(2); } BigInteger Cur = 3; IterationsComleted = 0; IterationsTotal = P; while (Cur < P) { if (FermatTest.IsPrime(Cur, mod) && (AbvMath.GetLegendreSymbolValue(N, Cur) == 1)) { Res.Add(Cur); IterationsComleted++; } Cur += 2; } return(Res); }
public BigInteger GetFactorBaseNext(List <BigInteger> bs) { List <BigInteger> mod = new List <BigInteger>() { 2, 3, 5, 7, 11 }; BigInteger Cur = bs[bs.Count - 1] + 2; if (Cur == 4) { Cur++; } while (true) { if (FermatTest.IsPrime(Cur, mod) && (AbvMath.GetLegendreSymbolValue(N, Cur) == 1)) { bs.Add(Cur); return(Cur); } Cur += 2; } }
// bug: 1705289942053 public List <BigInteger> GetPrimeDivisors(List <BigInteger> FactorBase) { BigInteger SQ = AbvMath.SqrtHero(N); List <Row> MainTable = new List <Row>(); for (IterationsTotal = A, IterationsComleted = 1, CurrentOperation = Operations.CreatingTable; IterationsComleted <= IterationsTotal; IterationsComleted++) { BigInteger X = SQ + IterationsComleted; MainTable.Add(Row.Create(BigInteger.Pow(X, 2) - N, X)); } IterationsComleted = 0; var buf = Row.CreateBase(FactorBase); MainTable.ForEach(x => x.Init(buf)); IterationsComleted = 0; IterationsTotal = MainTable.Count; CurrentOperation = Operations.Sieve; Sieve(MainTable); //MainTable.ForEach(x => Trace.Write(x.BaseT.ToString() + " ")); //Trace.WriteLine(""); MainTable = MainTable.Where(x => x.BaseT == 1).ToList(); GC.Collect(); //MainTable.ForEach(x => Trace.WriteLine(x.SourceT.ToString())); //Trace.WriteLine(string.Join(" ", FactorBase.Select(x => x.ToString()).ToArray())); //Trace.WriteLine("------------Before normalizing------------"); //MainTable.ForEach(x => Trace.WriteLine(string.Join(" ", x.Values.Select(y => y.BetaPow.ToString()).ToArray()))); //IterationsComleted = 0; //IterationsTotal = MainTable[0].Values.Count; //CurrentOperation = Operations.Normalize; //NormalizeTable(MainTable); //Trace.WriteLine("------------After normalizing------------"); //Trace.WriteLine(string.Join(" ", MainTable[0].Values.Select(x => x.p.ToString()))); //MainTable.ForEach(x => Trace.WriteLine(string.Join(" ", x.Values.Select(y => y.BetaPow.ToString()).ToArray()))); IterationsComleted = 0; CurrentOperation = Operations.Solve0; BigInteger N1 = 1, N2 = 1, r1 = 1; var S = Solve(MainTable); if (S.Count == 0) { throw new Exception("Incorrect parameters"); } //Trace.WriteLine(string.Join("\r\n", S)); for (IterationsComleted = 1, IterationsTotal = S.Count; IterationsComleted < IterationsTotal; IterationsComleted++) { int it = 0; var CurRes = MainTable.Where(x => S[(int)(IterationsTotal - IterationsComleted)][it++]).ToList(); CurRes.ForEach(x => N1 *= x.SourceT); N1 = AbvMath.SqrtHero(N1); CurRes.ForEach(x => N2 *= x.X * x.X); N2 = AbvMath.SqrtHero(N2); r1 = AbvMath.GetGCDBinary(N2 - N1, N); if (r1 != 1 && N != r1) { break; } } S = null; MainTable = null; GC.Collect(); return(new List <BigInteger>() { r1, N / r1 }); }
public static BigInteger[] GetAllPrimeDivisors(BigInteger N, QS qs) { List <BigInteger> answer = GetPrimeDivisiors1000(ref N); if (N == 1) { return(answer.ToArray()); } var mod = new List <BigInteger>() { 2, 3, 5, 7, 11, 13, 17, 19 }; if (FermatTest.IsPrime(N, mod)) { answer.Add(N); return(answer.ToArray()); } //QS qs = new QS() { N = N, A = (int)(AbvMath.GetLN(N)*1.3), BruteP = true, P=(int)(AbvMath.GetLN(N)*0.05+0.5) }; var LN = AbvMath.GetLN(N); qs.N = N; BigInteger PStart = (int)(LN * 0.1 + 0.5); BigInteger[] AValues = new BigInteger[] { (int)LN }; int AValId = 0; qs.P = PStart + 1; qs.A = AValues[0]; var bs = qs.GetFactorBase(); List <BigInteger> res = null; do { qs.P = qs.GetFactorBaseNext(bs); if (qs.P >= qs.A / 3) { if (AValId == AValues.Length - 1) { answer.Add(N); return(answer.ToArray()); } qs.P = PStart; qs.A = AValues[++AValId]; bs = bs.Where(x => x <= qs.P).ToList(); } try { res = qs.GetPrimeDivisors(bs); } catch (Exception) { } } while (res == null || res.Any(x => x.IsOne)); if (FermatTest.IsPrime(res[0], mod)) { answer.Add(res[0]); } else { answer.AddRange(GetAllPrimeDivisors(res[0], qs)); } if (FermatTest.IsPrime(res[1], mod)) { answer.Add(res[1]); } else { answer.AddRange(GetAllPrimeDivisors(res[1], qs)); } var ans = answer.ToArray(); Array.Sort(ans); return(ans); }